keybrd library is an open source library for creating custom-keyboard firmware.
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
This repo is archived. You can view files and clone it, but cannot push or open issues/pull-requests.

keybrd_4_split_with_IOE_annotated.ino 5.4KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171
  1. /* keybrd_4_split_with_IOE_annotated.ino
  2. This sketch:
  3. is a simple 1-layer keyboard
  4. runs on two matrices of a breadboard keyboard
  5. is annotated with a walk-through narrative
  6. This layout table shows left and right matrices:
  7. | Left | **0** | **1** | | Right | **0** | **1** |
  8. |:-----:|-------|-------|-|:-----:|-------|-------|
  9. | **0** | a | b | | **0** | 1 | 2 |
  10. | **1** | shift | c | | **1** | 3 | shift |
  11. MARTIX NAMING CONVENTION
  12. Since this keyboard has two matrices, we need a naming convention to distinguish the matrices.
  13. Matrix IDs are the letters 'L' and 'R' (left and right).
  14. Port object names and Port pointer array names end with matrix ID:
  15. port1_R
  16. rowPortF_L rowPort1_R
  17. port0_R
  18. colPortB_L colPort0_R
  19. ptrsColPorts_L ptrsColPorts_R
  20. COL_PORT_L_COUNT COL_PORT_R_COUNT
  21. Key pointer array names and Row objects names end with matrix ID and row number:
  22. ptrsKeys_L0 ptrsKeys_R0
  23. row_L0 row_R0
  24. Matrix object names end with matrix ID:
  25. matrix_L matrix_R
  26. */
  27. // ################## GLOBAL ###################
  28. // ================= INCLUDES ==================
  29. //Ports
  30. #include <RowPort_AVR_Optic.h>
  31. #include <ColPort_AVR.h>
  32. #include <IOExpanderPort.h>
  33. #include <RowPort_PCA9655E.h>
  34. #include <ColPort_PCA9655E.h>
  35. //Codes
  36. #include <Code_Sc.h>
  37. //Matrix
  38. #include <Row.h>
  39. #include <Matrix.h>
  40. // ============ SPEED CONFIGURATIONS ============
  41. const unsigned int Row::DELAY_MICROSECONDS = 1000;
  42. // ================ LEFT PORTS =================
  43. /*
  44. The left matrix is scanned by a micro-controller.
  45. */
  46. RowPort_AVR_Optic rowPortF_L(DDRF, PORTF);
  47. ColPort_AVR colPortB_L(DDRB, PORTB, PINB, 1<<0 | 1<<1 );
  48. ColPort* const ptrsColPorts_L[] = { &colPortB_L };
  49. const uint8_t COL_PORT_L_COUNT = sizeof(ptrsColPorts_L)/sizeof(*ptrsColPorts_L);
  50. // =============== RIGHT PORTS =================
  51. /*
  52. The right matrix is scanned by an I/O expander.
  53. The micro-controller and I/O expander communicates via I2C bus.
  54. Three hardware pins (AD0, AD1, AD2) are used to configure the I2C address of the I/O expander.
  55. ADDR is a static variable of class IOExpanderPort. The I2C address of this I/O expander is 0x18.
  56. An I/O expander used on a matrix has two ports. Each port has eight pins.
  57. One port is connected to the matrix's rows. The other port is connected to the matrix's columns.
  58. The IOExpanderPort constructor parameters specify the port number and initial output value.
  59. I/O Expander and AVR have similar constructor parameters for RowPort and ColPort.
  60. */
  61. const uint8_t IOExpanderPort::ADDR = 0x18;
  62. /*
  63. port1_R uses port 1 with an initial output value of 0.
  64. */
  65. IOExpanderPort port1_R(1, 0);
  66. /*
  67. The RowPort_PCA9655E constructor parameter specifies the IOExpanderPort.
  68. */
  69. RowPort_PCA9655E rowPort1_R(port1_R);
  70. /*
  71. port0_R uses port 0 with an initial output value of 0.
  72. */
  73. IOExpanderPort port0_R(0, 0);
  74. /*
  75. The ColPort_PCA9655E constructor parameter specifies the IOExpanderPort and the port pins to read:
  76. A number to the right of "1<<" is the pin number to read. 1<<0 reads pin 0, and 1<<1 reads pin 1.
  77. */
  78. ColPort_PCA9655E colPort0_R(port0_R, 1<<0 | 1<<1 );
  79. /*
  80. ColPort pointers are placed in an array because some keyboards use multiple column ports.
  81. This sketch only has one column port.
  82. sizeof() is used to compute the number of array elements.
  83. This eliminates the risk of forgetting to update the count after adding or removing an element.
  84. */
  85. ColPort* const ptrsColPorts_R[] = { &colPort0_R };
  86. const uint8_t COL_PORT_R_COUNT = sizeof(ptrsColPorts_R)/sizeof(*ptrsColPorts_R);
  87. // =================== CODES ===================
  88. /*
  89. Codes are not grouped into left and right because codes are independent of layout.
  90. - a keyboard can have differnt layouts
  91. - some codes may appear on both matrices
  92. */
  93. Code_Sc s_shiftL(MODIFIERKEY_LEFT_SHIFT);
  94. Code_Sc s_shiftR(MODIFIERKEY_RIGHT_SHIFT);
  95. Code_Sc s_a(KEY_A);
  96. Code_Sc s_b(KEY_B);
  97. Code_Sc s_c(KEY_C);
  98. Code_Sc s_1(KEY_1);
  99. Code_Sc s_2(KEY_2);
  100. Code_Sc s_3(KEY_3);
  101. // ================ LEFT MATRIX ================
  102. // ---------------- LEFT ROWS ------------------
  103. Key* const ptrsKeys_L0[] = { &s_a, &s_b };
  104. Row row_L0(rowPortF_L, 1<<0, ptrsColPorts_L, COL_PORT_L_COUNT, ptrsKeys_L0);
  105. Key* const ptrsKeys_L1[] = { &s_c, &s_shiftL };
  106. Row row_L1(rowPortF_L, 1<<1, ptrsColPorts_L, COL_PORT_L_COUNT, ptrsKeys_L1);
  107. // ---------------- LEFT MATRIX ----------------
  108. Row* const ptrsRows_L[] = { &row_L0, &row_L1 };
  109. const uint8_t ROW_L_COUNT = sizeof(ptrsRows_L)/sizeof(*ptrsRows_L);
  110. Matrix matrix_L(ptrsRows_L, ROW_L_COUNT, 1);
  111. // ================ RIGHT MATRIX ===============
  112. // ---------------- RIGHT ROWS -----------------
  113. Key* const ptrsKeys_R0[] = { &s_1, &s_2 };
  114. Row row_R0(rowPort1_R, 1<<0, ptrsColPorts_R, COL_PORT_R_COUNT, ptrsKeys_R0);
  115. Key* const ptrsKeys_R1[] = { &s_3, &s_shiftR };
  116. Row row_R1(rowPort1_R, 1<<1, ptrsColPorts_R, COL_PORT_R_COUNT, ptrsKeys_R1);
  117. // ---------------- RIGHT MATRIX ---------------
  118. Row* const ptrsRows_R[] = { &row_R0, &row_R1 };
  119. const uint8_t ROW_R_COUNT = sizeof(ptrsRows_R)/sizeof(*ptrsRows_R);
  120. Matrix matrix_R(ptrsRows_R, ROW_R_COUNT, 1);
  121. // ################### MAIN ####################
  122. void setup()
  123. {
  124. /*
  125. Call begin() for I/O expander's rowPort and colPort.
  126. */
  127. rowPort1_R.begin();
  128. colPort0_R.begin();
  129. Keyboard.begin();
  130. }
  131. /*
  132. loop() continually scans both Matrix objects.
  133. */
  134. void loop()
  135. {
  136. matrix_L.scan();
  137. matrix_R.scan();
  138. }