Вложений: 2
Вариация безвейтового контроллера PS/2 клавиатуры для Spectrum - компактный вариант
Как и большинство начинающих спектрумистов подошел к моменту, когда захотелось подключить к своему Ленинграду PS/2 клавиатуру.
Родной клавиатуре особенно не помогли ни замена пружин, ни подгибание контактов. Всё равно дребезг и периодические пропуски нажатий.
Мне очень нравится конструкция от Xrust https://zx-pk.ru/threads/33211-unive...viaturami.html
Уже был готов её собирать (тем более, что почти все детали были в наличии, оставалось купить печатную плату и MT8816), как подумалось: каким образом я буду размещать эту конструкцию?
В моем корпусе она не поместится (он очень компактный, чем мне и нравится). Тянуть наружу 15-жильный шлейф - тоже не кажется хорошим вариантом.
Постепенно пришел к конструкции из Altera Max EPM3064 (корпус tqfp-44) и ATTiny25 (корпус SOP-8).
Чипа ATTiny25 вполне хватает для взаимодействия с клавиатурой, но не хватает ног, чтобы передавать данные в MT8816.
Altera EPM3064 имеет большой недостаток по сравнению с MT8816 - её нужно прошивать.
Зато она компактнее и позволяет организовать последовательный интерфейс по двум проводам, что очень подходит ATTiny25.
Получилась такая схема:
https://pic.maxiol.com/thumbs2/16908...specscheme.png
Устройство состоит из двух плат. Одна плата включает EPM3064 и разъём, который вставляется непосредственно в клавиатурный разъём Ленинграда.
Вторая плата содержит разъём PS/2 и ATTiny25. Она размещается в любом удобном месте внутри корпуса спека.
Разводкой платы занимаюсь.
Часть, которая цепляется в клавиатурный разъём Ленинграда должна выглядеть примерно так:
https://pic.maxiol.com/thumbs2/16813....kbspecpcb.png
Соединены платы четырьмя проводами - по двум передаются данные, питание +5V и GND. ATTiny25 прошивается через клавиатурный разъём. Заменить прошивку можно не открывая корпус спека.
Текущая прошивка CPLD позволяет эмулировать 40-клавишную клавиатуру (выходы на Data с открытым коллектором), плюс имеет 5 дополнительных выходов произвольного назначения (на выходе логические уровни TTL).
Код Altera Max очень простой:
Код:
// Алгоритм работы:
// C помощью Clk и D заносим в регистр Buffer сначала номер группы клавиш, 3 бита (номер от 0 до 7, по 5 клавиш в группе)
// потом значения клавиш в группе (1 - нажатая клавиша) - 5 бит. От старшего бита к младшему,
// и в конце - признак, что занесенные данные относятся к клавиатуре (=0) или к пяти дополнительным выходам (=1)
// !!!Важно. Изменения D производить только при низком Clk.
// После того, как Buffer заполнен данными, поднимаем Clk, опускаем и поднимаем D,
// при этом значения из буффера копируются в ранее заданную группу клавиш.
//------------------------------------------------------------------------------------------------------------------
// Для взаимодействия с клавиатурой используется ATtiny13 или ATtiny25. 2 пина на клавиатуру и 2 пина на Altera.
// Также на разъём клавиатуры выносится Reset и дополнительно MISO/MOSI, для прошивки через этот разъём.
// Итого Int0 (SCK), MOSI, MISO, Reset.
module Spec_KB (
input [15:8] Addr, //От Спека
input D, Clk, //Интерфейс с AVR
output reg [4:0] Data, //В Спек
output reg [4:0] Ext_Data //Дополнительные выходы
);
reg [4:0] Key_Data [7:0]; //Массив состояний клавиш, 8 груп по 5 клавиш
reg [8:0] Buffer; //Входной буффер, переносится в массив состояний клавиш по положительному перепаду D, если Clk высокий
wire [2:0] Row; assign Row[2:0] = Buffer[8:6]; //Номер группы клавиш (строки)
wire Ext_data_sign; assign Ext_data_sign = Buffer[0]; //Признак, что в буфере данные для дополнительных выходов
wire [4:0] Data_internal; //Промежуточная переменная
assign Data_internal[4:0] = (~Key_Data[0] | {5{Addr[8]}})
& (~Key_Data[1] | {5{Addr[9]}})
& (~Key_Data[2] | {5{Addr[10]}})
& (~Key_Data[3] | {5{Addr[11]}})
& (~Key_Data[4] | {5{Addr[12]}})
& (~Key_Data[5] | {5{Addr[13]}})
& (~Key_Data[6] | {5{Addr[14]}})
& (~Key_Data[7] | {5{Addr[15]}});
integer i;
always @(Data_internal) //В зависимости от значения Data_internal[i], опускаем на 0 или отключаем выходной буффер Data[i] - аналог ОК
for(i=0; i<5; i=i+1) Data[i] <= Data_internal[i]? 1'bZ : 1'b0;
always @(posedge Clk) //Заталкиваем D в сдвиговый регистр Buffer по положительному перепаду Clk
Buffer[8:0] <= {Buffer[7:0], D};
always @(posedge D)
if(Clk) begin
if(Ext_data_sign) Ext_Data <= Buffer[5:1];
else Key_Data[Row] <= Buffer[5:1];
end
endmodule
Весь проект во вложении.
Код для ATTiny посложнее. Проект тоже во вложении. Использование дополнительных выходов в этой прошивке не реализовано.
Реализована передача сочетаний клавиш по нажатию на одну клавишу PS/2 клавиатуры.
Под свою клавиатуру (Diebold) выбрал раскладку, показанную на картинке ниже. Если клавиша в пустом кружке или прямоугольнике, её значение соответствует надписям на ней.
С удовольствием выслушаю критику и рекомендации.
https://pic.maxiol.com/thumbs2/16813...kbspeckeys.png
Фьюзы для ATTiny
https://pic.maxiol.com/images2/17500...uses071020.png