]> git.gir.st - tmk_keyboard.git/blob - mykey.c
store Keymap into program space.
[tmk_keyboard.git] / mykey.c
1 /* Keyboard example with debug channel, for Teensy USB Development Board
2 * http://www.pjrc.com/teensy/usb_keyboard.html
3 * Copyright (c) 2008 PJRC.COM, LLC
4 *
5 * Permission is hereby granted, free of charge, to any person obtaining a copy
6 * of this software and associated documentation files (the "Software"), to deal
7 * in the Software without restriction, including without limitation the rights
8 * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9 * copies of the Software, and to permit persons to whom the Software is
10 * furnished to do so, subject to the following conditions:
11 *
12 * The above copyright notice and this permission notice shall be included in
13 * all copies or substantial portions of the Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18 * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20 * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
21 * THE SOFTWARE.
22 */
23
24 #include <avr/io.h>
25 #include <avr/pgmspace.h>
26 #include <avr/interrupt.h>
27 #include <util/delay.h>
28 #include "usb_keyboard_debug.h"
29 #include "print.h"
30 #include "keymap.h"
31
32 #define LED_CONFIG (DDRD |= (1<<6))
33 #define LED_ON (PORTD &= ~(1<<6))
34 #define LED_OFF (PORTD |= (1<<6))
35 #define CPU_PRESCALE(n) (CLKPR = 0x80, CLKPR = (n))
36
37 uint8_t number_keys[10]=
38 {KEY_0,KEY_1,KEY_2,KEY_3,KEY_4,KEY_5,KEY_6,KEY_7,KEY_8,KEY_9};
39
40 uint16_t idle_count=0;
41
42
43
44 //
45 // scan matrix
46 //
47 uint8_t MAX_ROW = 9;
48
49 // initialize ports for matrix
50 void port_setup(void)
51 {
52 // Column: input w/pullup
53 DDRB = 0x00;
54 PORTB = 0xFF;
55
56 // Row: Hi-Z(unselected)
57 // PD:0,1,2,3,6,7
58 // PC:6,7
59 // PF:7
60 DDRD = 0x00;
61 PORTD = 0x00;
62 DDRC = 0x00;
63 PORTC = 0x00;
64 DDRF = 0x00;
65 PORTF = 0x00;
66 }
67
68 // select a row of matrix for read
69 void select_row(uint8_t row)
70 {
71 switch (row) {
72 case 0:
73 DDRD = (1<<0);
74 PORTD = 0x00;
75 DDRC = 0x00;
76 PORTC = 0x00;
77 DDRF = 0x00;
78 PORTF = 0x00;
79 break;
80 case 1:
81 DDRD = (1<<1);
82 PORTD = 0x00;
83 DDRC = 0x00;
84 PORTC = 0x00;
85 DDRF = 0x00;
86 PORTF = 0x00;
87 break;
88 case 2:
89 DDRD = (1<<2);
90 PORTD = 0x00;
91 DDRC = 0x00;
92 PORTC = 0x00;
93 DDRF = 0x00;
94 PORTF = 0x00;
95 break;
96 case 3:
97 DDRD = (1<<3);
98 PORTD = 0x00;
99 DDRC = 0x00;
100 PORTC = 0x00;
101 DDRF = 0x00;
102 PORTF = 0x00;
103 break;
104 case 4:
105 DDRD = (1<<6);
106 PORTD = 0x00;
107 DDRC = 0x00;
108 PORTC = 0x00;
109 DDRF = 0x00;
110 PORTF = 0x00;
111 break;
112 case 5:
113 DDRD = (1<<7);
114 PORTD = 0x00;
115 DDRC = 0x00;
116 PORTC = 0x00;
117 DDRF = 0x00;
118 PORTF = 0x00;
119 break;
120 case 6:
121 DDRD = 0x00;
122 PORTD = 0x00;
123 DDRC = (1<<6);
124 PORTC = 0x00;
125 DDRF = 0x00;
126 PORTF = 0x00;
127 break;
128 case 7:
129 DDRD = 0x00;
130 PORTD = 0x00;
131 DDRC = (1<<7);
132 PORTC = 0x00;
133 DDRF = 0x00;
134 PORTF = 0x00;
135 break;
136 case 8:
137 DDRD = 0x00;
138 PORTD = 0x00;
139 DDRC = 0x00;
140 PORTC = 0x00;
141 DDRF = (1<<7);
142 PORTF = 0x00;
143 break;
144 }
145 }
146
147 uint8_t read_col(void)
148 {
149 return PINB;
150 }
151
152 int main(void)
153 {
154 uint8_t i, reset_idle;
155 uint8_t prev_state[MAX_ROW];
156 for (int i=0; i < MAX_ROW; i++) prev_state[i] = 0xFF;
157
158 // set for 16 MHz clock
159 CPU_PRESCALE(0);
160
161 port_setup();
162
163
164 // Initialize the USB, and then wait for the host to set configuration.
165 // If the Teensy is powered without a PC connected to the USB port,
166 // this will wait forever.
167 usb_init();
168 while (!usb_configured()) /* wait */ ;
169
170 // Wait an extra second for the PC's operating system to load drivers
171 // and do whatever it does to actually be ready for input
172 _delay_ms(1000);
173
174 // Configure timer 0 to generate a timer overflow interrupt every
175 // 256*1024 clock cycles, or approx 61 Hz when using 16 MHz clock
176 // This demonstrates how to use interrupts to implement a simple
177 // inactivity timeout.
178 TCCR0A = 0x00;
179 TCCR0B = 0x05;
180 TIMSK0 = (1<<TOIE0);
181
182 print("Begin keyboard example program\n");
183 print("All Port B or Port D pins are inputs with pullup resistors.\n");
184 print("Any connection to ground on Port B or D pins will result in\n");
185 print("keystrokes sent to the PC (and debug messages here).\n");
186
187 uint8_t col;
188 uint8_t code;
189 while (1) {
190 reset_idle = 0;
191
192 for (uint8_t r=0; r < MAX_ROW; r++) {
193 select_row(r);
194
195 // without this read unstable value.
196 _delay_us(30);
197
198 col = read_col();
199 if (col != prev_state[r]) {
200 prev_state[r] = col;
201 phex(r);
202 print(": ");
203 pbin(col);
204 print("\n");
205
206 for (int c = 0; c < 8; c++) {
207 if (col & 1<<c) continue;
208 code = get_keycode(r, c);
209 phex(code);
210 print("\n");
211 usb_keyboard_press(code, 0);
212 }
213
214 reset_idle = 1;
215 }
216 }
217
218
219
220 // if any keypresses were detected, reset the idle counter
221 if (reset_idle) {
222 // variables shared with interrupt routines must be
223 // accessed carefully so the interrupt routine doesn't
224 // try to use the variable in the middle of our access
225 cli();
226 idle_count = 0;
227 sei();
228 }
229
230 // now the current pins will be the previous, and
231 // wait a short delay so we're not highly sensitive
232 // to mechanical "bounce".
233 _delay_ms(2);
234 }
235 }
236
237 // This interrupt routine is run approx 61 times per second.
238 // A very simple inactivity timeout is implemented, where we
239 // will send a space character and print a message to the
240 // hid_listen debug message window.
241 ISR(TIMER0_OVF_vect)
242 {
243 idle_count++;
244 if (idle_count > 61 * 8) {
245 idle_count = 0;
246 print("Timer Event :)\n");
247 //usb_keyboard_press(KEY_SPACE, 0);
248 }
249 }
250
251
Imprint / Impressum