我有一个设备有9个键就像一个普通的手机。 我想打印正常的字母如ABCD使用这9个键完全按照手机让你这样做。逻辑9键键盘打印QWERTY键
这是一个嵌入式系统编程项目。我无法弄清楚实现这个功能的逻辑。
我通过轮询而不是中断来检测密钥。
有人可以帮忙吗?如果您能指出相关资源,我将不胜感激。
我有一个设备有9个键就像一个普通的手机。 我想打印正常的字母如ABCD使用这9个键完全按照手机让你这样做。逻辑9键键盘打印QWERTY键
这是一个嵌入式系统编程项目。我无法弄清楚实现这个功能的逻辑。
我通过轮询而不是中断来检测密钥。
有人可以帮忙吗?如果您能指出相关资源,我将不胜感激。
这是一个小键盘解码演示程序,应该可以帮助您顺利完成任务。您需要重新编写硬件的主要扫描例程。另外,连续两次选择相同的数字会有某种超时。你也应该有一点麻烦搞清楚如何添加大写,标点符号和Meta键支持...
#include <stdio.h>
#define NUM_KEYS 10
#define NUM_PHASES 6
char KeyMap[NUM_KEYS][NUM_PHASES] =
{ { '0', 0, 0, 0, 0, 0 },
{ '1', 0, 0, 0, 0, 0 },
{ '2', 'A', 'B', 'C', 0, 0 },
{ '3', 'D', 'E', 'F', 0, 0 },
{ '4', 'G', 'H', 'I', 0, 0 },
{ '5', 'J', 'K', 'L', 0, 0 },
{ '6', 'M', 'N', 'O', 0, 0 },
{ '7', 'P', 'Q', 'R', 'S', 0 },
{ '8', 'T', 'U', 'V', 0, 0 },
{ '9', 'W', 'X', 'Y', 'Z', 0 } };
char KeyGet()
{
char key;
/* do whatever it takes to scan your
keyboard and return the _numeric_ digit. */
/* for this test simulate with console input */
key = getc(stdin);
if ((key >= '0') && (key <= '9'))
{
key -= 0x30;
}
else
{
key = 0;
}
return key;
}
char DecodeKey(char NewKey, char *pOldKey, int *pPhase)
{
char ch = 0;
/* Validate Phase */
if ((*pPhase < 0) || (*pPhase >= NUM_PHASES))
{
*pPhase = 0;
}
/* see if a different key was pressed than last time */
/* if it was then restart the phase counter */
if (NewKey != *pOldKey)
{
*pPhase = 0;
*pOldKey = NewKey;
}
/* Validate Key */
if ((NewKey >= 0) && (NewKey < NUM_KEYS))
{
ch = KeyMap[(int)NewKey][*pPhase];
/* if the phase position is NULL, just get the numeric digit */
if (ch == 0)
{
*pPhase = 0;
ch = KeyMap[(int)NewKey][*pPhase];
}
/* bump the phase */
++(*pPhase);
if (*pPhase >= NUM_PHASES)
{
*pPhase = 0;
}
}
return ch;
}
int main()
{
char nk; /* new key */
char ok = 0; /* old key */
char c; /* resulting character */
int phase = 0; /* tracks the key presses */
while (1)
{
/* get a key */
nk = KeyGet();
/* convert it to a character */
c = DecodeKey(nk, &ok, &phase);
if (c != 0)
{
printf("%c", c);
}
}
return 0;
}
要做到一个很好的设计,你需要一个键盘输入程序,可以告诉你何时按键已经被搁置了一段时间,并且当它们被释放了一段时间。在按下数字后的短时间内,应该将光标保持在新输入的字符上;如果再次按下相同的数字,则应该更改新输入的字符。如果输入另一位数字,则将选定数字设为“永久”,并将光标显示在新密钥的字符上。如果没有按键被按下一秒左右,请将光标移到下一个位置。如果在光标位于新输入的数字上时按下Enter键,只需前进光标即可。如果它在光标自动前进的大约1/4秒内被推入,则不执行任何操作。如果在光标不在字符上并且不仅仅是自动提前时被按下,请确认输入。
把你的控制器的6个引脚用于键盘P0-> P6。将你的3列P0-> P3和3行连接到P4-> P6。用代码将所有引脚拉高。通过在每列上设置低位来扫描每行。因此,通过获取特定的行和列,你将能够获得进入关键.. 希望你看这个..
适应Amardeep的回答是:
char KeyMap[NUM_KEYS][NUM_PHASES] =
{ { '0', 0, 0, 0, 0, 0 },
{ '1', 0, 0, 0, 0, 0 },
{ '2', 'A', 'B', 'C', 0, 0 },
{ '3', 'D', 'E', 'F', 0, 0 },
{ '4', 'G', 'H', 'I', 0, 0 },
{ '5', 'J', 'K', 'L', 0, 0 },
{ '6', 'M', 'N', 'O', 0, 0 },
{ '7', 'P', 'Q', 'R', 'S', 0 },
{ '8', 'T', 'U', 'V', 0, 0 },
{ '9', 'W', 'X', 'Y', 'Z', 0 } };
//Gets the system time, e.g. as number of timer ticks since power up. You write this.
sometype GetSystemTime();
//Checks if key has been pressed. Returns 0-9 if a key was pressed or -1 if no key was pressed. You write this.
int KeyAvailable();
int main()
{
const sometype PHASE_WAIT = somevalue; //The delay before shifting to the next character.
char keyBuffer[BUFFER_SIZE]; //The input buffer.
int keyIndex = 0; //The index into keyBuffer.
int keyPress1 = -1, keyPress2; // keyboard inputs.
sometype lastKeyPressTime; // The time a key was last pressed.
int numKeyPresses; // The number of times the same key has been pressed this phase.
/* keyboard processing loop. */
while (1)
{
if ((GetSystemTime() - lastKeyPressTime > PHASE_WAIT) && (-1 != keyPress1))
{
// Phase timed out. Commit current character.
keyBuffer[keyIndex++] = KeyMap[keyPress1][numKeyPresses - 1];
keyPress1 = -1;
}
if ((keyPress2 = KeyAvailable()) > -1)
{
// Key pressed.
lastKeyPressTime = GetSystemTime();
if ((keyPress2 != keyPress1) && (-1 != keyPress1))
{
// Different than last key. Commit current character and start a new one.
keyBuffer[keyIndex++] = KeyMap[keypress1][numKeyPresses - 1];
numKeyPresses = 1; // Yes, I"m using 1-based indexing. Deal.
}else if (keyPress2 == keyPress1)
{
// Pressed same key multiple times in same phase.
numKeyPresses = ((numKeyPresses) % KEYMAPROWSIZE) + 1;
if (0 == KeyMap[keypress2][numKeyPresses - 1])
{
//Loop back to first 'valid' character associated with this key.
numKeyPresses = 1;
}
}else // -1 == keyPress1
{
// Pressed new key. Start new phase.
numKeyPresses = 1;
}
keyPress1 = keyPress2.
}
}
}
键= GETC(标准输入);是阻止呼叫? – 2010-10-17 10:13:32
@Akshar:是的,这是一个用于此演示的阻止呼叫。标准C没有非阻塞控制台输入库例程。实施者需要为实际目标编写一个自定义例程。 – 2010-10-17 11:18:09