summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--README.md26
-rw-r--r--doc/COPYING.GPLv2339
-rw-r--r--doc/FUSE.txt40
-rw-r--r--doc/POWER.txt62
-rw-r--r--doc/USB_NKRO.txt160
-rw-r--r--doc/build.md185
-rw-r--r--doc/keycode.txt261
-rw-r--r--doc/keymap.md593
-rw-r--r--doc/other_projects.md62
-rw-r--r--keyboard/atomic/Makefile164
-rw-r--r--keyboard/atomic/Makefile.pjrc116
-rw-r--r--keyboard/atomic/PCB_GUIDE.md110
-rw-r--r--keyboard/atomic/README.md56
-rw-r--r--keyboard/atomic/__avr_gdbinit6
-rw-r--r--keyboard/atomic/analog.c53
-rw-r--r--keyboard/atomic/analog.h36
-rw-r--r--keyboard/atomic/backlight.c49
-rw-r--r--keyboard/atomic/common_keymaps/keymap_brett.c42
-rw-r--r--keyboard/atomic/common_keymaps/keymap_dotcom.c34
-rw-r--r--keyboard/atomic/common_keymaps/keymap_jack.c50
-rw-r--r--keyboard/atomic/common_keymaps/keymap_joe.c83
-rw-r--r--keyboard/atomic/common_keymaps/keymap_matthew.c70
-rw-r--r--keyboard/atomic/common_keymaps/keymap_nathan.c153
-rw-r--r--keyboard/atomic/common_keymaps/keymap_peasant.c51
-rw-r--r--keyboard/atomic/common_keymaps/keymap_reed.c74
-rw-r--r--keyboard/atomic/common_keymaps/keymap_sean.c57
-rw-r--r--keyboard/atomic/common_keymaps/keymap_shane.c98
-rw-r--r--keyboard/atomic/common_keymaps/keymap_simon.c44
-rw-r--r--keyboard/atomic/common_keymaps/keymap_tim.c44
-rw-r--r--keyboard/atomic/common_keymaps/keymap_wilba.c56
-rw-r--r--keyboard/atomic/config.h74
-rw-r--r--keyboard/atomic/extended_keymap_common.c208
-rw-r--r--keyboard/atomic/extended_keymap_common.h177
-rw-r--r--keyboard/atomic/extended_keymaps/extended_keymap_abienz.c36
-rw-r--r--keyboard/atomic/extended_keymaps/extended_keymap_austin.c50
-rw-r--r--keyboard/atomic/extended_keymaps/extended_keymap_charlie.c54
-rw-r--r--keyboard/atomic/extended_keymaps/extended_keymap_daniel.c48
-rw-r--r--keyboard/atomic/extended_keymaps/extended_keymap_default.c79
-rw-r--r--keyboard/atomic/extended_keymaps/extended_keymap_dzobert.c49
-rw-r--r--keyboard/atomic/extended_keymaps/extended_keymap_jack.c188
-rw-r--r--keyboard/atomic/extended_keymaps/extended_keymap_joe.c90
-rw-r--r--keyboard/atomic/extended_keymaps/extended_keymap_kyle.c49
-rw-r--r--keyboard/atomic/extended_keymaps/extended_keymap_numpad.c26
-rwxr-xr-xkeyboard/atomic/flash-pcb.sh3
-rw-r--r--keyboard/atomic/keymap_common.c30
-rw-r--r--keyboard/atomic/keymap_common.h130
-rw-r--r--keyboard/atomic/keymap_grid.c40
-rw-r--r--keyboard/atomic/led.c38
-rw-r--r--keyboard/atomic/matrix.c227
-rw-r--r--keyboard/atomic/matrix_center.c269
-rw-r--r--keyboard/atomic/matrix_pcb.c231
-rw-r--r--keyboard/atomic_old/Makefile135
-rw-r--r--keyboard/atomic_old/Makefile.pjrc116
-rw-r--r--keyboard/atomic_old/README 2.md141
-rw-r--r--keyboard/atomic_old/config.h70
-rw-r--r--keyboard/atomic_old/keymap_common.c30
-rw-r--r--keyboard/atomic_old/keymap_common.h87
-rw-r--r--keyboard/atomic_old/keymap_plain.c46
-rw-r--r--keyboard/atomic_old/keymap_ricky.c15
-rw-r--r--keyboard/atomic_old/keymap_vlad.c14
-rw-r--r--keyboard/atomic_old/led.c25
-rw-r--r--keyboard/atomic_old/matrix.c211
-rw-r--r--keyboard/ergodox_ez/Makefile114
-rw-r--r--keyboard/ergodox_ez/README.md1
-rw-r--r--keyboard/ergodox_ez/config.h87
-rw-r--r--keyboard/ergodox_ez/ergodox_ez.c123
-rw-r--r--keyboard/ergodox_ez/ergodox_ez.h145
-rw-r--r--keyboard/ergodox_ez/i2cmaster.h178
-rw-r--r--keyboard/ergodox_ez/keymaps/keymap_default.c133
-rw-r--r--keyboard/ergodox_ez/keymaps/keymap_ergodox_ez.c211
-rw-r--r--keyboard/ergodox_ez/matrix.c348
-rw-r--r--keyboard/ergodox_ez/twimaster.c208
-rw-r--r--keyboard/gh60/Makefile2
-rw-r--r--keyboard/gh60/keymap_common.h48
-rw-r--r--keyboard/gh60/led.c14
-rw-r--r--keyboard/gh60/matrix.c98
-rw-r--r--keyboard/planck/Makefile140
-rw-r--r--keyboard/planck/PCB_GUIDE.md114
-rw-r--r--keyboard/planck/README.md48
-rw-r--r--keyboard/planck/backlight.c61
-rw-r--r--keyboard/planck/config.h79
-rwxr-xr-xkeyboard/planck/flash-pcb.sh3
-rw-r--r--keyboard/planck/keymaps/keymap_angerthosenear.c50
-rw-r--r--keyboard/planck/keymaps/keymap_austin.c50
-rw-r--r--keyboard/planck/keymaps/keymap_charlie.c54
-rw-r--r--keyboard/planck/keymaps/keymap_daniel.c48
-rw-r--r--keyboard/planck/keymaps/keymap_david.c76
-rw-r--r--keyboard/planck/keymaps/keymap_default.c68
-rw-r--r--keyboard/planck/keymaps/keymap_dzobert.c49
-rw-r--r--keyboard/planck/keymaps/keymap_jack.c50
-rw-r--r--keyboard/planck/keymaps/keymap_joe.c88
-rw-r--r--keyboard/planck/keymaps/keymap_kyle.c49
-rw-r--r--keyboard/planck/keymaps/keymap_leo.c46
-rw-r--r--keyboard/planck/keymaps/keymap_lock.c121
-rw-r--r--keyboard/planck/keymaps/keymap_max.c49
-rw-r--r--keyboard/planck/keymaps/keymap_monkey.c76
-rw-r--r--keyboard/planck/keymaps/keymap_numpad.c26
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_brett.c42
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_dotcom.c34
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_jack.c50
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_joe.c83
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_matthew.c70
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_nathan.c153
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_paul.c49
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_peasant.c51
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_reed.c74
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_sean.c53
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_shane.c98
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_simon.c44
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_tim.c44
-rw-r--r--keyboard/planck/old_keymap_files/common_keymaps/keymap_wilba.c56
-rw-r--r--keyboard/planck/old_keymap_files/keymap_common.c30
-rw-r--r--keyboard/planck/old_keymap_files/keymap_common.h129
-rw-r--r--keyboard/planck/planck.c31
-rw-r--r--keyboard/planck/planck.h38
-rw-r--r--keyboard/planck/planck_pcb.hex1544
-rwxr-xr-xkeyboard/planck/planck_with_bootloader.hex1796
-rw-r--r--keyboard/preonic/Makefile143
-rw-r--r--keyboard/preonic/Makefile.pjrc116
-rw-r--r--keyboard/preonic/PCB_GUIDE.md116
-rw-r--r--keyboard/preonic/README.md56
-rw-r--r--keyboard/preonic/__avr_gdbinit6
-rw-r--r--keyboard/preonic/analog.c53
-rw-r--r--keyboard/preonic/analog.h36
-rw-r--r--keyboard/preonic/backlight.c61
-rw-r--r--keyboard/preonic/beeps.c246
-rw-r--r--keyboard/preonic/beeps.h12
-rw-r--r--keyboard/preonic/config.h76
-rw-r--r--keyboard/preonic/config_definitions.h50
-rw-r--r--keyboard/preonic/extended_keymap_common.c216
-rw-r--r--keyboard/preonic/extended_keymap_common.h181
-rw-r--r--keyboard/preonic/extended_keymaps/extended_keymap_default.c70
-rw-r--r--keyboard/preonic/extended_keymaps/extended_keymap_lock.c81
-rw-r--r--keyboard/preonic/keymap_midi.c110
-rw-r--r--keyboard/preonic/keymap_midi.h220
-rw-r--r--keyboard/preonic/led.c38
-rw-r--r--keyboard/preonic/matrix.c234
-rw-r--r--keyboard/quark/Makefile155
-rw-r--r--keyboard/quark/Makefile.pjrc116
-rw-r--r--keyboard/quark/README.md53
-rw-r--r--keyboard/quark/backlight.c46
-rw-r--r--keyboard/quark/backlight.h2
-rw-r--r--keyboard/quark/common_keymaps/keymap_brett.c42
-rw-r--r--keyboard/quark/common_keymaps/keymap_dotcom.c34
-rw-r--r--keyboard/quark/common_keymaps/keymap_jack.c50
-rw-r--r--keyboard/quark/common_keymaps/keymap_joe.c107
-rw-r--r--keyboard/quark/common_keymaps/keymap_matthew.c70
-rw-r--r--keyboard/quark/common_keymaps/keymap_nathan.c153
-rw-r--r--keyboard/quark/common_keymaps/keymap_peasant.c51
-rw-r--r--keyboard/quark/common_keymaps/keymap_reed.c74
-rw-r--r--keyboard/quark/common_keymaps/keymap_sean.c57
-rw-r--r--keyboard/quark/common_keymaps/keymap_shane.c100
-rw-r--r--keyboard/quark/common_keymaps/keymap_simon.c44
-rw-r--r--keyboard/quark/common_keymaps/keymap_tim.c44
-rw-r--r--keyboard/quark/common_keymaps/keymap_wilba.c56
-rw-r--r--keyboard/quark/config.h74
-rw-r--r--keyboard/quark/extended_keymap_common.c184
-rw-r--r--keyboard/quark/extended_keymap_common.h152
-rw-r--r--keyboard/quark/extended_keymaps/extended_keymap_default.c40
-rw-r--r--keyboard/quark/keymap_common.c30
-rw-r--r--keyboard/quark/keymap_common.h86
-rw-r--r--keyboard/quark/led.c38
-rw-r--r--keyboard/quark/matrix.c193
-rw-r--r--quantum.mk30
-rw-r--r--quantum/analog.c53
-rw-r--r--quantum/analog.h36
-rw-r--r--quantum/beeps.c246
-rw-r--r--quantum/beeps.h12
-rw-r--r--quantum/config_common.h116
-rw-r--r--quantum/keymap_common.c255
-rw-r--r--quantum/keymap_common.h184
-rw-r--r--quantum/keymap_extras/keymap_colemak.h74
-rw-r--r--quantum/keymap_extras/keymap_dvorak.h72
-rw-r--r--quantum/keymap_extras/keymap_french.h83
-rw-r--r--quantum/keymap_extras/keymap_nordic.h59
-rw-r--r--quantum/keymap_extras/keymap_spanish.h62
-rw-r--r--quantum/keymap_extras/keymap_uk.h36
-rw-r--r--quantum/keymap_midi.c110
-rw-r--r--quantum/keymap_midi.h220
-rw-r--r--quantum/keymap_unicode.c59
-rw-r--r--quantum/led.c38
-rw-r--r--quantum/matrix.c311
m---------teensy-sdk0
-rw-r--r--tmk_core/common.mk9
-rw-r--r--tmk_core/common/keymap.c1
-rw-r--r--tmk_core/common/matrix.h4
-rw-r--r--tmk_core/protocol/bluefruit/bluefruit.c15
-rw-r--r--tmk_core/protocol/bluefruit/bluefruit.h5
-rw-r--r--tmk_core/protocol/bluefruit/main.c100
-rw-r--r--tmk_core/protocol/lufa.mk13
-rw-r--r--tmk_core/protocol/lufa/bluetooth.c37
-rw-r--r--tmk_core/protocol/lufa/bluetooth.h63
-rw-r--r--tmk_core/protocol/lufa/descriptor.c161
-rw-r--r--tmk_core/protocol/lufa/descriptor.h45
-rw-r--r--tmk_core/protocol/lufa/lufa.c357
-rw-r--r--tmk_core/protocol/lufa/lufa.h19
-rwxr-xr-xtmk_core/protocol/lufa/midi/Config/LUFAConfig.h93
-rwxr-xr-x[-rw-r--r--]tmk_core/protocol/lufa/midi/bytequeue/COPYING (renamed from doc/COPYING.GPLv3)0
-rwxr-xr-xtmk_core/protocol/lufa/midi/bytequeue/bytequeue.c65
-rwxr-xr-xtmk_core/protocol/lufa/midi/bytequeue/bytequeue.h59
-rwxr-xr-xtmk_core/protocol/lufa/midi/bytequeue/interrupt_setting.c36
-rwxr-xr-xtmk_core/protocol/lufa/midi/bytequeue/interrupt_setting.h39
-rwxr-xr-xtmk_core/protocol/lufa/midi/midi.c277
-rwxr-xr-xtmk_core/protocol/lufa/midi/midi.h498
-rwxr-xr-xtmk_core/protocol/lufa/midi/midi_device.c291
-rwxr-xr-xtmk_core/protocol/lufa/midi/midi_device.h156
-rwxr-xr-xtmk_core/protocol/lufa/midi/midi_function_types.h50
-rwxr-xr-xtmk_core/protocol/lufa/midi/sysex_tools.c99
-rwxr-xr-xtmk_core/protocol/lufa/midi/sysex_tools.h95
209 files changed, 20627 insertions, 1872 deletions
diff --git a/README.md b/README.md
index 4f850619e3..a6d92e006a 100644
--- a/README.md
+++ b/README.md
@@ -1,9 +1,6 @@
-TMK Keyboard Firmware Collection
+Quantum MK Firmware
================================
-This is a keyboard firmware with some useful features for Atmel AVR controller.
-
-Source code is available here: <http://github.com/tmk/tmk_keyboard>
-
+This is a keyboard firmware based on the [tmk_keyboard firmware](http://github.com/tmk/tmk_keyboard) with some useful features for Atmel AVR controller, and more specifically, the OLKB product line.
Updates
-------
@@ -42,6 +39,18 @@ Projects
--------
You can find some keyboard specific projects under `converter` and `keyboard` directory.
+## Main projects
+
+### OLKB products
+* [planck](keyboard/planck/) - [Planck] Ortholinear 40% keyboard
+* [preonic](keyboard/preonic/) - [Preonic] Ortholinear 50% keyboard
+* [atomic](keyboard/atomic/) - [Atomic] Ortholinear 60% keyboard
+
+### Ergodox EZ
+* [ergodox_ez](keyboard/ergodox_ez) - [Ergodox_EZ] Assembled split keyboard
+
+## Other projects
+
### converter
* [ps2_usb](converter/ps2_usb/) - [PS/2 keyboard to USB][GH_ps2]
* [adb_usb](converter/adb_usb/) - [ADB keyboard to USB][GH_adb]
@@ -101,7 +110,10 @@ You can find some keyboard specific projects under `converter` and `keyboard` di
[cub-uanic]: https://github.com/cub-uanic/tmk_keyboard/tree/master/keyboard/ergodox
[mcdox]: https://github.com/DavidMcEwan/mcdox
[mcdox_tmk]: https://github.com/DavidMcEwan/tmk_keyboard/tree/master/keyboard/mcdox
-
+[Planck]: http://olkb.co/planck
+[Preonic]: http://olkb.co/preonic
+[Atomic]: http://olkb.co/atomic
+[Ergodox_EZ]: https://www.indiegogo.com/projects/ergodox-ez-an-incredible-mechanical-keyboard
License
@@ -114,7 +126,7 @@ Third party libraries like LUFA, PJRC and V-USB have their own license respectiv
Build Firmware and Program Controller
-------------------------------------
-See [doc/build.md](doc/build.md).
+See [doc/build.md](doc/build.md), or the README in the particular keyboard/* folder.
diff --git a/doc/COPYING.GPLv2 b/doc/COPYING.GPLv2
deleted file mode 100644
index d159169d10..0000000000
--- a/doc/COPYING.GPLv2
+++ /dev/null
@@ -1,339 +0,0 @@
- GNU GENERAL PUBLIC LICENSE
- Version 2, June 1991
-
- Copyright (C) 1989, 1991 Free Software Foundation, Inc.,
- 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
- Everyone is permitted to copy and distribute verbatim copies
- of this license document, but changing it is not allowed.
-
- Preamble
-
- The licenses for most software are designed to take away your
-freedom to share and change it. By contrast, the GNU General Public
-License is intended to guarantee your freedom to share and change free
-software--to make sure the software is free for all its users. This
-General Public License applies to most of the Free Software
-Foundation's software and to any other program whose authors commit to
-using it. (Some other Free Software Foundation software is covered by
-the GNU Lesser General Public License instead.) You can apply it to
-your programs, too.
-
- When we speak of free software, we are referring to freedom, not
-price. Our General Public Licenses are designed to make sure that you
-have the freedom to distribute copies of free software (and charge for
-this service if you wish), that you receive source code or can get it
-if you want it, that you can change the software or use pieces of it
-in new free programs; and that you know you can do these things.
-
- To protect your rights, we need to make restrictions that forbid
-anyone to deny you these rights or to ask you to surrender the rights.
-These restrictions translate to certain responsibilities for you if you
-distribute copies of the software, or if you modify it.
-
- For example, if you distribute copies of such a program, whether
-gratis or for a fee, you must give the recipients all the rights that
-you have. You must make sure that they, too, receive or can get the
-source code. And you must show them these terms so they know their
-rights.
-
- We protect your rights with two steps: (1) copyright the software, and
-(2) offer you this license which gives you legal permission to copy,
-distribute and/or modify the software.
-
- Also, for each author's protection and ours, we want to make certain
-that everyone understands that there is no warranty for this free
-software. If the software is modified by someone else and passed on, we
-want its recipients to know that what they have is not the original, so
-that any problems introduced by others will not reflect on the original
-authors' reputations.
-
- Finally, any free program is threatened constantly by software
-patents. We wish to avoid the danger that redistributors of a free
-program will individually obtain patent licenses, in effect making the
-program proprietary. To prevent this, we have made it clear that any
-patent must be licensed for everyone's free use or not licensed at all.
-
- The precise terms and conditions for copying, distribution and
-modification follow.
-
- GNU GENERAL PUBLIC LICENSE
- TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION
-
- 0. This License applies to any program or other work which contains
-a notice placed by the copyright holder saying it may be distributed
-under the terms of this General Public License. The "Program", below,
-refers to any such program or work, and a "work based on the Program"
-means either the Program or any derivative work under copyright law:
-that is to say, a work containing the Program or a portion of it,
-either verbatim or with modifications and/or translated into another
-language. (Hereinafter, translation is included without limitation in
-the term "modification".) Each licensee is addressed as "you".
-
-Activities other than copying, distribution and modification are not
-covered by this License; they are outside its scope. The act of
-running the Program is not restricted, and the output from the Program
-is covered only if its contents constitute a work based on the
-Program (independent of having been made by running the Program).
-Whether that is true depends on what the Program does.
-
- 1. You may copy and distribute verbatim copies of the Program's
-source code as you receive it, in any medium, provided that you
-conspicuously and appropriately publish on each copy an appropriate
-copyright notice and disclaimer of warranty; keep intact all the
-notices that refer to this License and to the absence of any warranty;
-and give any other recipients of the Program a copy of this License
-along with the Program.
-
-You may charge a fee for the physical act of transferring a copy, and
-you may at your option offer warranty protection in exchange for a fee.
-
- 2. You may modify your copy or copies of the Program or any portion
-of it, thus forming a work based on the Program, and copy and
-distribute such modifications or work under the terms of Section 1
-above, provided that you also meet all of these conditions:
-
- a) You must cause the modified files to carry prominent notices
- stating that you changed the files and the date of any change.
-
- b) You must cause any work that you distribute or publish, that in
- whole or in part contains or is derived from the Program or any
- part thereof, to be licensed as a whole at no charge to all third
- parties under the terms of this License.
-
- c) If the modified program normally reads commands interactively
- when run, you must cause it, when started running for such
- interactive use in the most ordinary way, to print or display an
- announcement including an appropriate copyright notice and a
- notice that there is no warranty (or else, saying that you provide
- a warranty) and that users may redistribute the program under
- these conditions, and telling the user how to view a copy of this
- License. (Exception: if the Program itself is interactive but
- does not normally print such an announcement, your work based on
- the Program is not required to print an announcement.)
-
-These requirements apply to the modified work as a whole. If
-identifiable sections of that work are not derived from the Program,
-and can be reasonably considered independent and separate works in
-themselves, then this License, and its terms, do not apply to those
-sections when you distribute them as separate works. But when you
-distribute the same sections as part of a whole which is a work based
-on the Program, the distribution of the whole must be on the terms of
-this License, whose permissions for other licensees extend to the
-entire whole, and thus to each and every part regardless of who wrote it.
-
-Thus, it is not the intent of this section to claim rights or contest
-your rights to work written entirely by you; rather, the intent is to
-exercise the right to control the distribution of derivative or
-collective works based on the Program.
-
-In addition, mere aggregation of another work not based on the Program
-with the Program (or with a work based on the Program) on a volume of
-a storage or distribution medium does not bring the other work under
-the scope of this License.
-
- 3. You may copy and distribute the Program (or a work based on it,
-under Section 2) in object code or executable form under the terms of
-Sections 1 and 2 above provided that you also do one of the following:
-
- a) Accompany it with the complete corresponding machine-readable
- source code, which must be distributed under the terms of Sections
- 1 and 2 above on a medium customarily used for software interchange; or,
-
- b) Accompany it with a written offer, valid for at least three
- years, to give any third party, for a charge no more than your
- cost of physically performing source distribution, a complete
- machine-readable copy of the corresponding source code, to be
- distributed under the terms of Sections 1 and 2 above on a medium
- customarily used for software interchange; or,
-
- c) Accompany it with the information you received as to the offer
- to distribute corresponding source code. (This alternative is
- allowed only for noncommercial distribution and only if you
- received the program in object code or executable form with such
- an offer, in accord with Subsection b above.)
-
-The source code for a work means the preferred form of the work for
-making modifications to it. For an executable work, complete source
-code means all the source code for all modules it contains, plus any
-associated interface definition files, plus the scripts used to
-control compilation and installation of the executable. However, as a
-special exception, the source code distributed need not include
-anything that is normally distributed (in either source or binary
-form) with the major components (compiler, kernel, and so on) of the
-operating system on which the executable runs, unless that component
-itself accompanies the executable.
-
-If distribution of executable or object code is made by offering
-access to copy from a designated place, then offering equivalent
-access to copy the source code from the same place counts as
-distribution of the source code, even though third parties are not
-compelled to copy the source along with the object code.
-
- 4. You may not copy, modify, sublicense, or distribute the Program
-except as expressly provided under this License. Any attempt
-otherwise to copy, modify, sublicense or distribute the Program is
-void, and will automatically terminate your rights under this License.
-However, parties who have received copies, or rights, from you under
-this License will not have their licenses terminated so long as such
-parties remain in full compliance.
-
- 5. You are not required to accept this License, since you have not
-signed it. However, nothing else grants you permission to modify or
-distribute the Program or its derivative works. These actions are
-prohibited by law if you do not accept this License. Therefore, by
-modifying or distributing the Program (or any work based on the
-Program), you indicate your acceptance of this License to do so, and
-all its terms and conditions for copying, distributing or modifying
-the Program or works based on it.
-
- 6. Each time you redistribute the Program (or any work based on the
-Program), the recipient automatically receives a license from the
-original licensor to copy, distribute or modify the Program subject to
-these terms and conditions. You may not impose any further
-restrictions on the recipients' exercise of the rights granted herein.
-You are not responsible for enforcing compliance by third parties to
-this License.
-
- 7. If, as a consequence of a court judgment or allegation of patent
-infringement or for any other reason (not limited to patent issues),
-conditions are imposed on you (whether by court order, agreement or
-otherwise) that contradict the conditions of this License, they do not
-excuse you from the conditions of this License. If you cannot
-distribute so as to satisfy simultaneously your obligations under this
-License and any other pertinent obligations, then as a consequence you
-may not distribute the Program at all. For example, if a patent
-license would not permit royalty-free redistribution of the Program by
-all those who receive copies directly or indirectly through you, then
-the only way you could satisfy both it and this License would be to
-refrain entirely from distribution of the Program.
-
-If any portion of this section is held invalid or unenforceable under
-any particular circumstance, the balance of the section is intended to
-apply and the section as a whole is intended to apply in other
-circumstances.
-
-It is not the purpose of this section to induce you to infringe any
-patents or other property right claims or to contest validity of any
-such claims; this section has the sole purpose of protecting the
-integrity of the free software distribution system, which is
-implemented by public license practices. Many people have made
-generous contributions to the wide range of software distributed
-through that system in reliance on consistent application of that
-system; it is up to the author/donor to decide if he or she is willing
-to distribute software through any other system and a licensee cannot
-impose that choice.
-
-This section is intended to make thoroughly clear what is believed to
-be a consequence of the rest of this License.
-
- 8. If the distribution and/or use of the Program is restricted in
-certain countries either by patents or by copyrighted interfaces, the
-original copyright holder who places the Program under this License
-may add an explicit geographical distribution limitation excluding
-those countries, so that distribution is permitted only in or among
-countries not thus excluded. In such case, this License incorporates
-the limitation as if written in the body of this License.
-
- 9. The Free Software Foundation may publish revised and/or new versions
-of the General Public License from time to time. Such new versions will
-be similar in spirit to the present version, but may differ in detail to
-address new problems or concerns.
-
-Each version is given a distinguishing version number. If the Program
-specifies a version number of this License which applies to it and "any
-later version", you have the option of following the terms and conditions
-either of that version or of any later version published by the Free
-Software Foundation. If the Program does not specify a version number of
-this License, you may choose any version ever published by the Free Software
-Foundation.
-
- 10. If you wish to incorporate parts of the Program into other free
-programs whose distribution conditions are different, write to the author
-to ask for permission. For software which is copyrighted by the Free
-Software Foundation, write to the Free Software Foundation; we sometimes
-make exceptions for this. Our decision will be guided by the two goals
-of preserving the free status of all derivatives of our free software and
-of promoting the sharing and reuse of software generally.
-
- NO WARRANTY
-
- 11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY
-FOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW. EXCEPT WHEN
-OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES
-PROVIDE THE PROGRAM "AS IS" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED
-OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
-MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. THE ENTIRE RISK AS
-TO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU. SHOULD THE
-PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,
-REPAIR OR CORRECTION.
-
- 12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING
-WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR
-REDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,
-INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING
-OUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED
-TO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY
-YOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER
-PROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE
-POSSIBILITY OF SUCH DAMAGES.
-
- END OF TERMS AND CONDITIONS
-
- How to Apply These Terms to Your New Programs
-
- If you develop a new program, and you want it to be of the greatest
-possible use to the public, the best way to achieve this is to make it
-free software which everyone can redistribute and change under these terms.
-
- To do so, attach the following notices to the program. It is safest
-to attach them to the start of each source file to most effectively
-convey the exclusion of warranty; and each file should have at least
-the "copyright" line and a pointer to where the full notice is found.
-
- <one line to give the program's name and a brief idea of what it does.>
- Copyright (C) <year> <name of author>
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 2 of the License, or
- (at your option) any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License along
- with this program; if not, write to the Free Software Foundation, Inc.,
- 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
-
-Also add information on how to contact you by electronic and paper mail.
-
-If the program is interactive, make it output a short notice like this
-when it starts in an interactive mode:
-
- Gnomovision version 69, Copyright (C) year name of author
- Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
- This is free software, and you are welcome to redistribute it
- under certain conditions; type `show c' for details.
-
-The hypothetical commands `show w' and `show c' should show the appropriate
-parts of the General Public License. Of course, the commands you use may
-be called something other than `show w' and `show c'; they could even be
-mouse-clicks or menu items--whatever suits your program.
-
-You should also get your employer (if you work as a programmer) or your
-school, if any, to sign a "copyright disclaimer" for the program, if
-necessary. Here is a sample; alter the names:
-
- Yoyodyne, Inc., hereby disclaims all copyright interest in the program
- `Gnomovision' (which makes passes at compilers) written by James Hacker.
-
- <signature of Ty Coon>, 1 April 1989
- Ty Coon, President of Vice
-
-This General Public License does not permit incorporating your program into
-proprietary programs. If your program is a subroutine library, you may
-consider it more useful to permit linking proprietary applications with the
-library. If this is what you want to do, use the GNU Lesser General
-Public License instead of this License.
diff --git a/doc/FUSE.txt b/doc/FUSE.txt
deleted file mode 100644
index 40055e5ab1..0000000000
--- a/doc/FUSE.txt
+++ /dev/null
@@ -1,40 +0,0 @@
-ATMega168P Fuse/Lock Bits
-=========================
-This configuration is from usbasploader's Makefile.
-
- HFUSE 0xD6
- LFUSE 0xDF
- EFUSE 0x00
- LOCK 0x3F(intact)
-
-#---------------------------------------------------------------------
-# ATMega168P
-#---------------------------------------------------------------------
-# Fuse extended byte:
-# 0x00 = 0 0 0 0 0 0 0 0 <-- BOOTRST (boot reset vector at 0x1800)
-# \+/
-# +------- BOOTSZ (00 = 2k bytes)
-# Fuse high byte:
-# 0xd6 = 1 1 0 1 0 1 1 0
-# ^ ^ ^ ^ ^ \-+-/
-# | | | | | +------ BODLEVEL 0..2 (110 = 1.8 V)
-# | | | | + --------- EESAVE (preserve EEPROM over chip erase)
-# | | | +-------------- WDTON (if 0: watchdog always on)
-# | | +---------------- SPIEN (allow serial programming)
-# | +------------------ DWEN (debug wire enable)
-# +-------------------- RSTDISBL (reset pin is enabled)
-# Fuse low byte:
-# 0xdf = 1 1 0 1 1 1 1 1
-# ^ ^ \ / \--+--/
-# | | | +------- CKSEL 3..0 (external >8M crystal)
-# | | +--------------- SUT 1..0 (crystal osc, BOD enabled)
-# | +------------------ CKOUT (if 0: Clock output enabled)
-# +-------------------- CKDIV8 (if 0: divide by 8)
-
-
-# Lock Bits
-# 0x3f = - - 1 1 1 1 1 1
-# \ / \-/ \-/
-# | | +----- LB 2..1 (No memory lock features enabled)
-# | +--------- BLB0 2..1 (No restrictions for SPM or LPM accessing the Application section)
-# +--------------- BLB1 2..1 (No restrictions for SPM or LPM accessing the Boot Loader section)
diff --git a/doc/POWER.txt b/doc/POWER.txt
deleted file mode 100644
index 0abbbe48e8..0000000000
--- a/doc/POWER.txt
+++ /dev/null
@@ -1,62 +0,0 @@
-Time to Sleep
-=============
-USB suspend no activity on USB line for 3ms
-No Interaction no user interaction
- matrix has no change
- matrix has no switch on
-
-
-AVR Power Management
-====================
-
-V-USB suspend
- USB suspend
- http://vusb.wikidot.com/examples
-
-MCUSR MCU Status Register
- WDRF Watchdog Reset Flag
- BORF
- EXTRF
- PORF Power-on Reset Flag
-
-SMCR Sleep Mode Control Register
- SE Sleep Enable
- SM2:0
- #define set_sleep_mode(mode) \
- #define SLEEP_MODE_IDLE (0)
- #define SLEEP_MODE_ADC _BV(SM0)
- #define SLEEP_MODE_PWR_DOWN _BV(SM1)
- #define SLEEP_MODE_PWR_SAVE (_BV(SM0) | _BV(SM1))
- #define SLEEP_MODE_STANDBY (_BV(SM1) | _BV(SM2))
- #define SLEEP_MODE_EXT_STANDBY (_BV(SM0) | _BV(SM1) | _BV(SM2))
-
-
-ACSR Analog Comparator Control and Status Register
- To disable Analog Comparator
- ACSR = 0x80;
- or
- ACSR &= ~_BV(ACIE);
- ACSR |= _BV(ACD);
-
- ACD: Analog Comparator Disable
- When this bit is written logic one, the power to the Analog Comparator is
- switched off. This bit can be set at any time to turn off the Analog
- Comparator. This will reduce power consumption in Active and Idle mode.
- When changing the ACD bit, the Analog Comparator Interrupt must be disabled
- by clearing the ACIE bit in ACSR. Otherwise an interrupt can occur when
- the bit is changed.
-
-DIDR1 Digital Input Disable Register 1
- AIN1D
- AIN0D
- When this bit is written logic one, the digital input buffer on the AIN1/0 pin is disabled. The corresponding PIN Register bit will always read as zero when this bit is set. When an analog signal is applied to the AIN1/0 pin and the digital input from this pin is not needed, this bit should be written logic one to reduce power consumption in the digital input buffer.
-
-
-PRR Power Reduction Register
- PRTWI
- PRTIM2
- PRTIM0
- PRTIM1
- PRSPI
- PRUSART0
- PRADC
diff --git a/doc/USB_NKRO.txt b/doc/USB_NKRO.txt
deleted file mode 100644
index d9f1d12292..0000000000
--- a/doc/USB_NKRO.txt
+++ /dev/null
@@ -1,160 +0,0 @@
-USB NKRO MEMO
-=============
-2010/12/09
-
-
-References
-----------
-USB - boot mode, NKRO, compatibility, etc...
- http://geekhack.org/showthread.php?t=13162
-NKey Rollover - Overview, Testing Methodology, and Results
- http://geekhack.org/showwiki.php?title=NKey+Rollover+-+Overview+Testing+Methodology+and+Results
-dfj's NKRO(2010/06)
- http://geekhack.org/showpost.php?p=191195&postcount=251
- http://geekhack.org/showthread.php?p=204389#post204389
-
-
-Terminology
----------
-NKRO
-ghost
-matrix
-mechanical with diodes
-membrane
-
-
-OS Support Status
------------------
-USB NKRO is possible *without* a custom driver.
-At least following OS's supports.
- Windows7 64bit
- WindowsXP
- Windows2000 SP4
- Ubuntu10.4(Linux 2.6)
- MacOSX(To be tested)
-
-
-Custom Driver for USB NKRO
---------------------------
-NOT NEEDED
-at least when using following report formats on Windows, Linux or MacOSX.
-
-
-USB NKRO methods
-----------------
-1. Virtual keyboards
- Keyboard can increase its KRO by using virtual keyboards with Standard or Extended report.
- If the keyboard has 2 virtual keyboard with Standard report(6KRO), it gets 12KRO.
- Using this method means the keyboard is a composite device.
-
-2. Extended report
- It needs large report size for this method to achieve NKRO.
- If a keyboard has 101keys, it needs 103byte report. It seems to be inefficient.
-
-3. Bitmap report
- If the keyboard has less than 128keys, 16byte report will be enough for NKRO.
- The 16byte report seems to be reasonable cost to get NKRO.
-
-
-Report Format
--------------
-Other report formats than followings are possible, though these format are typical one.
-
-1. Standard 8bytes
- modifiers(bitmap) 1byte
- reserved 1byte(not used)
- keys(array) 1byte*6
-Standard report can send 6keys plus 8modifiers simultaneously.
-Standard report is used by most keyboards in the marketplace.
-Standard report is identical to boot protocol report.
-Standard report is hard to suffer from compatibility problems.
-
-2. Extended standard 16,32,64bytes
- modifiers(bitmap) 1byte
- reserved 1byte(not used)
- keys(array) 1byte*(14,32,62)
-Extended report can send N-keys by using N+2bytes.
-Extended report is expected to be compatible with boot protocol.
-
-3. Bitmap 16,32,64bytes
- keys(bitmap) (16,32)bytes
-Bitmap report can send at most 128keys by 16bytes and 256keys by 32bytes.
-Bitmap report can achieve USB NKRO efficiently in terms of report size.
-Bitmap report needs a deliberation for boot protocol implementation.
-Bitmap report descriptor sample:
- 0x05, 0x01, // Usage Page (Generic Desktop),
- 0x09, 0x06, // Usage (Keyboard),
- 0xA1, 0x01, // Collection (Application),
- // bitmap of modifiers
- 0x75, 0x01, // Report Size (1),
- 0x95, 0x08, // Report Count (8),
- 0x05, 0x07, // Usage Page (Key Codes),
- 0x19, 0xE0, // Usage Minimum (224),
- 0x29, 0xE7, // Usage Maximum (231),
- 0x15, 0x00, // Logical Minimum (0),
- 0x25, 0x01, // Logical Maximum (1),
- 0x81, 0x02, // Input (Data, Variable, Absolute), ;Modifier byte
- // LED output report
- 0x95, 0x05, // Report Count (5),
- 0x75, 0x01, // Report Size (1),
- 0x05, 0x08, // Usage Page (LEDs),
- 0x19, 0x01, // Usage Minimum (1),
- 0x29, 0x05, // Usage Maximum (5),
- 0x91, 0x02, // Output (Data, Variable, Absolute),
- 0x95, 0x01, // Report Count (1),
- 0x75, 0x03, // Report Size (3),
- 0x91, 0x03, // Output (Constant),
- // bitmap of keys
- 0x95, (REPORT_BYTES-1)*8, // Report Count (),
- 0x75, 0x01, // Report Size (1),
- 0x15, 0x00, // Logical Minimum (0),
- 0x25, 0x01, // Logical Maximum(1),
- 0x05, 0x07, // Usage Page (Key Codes),
- 0x19, 0x00, // Usage Minimum (0),
- 0x29, (REPORT_BYTES-1)*8-1, // Usage Maximum (),
- 0x81, 0x02, // Input (Data, Variable, Absolute),
- 0xc0 // End Collection
-where REPORT_BYTES is a report size in bytes.
-
-
-Considerations
---------------
-Compatibility
- boot protocol
- minor/old system
- Some BIOS doesn't send SET_PROTOCOL request, a keyboard can't switch to boot protocol mode.
- This may cause a problem on a keyboard which uses other report than Standard.
-Reactivity
- USB polling time
- OS/Driver processing time
-
-
-Windows Problem
----------------
-1. Windows accepts only 6keys in case of Standard report.
- It should be able to send 6keys plus 8modifiers.
-2. Windows accepts only 10keys in case of 16bytes Extended report.
- It should be able to send 14keys plus 8modifiers.
-3. Windows accepts only 18keys in case of 32bytes Extended report.
- It should be able to send 30keys plus 8modifiers.
-If keys are pressed in excess of the number, wrong keys are registered on Windows.
-
-This problem will be reportedly fixed soon.(2010/12/05)
- http://forums.anandtech.com/showpost.php?p=30873364&postcount=17
-
-
-Tools for testing NKRO
-----------------------
-Browser App:
-http://www.microsoft.com/appliedsciences/content/projects/KeyboardGhostingDemo.aspx
-http://random.xem.us/rollover.html
-
-Windows:
-AquaKeyTest.exe http://geekhack.org/showthread.php?t=6643
-
-Linux:
-xkeycaps
-xev
-showkeys
-
-EOF
diff --git a/doc/build.md b/doc/build.md
deleted file mode 100644
index beff191b8c..0000000000
--- a/doc/build.md
+++ /dev/null
@@ -1,185 +0,0 @@
-Build Firmware and Program Controller
-=====================================
-
-
-Download and Install
---------------------
-### 1. Install Tools
-
-1. **Toolchain** On Windows install [Atmel AVR Toolchain][atmelgcc] for AVR GCC compiler and [Cygwin][cygwin](or [MinGW][mingw]) for shell terminal. On Mac you can use [CrossPack][crosspack] or your favorite package manager. On Linux you can install AVR GCC with your favorite package manager.
-
-2. **Programmer** Install [dfu-programmer][dfu-prog]. GUI tool [Atmel FLIP][flip] also can be used on Windows.
-
-3. **Driver** On Windows you start DFU bootloader on the chip first time you will see 'Found New Hardware Wizard' to install driver. If you install device driver properly you can find chip name like 'ATmega32U4' under 'LibUSB-Win32 Devices' tree on 'Device Manager'. If not you shall need to update its driver on 'Device Manager'. You will find the driver in `FLIP` install directory like: C:\Program Files (x86)\Atmel\Flip 3.4.5\usb\. In case of `dfu-programmer` use its driver.
-
-If you use PJRC Teensy you don't need step 2 and 3 above, just get [Teensy loader][teensy-loader].
-
-
-### 2. Download source
-You can find firmware source at github:
-
-- <https://github.com/tmk/tmk_keyboard>
-
-If you are familiar with `Git` tools you are recommended to use it but you can also download zip archive from:
-
-- <https://github.com/tmk/tmk_keyboard/archive/master.zip>
-
-
-Build firmware
---------------
-### 1. Open terminal
-Open terminal window to get access to commands. Use Cygwin(or MingGW) `shell terminal` in Windows or `Terminal.app` on Mac OSX. In Windows press `Windows` key and `R` then enter `cmd` in 'Run command' dialog showing up.
-
-### 2. Change directory
-Move to project directory in the firmware source.
-
- cd tmk_keyboard/{'keyboard' or 'converter'}/<project>
-
-### 3. Make
-Build firmware using GNU `make` command. You'll see `<project>_<variant>.hex` file in that directory unless something unexpected occurs in build process.
-
-
- make -f Makefile.<variant> clean
- make -f Makefile.<variant>
-
-
-
-
-Program Controller
-------------------
-Now you have **hex** file to program on current directory. This **hex** is only needed to program your controller, other files are used for development and you may leave and forget them.
-
-### 1. Start bootloader
-How to program controller depends on controller chip and its board design. To program AVR USB chips you'll need to start it up in bootloader mode. Most of boards with the chip have a push button to let bootloader come up. Consult with your controller board manual.
-
-### 2. Program with DFU bootloader
-Stock AVR USB chips have DFU bootloader by factory default. `FLIP` is a DFU programmer on Windows offered by Atmel. Open source command line tool `dfu-programmer` also supports AVR chips, it runs on Linux, Mac OSX and even Windows.
-
-To program AVR chip with DFU bootloader use `FLIP` or `dfu-programmer`.
-If you have a proper program command in `Makefile` just type this.
-
-`FLIP` has two version of tool, GUI app and command line program. If you want GUI see tutorial below.
-To use command line tool run this command. Note that you need to set PATH variable properly.
-
- $ make -f Makefile.<variant> flip
-
-Or to program with `dfu-programmer` run:
-
- $ make -f Makefile.<variant> dfu
-
-#### FLIP GUI tutorial
-1. On menu bar click Device -> Select, then choose your chip name.
-2. On menu bar click Settings -> Communication -> USB, then click 'Open' button on 'USB Port Connection' dialog.
-At this point you'll see grey-outed widgets on the app get colored and ready.
-
-3. On menu bar click File -> Load HEX File, then select your firmware hex file on File Selector dialog.
-4. On 'Operations Flow' panel click 'Run' button to load the firmware binary to the chip. Note that you should keep 'Erase', 'Blank Check', 'Program' and 'Verify' check boxes selected.
-5. Re-plug USB cord or click 'Start Application' button to restart your controller.
-Done.
-
-See also these instructions if you need.
-
-- <http://code.google.com/p/micropendous/wiki/LoadingFirmwareWithFLIP>
-- <http://www.atmel.com/Images/doc7769.pdf>
-
-
-### 3. Program with Teensy Loader
-If you have PJRC Teensy see instruction of `Teensy Loader`.
-
-- <http://www.pjrc.com/teensy/loader.html>
-
-Or use this command if you have command line version of Teensy Loader installed.
-
- $ make -f Makefile.<variant> teensy
-
-
-### 4. Program with Other programmer
-You may want to use other programmer like `avrdude` with AVRISPmkII, Arduino or USBasp. In that case you can still use make target `program` for build with configuring `PROGRAM_CMD` in Makefile.
-
- $ make -f Makefile.<variant> program
-
-
-[atmelgcc]: http://www.atmel.com/tools/ATMELAVRTOOLCHAINFORWINDOWS.aspx
-[cygwin]: https://www.cygwin.com/
-[mingw]: http://www.mingw.org/
-[crosspack]: http://www.obdev.at/products/crosspack/index.html
-[flip]: http://www.atmel.com/tools/FLIP.aspx
-[dfu-prog]: http://dfu-programmer.sourceforge.net/
-[teensy-loader]:http://www.pjrc.com/teensy/loader.html
-
-
-
-Makefile Options
-----------------
-### 1. MCU and Frequency.
-
- MCU = atmega32u4 # Teensy 2.0
- #MCU = at90usb1286 # Teensy++ 2.0
- F_CPU = 16000000
-
-Set your MCU and its clock in Hz.
-
- # Boot Section Size in *bytes*
- # Teensy halfKay 512
- # Atmel DFU loader 4096
- # LUFA bootloader 4096
- OPT_DEFS += -DBOOTLOADER_SIZE=4096
-
-If you are using PJRC Teensy use `512` for `BOOTLOADER_SIZE`, otherwise use `4096` unless you are sure.
-
-### 2. Features
-Optional. Note that ***comment out*** with `#` to disable them.
-
- BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration(+1000)
- MOUSEKEY_ENABLE = yes # Mouse keys(+4700)
- EXTRAKEY_ENABLE = yes # Audio control and System control(+450)
- CONSOLE_ENABLE = yes # Console for debug(+400)
- COMMAND_ENABLE = yes # Commands for debug and configuration
- SLEEP_LED_ENABLE = yes # Breathing sleep LED during USB suspend
- #NKRO_ENABLE = yes # USB Nkey Rollover - not yet supported in LUFA
- #BACKLIGHT_ENABLE = yes # Enable keyboard backlight functionality
-
-### 3. Programmer
-Optional. Set proper command for your controller, bootloader and programmer. This command can be used with `make program`. Not needed if you use `FLIP`, `dfu-programmer` or `Teensy Loader`.
-
- # avrdude with AVRISPmkII
- PROGRAM_CMD = avrdude -p $(MCU) -c avrispmkII -P USB -U flash:w:$(TARGET).hex
-
- # avrdude with USBaspLoader
- PROGRAM_CMD = avrdude -p $(MCU) -c usbasp -U flash:w:$(TARGET).hex
-
- # avrdude with arduino
- PROGRAM_CMD = avrdude -p $(MCU) -c arduino -P COM1 -b 57600 -U flash:w:$(TARGET).hex
-
-
-
-Config.h Options
-----------------
-### 1. Magic command key combination
-
- #define IS_COMMAND() (keyboard_report->mods == (MOD_BIT(KB_LSHIFT) | MOD_BIT(KB_RSHIFT)))
-
-### 2. Mechanical Locking Support for CapsLock
-
- /* Mechanical locking CapsLock support. Use KC_LCAP instead of KC_CAPS in keymap */
- #define CAPSLOCK_LOCKING_ENABLE
- /* Locking CapsLock re-synchronize hack */
- #define CAPSLOCK_LOCKING_RESYNC_ENABLE
-
-### 3. Disable Debug and Print
-
- /* disable debug print */
- #define NO_DEBUG
-
- /* disable print */
- #define NO_PRINT
-
-### 4. Disable Action Features
-
- #define NO_ACTION_LAYER
- #define NO_ACTION_TAPPING
- #define NO_ACTION_ONESHOT
- #define NO_ACTION_MACRO
- #define NO_ACTION_FUNCTION
-
-***TBD***
diff --git a/doc/keycode.txt b/doc/keycode.txt
deleted file mode 100644
index 44d7e27cd6..0000000000
--- a/doc/keycode.txt
+++ /dev/null
@@ -1,261 +0,0 @@
-Keycode Symbol Table
-====================
-Keycodes are defined in `common/keycode.h`.
-Range of 00-A4 and E0-E7 are identical with HID Usage:
-<http://www.usb.org/developers/devclass_docs/Hut1_11.pdf>
-Virtual keycodes are defined out of above range to support special actions.
-
-
-Keycode Symbol Short name Description
---------------------------------------------------------------------------------
-KC_NO 00 Reserved (no event indicated)
-KC_ROLL_OVER 01 Keyboard ErrorRollOver
-KC_POST_FAIL 02 Keyboard POSTFail
-KC_UNDEFINED 03 Keyboard ErrorUndefined
-KC_A 04 Keyboard a and A
-KC_B 05 Keyboard b and B
-KC_C 06 Keyboard c and C
-KC_D 07 Keyboard d and D
-KC_E 08 Keyboard e and E
-KC_F 09 Keyboard f and F
-KC_G 0A Keyboard g and G
-KC_H 0B Keyboard h and H
-KC_I 0C Keyboard i and I
-KC_J 0D Keyboard j and J
-KC_K 0E Keyboard k and K
-KC_L 0F Keyboard l and L
-KC_M 10 Keyboard m and M
-KC_N 11 Keyboard n and N
-KC_O 12 Keyboard o and O
-KC_P 13 Keyboard p and P
-KC_Q 14 Keyboard q and Q
-KC_R 15 Keyboard r and R
-KC_S 16 Keyboard s and S
-KC_T 17 Keyboard t and T
-KC_U 18 Keyboard u and U
-KC_V 19 Keyboard v and V
-KC_W 1A Keyboard w and W
-KC_X 1B Keyboard x and X
-KC_Y 1C Keyboard y and Y
-KC_Z 1D Keyboard z and Z
-KC_1 1E Keyboard 1 and !
-KC_2 1F Keyboard 2 and @
-KC_3 20 Keyboard 3 and #
-KC_4 21 Keyboard 4 and $
-KC_5 22 Keyboard 5 and %
-KC_6 23 Keyboard 6 and ^
-KC_7 24 Keyboard 7 and &
-KC_8 25 Keyboard 8 and *
-KC_9 26 Keyboard 9 and (
-KC_0 27 Keyboard 0 and )
-KC_ENTER KC_ENT 28 Keyboard Return (ENTER)
-KC_ESCAPE KC_ESC 29 Keyboard ESCAPE
-KC_BSPACE KC_BSPC 2A Keyboard DELETE (Backspace)
-KC_TAB 2B Keyboard Tab
-KC_SPACE KC_SPC 2C Keyboard Spacebar
-KC_MINUS KC_MINS 2D Keyboard - and (underscore)
-KC_EQUAL KC_EQL 2E Keyboard = and +
-KC_LBRACKET KC_LBRC 2F Keyboard [ and {
-KC_RBRACKET KC_RBRC 30 Keyboard ] and }
-KC_BSLASH KC_BSLS 31 Keyboard \ and |
-KC_NONUS_HASH KC_NUHS 32 Keyboard Non-US # and ~
-KC_SCOLON KC_SCLN 33 Keyboard ; and :
-KC_QUOTE KC_QUOT 34 Keyboard ‘ and “
-KC_GRAVE KC_GRV 35 Keyboard Grave Accent and Tilde
-KC_COMMA KC_COMM 36 Keyboard, and <
-KC_DOT 37 Keyboard . and >
-KC_SLASH KC_SLSH 38 Keyboard / and ?
-KC_CAPSLOCK KC_CAPS 39 Keyboard Caps Lock
-KC_F1 3A Keyboard F1
-KC_F2 3B Keyboard F2
-KC_F3 3C Keyboard F3
-KC_F4 3D Keyboard F4
-KC_F5 3E Keyboard F5
-KC_F6 3F Keyboard F6
-KC_F7 40 Keyboard F7
-KC_F8 41 Keyboard F8
-KC_F9 42 Keyboard F9
-KC_F10 43 Keyboard F10
-KC_F11 44 Keyboard F11
-KC_F12 45 Keyboard F12
-KC_PSCREEN KC_PSCR 46 Keyboard PrintScreen1
-KC_SCKLOCK KC_SLCK 47 Keyboard Scroll Lock11
-KC_PAUSE KC_PAUS 48 Keyboard Pause1
-KC_INSERT KC_INS 49 Keyboard Insert1
-KC_HOME 4A Keyboard Home1
-KC_PGUP 4B Keyboard PageUp1
-KC_DELETE KC_DELETE 4C Keyboard Delete Forward
-KC_END 4D Keyboard End1
-KC_PGDOWN KC_PGDN 4E Keyboard PageDown1
-KC_RIGHT KC_RGHT 4F Keyboard RightArrow1
-KC_LEFT 50 Keyboard LeftArrow1
-KC_DOWN 51 Keyboard DownArrow1
-KC_UP 52 Keyboard UpArrow1
-KC_NUMLOCK KC_NLCK 53 Keypad Num Lock and Clear11
-KC_KP_SLASH KC_PSLS 54 Keypad /1
-KC_KP_ASTERISK KC_PAST 55 Keypad *
-KC_KP_MINUS KC_PMNS 56 Keypad -
-KC_KP_PLUS KC_PPLS 57 Keypad +
-KC_KP_ENTER KC_PENT 58 Keypad ENTER5
-KC_KP_1 KC_P1 59 Keypad 1 and End
-KC_KP_2 KC_P2 5A Keypad 2 and Down Arrow
-KC_KP_3 KC_P3 5B Keypad 3 and PageDn
-KC_KP_4 KC_P4 5C Keypad 4 and Left Arrow
-KC_KP_5 KC_P5 5D Keypad 5
-KC_KP_6 KC_P6 5E Keypad 6 and Right Arrow
-KC_KP_7 KC_P7 5F Keypad 7 and Home
-KC_KP_8 KC_P8 60 Keypad 8 and Up Arrow
-KC_KP_9 KC_P9 61 Keypad 9 and PageUp
-KC_KP_0 KC_P0 62 Keypad 0 and Insert
-KC_KP_DOT KC_PDOT 63 Keypad . and Delete
-KC_NONUS_BSLASH KC_NUBS 64 Keyboard Non-US \ and |
-KC_APPLICATION KC_APP 65 Keyboard Application10
-KC_POWER 66 Keyboard Power9
-KC_KP_EQUAL KC_PEQL 67 Keypad =
-KC_F13 68 Keyboard F13
-KC_F14 69 Keyboard F14
-KC_F15 6A Keyboard F15
-KC_F16 6B Keyboard F16
-KC_F17 6C Keyboard F17
-KC_F18 6D Keyboard F18
-KC_F19 6E Keyboard F19
-KC_F20 6F Keyboard F20
-KC_F21 70 Keyboard F21
-KC_F22 71 Keyboard F22
-KC_F23 72 Keyboard F23
-KC_F24 73 Keyboard F24
-KC_EXECUTE 74 Keyboard Execute
-KC_HELP 75 Keyboard Help
-KC_MENU 76 Keyboard Menu
-KC_SELECT 77 Keyboard Select
-KC_STOP 78 Keyboard Stop
-KC_AGAIN 79 Keyboard Again
-KC_UNDO 7A Keyboard Undo
-KC_CUT 7B Keyboard Cut
-KC_COPY 7C Keyboard Copy
-KC_PASTE 7D Keyboard Paste
-KC_FIND 7E Keyboard Find
-KC__MUTE 7F Keyboard Mute
-KC__VOLUP 80 Keyboard Volume Up
-KC__VOLDOWN 81 Keyboard Volume Down
-KC_LOCKING_CAPS 82 Keyboard Locking Caps Lock12
-KC_LOCKING_NUM 83 Keyboard Locking Num Lock12
-KC_LOCKING_SCROLL 84 Keyboard Locking Scroll Lock12
-KC_KP_COMMA KC_PCMM 85 Keypad Comma27
-KC_KP_EQUAL_AS400 86 Keypad Equal Sign29
-KC_INT1 KC_RO 87 Keyboard International115,28
-KC_INT2 KC_KANA 88 Keyboard International216
-KC_INT3 KC_JYEN 89 Keyboard International317
-KC_INT4 KC_HENK 8A Keyboard International418
-KC_INT5 KC_MHEN 8B Keyboard International519
-KC_INT6 8C Keyboard International620
-KC_INT7 8D Keyboard International721
-KC_INT8 8E Keyboard International822
-KC_INT9 8F Keyboard International922
-KC_LANG1 90 Keyboard LANG125
-KC_LANG2 91 Keyboard LANG226
-KC_LANG3 92 Keyboard LANG330
-KC_LANG4 93 Keyboard LANG431
-KC_LANG5 94 Keyboard LANG532
-KC_LANG6 95 Keyboard LANG68
-KC_LANG7 96 Keyboard LANG78
-KC_LANG8 97 Keyboard LANG88
-KC_LANG9 98 Keyboard LANG98
-KC_ALT_ERASE 99 Keyboard Alternate Erase7
-KC_SYSREQ 9A Keyboard SysReq/Attention1
-KC_CANCEL 9B Keyboard Cancel
-KC_CLEAR 9C Keyboard Clear
-KC_PRIOR 9D Keyboard Prior
-KC_RETURN 9E Keyboard Return
-KC_SEPARATOR 9F Keyboard Separator
-KC_OUT A0 Keyboard Out
-KC_OPER A1 Keyboard Oper
-KC_CLEAR_AGAIN A2 Keyboard Clear/Again
-KC_CRSEL A3 Keyboard CrSel/Props
-KC_EXSEL A4 Keyboard ExSel
-/* Modifiers */
-KC_LCTRL KC_LCTL E0 Keyboard LeftControl
-KC_LSHIFT KC_LSFT E1 Keyboard LeftShift
-KC_LALT E2 Keyboard LeftAlt
-KC_LGUI E3 Keyboard Left GUI(Windows/Apple/Meta key)
-KC_RCTRL KC_RCTL E4 Keyboard RightControl
-KC_RSHIFT KC_RSFT E5 Keyboard RightShift
-KC_RALT E6 Keyboard RightAlt
-KC_RGUI E7 Keyboard Right GUI(Windows/Apple/Meta key)
-
-/*
- * Virtual keycodes
- */
-/* System Control */
-KC_SYSTEM_POWER KC_PWR System Power Down
-KC_SYSTEM_SLEEP KC_SLEP System Sleep
-KC_SYSTEM_WAKE KC_WAKE System Wake
-/* Consumer Page */
-KC_AUDIO_MUTE KC_MUTE
-KC_AUDIO_VOL_UP KC_VOLU
-KC_AUDIO_VOL_DOWN KC_VOLD
-KC_MEDIA_NEXT_TRACK KC_MNXT
-KC_MEDIA_PREV_TRACK KC_MPRV
-KC_MEDIA_STOP KC_MSTP
-KC_MEDIA_PLAY_PAUSE KC_MPLY
-KC_MEDIA_SELECT KC_MSEL
-KC_MAIL KC_MAIL
-KC_CALCULATOR KC_CALC
-KC_MY_COMPUTER KC_MYCM
-KC_WWW_SEARCH KC_WSCH
-KC_WWW_HOME KC_WHOM
-KC_WWW_BACK KC_WBAK
-KC_WWW_FORWARD KC_WFWD
-KC_WWW_STOP KC_WSTP
-KC_WWW_REFRESH KC_WREF
-KC_WWW_FAVORITES KC_WFAV
-/* Mousekey */
-KC_MS_UP KC_MS_U Mouse Cursor Up
-KC_MS_DOWN KC_MS_D Mouse Cursor Down
-KC_MS_LEFT KC_MS_L Mouse Cursor Left
-KC_MS_RIGHT KC_MS_R Mouse Cursor Right
-KC_MS_BTN1 KC_BTN1 Mouse Button 1
-KC_MS_BTN2 KC_BTN2 Mouse Button 2
-KC_MS_BTN3 KC_BTN3 Mouse Button 3
-KC_MS_BTN4 KC_BTN4 Mouse Button 4
-KC_MS_BTN5 KC_BTN5 Mouse Button 5
-KC_MS_WH_UP KC_WH_U Mouse Wheel Up
-KC_MS_WH_DOWN KC_WH_D Mouse Wheel Down
-KC_MS_WH_LEFT KC_WH_L Mouse Wheel Left
-KC_MS_WH_RIGHT KC_WH_R Mouse Wheel Right
-KC_MS_ACCEL0 KC_ACL0 Mouse Acceleration 0
-KC_MS_ACCEL1 KC_ACL1 Mouse Acceleration 1
-KC_MS_ACCEL2 KC_ACL2 Mouse Acceleration 2
-/* Fn key */
-KC_FN0
-KC_FN1
-KC_FN2
-KC_FN3
-KC_FN4
-KC_FN5
-KC_FN6
-KC_FN7
-KC_FN8
-KC_FN9
-KC_FN10
-KC_FN11
-KC_FN12
-KC_FN13
-KC_FN14
-KC_FN15
-KC_FN16
-KC_FN17
-KC_FN18
-KC_FN19
-KC_FN20
-KC_FN21
-KC_FN22
-KC_FN23
-KC_FN24
-KC_FN25
-KC_FN26
-KC_FN27
-KC_FN28
-KC_FN29
-KC_FN30
-KC_FN31
diff --git a/doc/keymap.md b/doc/keymap.md
deleted file mode 100644
index d4a129b208..0000000000
--- a/doc/keymap.md
+++ /dev/null
@@ -1,593 +0,0 @@
-Keymap framework - how to define your keymap
-============================================
-***NOTE: This is not final version, may be inconsistent with source code and changed occasionally for a while.***
-
-## 0. Keymap and layers
-**Keymap** is comprised of multiple layers of key layout, you can define **32 layers** at most.
-**Layer** is an array of **keycodes** to define **actions** for each physical keys.
-respective layers can be validated simultaneously. Layers are indexed with 0 to 31 and higher layer has precedence.
-
- Keymap: 32 Layers Layer: Keycode matrix
- ----------------- ---------------------
- stack of layers array_of_keycode[row][column]
- ____________ precedence _______________________
- / / | high / ESC / F1 / F2 / F3 ....
- 31 /___________// | /-----/-----/-----/-----
- 30 /___________// | / TAB / Q / W / E ....
- 29 /___________/ | /-----/-----/-----/-----
- : _:_:_:_:_:__ | : /LCtrl/ A / S / D ....
- : / : : : : : / | : / : : : :
- 2 /___________// | 2 `--------------------------
- 1 /___________// | 1 `--------------------------
- 0 /___________/ V low 0 `--------------------------
-
-
-
-### 0.1 Keymap status
-Keymap has its state in two parameters:
-**`default_layer`** indicates a base keymap layer(0-31) which is always valid and to be referred, **`keymap_stat`** is 16bit variable which has current on/off status of layers on its each bit.
-
-Keymap layer '0' is usually `default_layer` and which is the only valid layer and other layers is initially off after boot up firmware, though, you can configured them in `config.h`.
-To change `default_layer` will be useful when you switch key layout completely, say you want Colmak instead of Qwerty.
-
- Initial state of Keymap Change base layout
- ----------------------- ------------------
-
- 31 31
- 30 30
- 29 29
- : :
- : : ____________
- 2 ____________ 2 / /
- 1 / / ,->1 /___________/
- ,->0 /___________/ | 0
- | |
- `--- default_layer = 0 `--- default_layer = 1
- layer_state = 0x00000001 layer_state = 0x00000002
-
-On the other hand, you shall change `layer_state` to overlay base layer with some layers for feature such as navigation keys, function key(F1-F12), media keys or special actions.
-
- Overlay feature layer
- --------------------- bit|status
- ____________ ---+------
- 31 / / 31 | 0
- 30 /___________// -----> 30 | 1
- 29 /___________/ -----> 29 | 1
- : : | :
- : ____________ : | :
- 2 / / 2 | 0
- ,->1 /___________/ -----> 1 | 1
- | 0 0 | 0
- | +
- `--- default_layer = 1 |
- layer_state = 0x60000002 <-'
-
-
-
-### 0.2 Layer Precedence and Transparency
-Note that ***higher layer has higher priority on stack of layers***, namely firmware falls down from top layer to bottom to look up keycode. Once it spots keycode other than **`KC_TRNS`**(transparent) on a layer it stops searching and lower layers aren't referred.
-
-You can place `KC_TRNS` on overlay layer changes just part of layout to fall back on lower or base layer.
-Key with `KC_TRANS` doesn't has its own keycode and refers to lower valid layers for keycode, instead.
-See example below.
-
-
-### 0.3 Keymap Example
-Keymap is **`keymaps[]`** C array in fact and you can define layers in it with **`KEYMAP()`** C macro and keycodes. To use complex actions you need to define `Fn` keycode in **`fn_actions[]`** array.
-
-This is a keymap example for [HHKB](http://en.wikipedia.org/wiki/Happy_Hacking_Keyboard) keyboard.
-This example has three layers, 'Qwerty' as base layer, 'Cursor' and 'Mousekey'.
-In this example,
-
- `Fn0` is a **momentary layer switching** key, you can use keys on Cursor layer while holding the key.
-
- `Fn1` is a momentary layer switching key with tapping feature, you can get semicolon **';'** with taping the key and switch layers while holding the key. The word **'tap'** or **'tapping'** mean to press and release a key quickly.
-
- `Fn2` is a **toggle layer switch** key, you can stay switched layer after releasing the key unlike momentary switching.
-
-You can find other keymap definitions in file `keymap.c` located on project directories.
-
- static const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
- /* 0: Qwerty
- * ,-----------------------------------------------------------.
- * |Esc| 1| 2| 3| 4| 5| 6| 7| 8| 9| 0| -| =| \| `|
- * |-----------------------------------------------------------|
- * |Tab | Q| W| E| R| T| Y| U| I| O| P| [| ]|Backs|
- * |-----------------------------------------------------------|
- * |Contro| A| S| D| F| G| H| J| K| L|Fn1| '|Enter |
- * |-----------------------------------------------------------|
- * |Shift | Z| X| C| V| B| N| M| ,| .| /|Shift |Fn0|
- * `-----------------------------------------------------------'
- * |Gui|Alt |Space |Alt |Fn2|
- * `-------------------------------------------'
- */
- KEYMAP(ESC, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, MINS,EQL, BSLS,GRV, \
- TAB, Q, W, E, R, T, Y, U, I, O, P, LBRC,RBRC,BSPC, \
- LCTL,A, S, D, F, G, H, J, K, L, FN1, QUOT,ENT, \
- LSFT,Z, X, C, V, B, N, M, COMM,DOT, SLSH,RSFT,FN0, \
- LGUI,LALT, SPC, RALT,FN2),
- /* 1: Cursor(HHKB mode)
- * ,-----------------------------------------------------------.
- * |Pwr| F1| F2| F3| F4| F5| F6| F7| F8| F9|F10|F11|F12|Ins|Del|
- * |-----------------------------------------------------------|
- * |Caps | | | | | | | |Psc|Slk|Pus|Up | |Backs|
- * |-----------------------------------------------------------|
- * |Contro|VoD|VoU|Mut| | | *| /|Hom|PgU|Lef|Rig|Enter |
- * |-----------------------------------------------------------|
- * |Shift | | | | | | +| -|End|PgD|Dow|Shift | |
- * `-----------------------------------------------------------'
- * |Gui |Alt |Space |Alt |Gui|
- * `--------------------------------------------'
- */
- KEYMAP(PWR, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12, INS, DEL, \
- CAPS,TRNS,TRNS,TRNS,TRNS,TRNS,TRNS,TRNS,PSCR,SLCK,PAUS,UP, TRNS,BSPC, \
- LCTL,VOLD,VOLU,MUTE,TRNS,TRNS,PAST,PSLS,HOME,PGUP,LEFT,RGHT,ENT, \
- LSFT,TRNS,TRNS,TRNS,TRNS,TRNS,PPLS,PMNS,END, PGDN,DOWN,RSFT,TRNS, \
- LGUI,LALT, SPC, RALT,RGUI),
- /* 2: Mousekey
- * ,-----------------------------------------------------------.
- * |Esc| F1| F2| F3| F4| F5| F6| F7| F8| F9|F10|F11|F12|Ins|Del|
- * |-----------------------------------------------------------|
- * |Tab | | | | | |MwL|MwD|MwU|MwR| | | |Backs|
- * |-----------------------------------------------------------|
- * |Contro| | | | | |McL|McD|McU|McR| | |Return |
- * |-----------------------------------------------------------|
- * |Shift | | | | |Mb3|Mb2|Mb1|Mb4|Mb5| |Shift | |
- * `-----------------------------------------------------------'
- * |Gui |Alt |Mb1 |Alt | |
- * `--------------------------------------------'
- * Mc: Mouse Cursor / Mb: Mouse Button / Mw: Mouse Wheel
- */
- KEYMAP(ESC, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12, INS, DEL, \
- TAB, TRNS,TRNS,TRNS,TRNS,TRNS,WH_L,WH_D,WH_U,WH_R,TRNS,TRNS,TRNS,BSPC, \
- LCTL,TRNS,ACL0,ACL1,ACL2,TRNS,MS_L,MS_D,MS_U,MS_R,TRNS,QUOT,ENT, \
- LSFT,TRNS,TRNS,TRNS,TRNS,BTN3,BTN2,BTN1,BTN4,BTN5,SLSH,RSFT,TRNS, \
- LGUI,LALT, BTN1, RALT,TRNS),
- };
-
- static const uint16_t PROGMEM fn_actions[] = {
- ACTION_LAYER_MOMENTARY(1), // FN0
- ACTION_LAYER_TAP_KEY(2, KC_SCLN), // FN1
- ACTION_LAYER_TOGGLE(2), // FN2
- };
-
-
-
-
-## 1. Keycode
-See [`common/keycode.h`](../common/keycode.h) or keycode table below for the detail. Keycode is internal **8bit code** to indicate action performed on key in keymap. Keycode has `KC_` prefixed symbol respectively. Most of keycodes like `KC_A` have simple action registers key to host on press and unregister on release, while some of other keycodes has some special actions like `Fn` keys, Media control keys, System control keys and Mousekeys.
-
- ***In `KEYMAP()` macro you should omit prefix part `KC_` of keycode to keep keymap compact.*** For example, just use `A` instead you place `KC_A` in `KEYMAP()`. Some keycodes has 4-letter **short name** in addition to descriptive name, you'll prefer short one in `KEYMAP()`.
-
-### 1.0 Other key
-- `KC_NO` for no action
-- `KC_TRNS` for layer transparency (See above)
-
-### 1.1 Normal key
-- `KC_A` to `KC_Z`, `KC_1` to `KC_0` for alpha numeric key
-- `KC_MINS`, `KC_EQL`, `KC_GRV`, `KC_RBRC`, `KC_LBRC`, `KC_COMM`, `KC_DOT`, `KC_BSLS`, `KC_SLSH`, `KC_SCLN`, `KC_QUOT`
-- `KC_ESC`, `KC_TAB`, `KC_SPC`, `KC_BSPC`, `KC_ENT`, `KC_DEL`, `KC_INS`
-- `KC_UP`, `KC_DOWN`, `KC_RGHT`, `KC_LEFT`, `KC_PGUP`, `KC_PGDN`, `KC_HOME`, `KC_END`
-- `KC_CAPS`, `KC_NLCK`, `KC_SLCK`, `KC_PSCR`, `KC_PAUS`, `KC_APP`, `KC_F1` to `KC_F24`
-- `KC_P1` to `KC_P0`, `KC_PDOT`, `KC_PCMM`, `KC_PSLS`, `KC_PAST`, `KC_PMNS`, `KC_PPLS`, `KC_PEQL`, `KC_PENT` for keypad.
-
-### 1.2 Modifier
-There are 8 modifiers which has discrimination between left and right.
-
-- `KC_LCTL` and `KC_RCTL` for Control
-- `KC_LSFT` and `KC_RSFT` for Shift
-- `KC_LALT` and `KC_RALT` for Alt
-- `KC_LGUI` and `KC_RGUI` for Windows key or Command key in Mac
-
-### 1.3 Mousekey
-- `KC_MS_U`, `KC_MS_D`, `KC_MS_L`, `KC_MS_R` for mouse cursor
-- `KC_WH_U`, `KC_WH_D`, `KC_WH_L`, `KC_WH_R` for mouse wheel
-- `KC_BTN1`, `KC_BTN2`, `KC_BTN3`, `KC_BTN4`, `KC_BTN5` for mouse buttons
-
-### 1.4 System & Media key
-- `KC_PWR`, `KC_SLEP`, `KC_WAKE` for Power, Sleep, Wake
-- `KC_MUTE`, `KC_VOLU`, `KC_VOLD` for audio volume control
-- `KC_MNXT`, `KC_MPRV`, `KC_MSTP`, `KC_MPLY`, `KC_MSEL` for media control
-- `KC_MAIL`, `KC_CALC`, `KC_MYCM` for application launch
-- `KC_WSCH`, `KC_WHOM`, `KC_WBAK`, `KC_WFWD`, `KC_WSTP`, `KC_WREF`, `KC_WFAV` for web browser operation
-
-### 1.5 Fn key
-`KC_FNnn` are keycodes for `Fn` key which not given any actions at the beginning unlike most of keycodes has its own inborn action. To use these keycodes in `KEYMAP()` you need to assign action you want at first. Action of `Fn` key is defined in `fn_actions[]` and its index of the array is identical with number part of `KC_FNnn`. Thus `KC_FN0` keycode indicates the action defined in first element of the array. ***32 `Fn` keys can be defined at most.***
-
-### 1.6 Keycode Table
- See keycode table in [`doc/keycode.txt`](./keycode.txt) for description of keycodes.
-
- In regard to implementation side most of keycodes are identical with [HID usage][HID_usage](pdf) sent to host for real and some virtual keycodes are defined to support special actions.
-[HID_usage]: http://www.usb.org/developers/hidpage/Hut1_12v2.pdf
-
-
-
-## 2. Action
-See [`common/action_code.h`](../common/action_code.h). Action is a **16bit code** and defines function to perform on events of a key like press, release, holding and tapping.
-
-Most of keys just register 8bit scancode to host, but to support other complex features needs 16bit extended action codes internally. However, using 16bit action codes in keymap results in double size in memory compared to using just keycodes. To avoid this waste 8bit keycodes are used in `KEYMAP()` instead of action codes.
-
-***You can just use keycodes of `Normal key`, `Modifier`, `Mousekey` and `System & Media key` in keymap*** to indicate corresponding actions instead of using action codes. While ***to use other special actions you should use keycode of `Fn` key defined in `fn_actions[]`.***
-
-
-### 2.1 Key Action
-This is a simple action that registers scancodes(HID usage in fact) to host on press event of key and unregister on release.
-
-#### Parameters
-+ **mods**: { ` MOD_LCTL`, ` MOD_LSFT`, ` MOD_LALT`, ` MOD_LGUI`,
- ` MOD_RCTL`, ` MOD_RSFT`, ` MOD_RALT`, ` MOD_RGUI` }
-+ **key**: keycode
-
-
-#### 2.1.1 Normal key and Modifier
-***This action usually won't be used expressly in keymap*** because you can just use keycodes in `KEYMAP()` instead.
-
-You can define these actions on *'A'* key and *'left shift'* modifier with:
-
- ACTION_KEY(KC_A)
- ACTION_KEY(KC_LSFT)
-
-#### 2.1.2 Modified key
-This action is comprised of strokes of modifiers and a key. `Macro` action is needed if you want more complex key strokes.
-
-Say you want to assign a key to `Shift + 1` to get character *'!'* or `Alt + Tab` to switch application windows.
-
- ACTION_MODS_KEY(MOD_LSFT, KC_1)
- ACTION_MODS_KEY(MOD_LALT, KC_TAB)
-
-Or `Alt,Shift + Tab` can be defined. `ACTION_MODS_KEY(mods, key)` requires **4-bit modifier state** and a **keycode** as arguments. See `keycode.h` for `MOD_BIT()` macro.
-
- ACTION_MODS_KEY(MOD_LALT | MOD_LSFT, KC_TAB)
-
-#### 2.1.3 Multiple Modifiers
-Registers multiple modifiers with pressing a key. To specify multiple modifiers use `|`.
-
- ACTION_MODS(MOD_ALT | MOD_LSFT)
-
-#### 2.1.3 Modifier with Tap key([Dual role][dual_role])
-Works as a modifier key while holding, but registers a key on tap(press and release quickly).
-
-
- ACTION_MODS_TAP_KEY(MOD_RCTL, KC_ENT)
-
-
-
-### 2.2 Layer Action
-These actions operate layers of keymap.
-
-#### Parameters
-You can specify a **target layer** of action and **when the action is executed**. Some actions take a **bit value** for bitwise operation.
-
-
-+ **layer**: `0`-`31`
-+ **on**: { `ON_PRESS` | `ON_RELEASE` | `ON_BOTH` }
-+ **bits**: 4-bit value and 1-bit mask bit
-
-
-#### 2.2.1 Default Layer
-Default Layer is a layer which always is valid and referred to when actions is not defined on other overlay layers.
-
-This sets Default Layer to given parameter `layer` and activate it.
-
- ACTION_DEFAULT_LAYER_SET(layer)
-
-
-#### 2.2.2 Momentary
-Turns on `layer` momentarily while holding, in other words it activates when key is pressed and deactivate when released.
-
- ACTION_LAYER_MOMENTARY(layer)
-
-
-#### 2.2.3 Toggle Switch
-Turns on `layer` with first type(press and release) and turns off with next.
-
- ACTION_LAYER_TOGGLE(layer)
-
-
-#### 2.2.4 Momentary Switch with tap key
-Turns on `layer` momentary while holding, but registers key on tap(press and release quickly).
-
- ACTION_LAYER_TAP_KEY(layer, key)
-
-
-#### 2.2.5 Momentary Switch with tap toggle
-Turns on `layer` momentary while holding and toggles it with serial taps.
-
- ACTION_LAYER_TAP_TOGGLE(layer)
-
-
-#### 2.2.6 Invert state of layer
-Inverts current state of `layer`. If the layer is on it becomes off with this action.
-
- ACTION_LAYER_INVERT(layer, on)
-
-
-#### 2.2.7 Turn On layer
-Turns on layer state.
-
- ACTION_LAYER_ON(layer, on)
-
-Turns on layer state on press and turns off on release.
-
- ACTION_LAYER_ON_OFF(layer)
-
-
-#### 2.2.8 Turn Off layer
-Turns off layer state.
-
- ACTION_LAYER_OFF(layer, on)
-
-Turns off layer state on press and activates on release.
-
- ACTION_LAYER_OFF_ON(layer)
-
-
-#### 2.2.9 Set layer
-Turn on layer only.
-`layer_state = (1<<layer) [layer: 0-31]`
-
- ACTION_LAYER_SET(layer, on)
-
-Turns on layer only and clear all layer on release..
-
- ACTION_LAYER_SET_CLEAR(layer)
-
-
-#### 2.2.10 Bitwise operation
-
-**part** indicates which part of 32bit layer state(0-7). **bits** is 5-bit value. **on** indicates when the action is executed.
-
- ACTION_LAYER_BIT_AND(part, bits, on)
- ACTION_LAYER_BIT_OR(part, bits, on)
- ACTION_LAYER_BIT_XOR(part, bits, on)
- ACTION_LAYER_BIT_SET(part, bits, on)
-
-These actions works with parameters as following code.
-
- uint8_t shift = part*4;
- uint32_t mask = (bits&0x10) ? ~(0xf<<shift) : 0;
- uint32_t layer_state = layer_state <bitop> ((bits<<shift)|mask);
-
-
-Default Layer also has bitwise operations, they are executed when key is released.
-
- ACTION_DEFAULT_LAYER_BIT_AND(part, bits)
- ACTION_DEFAULT_LAYER_BIT_OR(part, bits)
- ACTION_DEFAULT_LAYER_BIT_XOR(part, bits)
- ACTION_DEFAULT_LAYER_BIT_SET(part, bits)
-
-
-
-### 2.3 Macro action
-***TBD***
-
-`Macro` action indicates complex key strokes.
-
- MACRO( D(LSHIFT), D(D), END )
- MACRO( U(D), U(LSHIFT), END )
- MACRO( I(255), T(H), T(E), T(L), T(L), W(255), T(O), END )
-
-#### 2.3.1 Macro Commands
-- **I()** change interval of stroke.
-- **D()** press key
-- **U()** release key
-- **T()** type key(press and release)
-- **W()** wait
-- **END** end mark
-
-#### 2.3.2 Examples
-
-***TODO: sample implementation***
-See `keyboard/hhkb/keymap.c` for sample.
-
-
-
-### 2.4 Function action
-***TBD***
-
-There are two type of action, normal `Function` and tappable `Function`.
-These actions call user defined function with `id`, `opt`, and key event information as arguments.
-
-#### 2.4.1 Function
-To define normal `Function` action in keymap use this.
-
- ACTION_FUNCTION(id, opt)
-
-#### 2.4.2 Function with tap
-To define tappable `Function` action in keymap use this.
-
- ACTION_FUNCTION_TAP(id, opt)
-
-#### 2.4.3 Implement user function
-`Function` actions can be defined freely with C by user in callback function:
-
- void keymap_call_function(keyrecord_t *event, uint8_t id, uint8_t opt)
-
-This C function is called every time key is operated, argument `id` selects action to be performed and `opt` can be used for option. Function `id` can be 0-255 and `opt` can be 0-15.
-
- `keyrecord_t` is comprised of key event and tap count. `keyevent_t` indicates which and when key is pressed or released. From `tap_count` you can know tap state, 0 means no tap. These information will be used in user function to decide how action of key is performed.
-
- typedef struct {
- keyevent_t event;
- uint8_t tap_count;
- } keyrecord_t;
-
- typedef struct {
- key_t key;
- bool pressed;
- uint16_t time;
- } keyevent_t;
-
- typedef struct {
- uint8_t col;
- uint8_t row;
- } key_t;
-
-***TODO: sample implementation***
-See `keyboard/hhkb/keymap.c` for sample.
-
-
-
-### 2.5 Backlight Action
-These actions control the backlight.
-
-#### 2.5.1 Change backlight level
-Increase backlight level.
-
- ACTION_BACKLIGHT_INCREASE()
-
-Decrease backlight level.
-
- ACTION_BACKLIGHT_DECREASE()
-
-Step through backlight levels.
-
- ACTION_BACKLIGHT_STEP()
-
-Turn a specific backlight level on or off.
-
- ACTION_BACKLIGHT_LEVEL(1)
-
-#### 2.5.2 Turn on / off backlight
-Turn the backlight on and off without changing level.
-
- ACTION_BACKLIGHT_TOGGLE()
-
-
-
-## 3. Layer switching Example
-There are some ways to switch layer with 'Layer' actions.
-
-### 3.1 Momentary switching
-Momentary switching changes layer only while holding Fn key.
-
-This action makes 'Layer 1' active(valid) on key press event and inactive on release event. Namely you can overlay a layer on lower layers or default layer temporarily with this action.
-
- ACTION_LAYER_MOMENTARY(1)
-
-
-Note that after switching on press the actions on destination layer(Layer 1) are performed.
-***Thus you shall need to place an action to go back on destination layer***, or you will be stuck in destination layer without way to get back. Usually you need to place same action or 'KC_TRNS` on destination layer to get back.
-
-
-### 3.2 Toggle switching
-Toggle switching performed after releasing a key. With this action you can keep staying on the destination layer until you type the key again to return.
-
-This performs toggle switching action of 'Layer 2'.
-
- ACTION_LAYER_TOGGLE(2)
-
-
-
-### 3.3 Momentary switching with Tap key
-These actions switch a layer only while holding a key but register the key on tap. **Tap** means to press and release a key quickly.
-
- ACTION_LAYER_TAP_KEY(2, KC_SCLN)
-
-With this you can place a layer switching action on normal key like ';' without losing its original key register function. This action allows you to have layer switching action without necessity of a dedicated key. It means you can have it even on home row of keyboard.
-
-
-
-### 3.4 Momentary switching with Tap Toggle
-This switches layer only while holding a key but toggle layer with several taps. **Tap** means to press and release key quickly.
-
- ACTION_LAYER_TAP_TOGGLE(1)
-
-Number of taps can be configured with `TAPPING_TOGGLE` in `config.h`, `5` by default.
-
-
-
-### 3.5 Momentary switching with Modifiers
-This registers modifier key(s) simultaneously with layer switching.
-
- ACTION_LAYER_MODS(2, MOD_LSFT | MOD_LALT)
-
-
-
-## 4. Tapping
-Tapping is to press and release a key quickly. Tapping speed is determined with setting of `TAPPING_TERM`, which can be defined in `config.h`, 200ms by default.
-
-### 4.1 Tap Key
-This is a feature to assign normal key action and modifier including layer switching to just same one physical key. This is a kind of [Dual role key][dual_role]. It works as modifier when holding the key but registers normal key when tapping.
-
-Modifier with tap key:
-
- ACTION_MODS_TAP_KEY(MOD_RSFT, KC_GRV)
-
-Layer switching with tap key:
-
- ACTION_LAYER_TAP_KEY(2, KC_SCLN)
-
-[dual_role]: http://en.wikipedia.org/wiki/Modifier_key#Dual-role_keys
-
-
-### 4.2 Tap Toggle
-This is a feature to assign both toggle layer and momentary switch layer action to just same one physical key. It works as momentary layer switch when holding a key but toggle switch with several taps.
-
- ACTION_LAYER_TAP_TOGGLE(1)
-
-
-### 4.3 Oneshot Modifier
-This runs onetime effects which modify only on just one following key. It works as normal modifier key when holding down while oneshot modifier when tapping.
-
- ACTION_MODS_ONESHOT(MOD_LSFT)
-
-Say you want to type 'The', you have to push and hold Shift key before type 't' then release it before type 'h' and 'e', otherwise you'll get 'THe' or 'the' unintentionally. With Oneshot Modifier you can tap Shift then type 't', 'h' and 'e' normally, you don't need to holding Shift key properly here. This mean you can release Shift before 't' is pressed down.
-
-Oneshot effect is cancel unless following key is pressed down within `ONESHOT_TIMEOUT` of `config.h`. No timeout when it is `0` or not defined.
-
-
-### 4.4 Tap Toggle Mods
-Similar to layer tap toggle, this works as a momentary modifier when holding, but toggles on with several taps. A single tap will 'unstick' the modifier again.
-
- ACTION_MODS_TAP_TOGGLE(MOD_LSFT)
-
-
-
-
-## 5. Legacy Keymap
-This was used in prior version and still works due to legacy support code in `common/keymap.c`. Legacy keymap doesn't support many of features that new keymap offers. ***It is not recommended to use Legacy Keymap for new project.***
-
-To enable Legacy Keymap support define this macro in `config.h`.
-
- #define USE_LEGACY_KEYMAP
-
-Legacy Keymap uses two arrays `fn_layer[]` and `fn_keycode[]` to define Fn key. The index of arrays corresponds with postfix number of `Fn` key. Array `fn_layer[]` indicates destination layer to switch and `fn_keycode[]` has keycodes to send when tapping `Fn` key.
-
-In following setting example, `Fn0`, `Fn1` and `Fn2` switch layer to 1, 2 and 2 respectively. `Fn2` registers `Space` key when tapping while `Fn0` and `Fn1` doesn't send any key.
-
- static const uint8_t PROGMEM fn_layer[] = {
- 1, // Fn0
- 2, // Fn1
- 2, // Fn2
- };
-
- static const uint8_t PROGMEM fn_keycode[] = {
- KC_NO, // Fn0
- KC_NO, // Fn1
- KC_SPC, // Fn2
- };
-
-
-## 6. Terminology
-***TBD***
-### keymap
-is comprised of multiple layers.
-### layer
-is matrix of keycodes.
-### key
-is physical button on keyboard or logical switch on software.
-### keycode
-is codes used on firmware.
-### action
-is a function assigned on a key.
-### layer transparency
-Using transparent keycode one layer can refer key definition on other lower layer.
-### layer precedence
-Top layer has higher precedence than lower layers.
-### tapping
-is to press and release a key quickly.
-### Fn key
-is key which executes a special action like layer switching, mouse key, macro or etc.
-### dual role key
-<http://en.wikipedia.org/wiki/Modifier_key#Dual-role_keys>
diff --git a/doc/other_projects.md b/doc/other_projects.md
deleted file mode 100644
index bf980b0a9e..0000000000
--- a/doc/other_projects.md
+++ /dev/null
@@ -1,62 +0,0 @@
-Other Keyboard Firmware Projects
-================================
-## PJRC USB Keyboard/Mouse Example[USB][PJRC][Teensy][AVR]
-- <http://www.pjrc.com/teensy/usb_keyboard.html>
-- <http://www.pjrc.com/teensy/usb_mouse.html>
-
-## kbupgrade[USB][V-USB][AVR]
-- <http://github.com/rhomann/kbupgrade>
-- <http://geekhack.org/showwiki.php?title=Island:8406>
-
-## c64key[USB][V-USB][AVR]
-- <http://symlink.dk/projects/c64key/>
-
-## rump[USB][V-USB][AVR]
-- <http://mg8.org/rump/>
-- <http://github.com/clee/rump>
-
-## dulcimer[USB][V-USB][AVR]
-- <http://www.schatenseite.de/dulcimer.html>
-
-## humblehacker-keyboard[USB][LUFA][AVR][Ergo]
-- <http://github.com/humblehacker>
-- <http://www.humblehacker.com/keyboard/>
-- <http://geekhack.org/showwiki.php?title=Island:6292>
-
-## ps2avr[PS/2][AVR]
-- <http://sourceforge.net/projects/ps2avr/>
-
-## ErgoDox[Ergo][Split][USB][AVR]
-- <http://geekhack.org/index.php?topic=22780.0>
-- <https://github.com/benblazak/ergodox-firmware>
-- <https://github.com/cub-uanic/tmk_keyboard>
-
-## Suka's keyboard collection[Ergo][Split][3DPrinting][USB][AVR]
-- <http://deskthority.net/workshop-f7/my-diy-keyboard-collection-or-how-i-became-a-kb-geek-t2534.html>
-- <https://github.com/frobiac/adnw>
-
-## bpiphany's AVR-Keyboard[PJRC][AVR][USB]
-- <https://github.com/BathroomEpiphanies/AVR-Keyboard>
-- <http://deskthority.net/wiki/HID_Liberation_Device_-_DIY_Instructions>
-- <http://deskthority.net/wiki/Phantom>
-
-## USB-USB keyboard remapper[converter][USB-USB][AVR][Arduino]
-- <http://forum.colemak.com/viewtopic.php?pid=10837>
-- <https://github.com/darkytoothpaste/keymapper>
-
-## USB-USB converter threads[converter][USB-USB]
-- <http://deskthority.net/workshop-f7/is-remapping-a-usb-keyboard-using-teensy-possible-t2841-30.html>
-- <http://geekhack.org/index.php?topic=19458.0>
-
-## kbdbabel.org[converter][vintage][protocol][8051]
-Great resource of vintage keyboard protocol information and code
-
-- <http://www.kbdbabel.org/>
-
-## Haata's kiibohd Controller[converter][vintage][protocol][AVR][PJRC][Cortex]
-A lots of vintage keyboard protocol supports
-
-- <http://gitorious.org/kiibohd-controller>
-
-## Kinesis ergonomic keyboard firmware replacement[V-USB][LUFA][Ergo]
-- <https://github.com/chrisandreae/kinesis-firmware>
diff --git a/keyboard/atomic/Makefile b/keyboard/atomic/Makefile
new file mode 100644
index 0000000000..02153214f3
--- /dev/null
+++ b/keyboard/atomic/Makefile
@@ -0,0 +1,164 @@
+#----------------------------------------------------------------------------
+# On command line:
+#
+# make all = Make software.
+#
+# make clean = Clean out built project files.
+#
+# make coff = Convert ELF to AVR COFF.
+#
+# make extcoff = Convert ELF to AVR Extended COFF.
+#
+# make program = Download the hex file to the device.
+# Please customize your programmer settings(PROGRAM_CMD)
+#
+# make teensy = Download the hex file to the device, using teensy_loader_cli.
+# (must have teensy_loader_cli installed).
+#
+# make dfu = Download the hex file to the device, using dfu-programmer (must
+# have dfu-programmer installed).
+#
+# make flip = Download the hex file to the device, using Atmel FLIP (must
+# have Atmel FLIP installed).
+#
+# make dfu-ee = Download the eeprom file to the device, using dfu-programmer
+# (must have dfu-programmer installed).
+#
+# make flip-ee = Download the eeprom file to the device, using Atmel FLIP
+# (must have Atmel FLIP installed).
+#
+# make debug = Start either simulavr or avarice as specified for debugging,
+# with avr-gdb or avr-insight as the front end for debugging.
+#
+# make filename.s = Just compile filename.c into the assembler code only.
+#
+# make filename.i = Create a preprocessed source file for use in submitting
+# bug reports to the GCC project.
+#
+# To rebuild project do "make clean" then "make all".
+#----------------------------------------------------------------------------
+
+# Target file name (without extension).
+TARGET = atomic_lufa
+
+# Directory common source filess exist
+TOP_DIR = ../..
+
+# Directory keyboard dependent files exist
+TARGET_DIR = .
+
+# # project specific files
+ifdef COMMON
+
+ SRC = keymap_common.c \
+ led.c \
+ backlight.c
+
+ifdef KEYMAP
+ SRC := common_keymaps/keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := common_keymaps/keymap_jack.c $(SRC)
+endif
+
+ifdef MATRIX
+ SRC := matrix_$(MATRIX).c $(SRC)
+else
+ SRC := matrix_pcb.c $(SRC)
+endif
+
+else
+
+SRC = extended_keymap_common.c \
+ analog.c \
+ led.c \
+ backlight.c
+
+ifdef KEYMAP
+ SRC := extended_keymaps/extended_keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := extended_keymaps/extended_keymap_default.c $(SRC)
+endif
+
+ifdef MATRIX
+ SRC := matrix_$(MATRIX).c $(SRC)
+else
+ SRC := matrix_pcb.c $(SRC)
+endif
+
+endif
+
+CONFIG_H = config.h
+
+# MCU name
+#MCU = at90usb1287
+MCU = atmega32u4
+
+# Processor frequency.
+# This will define a symbol, F_CPU, in all source code files equal to the
+# processor frequency in Hz. You can then use this symbol in your source code to
+# calculate timings. Do NOT tack on a 'UL' at the end, this will be done
+# automatically to create a 32-bit value in your source code.
+#
+# This will be an integer division of F_USB below, as it is sourced by
+# F_USB after it has run through any CPU prescalers. Note that this value
+# does not *change* the processor frequency - it should merely be updated to
+# reflect the processor speed set externally so that the code can use accurate
+# software delays.
+F_CPU = 16000000
+
+
+#
+# LUFA specific
+#
+# Target architecture (see library "Board Types" documentation).
+ARCH = AVR8
+
+# Input clock frequency.
+# This will define a symbol, F_USB, in all source code files equal to the
+# input clock frequency (before any prescaling is performed) in Hz. This value may
+# differ from F_CPU if prescaling is used on the latter, and is required as the
+# raw input clock is fed directly to the PLL sections of the AVR for high speed
+# clock generation for the USB and other AVR subsections. Do NOT tack on a 'UL'
+# at the end, this will be done automatically to create a 32-bit value in your
+# source code.
+#
+# If no clock division is performed on the input clock inside the AVR (via the
+# CPU clock adjust registers or the clock division fuses), this will be equal to F_CPU.
+F_USB = $(F_CPU)
+
+# Interrupt driven control endpoint task(+60)
+OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT
+
+
+# Boot Section Size in *bytes*
+# Teensy halfKay 512
+# Teensy++ halfKay 1024
+# Atmel DFU loader 4096
+# LUFA bootloader 4096
+# USBaspLoader 2048
+OPT_DEFS += -DBOOTLOADER_SIZE=4096
+
+
+# Build Options
+# comment out to disable the options.
+#
+BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration(+1000)
+MOUSEKEY_ENABLE = yes # Mouse keys(+4700)
+EXTRAKEY_ENABLE = yes # Audio control and System control(+450)
+CONSOLE_ENABLE = yes # Console for debug(+400)
+COMMAND_ENABLE = yes # Commands for debug and configuration
+# Do not enable SLEEP_LED_ENABLE. it uses the same timer as BACKLIGHT_ENABLE
+#SLEEP_LED_ENABLE = yes # Breathing sleep LED during USB suspend
+NKRO_ENABLE = yes # USB Nkey Rollover - not yet supported in LUFA
+BACKLIGHT_ENABLE = yes # Enable keyboard backlight functionality
+
+# Optimize size but this may cause error "relocation truncated to fit"
+#EXTRALDFLAGS = -Wl,--relax
+
+# Search Path
+VPATH += $(TARGET_DIR)
+VPATH += $(TOP_DIR)
+
+include $(TOP_DIR)/protocol/lufa.mk
+include $(TOP_DIR)/common.mk
+include $(TOP_DIR)/rules.mk
diff --git a/keyboard/atomic/Makefile.pjrc b/keyboard/atomic/Makefile.pjrc
new file mode 100644
index 0000000000..be83ba18b1
--- /dev/null
+++ b/keyboard/atomic/Makefile.pjrc
@@ -0,0 +1,116 @@
+#----------------------------------------------------------------------------
+# On command line:
+#
+# make all = Make software.
+#
+# make clean = Clean out built project files.
+#
+# make coff = Convert ELF to AVR COFF.
+#
+# make extcoff = Convert ELF to AVR Extended COFF.
+#
+# make program = Download the hex file to the device.
+# Please customize your programmer settings(PROGRAM_CMD)
+#
+# make teensy = Download the hex file to the device, using teensy_loader_cli.
+# (must have teensy_loader_cli installed).
+#
+# make dfu = Download the hex file to the device, using dfu-programmer (must
+# have dfu-programmer installed).
+#
+# make flip = Download the hex file to the device, using Atmel FLIP (must
+# have Atmel FLIP installed).
+#
+# make dfu-ee = Download the eeprom file to the device, using dfu-programmer
+# (must have dfu-programmer installed).
+#
+# make flip-ee = Download the eeprom file to the device, using Atmel FLIP
+# (must have Atmel FLIP installed).
+#
+# make debug = Start either simulavr or avarice as specified for debugging,
+# with avr-gdb or avr-insight as the front end for debugging.
+#
+# make filename.s = Just compile filename.c into the assembler code only.
+#
+# make filename.i = Create a preprocessed source file for use in submitting
+# bug reports to the GCC project.
+#
+# To rebuild project do "make clean" then "make all".
+#----------------------------------------------------------------------------
+
+# Target file name (without extension).
+TARGET = gh60_pjrc
+
+# Directory common source filess exist
+TOP_DIR = ../..
+
+# Directory keyboard dependent files exist
+TARGET_DIR = .
+
+# project specific files
+SRC = keymap_common.c \
+ matrix.c \
+ led.c
+
+ifdef KEYMAP
+ SRC := keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := keymap_jack.c $(SRC)
+endif
+
+CONFIG_H = config.h
+
+
+# MCU name, you MUST set this to match the board you are using
+# type "make clean" after changing this, so all files will be rebuilt
+MCU = atmega32u4
+#MCU = at90usb1286
+
+
+# Processor frequency.
+# Normally the first thing your program should do is set the clock prescaler,
+# so your program will run at the correct speed. You should also set this
+# variable to same clock speed. The _delay_ms() macro uses this, and many
+# examples use this variable to calculate timings. Do not add a "UL" here.
+F_CPU = 16000000
+
+
+# Boot Section Size in *bytes*
+# Teensy halfKay 512
+# Atmel DFU loader 4096
+# LUFA bootloader 4096
+OPT_DEFS += -DBOOTLOADER_SIZE=4096
+
+
+# Build Options
+# comment out to disable the options.
+#
+BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration(+1000)
+MOUSEKEY_ENABLE = yes # Mouse keys(+5000)
+EXTRAKEY_ENABLE = yes # Audio control and System control(+600)
+CONSOLE_ENABLE = yes # Console for debug
+COMMAND_ENABLE = yes # Commands for debug and configuration
+SLEEP_LED_ENABLE = yes # Breathing sleep LED during USB suspend
+NKRO_ENABLE = yes # USB Nkey Rollover(+500)
+#PS2_MOUSE_ENABLE = yes # PS/2 mouse(TrackPoint) support
+
+
+# Search Path
+VPATH += $(TARGET_DIR)
+VPATH += $(TOP_DIR)
+
+include $(TOP_DIR)/protocol/pjrc.mk
+include $(TOP_DIR)/common.mk
+include $(TOP_DIR)/rules.mk
+
+plain: OPT_DEFS += -DKEYMAP_PLAIN
+plain: all
+
+poker: OPT_DEFS += -DKEYMAP_POKER
+poker: all
+
+poker_set: OPT_DEFS += -DKEYMAP_POKER_SET
+poker_set: all
+
+poker_bit: OPT_DEFS += -DKEYMAP_POKER_BIT
+poker_bit: all
diff --git a/keyboard/atomic/PCB_GUIDE.md b/keyboard/atomic/PCB_GUIDE.md
new file mode 100644
index 0000000000..833e144b3b
--- /dev/null
+++ b/keyboard/atomic/PCB_GUIDE.md
@@ -0,0 +1,110 @@
+# Planck Firmware Guide
+
+## Setting up the environment
+
+### Windows
+1. Install [MHV AVR Tools][mhv] for AVR GCC compiler and [Cygwin][cygwin](or [MinGW][mingw]) for shell terminal.
+2. Install [DFU-Programmer][dfu-prog] (the -win one).
+3. Start DFU bootloader on the chip first time you will see 'Found New Hardware Wizard' to install driver. If you install device driver properly you can find chip name like 'ATmega32U4' under 'LibUSB-Win32 Devices' tree on 'Device Manager'. If not you will need to update its driver on 'Device Manager' to the `dfu-programmer` driver.
+
+### Mac
+1. Install [CrossPack](https://www.obdev.at/downloads/crosspack/CrossPack-AVR-20131216.dmg).
+2. Install [DFU-Programmer][dfu-prog].
+
+### Linux
+1. Install AVR GCC with your favorite package manager.
+2. Install [DFU-Programmer][dfu-prog].
+
+## Using the built-in functions
+
+Here is a list of some of the functions avaiable from the command line:
+
+* `make clean`: clean the environment - may be required in-between builds
+* `make`: compile the code
+* `make COMMON=true`: compile with the common (non-extended) keymap
+* `make KEYMAP=<keymap>`: compile with the extended keymap file `extended_keymaps_extended_keymap_<keymap>.c`
+* `make COMMON=true KEYMAP=<keymap>`: compile with the common keymap file `common_keymaps/keymap_<keymap>.c`
+* `make dfu`: build and flash the layout to the PCB
+* `make dfu-force`: build and force-flash the layout to the PCB (may be require for first flash)
+
+Generally, the instructions to flash the PCB are as follows:
+
+1. Make changes to the appropriate keymap file
+2. Save the file
+3. `make clean`
+4. Press the reset button on the PCB/press the key with the `RESET` keycode
+5. `make <arguments> dfu` - use the necessary `KEYMAP=<keymap>` and/or `COMMON=true` arguments here.
+
+## Extended keymap
+
+### Keymap
+
+Unlike the common keymap, prefixing the keycodes with `KC_` is required. A full list of the keycodes is available [here](https://github.com/jackhumbert/tmk_keyboard/blob/master/doc/keycode.txt). For the keycodes available only in the extended keymap, see this [header file](https://github.com/jackhumbert/tmk_keyboard/blob/master/keyboard/planck/extended_keymap_common.h).
+
+You can use modifiers with keycodes like this:
+
+ LCTL(KC_C)
+
+Which will generate Ctrl+c. These are daisy-chainable, meaning you can do things like:
+
+ LCTL(LALT(KC_C))
+
+That will generate Ctrl+Alt+c. The entire list of these functions is here:
+
+* `LCTL()`: Left control
+* `LSFT()` / `S()`: Left shift
+* `LALT()`: Left alt/opt
+* `LGUI()`: Left win/cmd
+* `RCTL()`: Right control
+* `RSFT()`: Right shift
+* `RALT()`: Right alt/opt
+* `RGUI()`: Right win/cmd
+
+`S(KC_1)`-like entries are useful in writing keymaps for the Planck.
+
+### Other keycodes
+
+A number of other keycodes have been added that you may find useful:
+
+* `CM_<key>`: the Colemak equivalent of a key (in place of `KC_<key>`), when using Colemak in software (`CM_O` generates `KC_SCLN`)
+* `RESET`: jump to bootloader for flashing (same as press the reset button)
+* `BL_STEP`: step through the backlight brightnesses
+* `BL_<0-15>`: set backlight brightness to 0-15
+* `BL_DEC`: lower the backlight brightness
+* `BL_INC`: raise the backlight brightness
+* `BL_TOGG`: toggle the backlight on/off
+
+### Function layers
+
+The extended keymap extends the number of function layers from 32 to the near-infinite value of 256. Rather than using `FN<num>` notation (still avaiable, but limited to `FN0`-`FN31`), you can use the `FUNC(<num>)` notation. `F(<num>)` is a shortcut for this.
+
+The function actions are unchanged, and you can see the full list of them [here](https://github.com/jackhumbert/tmk_keyboard/blob/master/common/action_code.h). They are explained in detail [here](https://github.com/jackhumbert/tmk_keyboard/blob/master/doc/keymap.md#2-action).
+
+### Macros
+
+Macros have been setup in the `extended_keymaps/extended_keymaps_default.c` file so that you can use `M(<num>)` to access a macro in the `action_get_macro` section on your keymap. The switch/case structure you see here is required, and is setup for `M(0)` - you'll need to copy and paste the code to look like this (e.g. to support `M(3)`):
+
+ switch(id) {
+ case 0:
+ return MACRODOWN(TYPE(KC_A), END);
+ break;
+ case 1:
+ return MACRODOWN(TYPE(KC_B), END);
+ break;
+ case 2:
+ return MACRODOWN(TYPE(KC_C), END);
+ break;
+ case 3:
+ return MACRODOWN(TYPE(KC_D), END);
+ break;
+ }
+ return MACRO_NONE;
+
+`MACRODOWN()` is a shortcut for `(record->event.pressed ? MACRO(__VA_ARGS__) : MACRO_NONE)` which tells the macro to execute when the key is pressed. Without this, the macro will be executed on both the down and up stroke.
+
+[cygwin]: https://www.cygwin.com/
+[mingw]: http://www.mingw.org/
+[mhv]: https://infernoembedded.com/products/avr-tools
+[winavr]: http://winavr.sourceforge.net/
+[crosspack]: http://www.obdev.at/products/crosspack/index.html
+[dfu-prog]: http://dfu-programmer.sourceforge.net/
diff --git a/keyboard/atomic/README.md b/keyboard/atomic/README.md
new file mode 100644
index 0000000000..3ddaed3a39
--- /dev/null
+++ b/keyboard/atomic/README.md
@@ -0,0 +1,56 @@
+Atomic keyboard firmware
+======================
+DIY/Assembled ortholinear 60% keyboard by [Ortholinear Keyboards](http://ortholinearkeyboards.com).
+
+## Extended Keymap
+If you include extended_keymap_common.h instead of keymap_common.h at the top of your file, you'll have access to a bunch of goodies:t
+
+- Use `LSFT()`, `LCTL()`, et. al. (listed in extended_keymap_common.h) as modifiers for keys (daisy-chain-able)
+- Use `FUNC(1)` instead of `FN1` (etc.) to access the function layers beyond the 32 function layer limit
+- Use `CM_F` instead of `KC_F` to get the ColeMak equivilent for shortcuts (maps backwards)
+- Use `MACRODOWN()` instead of `MACRO()` to easily make a keydown macro (`CM_*` works here too)
+
+### Some notes on usage:
+
+- The `KEYMAP()` macro is unable to be used due to the bitwise modifications that take place - refer to extended_keymap_jack.c to see how to set things up with the `KC_` prefix
+- Keep an eye on the Makefile - this needs to include the correct files to work
+- Don't forget to use `const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {` instead of the 8bit equivilent
+
+## Build
+
+Follow [this guide](http://deskthority.net/workshop-f7/how-to-build-your-very-own-keyboard-firmware-t7177.html) to setup your development environment before anything else. Abbreviated instructions are provide at the [bottom of this document](https://github.com/rswiernik/tmk_keyboard/tree/rswiernik_dev/keyboard/planck#environment-setup)
+
+Download the whole firmware [here](https://github.com/jackhumbert/tmk_keyboard/archive/master.zip) and navigate to the keyboard/planck folder. Once your dev env is setup, you'll be able to type `make` to generate your .hex that you can load with the Teensy app onto your Planck (once you've hit reset/shorted GND & RST).
+
+Depending on which keymap you would like to use, you will have to compile slightly differently.
+
+####Default
+To build with the default keymap, simply move to the tmk\_keyboard/keyboard/planck/ and run `make` as follows:
+```
+$ make
+```
+
+## Keymap
+Several version of keymap are available in advance but you are recommended to define your favorite layout yourself. To define your own keymap create file named `keymap_<name>.c` and see keymap document (you can find in top README.md) and existent keymap files.
+
+####**Extended Keymaps**
+
+To build the firmware binary hex file with an extended keymap just do `make` with `KEYMAP` option like:
+```
+$ make KEYMAP=[common|jack|<name>]
+```
+_The only applicable keymaps will work with this option._ Extended keymaps follow the format **__extended\_keymap\_\<name\>.c__**
+
+####**Common Keymaps**
+
+Building with a common keymap is as simple as adding the COMMON option. Note that only
+```
+$ make KEYMAP=[common|jack|<name>] COMMON=true
+```
+_The only applicable keymaps will work with this option._ Common keymaps follow the format **__keymap\_\<name\>.c__**
+
+## Notable TMK forks (which some of the keymap files are from)
+- [Shane's Fork](https://github.com/shanecelis/tmk_keyboard/tree/master/keyboard/planck)
+- [Pierre's Fork](https://github.com/pcarrier/tmk_keyboard/blob/pcarrier/planck/keyboard/gh60/keymap_planck.c)
+- [Nathan's Fork](https://github.com/nathanrosspowell/tmk_keyboard/tree/planck-jack/keyboard/planck)
+- [Matthew's Fork](https://github.com/pepers/tmk_keyboard/tree/master/keyboard/planck_grid)
diff --git a/keyboard/atomic/__avr_gdbinit b/keyboard/atomic/__avr_gdbinit
new file mode 100644
index 0000000000..afc51e6d19
--- /dev/null
+++ b/keyboard/atomic/__avr_gdbinit
@@ -0,0 +1,6 @@
+define reset
+SIGNAL SIGHUP
+end
+file planck_lufa.elf
+target remote localhost:4242
+break main
diff --git a/keyboard/atomic/analog.c b/keyboard/atomic/analog.c
new file mode 100644
index 0000000000..49b84ee0e8
--- /dev/null
+++ b/keyboard/atomic/analog.c
@@ -0,0 +1,53 @@
+// Simple analog to digitial conversion
+
+#include <avr/io.h>
+#include <avr/pgmspace.h>
+#include <stdint.h>
+#include "analog.h"
+
+
+static uint8_t aref = (1<<REFS0); // default to AREF = Vcc
+
+
+void analogReference(uint8_t mode)
+{
+ aref = mode & 0xC0;
+}
+
+
+// Arduino compatible pin input
+int16_t analogRead(uint8_t pin)
+{
+#if defined(__AVR_ATmega32U4__)
+ static const uint8_t PROGMEM pin_to_mux[] = {
+ 0x00, 0x01, 0x04, 0x05, 0x06, 0x07,
+ 0x25, 0x24, 0x23, 0x22, 0x21, 0x20};
+ if (pin >= 12) return 0;
+ return adc_read(pgm_read_byte(pin_to_mux + pin));
+#elif defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__)
+ if (pin >= 8) return 0;
+ return adc_read(pin);
+#else
+ return 0;
+#endif
+}
+
+// Mux input
+int16_t adc_read(uint8_t mux)
+{
+#if defined(__AVR_AT90USB162__)
+ return 0;
+#else
+ uint8_t low;
+
+ ADCSRA = (1<<ADEN) | ADC_PRESCALER; // enable ADC
+ ADCSRB = (1<<ADHSM) | (mux & 0x20); // high speed mode
+ ADMUX = aref | (mux & 0x1F); // configure mux input
+ ADCSRA = (1<<ADEN) | ADC_PRESCALER | (1<<ADSC); // start the conversion
+ while (ADCSRA & (1<<ADSC)) ; // wait for result
+ low = ADCL; // must read LSB first
+ return (ADCH << 8) | low; // must read MSB only once!
+#endif
+}
+
+
diff --git a/keyboard/atomic/analog.h b/keyboard/atomic/analog.h
new file mode 100644
index 0000000000..9b95a93bef
--- /dev/null
+++ b/keyboard/atomic/analog.h
@@ -0,0 +1,36 @@
+#ifndef _analog_h_included__
+#define _analog_h_included__
+
+#include <stdint.h>
+
+void analogReference(uint8_t mode);
+int16_t analogRead(uint8_t pin);
+int16_t adc_read(uint8_t mux);
+
+#define ADC_REF_POWER (1<<REFS0)
+#define ADC_REF_INTERNAL ((1<<REFS1) | (1<<REFS0))
+#define ADC_REF_EXTERNAL (0)
+
+// These prescaler values are for high speed mode, ADHSM = 1
+#if F_CPU == 16000000L
+#define ADC_PRESCALER ((1<<ADPS2) | (1<<ADPS1))
+#elif F_CPU == 8000000L
+#define ADC_PRESCALER ((1<<ADPS2) | (1<<ADPS0))
+#elif F_CPU == 4000000L
+#define ADC_PRESCALER ((1<<ADPS2))
+#elif F_CPU == 2000000L
+#define ADC_PRESCALER ((1<<ADPS1) | (1<<ADPS0))
+#elif F_CPU == 1000000L
+#define ADC_PRESCALER ((1<<ADPS1))
+#else
+#define ADC_PRESCALER ((1<<ADPS0))
+#endif
+
+// some avr-libc versions do not properly define ADHSM
+#if defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__)
+#if !defined(ADHSM)
+#define ADHSM (7)
+#endif
+#endif
+
+#endif
diff --git a/keyboard/atomic/backlight.c b/keyboard/atomic/backlight.c
new file mode 100644
index 0000000000..06f103b4ac
--- /dev/null
+++ b/keyboard/atomic/backlight.c
@@ -0,0 +1,49 @@
+
+#include <avr/io.h>
+#include "backlight.h"
+
+#define CHANNEL OCR1C
+
+void backlight_init_ports()
+{
+
+ // Setup PB7 as output and output low.
+ DDRB |= (1<<7);
+ PORTB &= ~(1<<7);
+
+ // Use full 16-bit resolution.
+ ICR1 = 0xFFFF;
+
+ // I could write a wall of text here to explain... but TL;DW
+ // Go read the ATmega32u4 datasheet.
+ // And this: http://blog.saikoled.com/post/43165849837/secret-konami-cheat-code-to-high-resolution-pwm-on
+
+ // Pin PB7 = OCR1C (Timer 1, Channel C)
+ // Compare Output Mode = Clear on compare match, Channel C = COM1C1=1 COM1C0=0
+ // (i.e. start high, go low when counter matches.)
+ // WGM Mode 14 (Fast PWM) = WGM13=1 WGM12=1 WGM11=1 WGM10=0
+ // Clock Select = clk/1 (no prescaling) = CS12=0 CS11=0 CS10=1
+
+ TCCR1A = _BV(COM1C1) | _BV(WGM11); // = 0b00001010;
+ TCCR1B = _BV(WGM13) | _BV(WGM12) | _BV(CS10); // = 0b00011001;
+
+ backlight_init();
+}
+
+void backlight_set(uint8_t level)
+{
+ if ( level == 0 )
+ {
+ // Turn off PWM control on PB7, revert to output low.
+ TCCR1A &= ~(_BV(COM1C1));
+ // CHANNEL = level << OFFSET | 0x0FFF;
+ CHANNEL = ((1 << level) - 1);
+ }
+ else
+ {
+ // Turn on PWM control of PB7
+ TCCR1A |= _BV(COM1C1);
+ // CHANNEL = level << OFFSET | 0x0FFF;
+ CHANNEL = ((1 << level) - 1);
+ }
+} \ No newline at end of file
diff --git a/keyboard/atomic/common_keymaps/keymap_brett.c b/keyboard/atomic/common_keymaps/keymap_brett.c
new file mode 100644
index 0000000000..97d832b47a
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_brett.c
@@ -0,0 +1,42 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP(
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ LCTL, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, RSFT,
+ TAB, LGUI, RSFT, LALT, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* RAISE */
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, DEL,
+ TRNS, F1, F2, F3, F4, F5, F6, 4, 5, 6, QUOT, TRNS,
+ TRNS, F7, F8, F9, F10, F11, F12, 1, 2, 3, TRNS, PGUP,
+ MPRV, MNXT, TRNS, MUTE, TRNS, TRNS, FN1, 0, 0, TRNS, PGDN),
+[2] = KEYMAP( /* LOWER */
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MINS,
+ TRNS, TRNS, TRNS, PAUSE, TRNS, TRNS, TRNS, TRNS, LBRC, RBRC, BSLS, EQL,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ MPLY, MSTP, VOLU, VOLD, FN2, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/atomic/common_keymaps/keymap_dotcom.c b/keyboard/atomic/common_keymaps/keymap_dotcom.c
new file mode 100644
index 0000000000..347f6dea91
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_dotcom.c
@@ -0,0 +1,34 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP(
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ FN1, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, LBRC,
+ LCTL, BSLS, QUOT, LALT, FN22, SPC, LEFT, UP, DOWN, RGHT, RBRC),
+[1] = KEYMAP(
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, DEL,
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, TRNS, TRNS, TRNS,
+ TRNS, FN18, FN19, FN22, EQL, MINS, FN20, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, TRNS, VOLD, VOLU, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to Fn overlay
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+};
diff --git a/keyboard/atomic/common_keymaps/keymap_jack.c b/keyboard/atomic/common_keymaps/keymap_jack.c
new file mode 100644
index 0000000000..c74812121f
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_jack.c
@@ -0,0 +1,50 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Jack */
+ TAB, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ ESC, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ RSFT, LCTL, LALT, LGUI, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* Jack colemak */
+ TAB, Q, W, F, P, G, J, L, U, Y, SCLN, BSPC,
+ ESC, A, R, S, T, D, H, N, E, I, O, QUOT,
+ LSFT, Z, X, C, V, B, K, M, COMM, DOT, SLSH, ENT,
+ FN3, LCTL, LALT, LGUI, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[2] = KEYMAP( /* Jack RAISE */
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, BSPC,
+ TRNS, FN3, FN4, PAUSE, TRNS, TRNS, TRNS, MINS, EQL, LBRC, RBRC, BSLS,
+ TRNS, F11, F12, F13, F14, F15, F16, F17, F18, F19, F20, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, MNXT, VOLD, VOLU, MPLY),
+[3] = KEYMAP( /* Jack LOWER */
+ FN22, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, BSPC,
+ TRNS, FN3, FN4, PAUSE, TRNS, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, MNXT, VOLD, VOLU, MPLY),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/atomic/common_keymaps/keymap_joe.c b/keyboard/atomic/common_keymaps/keymap_joe.c
new file mode 100644
index 0000000000..598b0c455c
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_joe.c
@@ -0,0 +1,83 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Joe qwerty */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, MINS,
+ BSPC, A, S, D, F, G, H, J, K, L, SCLN, ENTER,
+ FN7, Z, X, C, V, B, N, M, COMM, DOT, SLSH, QUOT,
+ LCTL, LGUI, LALT, LSFT, FN1, SPC, FN0, LEFT, UP, DOWN, RGHT),
+[1] = KEYMAP( /* Joe colemak */
+ ESC, Q, W, F, P, G, J, L, U, Y, SCLN, MINS,
+ BSPC, A, R, S, T, D, H, N, E, I, O, ENTER,
+ FN7, Z, X, C, V, B, K, M, COMM, DOT, SLSH, QUOT,
+ LCTL, LGUI, LALT, LSFT, FN1, SPC, FN0, LEFT, UP, DOWN, RGHT),
+[2] = KEYMAP( /* Joe UPPER */
+ F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12,
+ DEL, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, MENU, CAPS, INS, PSCR, TRNS, FN5, FN6,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, FN0, FN26, FN27, FN28, FN29),
+[3] = KEYMAP( /* Joe LOWER */
+ GRV, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN8, FN9, FN30,
+ BSPC, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, TRNS,
+ BSLS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, LBRC, RBRC, TRNS, EQL,
+ TRNS, TRNS, TRNS, TRNS, FN1, TRNS, FN2, HOME, PGUP, PGDN, END),
+[4] = KEYMAP( /* Joe LOWER + UPPER */
+ FN3, FN4, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, SLEP,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MUTE, VOLD, VOLU, MPLY),
+};
+
+enum macro_id {
+ M_Q0,
+ M_Q1,
+ M_Q2
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [0] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [1] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(4), // to Fn overlay
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [5] = ACTION_MODS_KEY(MOD_LCTL, KC_PGUP),
+ [6] = ACTION_MODS_KEY(MOD_LCTL, KC_PGDN),
+
+ /* tab on tap, shift on hold */
+ [7] = ACTION_MODS_TAP_KEY(MOD_LSFT, KC_TAB),
+
+ [8] = ACTION_MACRO(M_Q0),
+ [9] = ACTION_MACRO(M_Q1),
+
+ [26] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_LEFT),
+ [27] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_UP),
+ [28] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_DOWN),
+ [29] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_RGHT),
+
+ [30] = ACTION_MACRO(M_Q2),
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ keyevent_t event = record->event;
+ switch (id) {
+ case M_Q0:
+ /* :( | ): */
+ return event.pressed ?
+ MACRO( D(LSFT), T(P), T(9), T(SPC), T(SPC), T(0), T(P), U(LSFT), T(LEFT), T(LEFT), T(LEFT), END ) :
+ MACRO_NONE;
+ case M_Q1:
+ /* (: | :) */
+ return event.pressed ?
+ MACRO( D(LSFT), T(9), T(P), T(SPC), T(SPC), T(P), T(0), U(LSFT), T(LEFT), T(LEFT), T(LEFT), END ) :
+ MACRO_NONE;
+ case M_Q2:
+ /* :) */
+ return event.pressed ?
+ MACRO( D(LSFT), T(P), T(0), U(LSFT), END ) :
+ MACRO_NONE;
+ }
+ return MACRO_NONE;
+}
diff --git a/keyboard/atomic/common_keymaps/keymap_matthew.c b/keyboard/atomic/common_keymaps/keymap_matthew.c
new file mode 100644
index 0000000000..56e7003a97
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_matthew.c
@@ -0,0 +1,70 @@
+// by Matthew Pepers - https://github.com/pepers
+
+/* grid planck layout - modified programmer dvorak
+,-----------------------------------------------------------------------------------------------.
+| pause | @ | | | ^ | | | | | * | # | $ | del |
+| esc | ; : | , < | . > | P | Y | F | G | G | C | R | bkspc |
+| F1 | F2 | F3 | F4 | F5 | F6 | F7 | F8 | F9 | F10 | F11 | F12 |
+|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|
+| & | / | { | ( | [ | = | ! | ] | ) | } | \ | + |
+| ` ~ | A | O | E | U | I | D | H | T | N | S | - _ |
+| % | 7 | 5 | 3 | 1 | 9 | 0 | 2 | 4 | 6 | 8 | ? |
+|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|
+| | | | | | | | | | | | prtsc |
+| tab | ' " | Q | J | K | X | B | M | W | V | Z | retrn |
+| | | | | | | | | | | | insrt |
+|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|
+| | | | | | | | | | | | |
+| lctrl | lgui | lalt | ralt | lower | shift | space | raise | left | down | up | right |
+| | | | | | | | | home | pgdn | pgup | end |
+`-----------------------------------------------------------------------------------------------'
+*/
+
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ /* 0: dvorak */
+ [0] = KEYMAP_GRID( ESC, SCLN, COMM, DOT, P, Y, F, G, C, R, L, BSPC, \
+ GRV, A, O, E, U, I, D, H, T, N, S, MINS, \
+ TAB, QUOT, Q, J, K, X, B, M, W, V, Z, ENT, \
+ LCTL, LGUI, LALT, RALT, FN1, LSFT, SPC, FN2, LEFT, DOWN, UP, RGHT),
+
+ /* 1: lower (FN1) */
+ [1] = KEYMAP_GRID( F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12, \
+ FN17, 7, 5, 3, 1, 9, 0, 2, 4, 6, 8, FN18, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, INS, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, HOME, PGDN, PGUP, END),
+
+ /* 2: raise (FN2) */
+ [2] = KEYMAP_GRID(PAUS, FN19, FN20, FN21, TRNS, TRNS, TRNS, TRNS, FN22, FN23, FN24, DEL, \
+ FN10, SLSH, FN11, FN12, LBRC, EQL, FN13, RBRC, FN14, FN15, BSLS, FN16, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, PSCR, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // lower Fn layer
+ [2] = ACTION_LAYER_MOMENTARY(2), // raise Fn layer
+
+ // lower row1
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_5), // %
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_SLASH), // ?
+
+ // raise row0
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_2), // @
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLASH), // |
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_6), // ^
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_8), // *
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_3), // #
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_4), // $
+
+ // raise row1
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_7), // &
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRACKET), // {
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_9), // (
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_1), // !
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_0), // )
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRACKET), // }
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_EQUAL), // +
+};
diff --git a/keyboard/atomic/common_keymaps/keymap_nathan.c b/keyboard/atomic/common_keymaps/keymap_nathan.c
new file mode 100644
index 0000000000..5a0900b66d
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_nathan.c
@@ -0,0 +1,153 @@
+// Author: Nathan Ross Powell <nathanrospowell@gmail.com>
+// https://github.com/nathanrosspowell/tmk_keyboard/blob/planck-jack/keyboard/planck/keymap_nathan.c
+
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ /* 0: main layer
+ * ,-----------------------------------------------------------------------.
+ * |Tab | q | w | e | r | t | y | u | i | o | p | BS |
+ * |-----------------------------------------------------------------------|
+ * |Ctrl | a | s | d | f | g | h | j | k | l | ; | Ret |
+ * |-----------------------------------------------------------------------|
+ * |Shift| z | x | c | v | b | n | m | [ | ( | { | < |
+ * |-----------------------------------------------------------------------|
+ * |Meta | \ | / | Alt |Lower|Space|Space|Upper|Left |Down | Up |Right|
+ * `-----------------------------------------------------------------------'
+ */
+ [0] = KEYMAP_GRID(
+ TAB, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ LCTL, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ RSFT, Z, X, C, V, B, N, M, LBRC, FN10, FN11, FN12,
+ LGUI, BSLS, SLSH, LALT, FN0, SPC, SPC, FN1, LEFT, DOWN, UP, RGHT),
+
+ /* 1: fn left/lower layer
+ * The top row are Visual Studio combos:
+ * 'Run', 'Breakpoint', 'Step over', 'Step into', 'Set cursor to line'
+ * 2nd row are key combos:
+ * 'ctrl-alt-delete', 'ctrl-shift-escape'
+ * 3rd row are macros keys:
+ * 'P0' - 'P5' execute a script on Windows machines
+ * ,-----------------------------------------------------------------------.
+ * | ESC | F5 | F9 | F10 | F11 |S+F11|CSF10|NLock|Num7 |Num8 |Num9 | Del |
+ * |-----------------------------------------------------------------------|
+ * | |C/A/D|C/S/E| Ins |Print|Pause|SLock|Num0 |Num4 |Num5 |Num6 |Num= |
+ * |-----------------------------------------------------------------------|
+ * | | P0 | P1 | P2 | P3 | P4 | P5 |Num. |Num1 |Num2 |Num3 |Num/ |
+ * |-----------------------------------------------------------------------|
+ * | |User | | | | | | |Home |PgDn |PgUp | End |
+ * `-----------------------------------------------------------------------'
+ */
+ [1] = KEYMAP_GRID(
+ ESC, F5, F9, F10, F11, FN30, FN31, NLCK, P7, P8, P9, DEL,
+ TRNS, FN16, FN17, INS, PSCR, PAUS, SLCK, P0, P4, P5, P6, PEQL,
+ TRNS, FN2, FN3, FN4, FN5, FN6, FN7, PDOT, P1, P2, P3, PSLS,
+ TRNS, FN8, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, HOME, PGDN, PGUP, END ),
+
+ /* 2: fn right/raise layer
+ * ,-----------------------------------------------------------------------.
+ * | F1 | F2 | F3 | F4 |F5 | F6 | F7 | F8 | F9 | F10 | F11 | F12 |
+ * |-----------------------------------------------------------------------|
+ * | | ! | @ | # | $ | % | ^ | & | * | - | + | = |
+ * |-----------------------------------------------------------------------|
+ * | | _ | ' | " | ` | ~ | , | . | ] | ) | } | > |
+ * |-----------------------------------------------------------------------|
+ * | |NextT|PrevT| | | | Esc | |Mute |Vol- |Vol+ | P/P |
+ * `-----------------------------------------------------------------------'
+ */
+ [2] = KEYMAP_GRID(
+ F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12,
+ TRNS, FN18, FN19, FN20, FN21, FN22, FN23, FN24, FN25, MINS, FN26, PAST,
+ TRNS, FN27, QUOT, FN28, GRV, FN29, COMM, DOT, RBRC, FN13, FN14, FN15,
+ TRNS, MNXT, MPRV, TRNS, TRNS, TRNS, ESC, TRNS, MUTE, VOLD, VOLU, MPLY ),
+};
+
+enum macro_id {
+ M_P0,
+ M_P1,
+ M_P2,
+ M_P3,
+ M_P4,
+ M_P5,
+ M_USERNAME
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [0] = ACTION_LAYER_MOMENTARY(1), // left/lower layer
+ [1] = ACTION_LAYER_MOMENTARY(2), // right/raise layer
+ // Program macros
+ [2] = ACTION_MACRO(M_P0),
+ [3] = ACTION_MACRO(M_P1),
+ [4] = ACTION_MACRO(M_P2),
+ [5] = ACTION_MACRO(M_P3),
+ [6] = ACTION_MACRO(M_P4),
+ [7] = ACTION_MACRO(M_P5),
+ [8] = ACTION_MACRO(M_USERNAME),
+ // Braces
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_9), // (
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC), // {
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_COMMA), // <
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_0), // )
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC), // }
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_DOT), // >
+ // Combo
+ [16] = ACTION_MODS_KEY(MOD_LALT | MOD_LCTL, KC_DEL), // Ctrl+Alt+Delete
+ [17] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_ESC), // Ctrl+Shft+Escape
+ // Symbols
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_1), // !
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_2), // @
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_3), // #
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_4), // $
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_5), // %
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_6), // ^
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_7), // &
+ [25] = ACTION_MODS_KEY(MOD_LSFT, KC_8), // *
+ [26] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // +
+ [27] = ACTION_MODS_KEY(MOD_LSFT, KC_MINUS), // _
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_QUOTE), // "
+ [29] = ACTION_MODS_KEY(MOD_LSFT, KC_GRAVE), // ~
+ // Debugging
+ [30] = ACTION_MODS_KEY(MOD_LSFT, KC_F11), // Step into
+ [31] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_F10), // Set cursor to line
+ };
+
+// Run a script and pass a key number to it. This is Windows specific and the script needs to be on your path.
+// *open run dialog* keypress.py [PRG_NUM]
+#define ADD_PYTHON_PROGRAM_ON_WIN( PRG_NUM ) MACRO( D(LGUI), T(R), U(LGUI), W(100), T(K), T(E), T(Y), T(P), T(R), T(E), T(S), T(S), T(DOT), T(P), T(Y), T(SPC), T(PRG_NUM), END )
+// *return*
+#define RUN_PYTHON_PROGRAM_ON_WIN MACRO( T(ENT), END )
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt) {
+ keyevent_t event = record->event;
+ switch (id) {
+ case M_P0:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 0 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P1:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 1 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P2:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 2 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P3:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 3 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P4:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 4 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P5:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 5 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_USERNAME:
+ return event.pressed ?
+ MACRO( T(N), T(A), T(T), T(H), T(A), T(N), T(R), T(O), T(S), T(S), T(P), T(O), T(W), T(E), T(L), T(L), END ) :
+ MACRO_NONE;
+ }
+ return MACRO_NONE;
+}
diff --git a/keyboard/atomic/common_keymaps/keymap_peasant.c b/keyboard/atomic/common_keymaps/keymap_peasant.c
new file mode 100644
index 0000000000..ddacb614e6
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_peasant.c
@@ -0,0 +1,51 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = KEYMAP( /* Native */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, FN2,
+ BSPC, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ TAB, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ DEL, LCTL, NO, LSFT, LALT, SPC, NO, LEFT, DOWN, UP, RGHT),
+ [1] = KEYMAP( /* QWERTY->PHOTOSHOP */
+ DELETE, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, FN1,
+ O, G, S, U, T, FN27, F21, F10, F11, F7, F8, F9,
+ TAB, FN4, FN5, FN6, F1, FN7, F18, F19, F23, F20, F22, FN9,
+ COMM, DOT, FN10, FN11, FN3, SPC, FN12, F2, FN8, F3, F14),
+ [2] = KEYMAP( /* 2: FN3 PHOTOSHOP */
+ ESC, FN25, FN26, NO, NO, NO, NO, NO, NO, NO, NO, NO,
+ NO, NO, NO, NO, NO, NO, NO, NO, NO, FN19, FN20, FN21,
+ C, NO, FN22, FN5, NO, FN23, NO, NO, NO, NO, FN13, NO,
+ FN14, FN15, FN16, FN17, FN3, SPC, FN18, NO, NO, F24, NO),
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_DEFAULT_LAYER_SET(0), // set Qwerty layout
+ [2] = ACTION_DEFAULT_LAYER_SET(1), // set Photoshop presets
+ [3] = ACTION_LAYER_ON_OFF(2), // Photoshop function layer
+
+ [4] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F9), // photo folder AHK
+ [5] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_I), // select inverse
+ [6] = ACTION_MODS_KEY(MOD_LSFT, KC_M), // marquee select
+ [7] = ACTION_MODS_KEY(MOD_LALT, KC_BSPC), // fill
+ [8] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_X), // warp
+ [9] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT | MOD_LSFT, KC_F12), // merge all new layer
+ [10] = ACTION_MODS_KEY(MOD_LCTL, KC_MINS), // zoom out
+ [11] = ACTION_MODS_KEY(MOD_LCTL, KC_H), // RBG sliders
+ [12] = ACTION_MODS_KEY(MOD_LCTL, KC_S), // save
+ [13] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_F5), // layer mask from transparancy
+ [14] = ACTION_MODS_KEY(MOD_LALT, KC_LBRC), // prev layer
+ [15] = ACTION_MODS_KEY(MOD_LALT, KC_RBRC), // next layer
+ [16] = ACTION_MODS_KEY(MOD_LCTL, KC_EQL), // zoom in
+ [17] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_H), // HSV sliders
+ [18] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F11), // save as PNG
+ [19] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F7), // gaussian blur
+ [20] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F8), // motion blur
+ [21] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_X), // liquify filter
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS), // prev layer blending
+ [23] = ACTION_MODS_KEY(MOD_LSFT | MOD_LALT, KC_N), // normal layer blending
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // next layer blending
+ [25] = ACTION_MODS_KEY(MOD_LCTL, KC_Z), // step back
+ [26] = ACTION_MODS_KEY(MOD_LCTL, KC_Y), // step forward
+ [27] = ACTION_MODS_KEY(MOD_LCTL, KC_R), // rasterize
+
+};
diff --git a/keyboard/atomic/common_keymaps/keymap_reed.c b/keyboard/atomic/common_keymaps/keymap_reed.c
new file mode 100644
index 0000000000..1aa24e10de
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_reed.c
@@ -0,0 +1,74 @@
+#include "keymap_common.h"
+
+/*
+ * BUILD:
+ * Simply run the command below in the keyboard/planck directory
+ * to build against this keymap
+ *
+ * make KEYMAP=reed COMMON_KEYMAP=true
+ *
+ *
+ * DETAILS:
+ *
+ * This layout works off of Jack's layout, making some changes that I
+ * feel significantly improve the function of the keyboard. Major changes
+ * include adding a "gaming mode" that will allow users to still access
+ * the number keys 1 through 4 easily for games that require it. Also
+ * included is the ability to use the tap/hold function for easy use of
+ * right shift and thumb shift with their tapped companions.
+ *
+ */
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP_GRID( /* Reed */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, FN5,
+ LCTL, CAPS, LALT, LGUI, FN2, FN7, SPC, FN1, LEFT, DOWN, UP, RGHT),
+
+[1] = KEYMAP_GRID( /* Reed EXTREME GAMING */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, FN5,
+ LCTL, 1, 2, 3, 4, SPC, FN2, FN1, LEFT, DOWN, UP, RGHT),
+
+[2] = KEYMAP_GRID( /* Reed RAISE */
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, BSPC,
+ TRNS, FN3, FN4, PAUSE, TRNS, TRNS, TRNS, MINS, EQL, LBRC, RBRC, BSLS,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, MNXT, VOLD, VOLU, MPLY),
+
+[3] = KEYMAP_GRID( /* Reed LOWER */
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, DEL,
+ TRNS, TRNS, INS, HOME, PGUP, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, TRNS, DEL, END, PGDN, F11, F12, F13, TRNS, VOLD, VOLU, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, TRNS, MPRV, MUTE, MPLY, MNXT),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay - RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay - LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+ // Actions for the tap/hold modifiers listed above
+ [5] = ACTION_MODS_TAP_KEY(MOD_RSFT, KC_ENT),
+ [7] = ACTION_MODS_TAP_KEY(MOD_LSFT, KC_BSPC),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/atomic/common_keymaps/keymap_sean.c b/keyboard/atomic/common_keymaps/keymap_sean.c
new file mode 100644
index 0000000000..4fe07f701a
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_sean.c
@@ -0,0 +1,57 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = KEYMAP( /* Matrix Dvorak */
+ QUOT, COMM, DOT, P, Y, SLSH, EQL, F, G, C, R, L,
+ A, O, E, U, I, ESC, BSPC, D, H, T, N, S,
+ SCLN, Q, J, K, X, TAB, ENT, B, M, W, V, Z,
+ LSFT, LCTL, LALT, LGUI, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+
+ [1] = KEYMAP( /* Matrix Qwerty */
+ Q, W, E, R, T, QUOT, EQL, Y, U, I, O, P,
+ A, S, D, F, G, ESC, BSPC, H, J, K, L, SCLN,
+ Z, X, C, V, B, TAB, ENT, N, M, COMM, DOT, SLSH,
+ LSFT, LCTL, LALT, LGUI, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+
+ [2] = KEYMAP( /* fn1 lower */
+ F1, F2, F3, F4, F5, TRNS, TRNS, F6, F7, F8, F9, F10,
+ 1, 2, 3, 4, 5, F18, DEL, 6, 7, 8, 9, 0,
+ FN3, FN4, TRNS, GRV, MINS, TRNS, TRNS, BSLS, LBRC, RBRC, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN5, HOME, PGDN, PGUP, END),
+
+ [3] = KEYMAP( /* fn2 raise */
+ F1, F2, F3, F4, F5, TRNS, TRNS, F6, F7, F8, F9, F10,
+ F11, F12, F13, F14, F15, F18, DEL, F16, F17, F18, F19, F20,
+ FN3, FN4, TRNS, TRNS, TRNS, TRNS, TRNS, EJCT, PWR, LSFT,PAUSE, RSFT,
+ LEFT, DOWN, UP, RGHT, FN5, TRNS, TRNS, MNXT, VOLD, VOLU, MUTE),
+
+ [4] = KEYMAP( /* lower + raise */
+ LEFT, DOWN, UP, RGHT, TRNS, TRNS, TRNS, TRNS, LEFT, DOWN, UP, RGHT,
+ HOME, PGDN, PGUP, END, TRNS, F18, DEL, TRNS, HOME, PGDN, PGUP, END,
+ FN3, FN4, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, EJCT, PWR, MPLY, RSFT,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MNXT, VOLD, VOLU, MUTE),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay LOWER
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay RAISE
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+ [5] = ACTION_LAYER_MOMENTARY(4), // to Fn overlay LOWER + RAISE
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+};
diff --git a/keyboard/atomic/common_keymaps/keymap_shane.c b/keyboard/atomic/common_keymaps/keymap_shane.c
new file mode 100644
index 0000000000..8d5ad68753
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_shane.c
@@ -0,0 +1,98 @@
+#include "keymap_common.h"
+#include "action_layer.h"
+#include "action.h"
+#include "action_util.h"
+
+/*
+ Shane's Planck Layout
+ http://www.keyboard-layout-editor.com/#/layouts/015d9011102619d7695c86ffe57cf441
+*/
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = KEYMAP_AND_SWAP( /* Base */
+ TAB, Q, W, E, R, T, Y, U, I, O, P, MINS,
+ LCTL, A, S, D, F, G, H, J, K, L, SCLN, BSPC,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, FN5,
+ /*ALPHA*/FN3, /*HYPER*/ /*SUPER*/LGUI, /*META*/LALT, LCTL, FN2, FN6, FN1, LEFT, DOWN, UP, RGHT),
+ [2] = KEYMAP_AND_SWAP( /* More modifiers */
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, RCTL, RALT, RGUI, TRNS),
+ [4] = KEYMAP_AND_SWAP( /* WASD */
+ TRNS, TRNS, UP, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, LEFT, DOWN, RIGHT, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+ [6] = KEYMAP_AND_SWAP( /* Raise/FN1 */
+ FN23, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, EQL,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, ENT,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, BSLS, TRNS,
+ PAUS, TRNS, TRNS, TRNS, TRNS, BSPC, TRNS, MUTE, PGUP, PGDN, MNXT),
+ [8] = KEYMAP_AND_SWAP( /* Lower/FN2 */
+ ESC, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN19, FN20, TRNS,
+ TRNS, TRNS, TRNS, TRNS, CAPS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, QUOT,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN24, FN25, LBRC, RBRC, TRNS, TRNS,
+ FN4, TRNS, TRNS, TRNS, TRNS, ENT, TRNS, MPLY, VOLD, VOLU, MPRV),
+};
+
+enum function_id {
+ SPACE_FN,
+};
+
+void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ switch (id) {
+ case SPACE_FN:
+ if (record->event.pressed) {
+ // Change the keyboard maps.
+ // Whatever even layer's are on, turn on the odd one's too.
+ for (uint8_t i = 0; i < 9; i += 2) {
+ if (layer_state & (1UL << i))
+ layer_on(i + 1);
+ }
+ layer_on(1);
+ } else {
+ // turn off all the even layers.
+ for (uint8_t i = 0; i < 9; i += 2)
+ layer_off(i + 1);
+
+ if (record->tap.count != 0) {
+ // Space was tapped rather than used like a modifier.
+ // So send a space up and down event.
+ add_key(KC_SPC);
+ send_keyboard_report();
+ del_key(KC_SPC);
+ send_keyboard_report();
+ }
+ }
+ break;
+ }
+}
+
+
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(6), // to fist Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(8), // to second Fn overlay
+ [3] = ACTION_LAYER_TOGGLE(2), // toggle more modifiers
+ [4] = ACTION_LAYER_TOGGLE(4), // toggle wasd
+ [5] = ACTION_MODS_TAP_KEY(MOD_RSFT, KC_ENT),
+ [6] = ACTION_FUNCTION_TAP(SPACE_FN),
+
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [25] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [26] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+}; \ No newline at end of file
diff --git a/keyboard/atomic/common_keymaps/keymap_simon.c b/keyboard/atomic/common_keymaps/keymap_simon.c
new file mode 100644
index 0000000000..37951364be
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_simon.c
@@ -0,0 +1,44 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Jack */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, DOT, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SCLN, DEL,
+ LCTL, ENT, LALT, CAPS, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* Jack RAISE */
+ TRNS, F1, F2, F3, F4, NO, FN11, FN9, FN12, NO, FN14, TRNS,
+ TRNS, F5, F6, F7, F8, FN16, SLSH, MINS, EQL, LBRC, FN8, TRNS,
+ TRNS, F9, F10, F11, F12, F15, F16, FN22, SCLN, MINS, QUOT, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+[2] = KEYMAP( /* Jack LOWER */
+ FN22, 1, 2, 3, FN13, FN14, FN15, FN16, FN17, FN18, FN19, BSPC,
+ TRNS, 4, 5, 6, TRNS, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, 7, 8, 9, 0, FN28, FN15, F7, F8, F9, F10, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+
+ [8] = ACTION_MODS_KEY(MOD_LSFT, KC_SLSH),
+ [9] = ACTION_MODS_KEY(MOD_LSFT, KC_QUOT),
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/atomic/common_keymaps/keymap_tim.c b/keyboard/atomic/common_keymaps/keymap_tim.c
new file mode 100644
index 0000000000..7444f3877b
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_tim.c
@@ -0,0 +1,44 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP(
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, RSFT,
+ LCTL, LALT, DEL, LGUI, FN2, SPC, FN1, F2, F5, F9, F12),
+[2] = KEYMAP( /* RAISE */
+ TRNS, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, BSPC,
+ GRV, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MINS, EQL, LBRC, RBRC, BSLS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, QUOT, FN29, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, TRNS, TRNS, TRNS, TRNS),
+[3] = KEYMAP( /* LOWER */
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, BSPC,
+ FN22, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, QUOT, FN29, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+ [29] = ACTION_MODS_KEY(MOD_LSFT, KC_QUOT),
+};
diff --git a/keyboard/atomic/common_keymaps/keymap_wilba.c b/keyboard/atomic/common_keymaps/keymap_wilba.c
new file mode 100644
index 0000000000..9781f8fcd8
--- /dev/null
+++ b/keyboard/atomic/common_keymaps/keymap_wilba.c
@@ -0,0 +1,56 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Wilba */
+ FN27, FN28, FN29, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ LCTL, LGUI, LALT, RSFT, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* Wilba Alternate */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ LCTL, LGUI, LALT, RSFT, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+[2] = KEYMAP( /* Wilba LOWER */
+ TRNS, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, TRNS,
+ TRNS, F11, F12, LBRC, RBRC, FN20, EQL, FN23, FN24, MINS, FN21, TRNS,
+ TRNS, BSLS, GRV, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN1, TRNS, TRNS, MNXT, VOLD, VOLU, MPLY),
+[3] = KEYMAP( /* Wilba RAISE */
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, TRNS,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, TRNS,
+ TRNS, FN25, FN22, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // LOWER
+ [2] = ACTION_LAYER_MOMENTARY(3), // RAISE
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1), // !
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2), // @
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3), // #
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4), // $
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5), // %
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6), // ^
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7), // &
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8), // *
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9), // (
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0), // )
+
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS), // _
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // +
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV), // ~
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC), // {
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC), // }
+ [25] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS), // |
+
+ [26] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+
+ [27] = ACTION_BACKLIGHT_TOGGLE(),
+ [28] = ACTION_BACKLIGHT_INCREASE(),
+ [29] = ACTION_BACKLIGHT_DECREASE()
+
+};
diff --git a/keyboard/atomic/config.h b/keyboard/atomic/config.h
new file mode 100644
index 0000000000..fd286bb992
--- /dev/null
+++ b/keyboard/atomic/config.h
@@ -0,0 +1,74 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef CONFIG_H
+#define CONFIG_H
+
+
+/* USB Device descriptor parameter */
+#define VENDOR_ID 0xFEED
+#define PRODUCT_ID 0x6060
+#define DEVICE_VER 0x0001
+#define MANUFACTURER Ortholinear Keyboards
+#define PRODUCT Atomic
+#define DESCRIPTION A compact ortholinear keyboard
+
+/* key matrix size */
+#define MATRIX_ROWS 5
+#define MATRIX_COLS 15
+
+/* define if matrix has ghost */
+//#define MATRIX_HAS_GHOST
+
+/* number of backlight levels */
+/* NOTE: this is the max value of 0..BACKLIGHT_LEVELS so really 16 levels. */
+#define BACKLIGHT_LEVELS 15
+
+/* Set 0 if debouncing isn't needed */
+#define DEBOUNCE 5
+
+/* Mechanical locking support. Use KC_LCAP, KC_LNUM or KC_LSCR instead in keymap */
+#define LOCKING_SUPPORT_ENABLE
+/* Locking resynchronize hack */
+#define LOCKING_RESYNC_ENABLE
+
+/* key combination for command */
+#define IS_COMMAND() ( \
+ keyboard_report->mods == (MOD_BIT(KC_LSHIFT) | MOD_BIT(KC_RSHIFT)) \
+)
+
+
+
+/*
+ * Feature disable options
+ * These options are also useful to firmware size reduction.
+ */
+
+/* disable debug print */
+//#define NO_DEBUG
+
+/* disable print */
+//#define NO_PRINT
+
+/* disable action features */
+//#define NO_ACTION_LAYER
+//#define NO_ACTION_TAPPING
+//#define NO_ACTION_ONESHOT
+//#define NO_ACTION_MACRO
+//#define NO_ACTION_FUNCTION
+
+#endif
diff --git a/keyboard/atomic/extended_keymap_common.c b/keyboard/atomic/extended_keymap_common.c
new file mode 100644
index 0000000000..841b249431
--- /dev/null
+++ b/keyboard/atomic/extended_keymap_common.c
@@ -0,0 +1,208 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "extended_keymap_common.h"
+#include "report.h"
+#include "keycode.h"
+#include "action_layer.h"
+#include "action.h"
+#include "action_macro.h"
+#include "debug.h"
+#include "backlight.h"
+
+
+static action_t keycode_to_action(uint16_t keycode);
+
+
+/* converts key to action */
+action_t action_for_key(uint8_t layer, keypos_t key)
+{
+ // 16bit keycodes - important
+ uint16_t keycode = keymap_key_to_keycode(layer, key);
+
+ if (keycode >= 0x0100 && keycode < 0x2000) {
+ // Has a modifier
+ action_t action;
+ // Split it up
+ action.code = ACTION_MODS_KEY(keycode >> 8, keycode & 0xFF);
+ return action;
+ } else if (keycode >= 0x2000 && keycode < 0x3000) {
+ // Is a shortcut for function layer, pull last 12bits
+ return keymap_func_to_action(keycode & 0xFFF);
+ } else if (keycode >= 0x3000 && keycode < 0x4000) {
+ action_t action;
+ action.code = ACTION_MACRO(keycode & 0xFF);
+ return action;
+ } else if (keycode >= BL_0 & keycode <= BL_15) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_LEVEL(keycode & 0x000F);
+ return action;
+ } else if (keycode == BL_DEC) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_DECREASE();
+ return action;
+ } else if (keycode == BL_INC) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_INCREASE();
+ return action;
+ } else if (keycode == BL_TOGG) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_TOGGLE();
+ return action;
+ } else if (keycode == BL_STEP) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_STEP();
+ return action;
+ } else if (keycode == RESET) {
+ bootloader_jump();
+ return;
+ }
+
+ switch (keycode) {
+ case KC_FN0 ... KC_FN31:
+ return keymap_fn_to_action(keycode);
+#ifdef BOOTMAGIC_ENABLE
+ case KC_CAPSLOCK:
+ case KC_LOCKING_CAPS:
+ if (keymap_config.swap_control_capslock || keymap_config.capslock_to_control) {
+ return keycode_to_action(KC_LCTL);
+ }
+ return keycode_to_action(keycode);
+ case KC_LCTL:
+ if (keymap_config.swap_control_capslock) {
+ return keycode_to_action(KC_CAPSLOCK);
+ }
+ return keycode_to_action(KC_LCTL);
+ case KC_LALT:
+ if (keymap_config.swap_lalt_lgui) {
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_LGUI);
+ }
+ return keycode_to_action(KC_LALT);
+ case KC_LGUI:
+ if (keymap_config.swap_lalt_lgui) {
+ return keycode_to_action(KC_LALT);
+ }
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_LGUI);
+ case KC_RALT:
+ if (keymap_config.swap_ralt_rgui) {
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_RGUI);
+ }
+ return keycode_to_action(KC_RALT);
+ case KC_RGUI:
+ if (keymap_config.swap_ralt_rgui) {
+ return keycode_to_action(KC_RALT);
+ }
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_RGUI);
+ case KC_GRAVE:
+ if (keymap_config.swap_grave_esc) {
+ return keycode_to_action(KC_ESC);
+ }
+ return keycode_to_action(KC_GRAVE);
+ case KC_ESC:
+ if (keymap_config.swap_grave_esc) {
+ return keycode_to_action(KC_GRAVE);
+ }
+ return keycode_to_action(KC_ESC);
+ case KC_BSLASH:
+ if (keymap_config.swap_backslash_backspace) {
+ return keycode_to_action(KC_BSPACE);
+ }
+ return keycode_to_action(KC_BSLASH);
+ case KC_BSPACE:
+ if (keymap_config.swap_backslash_backspace) {
+ return keycode_to_action(KC_BSLASH);
+ }
+ return keycode_to_action(KC_BSPACE);
+#endif
+ default:
+ return keycode_to_action(keycode);
+ }
+}
+
+
+/* Macro */
+__attribute__ ((weak))
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ return MACRO_NONE;
+}
+
+/* Function */
+__attribute__ ((weak))
+void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+}
+
+/* translates keycode to action */
+static action_t keycode_to_action(uint16_t keycode)
+{
+ action_t action;
+ switch (keycode) {
+ case KC_A ... KC_EXSEL:
+ case KC_LCTRL ... KC_RGUI:
+ action.code = ACTION_KEY(keycode);
+ break;
+ case KC_SYSTEM_POWER ... KC_SYSTEM_WAKE:
+ action.code = ACTION_USAGE_SYSTEM(KEYCODE2SYSTEM(keycode));
+ break;
+ case KC_AUDIO_MUTE ... KC_WWW_FAVORITES:
+ action.code = ACTION_USAGE_CONSUMER(KEYCODE2CONSUMER(keycode));
+ break;
+ case KC_MS_UP ... KC_MS_ACCEL2:
+ action.code = ACTION_MOUSEKEY(keycode);
+ break;
+ case KC_TRNS:
+ action.code = ACTION_TRANSPARENT;
+ break;
+ default:
+ action.code = ACTION_NO;
+ break;
+ }
+ return action;
+}
+
+
+/* translates key to keycode */
+uint16_t keymap_key_to_keycode(uint8_t layer, keypos_t key)
+{
+ // Read entire word (16bits)
+ return pgm_read_word(&keymaps[(layer)][(key.row)][(key.col)]);
+}
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint16_t keycode)
+{
+ return (action_t){ .code = pgm_read_word(&fn_actions[FN_INDEX(keycode)]) };
+}
+
+action_t keymap_func_to_action(uint16_t keycode)
+{
+ // For FUNC without 8bit limit
+ return (action_t){ .code = pgm_read_word(&fn_actions[(int)keycode]) };
+}
diff --git a/keyboard/atomic/extended_keymap_common.h b/keyboard/atomic/extended_keymap_common.h
new file mode 100644
index 0000000000..21d8978b7b
--- /dev/null
+++ b/keyboard/atomic/extended_keymap_common.h
@@ -0,0 +1,177 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef KEYMAP_H
+#define KEYMAP_H
+
+#include <stdint.h>
+#include <stdbool.h>
+#include "action.h"
+#include <avr/pgmspace.h>
+#include "keycode.h"
+#include "keymap.h"
+#include "action_macro.h"
+#include "report.h"
+#include "host.h"
+#include "print.h"
+#include "debug.h"
+
+#ifdef BOOTMAGIC_ENABLE
+/* NOTE: Not portable. Bit field order depends on implementation */
+typedef union {
+ uint16_t raw;
+ struct {
+ bool swap_control_capslock:1;
+ bool capslock_to_control:1;
+ bool swap_lalt_lgui:1;
+ bool swap_ralt_rgui:1;
+ bool no_gui:1;
+ bool swap_grave_esc:1;
+ bool swap_backslash_backspace:1;
+ bool nkro:1;
+ };
+} keymap_config_t;
+keymap_config_t keymap_config;
+#endif
+
+/* translates key to keycode */
+uint16_t keymap_key_to_keycode(uint8_t layer, keypos_t key);
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint16_t keycode);
+
+/* translates Fn keycode to action */
+action_t keymap_func_to_action(uint16_t keycode);
+
+extern const uint16_t keymaps[][MATRIX_ROWS][MATRIX_COLS];
+extern const uint16_t fn_actions[];
+
+// Ability to use mods in layouts
+#define LCTL(kc) kc | 0x0100
+#define LSFT(kc) kc | 0x0200
+#define LALT(kc) kc | 0x0400
+#define LGUI(kc) kc | 0x0800
+#define RCTL(kc) kc | 0x1100
+#define RSFT(kc) kc | 0x1200
+#define RALT(kc) kc | 0x1400
+#define RGUI(kc) kc | 0x1800
+
+// Alias for function layers than expand past FN31
+#define FUNC(kc) kc | 0x2000
+
+// Aliases
+#define S(kc) LSFT(kc)
+#define F(kc) FUNC(kc)
+
+// For software implementation of colemak
+#define CM_Q KC_Q
+#define CM_W KC_W
+#define CM_F KC_E
+#define CM_P KC_R
+#define CM_G KC_T
+#define CM_J KC_Y
+#define CM_L KC_U
+#define CM_U KC_I
+#define CM_Y KC_O
+#define CM_SCLN KC_P
+
+#define CM_A KC_A
+#define CM_R KC_S
+#define CM_S KC_D
+#define CM_T KC_F
+#define CM_D KC_G
+#define CM_H KC_H
+#define CM_N KC_J
+#define CM_E KC_K
+#define CM_I KC_L
+#define CM_O KC_SCLN
+
+#define CM_Z KC_Z
+#define CM_X KC_X
+#define CM_C KC_C
+#define CM_V KC_V
+#define CM_B KC_B
+#define CM_K KC_N
+#define CM_M KC_M
+#define CM_COMM KC_COMM
+#define CM_DOT KC_DOT
+#define CM_SLSH KC_SLSH
+
+// Make it easy to support these in macros
+#define KC_CM_Q CM_Q
+#define KC_CM_W CM_W
+#define KC_CM_F CM_F
+#define KC_CM_P CM_P
+#define KC_CM_G CM_G
+#define KC_CM_J CM_J
+#define KC_CM_L CM_L
+#define KC_CM_U CM_U
+#define KC_CM_Y CM_Y
+#define KC_CM_SCLN CM_SCLN
+
+#define KC_CM_A CM_A
+#define KC_CM_R CM_R
+#define KC_CM_S CM_S
+#define KC_CM_T CM_T
+#define KC_CM_D CM_D
+#define KC_CM_H CM_H
+#define KC_CM_N CM_N
+#define KC_CM_E CM_E
+#define KC_CM_I CM_I
+#define KC_CM_O CM_O
+
+#define KC_CM_Z CM_Z
+#define KC_CM_X CM_X
+#define KC_CM_C CM_C
+#define KC_CM_V CM_V
+#define KC_CM_B CM_B
+#define KC_CM_K CM_K
+#define KC_CM_M CM_M
+#define KC_CM_COMM CM_COMM
+#define KC_CM_DOT CM_DOT
+#define KC_CM_SLSH CM_SLSH
+
+#define M(kc) kc | 0x3000
+
+#define MACRODOWN(...) (record->event.pressed ? MACRO(__VA_ARGS__) : MACRO_NONE)
+
+#define BL_ON 0x4009
+#define BL_OFF 0x4000
+#define BL_0 0x4000
+#define BL_1 0x4001
+#define BL_2 0x4002
+#define BL_3 0x4003
+#define BL_4 0x4004
+#define BL_5 0x4005
+#define BL_6 0x4006
+#define BL_7 0x4007
+#define BL_8 0x4008
+#define BL_9 0x4009
+#define BL_10 0x400A
+#define BL_11 0x400B
+#define BL_12 0x400C
+#define BL_13 0x400D
+#define BL_14 0x400E
+#define BL_15 0x400F
+#define BL_DEC 0x4010
+#define BL_INC 0x4011
+#define BL_TOGG 0x4012
+#define BL_STEP 0x4013
+
+#define RESET 0x5000
+
+#endif
diff --git a/keyboard/atomic/extended_keymaps/extended_keymap_abienz.c b/keyboard/atomic/extended_keymaps/extended_keymap_abienz.c
new file mode 100644
index 0000000000..172009cbcd
--- /dev/null
+++ b/keyboard/atomic/extended_keymaps/extended_keymap_abienz.c
@@ -0,0 +1,36 @@
+#include "extended_keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = { /* Colemak */
+ { KC_ESC, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_MINS, KC_EQL, KC_BSPC, KC_NO },
+ { KC_TAB, CM_Q, CM_W, CM_F, CM_P, CM_G, CM_J, CM_L, CM_U, CM_Y, CM_SCLN, KC_LBRC, KC_RBRC, KC_BSLS, KC_DEL },
+ { KC_BSPC, CM_A, CM_R, CM_S, CM_T, CM_D, CM_H, CM_N, CM_E, CM_I, CM_O, KC_QUOT, KC_ENT, KC_NO, KC_PGUP },
+ { KC_LSFT, CM_Z, CM_X, CM_C, CM_V, CM_B, CM_K, CM_M, CM_COMM, CM_DOT, CM_SLSH, KC_RSFT, KC_NO, KC_UP, KC_PGDN },
+ { KC_LCTL, KC_LGUI, KC_NO, KC_LALT, FUNC(1), KC_SPC, KC_NO, KC_RALT, FUNC(2), KC_RGUI, KC_NO, KC_RCTL, KC_LEFT, KC_DOWN, KC_RGHT },
+ },
+ [1] = { /* function */
+ { KC_GRV, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12, KC_BSPC, KC_NO },
+ { KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS },
+ { KC_TRNS, KC_TRNS, KC_TRNS, KC_SLEP, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS },
+ { KC_TRNS, KC_TRNS, KC_TRNS, KC_CALC, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_VOLU, KC_MPLY },
+ { KC_TRNS, KC_TRNS, KC_NO, KC_TRNS, FUNC(1), KC_TRNS, KC_NO, KC_TRNS, FUNC(2), KC_TRNS, KC_NO, KC_TRNS, KC_MPRV, KC_VOLD, KC_MNXT },
+ }
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1),
+ [2] = ACTION_LAYER_MOMENTARY(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
+
diff --git a/keyboard/atomic/extended_keymaps/extended_keymap_austin.c b/keyboard/atomic/extended_keymaps/extended_keymap_austin.c
new file mode 100644
index 0000000000..35330be747
--- /dev/null
+++ b/keyboard/atomic/extended_keymaps/extended_keymap_austin.c
@@ -0,0 +1,50 @@
+#include "extended_keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {BL_STEP, KC_LGUI, KC_LALT, KC_LCTL, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Colemak */
+ {KC_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN3, KC_LGUI, KC_LALT, KC_LCTL, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F11, KC_F12, KC_F13, KC_F14, KC_F15, KC_F16, KC_F17, KC_F18, KC_F19, KC_F20, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* LOWER */
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), KC_TRNS, KC_TRNS, KC_TRNS, S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), S(KC_BSLS)},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+}
+};
+
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/atomic/extended_keymaps/extended_keymap_charlie.c b/keyboard/atomic/extended_keymaps/extended_keymap_charlie.c
new file mode 100644
index 0000000000..18657c8e41
--- /dev/null
+++ b/keyboard/atomic/extended_keymaps/extended_keymap_charlie.c
@@ -0,0 +1,54 @@
+#include "extended_keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = { /* Native */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, FUNC(2)},
+ {KC_BSPC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_TAB, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_DEL, KC_LCTL, KC_NO, KC_LSFT, KC_LALT, KC_SPC, KC_NO, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+ [1] = { /* QWERTY->PHOTOSHOP */
+ {KC_DELETE, KC_0, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, FUNC(1)},
+ {KC_O, KC_G, KC_S, KC_U, KC_T, FUNC(27), KC_F21, KC_F10, KC_F11, KC_F7, KC_F8, KC_F9},
+ {KC_TAB, FUNC(4), FUNC(5), FUNC(6), KC_F1, FUNC(7), KC_F18, KC_F19, KC_F23, KC_F20, KC_F22, FUNC(9)},
+ {KC_COMM, KC_DOT, KC_R, FUNC(11), FUNC(3), KC_SPC, FUNC(12), KC_F2, FUNC(8), KC_F3, KC_F14}
+ },
+ [2] = { /* 2: FUNC(3 PHOTOSHOP */
+ {KC_ESC, FUNC(25), FUNC(26), KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO},
+ {KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, FUNC(19), FUNC(20), FUNC(21)},
+ {KC_C, KC_NO, FUNC(22), FUNC(5), KC_NO, FUNC(23), KC_NO, KC_NO, KC_NO, KC_NO, FUNC(13), KC_NO},
+ {FUNC(14), FUNC(15), FUNC(16), FUNC(17), FUNC(3), KC_SPC, FUNC(18), KC_NO, KC_NO, KC_F24, KC_NO}
+ }
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_DEFAULT_LAYER_SET(0), // set Qwerty layout
+ [2] = ACTION_DEFAULT_LAYER_SET(1), // set Photoshop presets
+ [3] = ACTION_LAYER_MOMENTARY(2), // Photoshop function layer
+
+ [4] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F9), // photo folder AHK
+ [5] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_I), // select inverse
+ [6] = ACTION_MODS_KEY(MOD_LSFT, KC_M), // marquee select
+ [7] = ACTION_MODS_KEY(MOD_LALT, KC_BSPC), // fill
+ [8] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_X), // warp
+ [9] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT | MOD_LSFT, KC_F12), // merge all new layer
+ [10] = ACTION_MODS_KEY(MOD_LCTL, KC_MINS), // zoom out
+ [11] = ACTION_MODS_KEY(MOD_LCTL, KC_H), // RBG sliders
+ [12] = ACTION_MODS_KEY(MOD_LCTL, KC_S), // save
+ [13] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_F5), // layer mask from transparancy
+ [14] = ACTION_MODS_KEY(MOD_LCTL, KC_F2), // stroke
+ [15] = ACTION_MODS_KEY(MOD_LCTL | MOD_LSFT, KC_F2), // stroke layer
+ [16] = ACTION_MODS_KEY(MOD_LCTL, KC_0), // zoom 0
+ [17] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_H), // HSV sliders
+ [18] = ACTION_MODS_KEY(MOD_LCTL | MOD_LSFT, KC_S), // save as
+ [19] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F7), // gaussian blur
+ [20] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F8), // motion blur
+ [21] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_X), // liquify filter
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS), // prev layer blending
+ [23] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_BSPC), // KC_NOrmal layer blending
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // next layer blending
+ [25] = ACTION_MODS_KEY(MOD_LCTL, KC_Z), // step back
+ [26] = ACTION_MODS_KEY(MOD_LCTL, KC_Y), // step forward
+ [27] = ACTION_MODS_KEY(MOD_LCTL, KC_R), // rasterize
+
+};
diff --git a/keyboard/atomic/extended_keymaps/extended_keymap_daniel.c b/keyboard/atomic/extended_keymaps/extended_keymap_daniel.c
new file mode 100644
index 0000000000..d3565495f5
--- /dev/null
+++ b/keyboard/atomic/extended_keymaps/extended_keymap_daniel.c
@@ -0,0 +1,48 @@
+#include "extended_keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_RSFT},
+ {FUNC(3), KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* RAISE */
+ {KC_GRV, S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_EQL},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_LBRC, KC_RBRC},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, S(KC_MINS), KC_BSLS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[2] = { /* LOWER */
+ {S(KC_GRV), KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, S(KC_EQL)},
+ {KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12},
+ {KC_CAPS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_ENT},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* Qwerty */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_DEL},
+ {KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_RSFT},
+ {KC_TRNS, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+}
+};
+
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(2), // to LOWER
+ [3] = ACTION_LAYER_MOMENTARY(3) // to LOWER
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/atomic/extended_keymaps/extended_keymap_default.c b/keyboard/atomic/extended_keymaps/extended_keymap_default.c
new file mode 100644
index 0000000000..ab08bb6d25
--- /dev/null
+++ b/keyboard/atomic/extended_keymaps/extended_keymap_default.c
@@ -0,0 +1,79 @@
+#include "extended_keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = { /* Qwerty */
+ { KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_MINS, KC_EQL, KC_BSPC, KC_DEL },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_LBRC, KC_RBRC, KC_BSLS, KC_DEL },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+ { KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT, KC_ENT, KC_ENT, KC_PGUP },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_RSFT, KC_RSFT, KC_UP, KC_PGDN },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { BL_STEP, KC_LCTL, KC_LALT, KC_LGUI, KC_LGUI, KC_SPC, KC_SPC, KC_RGUI, KC_RGUI, KC_RALT, KC_RCTL, BL_STEP, KC_LEFT, KC_DOWN, KC_RGHT },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 1.25u ──┬ 1.25u ───┬─── 1.25u ┬─── 1.25u ─┬─ 2u ────────────┬─ 1.25u ──┬─ 1.25u ──┬─── 1.25u ┬──── 1.25u ┐
+// │ X │ X │ X │ X │ X │ X │ X │ X │ X │
+// └──────────┴──────────┴──────────┴───────────┴─────────────────┴──────────┴──────────┴──────────┴───────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+// ┌───────────────────── 6.25u ────────────────────────────┐
+// │ X │
+// └────────────────────────────────────────────────────────┘
+// ┌─────────────────────── 6.25u ──────────────────────────┬─ 1.25u ──┬─ 1.25u ──┬─ 1.25u ──┬─── 1.25u ┬── 1.25u ──┐
+// │ X │ X │ X │ X │ X │ X │
+// └────────────────────────────────────────────────────────┴──────────┴──────────┴──────────┴──────────┴───────────┘
+ }
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/atomic/extended_keymaps/extended_keymap_dzobert.c b/keyboard/atomic/extended_keymaps/extended_keymap_dzobert.c
new file mode 100644
index 0000000000..6b3864b6c6
--- /dev/null
+++ b/keyboard/atomic/extended_keymaps/extended_keymap_dzobert.c
@@ -0,0 +1,49 @@
+#include "extended_keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_TAB},
+ {KC_LCTL, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_BSPC},
+ {KC_LALT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN4, KC_RSFT, KC_LGUI, KC_LSFT, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Colemak */
+ {KC_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_TAB},
+ {KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_BSPC},
+ {KC_LALT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN3, KC_RSFT, KC_LGUI, KC_LSFT, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* RAISE */
+ {KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12},
+ {KC_TRNS, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_DEL},
+ {KC_TRNS, KC_GRV, KC_MINS, KC_EQL, KC_QUOT, S(KC_QUOT), S(KC_LBRC), S(KC_RBRC), KC_LBRC, KC_RBRC, KC_BSLS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_HOME, KC_PGUP, KC_PGDN, KC_END}
+},
+[3] = { /* LOWER */
+ {KC_POWER,KC_PSCR, KC_SLCK, KC_PAUSE, KC_NLCK, KC_EXECUTE, KC_MENU, KC_APP, KC_7, KC_8, KC_9, KC_KP_SLASH},
+ {KC_TRNS, KC_VOLD, KC_VOLU, KC_MUTE, KC_CAPS, KC_CANCEL, KC_UNDO, KC_AGAIN, KC_4, KC_5, KC_6, KC_KP_ASTERISK},
+ {KC_TRNS, KC_INSERT,KC_CUT, KC_COPY, KC_PASTE, KC_BSLS, KC_9, KC_0, KC_1, KC_2, KC_3, KC_KP_MINUS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_0, KC_KP_DOT, KC_KP_ENTER, KC_KP_PLUS}
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+}; \ No newline at end of file
diff --git a/keyboard/atomic/extended_keymaps/extended_keymap_jack.c b/keyboard/atomic/extended_keymaps/extended_keymap_jack.c
new file mode 100644
index 0000000000..8ad61646c7
--- /dev/null
+++ b/keyboard/atomic/extended_keymaps/extended_keymap_jack.c
@@ -0,0 +1,188 @@
+#include "extended_keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = { /* Qwerty */
+ { KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_MINS, KC_EQL, KC_BSPC, KC_DEL },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_LBRC, KC_RBRC, KC_BSLS, KC_DEL },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+ { KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT, KC_ENT, KC_ENT, KC_PGUP },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_RSFT, KC_RSFT, KC_UP, KC_PGDN },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { KC_LCTL, KC_LGUI, KC_LALT, KC_LGUI, KC_LCTL, KC_SPC, KC_SPC, KC_RALT, KC_RGUI, KC_RALT, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 1.25u ──┬ 1.25u ───┬─── 1.25u ┬─── 1.25u ─┬─ 2u ────────────┬─ 1.25u ──┬─ 1.25u ──┬─── 1.25u ┬──── 1.25u ┐
+// │ X │ X │ X │ X │ X │ X │ X │ X │ X │
+// └──────────┴──────────┴──────────┴───────────┴─────────────────┴──────────┴──────────┴──────────┴───────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+// ┌───────────────────── 6.25u ────────────────────────────┐
+// │ X │
+// └────────────────────────────────────────────────────────┘
+// ┌─────────────────────── 6.25u ──────────────────────────┬─ 1.25u ──┬─ 1.25u ──┬─ 1.25u ──┬─── 1.25u ┬── 1.25u ──┐
+// │ X │ X │ X │ X │ X │ X │
+// └────────────────────────────────────────────────────────┴──────────┴──────────┴──────────┴──────────┴───────────┘
+ },
+ [1] = { /* Colemak */
+ { KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_MINS, KC_EQL, KC_BSPC, KC_DEL },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { KC_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_LBRC, KC_RBRC, KC_BSLS, KC_DEL },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+ { KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT, KC_ENT, KC_ENT, KC_PGUP },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_RSFT, KC_RSFT, KC_UP, KC_PGDN },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { KC_LCTL, KC_LGUI, KC_LALT, KC_LGUI, KC_LCTL, KC_SPC, KC_SPC, KC_RALT, KC_RGUI, KC_RALT, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 1.25u ──┬ 1.25u ───┬─── 1.25u ┬─── 1.25u ─┬─ 2u ────────────┬─ 1.25u ──┬─ 1.25u ──┬─── 1.25u ┬──── 1.25u ┐
+// │ X │ X │ X │ X │ X │ X │ X │ X │ X │
+// └──────────┴──────────┴──────────┴───────────┴─────────────────┴──────────┴──────────┴──────────┴───────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+// ┌───────────────────── 6.25u ────────────────────────────┐
+// │ X │
+// └────────────────────────────────────────────────────────┘
+// ┌─────────────────────── 6.25u ──────────────────────────┬─ 1.25u ──┬─ 1.25u ──┬─ 1.25u ──┬─── 1.25u ┬── 1.25u ──┐
+// │ X │ X │ X │ X │ X │ X │
+// └────────────────────────────────────────────────────────┴──────────┴──────────┴──────────┴──────────┴───────────┘
+ },
+
+ [2] = { /* Qwerty */
+ { KC_GRV, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12, KC_BSPC, KC_DEL },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_LBRC, KC_RBRC, KC_BSLS, KC_DEL },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+ { KC_ESC, FUNC(3), FUNC(4), KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT, KC_ENT, KC_ENT, KC_PGUP },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_RSFT, KC_RSFT, KC_UP, KC_PGDN },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+// ┌─ 2u ────────────┐ ┌─ 2u ────────────┐
+// │ X │ │ X │
+// └─────────────────┘ └─────────────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+ { KC_LCTL, KC_LGUI, KC_LALT, KC_LGUI, KC_LCTL, KC_SPC, KC_SPC, KC_RALT, KC_RGUI, KC_RALT, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT },
+// ┌────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┬────────┐
+// │ │ │ │ │ │ │ │ │ │ │ │ │ │ │ │
+// └────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┴────────┘
+// ┌─ 1.25u ──┬ 1.25u ───┬─── 1.25u ┬─── 1.25u ─┬─ 2u ────────────┬─ 1.25u ──┬─ 1.25u ──┬─── 1.25u ┬──── 1.25u ┐
+// │ X │ X │ X │ X │ X │ X │ X │ X │ X │
+// └──────────┴──────────┴──────────┴───────────┴─────────────────┴──────────┴──────────┴──────────┴───────────┘
+// ┌─ 2u ────────────┐
+// │ X │
+// └─────────────────┘
+// ┌───────────────────── 6.25u ────────────────────────────┐
+// │ X │
+// └────────────────────────────────────────────────────────┘
+// ┌─────────────────────── 6.25u ──────────────────────────┬─ 1.25u ──┬─ 1.25u ──┬─ 1.25u ──┬─── 1.25u ┬── 1.25u ──┐
+// │ X │ X │ X │ X │ X │ X │
+// └────────────────────────────────────────────────────────┴──────────┴──────────┴──────────┴──────────┴───────────┘
+ }
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2),
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/atomic/extended_keymaps/extended_keymap_joe.c b/keyboard/atomic/extended_keymaps/extended_keymap_joe.c
new file mode 100644
index 0000000000..9de6cf3964
--- /dev/null
+++ b/keyboard/atomic/extended_keymaps/extended_keymap_joe.c
@@ -0,0 +1,90 @@
+#include "extended_keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = { /* Joe colemak */
+ {FUNC(3), KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_MINS},
+ {KC_BSPC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_ENT },
+ {FUNC(15), KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_QUOT},
+ {KC_LCTL, KC_LGUI, KC_LALT, KC_LSFT, FUNC(1), KC_SPC, KC_SPC, FUNC(2), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ },
+ [1] = { /* Joe soft Colemak */
+ {FUNC(3), CM_Q, CM_W, CM_F, CM_P, CM_G, CM_J, CM_L, CM_U, CM_Y, CM_SCLN, KC_MINS},
+ {KC_BSPC, CM_A, CM_R, CM_S, CM_T, CM_D, CM_H, CM_N, CM_E, CM_I, CM_O, KC_ENT },
+ {FUNC(15), CM_Z, CM_X, CM_C, CM_V, CM_B, CM_K, CM_M, KC_COMM, KC_DOT, KC_SLSH, KC_QUOT},
+ {KC_LCTL, KC_LGUI, KC_LALT, KC_LSFT, FUNC(1), KC_SPC, KC_SPC, FUNC(2), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ },
+ [2] = { /* Joe NUMPAD */
+ {FUNC(3), KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, LSFT(KC_9), LSFT(KC_0), KC_P7, KC_P8, KC_P9, KC_PSLS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, LSFT(KC_5), KC_PEQL, KC_P4, KC_P5, KC_P6, KC_PAST},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_PCMM, KC_P1, KC_P2, KC_P3, KC_PMNS},
+ {KC_LCTL, KC_LGUI, KC_LALT, KC_LSFT, FUNC(1), KC_TRNS, KC_TRNS, FUNC(2), KC_P0, KC_PDOT, KC_PENT, KC_PPLS}
+ },
+ [4] = { /* Joe LOWER fn1 */
+ {KC_GRV, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(28), FUNC(27), FUNC(26), FUNC(25)},
+ {KC_TRNS, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_TRNS },
+ {KC_BSLS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_LBRC, KC_RBRC, KC_EQL },
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_TRNS, KC_TRNS, FUNC(2), KC_HOME, KC_PGDN, KC_PGUP, KC_END }
+ },
+ [5] = { /* Joe UPPER fn2 */
+ {KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12 },
+ {KC_DEL, KC_BTN1, KC_MS_U, KC_BTN2, KC_BTN3, KC_TRNS, KC_TRNS, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT, RESET },
+ {KC_TRNS, KC_MS_L, KC_MS_D, KC_MS_R, KC_BTN4, KC_MENU, KC_CAPS, KC_INS, KC_PSCR, KC_TRNS, LCTL(KC_PGUP), LCTL(KC_PGDN) },
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_TRNS, KC_TRNS, FUNC(2), LCTL(LALT(KC_LEFT)), LCTL(LALT(KC_DOWN)), LCTL(LALT(KC_UP)), LCTL(LALT(KC_RGHT))}
+ },
+ [6] = { /* Joe SPECIAL fn3 */
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, LCTL(LSFT(CM_U)), KC_TRNS, KC_TRNS, KC_SLEP},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, RESET },
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS},
+ {FUNC(6), FUNC(7), FUNC(8), KC_TRNS, FUNC(1), KC_TRNS, KC_TRNS, FUNC(2), KC_MUTE, KC_VOLD, KC_VOLU, KC_MPLY}
+ }
+};
+
+enum macro_id {
+ M_Q0,
+ M_Q1,
+ M_Q2,
+ M_Q3
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(4), // fn1
+ [2] = ACTION_LAYER_MOMENTARY(5), // fn2
+
+ /* ESC on tap, fn3 on hold */
+ [3] = ACTION_LAYER_TAP_KEY(6, KC_ESC),
+
+ /* toggle layers */
+ [6] = ACTION_DEFAULT_LAYER_SET(0),
+ [7] = ACTION_DEFAULT_LAYER_SET(1),
+ [8] = ACTION_DEFAULT_LAYER_SET(2),
+
+ /* tab on tap, shift on hold */
+ [15] = ACTION_MODS_TAP_KEY(MOD_LSFT, KC_TAB),
+
+ /* smiley macros */
+ [25] = ACTION_MACRO(M_Q0),
+ [26] = ACTION_MACRO(M_Q1),
+ [27] = ACTION_MACRO(M_Q2),
+ [28] = ACTION_MACRO(M_Q3),
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ switch (id) {
+ case M_Q0:
+ /* :) */
+ return MACRODOWN( DOWN(KC_LSFT), TYPE(KC_SCLN), TYPE(KC_0), UP(KC_LSFT), END );
+ case M_Q1:
+ /* :( */
+ return MACRODOWN( DOWN(KC_LSFT), TYPE(KC_SCLN), TYPE(KC_9), UP(KC_LSFT), END );
+ case M_Q2:
+ /* (: | :) */
+ return MACRODOWN( DOWN(KC_LSFT), TYPE(KC_9), TYPE(KC_SCLN), TYPE(KC_SPC), TYPE(KC_SPC), TYPE(KC_SCLN), TYPE(KC_0), UP(KC_LSFT), TYPE(KC_LEFT), TYPE(KC_LEFT), TYPE(KC_LEFT), END );
+ case M_Q3:
+ /* :( | ): */
+ return MACRODOWN( DOWN(KC_LSFT), TYPE(KC_SCLN), TYPE(KC_9), TYPE(KC_SPC), TYPE(KC_SPC), TYPE(KC_0), TYPE(KC_SCLN), UP(KC_LSFT), TYPE(KC_LEFT), TYPE(KC_LEFT), TYPE(KC_LEFT), END );
+ default:
+ break;
+ }
+ return MACRO_NONE;
+}
diff --git a/keyboard/atomic/extended_keymaps/extended_keymap_kyle.c b/keyboard/atomic/extended_keymaps/extended_keymap_kyle.c
new file mode 100644
index 0000000000..fc4569c7aa
--- /dev/null
+++ b/keyboard/atomic/extended_keymaps/extended_keymap_kyle.c
@@ -0,0 +1,49 @@
+#include "extended_keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {BL_STEP, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Colemak */
+ {KC_ESC, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_TAB, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN3, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F11, KC_F12, KC_F13, KC_F14, KC_F15, KC_F16, KC_F17, KC_F18, KC_F19, KC_F20, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* LOWER */
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), LSFT(RSFT(KC_D)), KC_TRNS, KC_TRNS, S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), S(KC_BSLS)},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/atomic/extended_keymaps/extended_keymap_numpad.c b/keyboard/atomic/extended_keymaps/extended_keymap_numpad.c
new file mode 100644
index 0000000000..721fd496b0
--- /dev/null
+++ b/keyboard/atomic/extended_keymaps/extended_keymap_numpad.c
@@ -0,0 +1,26 @@
+#include "extended_keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_KP_MINUS, KC_KP_PLUS, KC_KP_PLUS, KC_KP_ENTER, KC_KP_ENTER},
+ {KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_KP_ASTERISK, KC_KP_9, KC_KP_6, KC_KP_3, KC_KP_DOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_KP_SLASH, KC_KP_8, KC_KP_5, KC_KP_2, KC_KP_0},
+ {BL_STEP, KC_LCTL, KC_LALT, KC_LGUI, KC_NO, KC_SPC, KC_SPC, KC_NUMLOCK, KC_KP_7, KC_KP_4, KC_KP_1, KC_KP_0}
+ // Space is repeated to accommadate for both spacebar wiring positions
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+}; \ No newline at end of file
diff --git a/keyboard/atomic/flash-pcb.sh b/keyboard/atomic/flash-pcb.sh
new file mode 100755
index 0000000000..46abc6982a
--- /dev/null
+++ b/keyboard/atomic/flash-pcb.sh
@@ -0,0 +1,3 @@
+dfu-programmer atmega32u4 erase --force
+dfu-programmer atmega32u4 flash atomic_pcb.hex
+dfu-programmer atmega32u4 reset \ No newline at end of file
diff --git a/keyboard/atomic/keymap_common.c b/keyboard/atomic/keymap_common.c
new file mode 100644
index 0000000000..fdb1769e1c
--- /dev/null
+++ b/keyboard/atomic/keymap_common.c
@@ -0,0 +1,30 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+#include "keymap_common.h"
+
+
+/* translates key to keycode */
+uint8_t keymap_key_to_keycode(uint8_t layer, keypos_t key)
+{
+ return pgm_read_byte(&keymaps[(layer)][(key.row)][(key.col)]);
+}
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint8_t keycode)
+{
+ return (action_t){ .code = pgm_read_word(&fn_actions[FN_INDEX(keycode)]) };
+}
diff --git a/keyboard/atomic/keymap_common.h b/keyboard/atomic/keymap_common.h
new file mode 100644
index 0000000000..7c167eb51a
--- /dev/null
+++ b/keyboard/atomic/keymap_common.h
@@ -0,0 +1,130 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+#ifndef KEYMAP_COMMON_H
+#define KEYMAP_COMMON_H
+
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/pgmspace.h>
+#include "keycode.h"
+#include "action.h"
+#include "action_macro.h"
+#include "report.h"
+#include "host.h"
+#include "print.h"
+#include "debug.h"
+#include "keymap.h"
+
+
+extern const uint8_t keymaps[][MATRIX_ROWS][MATRIX_COLS];
+extern const uint16_t fn_actions[];
+
+
+// MIT Layout
+/*
+ * ,-----------------------------------------------------------------------.
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | |
+ * `-----------------------------------------------------------------------'
+ */
+#define KEYMAP( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K35, K37, K38, K39, K3A, K3B \
+) { \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_##K35, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B } \
+}
+
+// Grid Layout
+/*
+ * ,-----------------------------------------------------------------------.
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * `-----------------------------------------------------------------------'
+ */
+#define KEYMAP_GRID( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3B \
+) { \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_##K36, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B } \
+}
+
+#define KEYMAP_REVERSE( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K35, K37, K38, K39, K3A, K3B \
+ ) { \
+ { KC_##K0B, KC_##K0A, KC_##K09, KC_##K08, KC_##K07, KC_##K06, KC_##K05, KC_##K04, KC_##K03, KC_##K02, KC_##K01, KC_##K00 }, \
+ { KC_##K1B, KC_##K1A, KC_##K19, KC_##K18, KC_##K17, KC_##K16, KC_##K15, KC_##K14, KC_##K13, KC_##K12, KC_##K11, KC_##K10 }, \
+ { KC_##K2B, KC_##K2A, KC_##K29, KC_##K28, KC_##K27, KC_##K26, KC_##K25, KC_##K24, KC_##K23, KC_##K22, KC_##K21, KC_##K20 }, \
+ { KC_##K3B, KC_##K3A, KC_##K39, KC_##K38, KC_##K37, KC_##K35, KC_##K35, KC_##K34, KC_##K33, KC_##K32, KC_##K31, KC_##K30 }, \
+ }
+
+#define KEYMAP_AND_REVERSE(args...) KEYMAP(args), KEYMAP_REVERSE(args)
+
+#define KEYMAP_SWAP( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K35, K37, K38, K39, K3A, K3B \
+ ) { \
+ { KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B, KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05 }, \
+ { KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B, KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15 }, \
+ { KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B, KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25 }, \
+ { KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B, KC_##K35, KC_##K35, KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34 }, \
+}
+
+#define KEYMAP_AND_SWAP(args...) KEYMAP(args), KEYMAP_SWAP(args)
+
+// GRD: Grid layout
+
+#define KEYMAP_GRD( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, K0C, K0D, K0E, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, K1C, K1D, K1E, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, K2C, K2D, K2E, \
+ K30, K31, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3B, K3C, K3D, K3E, \
+ K40, K41, K42, K43, K44, K45, K46, K47, K48, K49, K4A, K4B, K4C, K4D, K4E \
+) { \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B, KC_##K0C, KC_##K0D, KC_##K0E }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B, KC_##K1C, KC_##K1D, KC_##K1E }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B, KC_##K2C, KC_##K2D, KC_##K2E }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_##K36, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B, KC_##K3C, KC_##K3D, KC_##K3E }, \
+ { KC_##K40, KC_##K41, KC_##K42, KC_##K43, KC_##K44, KC_##K45, KC_##K46, KC_##K47, KC_##K48, KC_##K49, KC_##K4A, KC_##K4B, KC_##K4C, KC_##K4D, KC_##K4E } \
+}
+
+
+#endif
diff --git a/keyboard/atomic/keymap_grid.c b/keyboard/atomic/keymap_grid.c
new file mode 100644
index 0000000000..9d42272e64
--- /dev/null
+++ b/keyboard/atomic/keymap_grid.c
@@ -0,0 +1,40 @@
+#include "keymap_common.h"
+
+// GRD: Grid layout
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = KEYMAP_GRD(FN29, FN30, FN31, 3, 4, 5, 6, 7, 8, 9, 0, MINS, EQL, BSLS, GRV, \
+ TAB, Q, W, E, R, T, Y, U, I, O, P, LBRC, RBRC, BSPC, DEL, \
+ CAPS, A, S, D, F, G, H, J, K, L, SCLN, QUOT, ENT, ENT, PGUP, \
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, RSFT, RSFT, UP, PGDN, \
+ LCTL, LALT, LGUI, SPC, SPC, SPC, SPC, SPC, SPC, RALT, APP, RCTL, LEFT, DOWN, RGHT), \
+
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [9] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_BACKLIGHT_TOGGLE(),
+ [30] = ACTION_BACKLIGHT_INCREASE(),
+ [31] = ACTION_BACKLIGHT_DECREASE()
+};
diff --git a/keyboard/atomic/led.c b/keyboard/atomic/led.c
new file mode 100644
index 0000000000..2c05746607
--- /dev/null
+++ b/keyboard/atomic/led.c
@@ -0,0 +1,38 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include <avr/io.h>
+#include "stdint.h"
+#include "led.h"
+
+
+void led_set(uint8_t usb_led)
+{
+ // // Using PE6 Caps Lock LED
+ // if (usb_led & (1<<USB_LED_CAPS_LOCK))
+ // {
+ // // Output high.
+ // DDRE |= (1<<6);
+ // PORTE |= (1<<6);
+ // }
+ // else
+ // {
+ // // Output low.
+ // DDRE &= ~(1<<6);
+ // PORTE &= ~(1<<6);
+ // }
+}
diff --git a/keyboard/atomic/matrix.c b/keyboard/atomic/matrix.c
new file mode 100644
index 0000000000..01f66e90fb
--- /dev/null
+++ b/keyboard/atomic/matrix.c
@@ -0,0 +1,227 @@
+/*
+Copyright 2012 Jun Wako
+Generated by planckkeyboard.com (2014 Jack Humbert)
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+/*
+ * scan matrix
+ */
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/io.h>
+#include <util/delay.h>
+#include "print.h"
+#include "debug.h"
+#include "util.h"
+#include "matrix.h"
+
+
+#ifndef DEBOUNCE
+# define DEBOUNCE 10
+#endif
+static uint8_t debouncing = DEBOUNCE;
+
+/* matrix state(1:on, 0:off) */
+static matrix_row_t matrix[MATRIX_ROWS];
+static matrix_row_t matrix_debouncing[MATRIX_ROWS];
+
+static matrix_row_t read_cols(void);
+static void init_cols(void);
+static void unselect_rows(void);
+static void select_row(uint8_t row);
+
+inline
+uint8_t matrix_rows(void)
+{
+ return MATRIX_ROWS;
+}
+
+inline
+uint8_t matrix_cols(void)
+{
+ return MATRIX_COLS;
+}
+
+void matrix_init(void)
+{
+ // To use PORTF disable JTAG with writing JTD bit twice within four cycles.
+ MCUCR |= (1<<JTD);
+ MCUCR |= (1<<JTD);
+
+ backlight_init_ports();
+
+ // Turn status LED on
+ DDRE |= (1<<6);
+ PORTE |= (1<<6);
+
+ // initialize row and col
+ unselect_rows();
+ init_cols();
+
+ // initialize matrix state: all keys off
+ for (uint8_t i=0; i < MATRIX_ROWS; i++) {
+ matrix[i] = 0;
+ matrix_debouncing[i] = 0;
+ }
+}
+
+uint8_t matrix_scan(void)
+{
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ select_row(i);
+ _delay_us(30); // without this wait read unstable value.
+ matrix_row_t cols = read_cols();
+ if (matrix_debouncing[i] != cols) {
+ matrix_debouncing[i] = cols;
+ if (debouncing) {
+ debug("bounce!: "); debug_hex(debouncing); debug("\n");
+ }
+ debouncing = DEBOUNCE;
+ }
+ unselect_rows();
+ }
+
+ if (debouncing) {
+ if (--debouncing) {
+ _delay_ms(1);
+ } else {
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ matrix[i] = matrix_debouncing[i];
+ }
+ }
+ }
+
+ return 1;
+}
+
+bool matrix_is_modified(void)
+{
+ if (debouncing) return false;
+ return true;
+}
+
+inline
+bool matrix_is_on(uint8_t row, uint8_t col)
+{
+ return (matrix[row] & ((matrix_row_t)1<col));
+}
+
+inline
+matrix_row_t matrix_get_row(uint8_t row)
+{
+ return matrix[row];
+}
+
+void matrix_print(void)
+{
+ print("\nr/c 0123456789ABCDEF\n");
+ for (uint8_t row = 0; row < MATRIX_ROWS; row++) {
+ phex(row); print(": ");
+ pbin_reverse16(matrix_get_row(row));
+ print("\n");
+ }
+}
+
+uint8_t matrix_key_count(void)
+{
+ uint8_t count = 0;
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ count += bitpop16(matrix[i]);
+ }
+ return count;
+}
+
+//
+// Atomic PCB Rev 0 Pin Assignments
+//
+// Column: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14
+// Pin: F1, F0, B0, C7, F4, F5, F6, F7, D4, D6, B4, D7, D3, D2, D1
+//
+
+static void init_cols(void)
+{
+ DDRB &= ~(1<<4 | 1<<0);
+ PORTB |= (1<<4 | 1<<0);
+ DDRC &= ~(1<<7);
+ PORTC |= (1<<7);
+ DDRD &= ~(1<<7 | 1<<6 | 1<<4 | 1<<3 | 1<<2 | 1<<1);
+ PORTD |= (1<<7 | 1<<6 | 1<<4 | 1<<3 | 1<<2 | 1<<1);
+ DDRF &= ~(1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+ PORTF |= (1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+}
+
+static matrix_row_t read_cols(void)
+{
+ return (PINF&(1<<1) ? 0 : (1<<0)) |
+ (PINF&(1<<0) ? 0 : (1<<1)) |
+ (PINB&(1<<0) ? 0 : (1<<2)) |
+ (PINC&(1<<7) ? 0 : (1<<3)) |
+ (PINF&(1<<4) ? 0 : (1<<4)) |
+ (PINF&(1<<5) ? 0 : (1<<5)) |
+ (PINF&(1<<6) ? 0 : (1<<6)) |
+ (PINF&(1<<7) ? 0 : (1<<7)) |
+ (PIND&(1<<4) ? 0 : (1<<8)) |
+ (PIND&(1<<6) ? 0 : (1<<9)) |
+ (PINB&(1<<4) ? 0 : (1<<10)) |
+ (PIND&(1<<7) ? 0 : (1<<11)) |
+ (PIND&(1<<3) ? 0 : (1<<12)) |
+ (PIND&(1<<2) ? 0 : (1<<13)) |
+ (PIND&(1<<1) ? 0 : (1<<14));
+}
+
+
+//
+// Atomic PCB Rev 0 Pin Assignments
+//
+// Row: 0, 1, 2, 3, 4
+// Pin: D0, D5, B5, B6, C6
+//
+
+static void unselect_rows(void)
+{
+ DDRB &= ~(1<<5 | 1<<6);
+ PORTB |= (1<<5 | 1<<6);
+ DDRD &= ~(1<<0 | 1<<5);
+ PORTD |= (1<<0 | 1<<5);
+ DDRC &= ~(1<<6);
+ PORTC |= (1<<6);
+}
+
+static void select_row(uint8_t row)
+{
+ switch (row) {
+ case 0:
+ DDRD |= (1<<0);
+ PORTD &= ~(1<<0);
+ break;
+ case 1:
+ DDRD |= (1<<5);
+ PORTD &= ~(1<<5);
+ break;
+ case 2:
+ DDRB |= (1<<5);
+ PORTB &= ~(1<<5);
+ break;
+ case 3:
+ DDRB |= (1<<6);
+ PORTB &= ~(1<<6);
+ break;
+ case 4:
+ DDRC |= (1<<6);
+ PORTC &= ~(1<<6);
+ break;
+ }
+}
diff --git a/keyboard/atomic/matrix_center.c b/keyboard/atomic/matrix_center.c
new file mode 100644
index 0000000000..7047f018b6
--- /dev/null
+++ b/keyboard/atomic/matrix_center.c
@@ -0,0 +1,269 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+/*
+ * scan matrix
+ */
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/io.h>
+#include <util/delay.h>
+#include "action_layer.h"
+#include "print.h"
+#include "debug.h"
+#include "util.h"
+#include "matrix.h"
+#include "analog.h"
+
+
+#ifndef DEBOUNCE
+# define DEBOUNCE 10
+#endif
+static uint8_t debouncing = DEBOUNCE;
+
+/* matrix state(1:on, 0:off) */
+static matrix_row_t matrix[MATRIX_ROWS];
+static matrix_row_t matrix_debouncing[MATRIX_ROWS];
+
+static matrix_row_t read_cols(void);
+static void init_cols(void);
+static void init_encoder(void);
+static void init_pot(void);
+static void unselect_rows(void);
+static void select_row(uint8_t row);
+int16_t analogRead(uint8_t pin);
+uint8_t state;
+int32_t position;
+int16_t value;
+
+inline
+uint8_t matrix_rows(void)
+{
+ return MATRIX_ROWS;
+}
+
+inline
+uint8_t matrix_cols(void)
+{
+ return MATRIX_COLS;
+}
+
+void matrix_init(void)
+{
+ // initialize row and col
+ unselect_rows();
+ init_cols();
+ init_encoder();
+ init_pot();
+
+ // initialize matrix state: all keys off
+ for (uint8_t i=0; i < MATRIX_ROWS; i++) {
+ matrix[i] = 0;
+ matrix_debouncing[i] = 0;
+ }
+}
+
+static void init_encoder(void)
+{
+ DDRC &= ~(1<<6 | 1<<7);
+ PORTC |= (1<<6 | 1<<7);
+
+ uint8_t s = 0;
+ _delay_ms(1);
+ if (PINC&(1<<6)) s |= 1;
+ if (PINC&(1<<7)) s |= 2;
+ state = s;
+ position = 0;
+}
+
+void read_encoder(void)
+{
+ uint8_t s = state & 3;
+ if (PINC&(1<<6)) s |= 4;
+ if (PINC&(1<<7)) s |= 8;
+ state = (s >> 2);
+ switch (s) {
+ case 1: case 7: case 8: case 14:
+ position++;
+ break;
+ case 2: case 4: case 11: case 13:
+ position--;
+ break;
+ case 3: case 12:
+ position += 2;
+ break;
+ case 6: case 9:
+ position -= 2;
+ break;
+ }
+}
+
+#define HEX(n) (((n) < 10) ? ((n) + '0') : ((n) + 'A' - 10))
+
+static void init_pot(void)
+{
+ // DDRD &= ~(1<<4);
+ // PORTD |= (1<<4);
+ // DIDR2 = (1<<0);
+}
+
+uint8_t matrix_scan(void)
+{
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ select_row(i);
+ _delay_us(30); // without this wait read unstable value.
+ matrix_row_t cols = read_cols();
+ if (matrix_debouncing[i] != cols) {
+ matrix_debouncing[i] = cols;
+ if (debouncing) {
+ debug("bounce!: "); debug_hex(debouncing); debug("\n");
+ }
+ debouncing = DEBOUNCE;
+ }
+ unselect_rows();
+ }
+
+ if (debouncing) {
+ if (--debouncing) {
+ _delay_ms(1);
+ } else {
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ matrix[i] = matrix_debouncing[i];
+ }
+ }
+ }
+
+ read_encoder();
+ if (position >= 2) {
+ register_code(KC_AUDIO_VOL_UP);
+ unregister_code(KC_AUDIO_VOL_UP);
+ position = 0;
+ } else if (position <= -2) {
+ register_code(KC_AUDIO_VOL_DOWN);
+ unregister_code(KC_AUDIO_VOL_DOWN);
+ position = 0;
+ }
+
+ uint16_t val = analogRead(11);
+
+ debug("analogRead: "); debug_hex(val); debug("\n");
+
+ return 1;
+}
+
+bool matrix_is_modified(void)
+{
+ if (debouncing) return false;
+ return true;
+}
+
+inline
+bool matrix_is_on(uint8_t row, uint8_t col)
+{
+ return (matrix[row] & ((matrix_row_t)1<<col));
+}
+
+inline
+matrix_row_t matrix_get_row(uint8_t row)
+{
+ return matrix[row];
+}
+
+void matrix_print(void)
+{
+ print("\nr/c 0123456789ABCDEF\n");
+ for (uint8_t row = 0; row < MATRIX_ROWS; row++) {
+ phex(row); print(": ");
+ pbin_reverse16(matrix_get_row(row));
+ print("\n");
+ }
+}
+
+uint8_t matrix_key_count(void)
+{
+ uint8_t count = 0;
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ count += bitpop16(matrix[i]);
+ }
+ return count;
+}
+
+/* Column pin configuration
+ * col: 0 1 2 3 4 5 6 7 8 9 10 11
+ * pin: F0 F1 F4 F5 F6 F7 B6 B5 B4 D7 D5 D4
+ */
+
+static void init_cols(void)
+{
+ DDRF &= ~(1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+ PORTF |= (1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+ DDRD &= ~(1<<0);
+ PORTD |= (1<<0);
+ DDRB &= ~(1<<0 | 1<<1 | 1<<2 | 1<<3 | 1<<7);
+ PORTB |= (1<<0 | 1<<1 | 1<<2 | 1<<3 | 1<<7);
+}
+
+static matrix_row_t read_cols(void)
+{
+ return (PINB&(1<<0) ? 0 : (1<< 0)) |
+ (PINB&(1<<1) ? 0 : (1<< 1)) |
+ (PINB&(1<<2) ? 0 : (1<< 2)) |
+ (PINB&(1<<3) ? 0 : (1<< 3)) |
+ (PINB&(1<<7) ? 0 : (1<< 4)) |
+ (PIND&(1<<0) ? 0 : (1<< 5)) |
+ (PINF&(1<<7) ? 0 : (1<< 6)) |
+ (PINF&(1<<6) ? 0 : (1<< 7)) |
+ (PINF&(1<<5) ? 0 : (1<< 8)) |
+ (PINF&(1<<4) ? 0 : (1<< 9)) |
+ (PINF&(1<<1) ? 0 : (1<<10)) |
+ (PINF&(1<<0) ? 0 : (1<<11));
+}
+
+/* Row pin configuration
+ * row: 0 1 2 3
+ * pin: B0 B1 B2 B3
+ */
+static void unselect_rows(void)
+{
+ // Hi-Z(DDR:0, PORT:0) to unselect
+ DDRB &= ~0b01110000;
+ PORTB &= ~0b01110000;
+ DDRD &= ~0b10000000;
+ PORTD &= ~0b10000000;
+}
+
+static void select_row(uint8_t row)
+{
+ switch (row) {
+ case 0:
+ DDRB |= (1<<6);
+ PORTB &= ~(1<<6);
+ break;
+ case 1:
+ DDRB |= (1<<5);
+ PORTB &= ~(1<<5);
+ break;
+ case 2:
+ DDRB |= (1<<4);
+ PORTB &= ~(1<<4);
+ break;
+ case 3:
+ DDRD |= (1<<7);
+ PORTD &= ~(1<<7);
+ break;
+ }
+}
diff --git a/keyboard/atomic/matrix_pcb.c b/keyboard/atomic/matrix_pcb.c
new file mode 100644
index 0000000000..47fb459a8b
--- /dev/null
+++ b/keyboard/atomic/matrix_pcb.c
@@ -0,0 +1,231 @@
+/*
+Copyright 2012 Jun Wako
+Generated by planckkeyboard.com (2014 Jack Humbert)
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+/*
+ * scan matrix
+ */
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/io.h>
+#include <util/delay.h>
+#include "print.h"
+#include "debug.h"
+#include "util.h"
+#include "matrix.h"
+#include "backlight.h" // TODO fix this dependency
+
+
+#ifndef DEBOUNCE
+# define DEBOUNCE 10
+#endif
+static uint8_t debouncing = DEBOUNCE;
+
+/* matrix state(1:on, 0:off) */
+static matrix_row_t matrix[MATRIX_ROWS];
+static matrix_row_t matrix_debouncing[MATRIX_ROWS];
+
+static matrix_row_t read_cols(void);
+static void init_cols(void);
+static void unselect_rows(void);
+static void select_row(uint8_t row);
+
+inline
+uint8_t matrix_rows(void)
+{
+ return MATRIX_ROWS;
+}
+
+inline
+uint8_t matrix_cols(void)
+{
+ return MATRIX_COLS;
+}
+
+void matrix_init(void)
+{
+ // To use PORTF disable JTAG with writing JTD bit twice within four cycles.
+ MCUCR |= (1<<JTD);
+ MCUCR |= (1<<JTD);
+
+ backlight_init_ports();
+
+ // Turn status LED on
+ DDRE |= (1<<6);
+ PORTE |= (1<<6);
+
+ // initialize row and col
+ unselect_rows();
+ init_cols();
+
+ // initialize matrix state: all keys off
+ for (uint8_t i=0; i < MATRIX_ROWS; i++) {
+ matrix[i] = 0;
+ matrix_debouncing[i] = 0;
+ }
+}
+
+uint8_t matrix_scan(void)
+{
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ select_row(i);
+ _delay_us(30); // without this wait read unstable value.
+ matrix_row_t cols = read_cols();
+ if (matrix_debouncing[i] != cols) {
+ matrix_debouncing[i] = cols;
+ if (debouncing) {
+ debug("bounce!: "); debug_hex(debouncing); debug("\n");
+ }
+ debouncing = DEBOUNCE;
+ }
+ unselect_rows();
+ }
+
+ if (debouncing) {
+ if (--debouncing) {
+ _delay_ms(1);
+ } else {
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ matrix[i] = matrix_debouncing[i];
+ }
+ }
+ }
+
+ return 1;
+}
+
+bool matrix_is_modified(void)
+{
+ if (debouncing) return false;
+ return true;
+}
+
+inline
+bool matrix_is_on(uint8_t row, uint8_t col)
+{
+ return (matrix[row] & ((matrix_row_t)1<col));
+}
+
+inline
+matrix_row_t matrix_get_row(uint8_t row)
+{
+ return matrix[row];
+}
+
+void matrix_print(void)
+{
+ print("\nr/c 0123456789ABCDEF\n");
+ for (uint8_t row = 0; row < MATRIX_ROWS; row++) {
+ phex(row); print(": ");
+ pbin_reverse16(matrix_get_row(row));
+ print("\n");
+ }
+}
+
+uint8_t matrix_key_count(void)
+{
+ uint8_t count = 0;
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ count += bitpop16(matrix[i]);
+ }
+ return count;
+}
+
+//
+// Atomic PCB Rev 0 Pin Assignments
+//
+// Column: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14
+// Pin: F1, F0, B0, C7, F4, F5, F6, F7, D4, D6, B4, D7, D3, D2, D1
+//
+
+static void init_cols(void)
+{
+ DDRB &= ~(1<<4 | 1<<0);
+ PORTB |= (1<<4 | 1<<0);
+ DDRC &= ~(1<<7);
+ PORTC |= (1<<7);
+ DDRD &= ~(1<<7 | 1<<6 | 1<<4 | 1<<2 | 1<<3 | 1<<1);
+ PORTD |= (1<<7 | 1<<6 | 1<<4 | 1<<2 | 1<<3 | 1<<1);
+ DDRF &= ~(1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+ PORTF |= (1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+
+}
+
+static matrix_row_t read_cols(void)
+{
+ return (PINF&(1<<1) ? 0 : (1<<0)) |
+ (PINF&(1<<0) ? 0 : (1<<1)) |
+ (PINB&(1<<0) ? 0 : (1<<2)) |
+ (PINC&(1<<7) ? 0 : (1<<3)) |
+ (PINF&(1<<4) ? 0 : (1<<4)) |
+ (PINF&(1<<5) ? 0 : (1<<5)) |
+ (PINF&(1<<6) ? 0 : (1<<6)) |
+ (PINF&(1<<7) ? 0 : (1<<7)) |
+ (PIND&(1<<4) ? 0 : (1<<8)) |
+ (PIND&(1<<6) ? 0 : (1<<9)) |
+ (PINB&(1<<4) ? 0 : (1<<10)) |
+ (PIND&(1<<7) ? 0 : (1<<11)) |
+ (PIND&(1<<3) ? 0 : (1<<12)) |
+ (PIND&(1<<2) ? 0 : (1<<13)) |
+ (PIND&(1<<1) ? 0 : (1<<14));
+
+}
+
+static void unselect_rows(void)
+{
+ DDRB &= ~(1<<5 | 1<<6);
+ PORTB |= (1<<5 | 1<<6);
+ DDRD &= ~(1<<0 | 1<<5);
+ PORTD |= (1<<0 | 1<<5);
+ DDRC &= ~(1<<6);
+ PORTC |= (1<<6);
+
+}
+
+//
+// Atomic PCB Rev 0 Pin Assignments
+//
+// Row: 0, 1, 2, 3, 4
+// Pin: D0, D5, B5, B6, C6
+//
+
+static void select_row(uint8_t row)
+{
+ switch (row) {
+ case 0:
+ DDRD |= (1<<0);
+ PORTD &= ~(1<<0);
+ break;
+ case 1:
+ DDRD |= (1<<5);
+ PORTD &= ~(1<<5);
+ break;
+ case 2:
+ DDRB |= (1<<5);
+ PORTB &= ~(1<<5);
+ break;
+ case 3:
+ DDRB |= (1<<6);
+ PORTB &= ~(1<<6);
+ break;
+ case 4:
+ DDRC |= (1<<6);
+ PORTC &= ~(1<<6);
+ break;
+
+ }
+} \ No newline at end of file
diff --git a/keyboard/atomic_old/Makefile b/keyboard/atomic_old/Makefile
new file mode 100644
index 0000000000..c4e0cb45d7
--- /dev/null
+++ b/keyboard/atomic_old/Makefile
@@ -0,0 +1,135 @@
+#----------------------------------------------------------------------------
+# On command line:
+#
+# make all = Make software.
+#
+# make clean = Clean out built project files.
+#
+# make coff = Convert ELF to AVR COFF.
+#
+# make extcoff = Convert ELF to AVR Extended COFF.
+#
+# make program = Download the hex file to the device.
+# Please customize your programmer settings(PROGRAM_CMD)
+#
+# make teensy = Download the hex file to the device, using teensy_loader_cli.
+# (must have teensy_loader_cli installed).
+#
+# make dfu = Download the hex file to the device, using dfu-programmer (must
+# have dfu-programmer installed).
+#
+# make flip = Download the hex file to the device, using Atmel FLIP (must
+# have Atmel FLIP installed).
+#
+# make dfu-ee = Download the eeprom file to the device, using dfu-programmer
+# (must have dfu-programmer installed).
+#
+# make flip-ee = Download the eeprom file to the device, using Atmel FLIP
+# (must have Atmel FLIP installed).
+#
+# make debug = Start either simulavr or avarice as specified for debugging,
+# with avr-gdb or avr-insight as the front end for debugging.
+#
+# make filename.s = Just compile filename.c into the assembler code only.
+#
+# make filename.i = Create a preprocessed source file for use in submitting
+# bug reports to the GCC project.
+#
+# To rebuild project do "make clean" then "make all".
+#----------------------------------------------------------------------------
+
+# Target file name (without extension).
+TARGET = atomic_lufa
+
+# Directory common source filess exist
+TOP_DIR = ../..
+
+# Directory keyboard dependent files exist
+TARGET_DIR = .
+
+# project specific files
+SRC = keymap_common.c \
+ matrix.c \
+ led.c
+
+ifdef KEYMAP
+ SRC := keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := keymap_vlad.c $(SRC)
+endif
+
+CONFIG_H = config.h
+
+
+# MCU name
+#MCU = at90usb1287
+MCU = atmega32u4
+
+# Processor frequency.
+# This will define a symbol, F_CPU, in all source code files equal to the
+# processor frequency in Hz. You can then use this symbol in your source code to
+# calculate timings. Do NOT tack on a 'UL' at the end, this will be done
+# automatically to create a 32-bit value in your source code.
+#
+# This will be an integer division of F_USB below, as it is sourced by
+# F_USB after it has run through any CPU prescalers. Note that this value
+# does not *change* the processor frequency - it should merely be updated to
+# reflect the processor speed set externally so that the code can use accurate
+# software delays.
+F_CPU = 16000000
+
+
+#
+# LUFA specific
+#
+# Target architecture (see library "Board Types" documentation).
+ARCH = AVR8
+
+# Input clock frequency.
+# This will define a symbol, F_USB, in all source code files equal to the
+# input clock frequency (before any prescaling is performed) in Hz. This value may
+# differ from F_CPU if prescaling is used on the latter, and is required as the
+# raw input clock is fed directly to the PLL sections of the AVR for high speed
+# clock generation for the USB and other AVR subsections. Do NOT tack on a 'UL'
+# at the end, this will be done automatically to create a 32-bit value in your
+# source code.
+#
+# If no clock division is performed on the input clock inside the AVR (via the
+# CPU clock adjust registers or the clock division fuses), this will be equal to F_CPU.
+F_USB = $(F_CPU)
+
+# Interrupt driven control endpoint task(+60)
+OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT
+
+
+# Boot Section Size in *bytes*
+# Teensy halfKay 512
+# Teensy++ halfKay 1024
+# Atmel DFU loader 4096
+# LUFA bootloader 4096
+# USBaspLoader 2048
+OPT_DEFS += -DBOOTLOADER_SIZE=4096
+
+
+# Build Options
+# comment out to disable the options.
+#
+BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration(+1000)
+MOUSEKEY_ENABLE = yes # Mouse keys(+4700)
+EXTRAKEY_ENABLE = yes # Audio control and System control(+450)
+CONSOLE_ENABLE = yes # Console for debug(+400)
+COMMAND_ENABLE = yes # Commands for debug and configuration
+#SLEEP_LED_ENABLE = yes # Breathing sleep LED during USB suspend
+NKRO_ENABLE = yes # USB Nkey Rollover - not yet supported in LUFA
+
+
+# Optimize size but this may cause error "relocation truncated to fit"
+#EXTRALDFLAGS = -Wl,--relax
+
+# Search Path
+VPATH += $(TARGET_DIR)
+VPATH += $(TOP_DIR)
+
+include $(TOP_DIR)/protocol/lufa.mk
+include $(TOP_DIR)/common.mk
+include $(TOP_DIR)/rules.mk
diff --git a/keyboard/atomic_old/Makefile.pjrc b/keyboard/atomic_old/Makefile.pjrc
new file mode 100644
index 0000000000..9655ff65a9
--- /dev/null
+++ b/keyboard/atomic_old/Makefile.pjrc
@@ -0,0 +1,116 @@
+#----------------------------------------------------------------------------
+# On command line:
+#
+# make all = Make software.
+#
+# make clean = Clean out built project files.
+#
+# make coff = Convert ELF to AVR COFF.
+#
+# make extcoff = Convert ELF to AVR Extended COFF.
+#
+# make program = Download the hex file to the device.
+# Please customize your programmer settings(PROGRAM_CMD)
+#
+# make teensy = Download the hex file to the device, using teensy_loader_cli.
+# (must have teensy_loader_cli installed).
+#
+# make dfu = Download the hex file to the device, using dfu-programmer (must
+# have dfu-programmer installed).
+#
+# make flip = Download the hex file to the device, using Atmel FLIP (must
+# have Atmel FLIP installed).
+#
+# make dfu-ee = Download the eeprom file to the device, using dfu-programmer
+# (must have dfu-programmer installed).
+#
+# make flip-ee = Download the eeprom file to the device, using Atmel FLIP
+# (must have Atmel FLIP installed).
+#
+# make debug = Start either simulavr or avarice as specified for debugging,
+# with avr-gdb or avr-insight as the front end for debugging.
+#
+# make filename.s = Just compile filename.c into the assembler code only.
+#
+# make filename.i = Create a preprocessed source file for use in submitting
+# bug reports to the GCC project.
+#
+# To rebuild project do "make clean" then "make all".
+#----------------------------------------------------------------------------
+
+# Target file name (without extension).
+TARGET = gh60_pjrc
+
+# Directory common source filess exist
+TOP_DIR = ../..
+
+# Directory keyboard dependent files exist
+TARGET_DIR = .
+
+# project specific files
+SRC = keymap_common.c \
+ matrix.c \
+ led.c
+
+ifdef KEYMAP
+ SRC := keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := keymap_poker.c $(SRC)
+endif
+
+CONFIG_H = config.h
+
+
+# MCU name, you MUST set this to match the board you are using
+# type "make clean" after changing this, so all files will be rebuilt
+MCU = atmega32u4
+#MCU = at90usb1286
+
+
+# Processor frequency.
+# Normally the first thing your program should do is set the clock prescaler,
+# so your program will run at the correct speed. You should also set this
+# variable to same clock speed. The _delay_ms() macro uses this, and many
+# examples use this variable to calculate timings. Do not add a "UL" here.
+F_CPU = 16000000
+
+
+# Boot Section Size in *bytes*
+# Teensy halfKay 512
+# Atmel DFU loader 4096
+# LUFA bootloader 4096
+OPT_DEFS += -DBOOTLOADER_SIZE=4096
+
+
+# Build Options
+# comment out to disable the options.
+#
+BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration(+1000)
+MOUSEKEY_ENABLE = yes # Mouse keys(+5000)
+EXTRAKEY_ENABLE = yes # Audio control and System control(+600)
+CONSOLE_ENABLE = yes # Console for debug
+COMMAND_ENABLE = yes # Commands for debug and configuration
+SLEEP_LED_ENABLE = yes # Breathing sleep LED during USB suspend
+NKRO_ENABLE = yes # USB Nkey Rollover(+500)
+#PS2_MOUSE_ENABLE = yes # PS/2 mouse(TrackPoint) support
+
+
+# Search Path
+VPATH += $(TARGET_DIR)
+VPATH += $(TOP_DIR)
+
+include $(TOP_DIR)/protocol/pjrc.mk
+include $(TOP_DIR)/common.mk
+include $(TOP_DIR)/rules.mk
+
+plain: OPT_DEFS += -DKEYMAP_PLAIN
+plain: all
+
+poker: OPT_DEFS += -DKEYMAP_POKER
+poker: all
+
+poker_set: OPT_DEFS += -DKEYMAP_POKER_SET
+poker_set: all
+
+poker_bit: OPT_DEFS += -DKEYMAP_POKER_BIT
+poker_bit: all
diff --git a/keyboard/atomic_old/README 2.md b/keyboard/atomic_old/README 2.md
new file mode 100644
index 0000000000..510cb5c8b6
--- /dev/null
+++ b/keyboard/atomic_old/README 2.md
@@ -0,0 +1,141 @@
+GH60 keyboard firmware
+======================
+DIY compact keyboard designed and run by komar007 and Geekhack community.
+
+- Both Rev.A and Rev.B PCB are supported by one firmware binary(issue #64)
+
+## GH60 Resources
+- [KOMAR's project page](http://blog.komar.be/projects/gh60-programmable-keyboard/)
+- [Prototyping](http://geekhack.org/index.php?topic=34959.0)
+- [Rev.A PCB test](http://geekhack.org/index.php?topic=37570.0)
+- [Rev.B PCB test](http://geekhack.org/index.php?topic=50685.0)
+- [Group buy](http://geekhack.org/index.php?topic=41464.0)
+
+
+## Build
+Move to this directory then just run `make` like:
+
+ $ make
+
+Use `make -f Makefile.pjrc` if you want to use PJRC stack but I find no reason to do so now.
+
+
+## Keymap
+Several version of keymap are available in advance but you are recommended to define your favorite layout yourself. To define your own keymap create file named `keymap_<name>.c` and see keymap document(you can find in top README.md) and existent keymap files.
+
+To build firmware binary hex file with a certain keymap just do `make` with `KEYMAP` option like:
+
+ $ make KEYMAP=[poker|poker_set|poker_bit|plain|hasu|spacefn|hhkb|<name>]
+
+
+### 1 Poker
+[keymap_poker.c](keymap_poker.c) emulates original Poker layers
+while both [keymap_poker_bit.c](keymap_poker_bit.c) and [keymap_poker_set.c](keymap_poker_set.c) implements same layout in different way and they fix a minor issue of original Poker and enhance arrow keys.
+
+ Fn + Esc = `
+ Fn + {left, down, up, right} = {home, pgdown, pgup, end}
+
+#### 1.0 Default layer
+ ,-----------------------------------------------------------.
+ | `| 1| 2| 3| 4| 5| 6| 7| 8| 9| 0| -| =|Backsp |
+ |-----------------------------------------------------------|
+ |Tab | Q| W| E| R| T| Y| U| I| O| P| [| ]| \|
+ |-----------------------------------------------------------|
+ |Caps | A| S| D| F| G| H| J| K| L| ;| '|Return |
+ |-----------------------------------------------------------|
+ |Shift | Z| X| C| V| B| N| M| ,| .| /|Shift |
+ |-----------------------------------------------------------|
+ |Ctrl|Gui |Alt | Space |Fn |Gui |App |Ctrl|
+ `-----------------------------------------------------------'
+#### 1.1 Poker Fn layer
+ ,-----------------------------------------------------------.
+ |Esc| F1| F2| F3| F4| F5| F6| F7| F8| F9|F10|F11|F12| |
+ |-----------------------------------------------------------|
+ | |FnQ| Up| | | | | | |Cal| |Hom|Ins| |
+ |-----------------------------------------------------------|
+ | |Lef|Dow|Rig| | |Psc|Slk|Pau| |Tsk|End| |
+ |-----------------------------------------------------------|
+ | |Del| |Web|Mut|VoU|VoD| |PgU|PgD|Del| Up |
+ |-----------------------------------------------------------|
+ | | | | FnS |Fn |Left|Down|Righ|
+ `-----------------------------------------------------------'
+
+
+### 2. Plain
+Without any Fn layer this will be useful if you want to use key remapping tool like AHK on host.
+See [keymap_plain.c](keymap_plain.c) for detail.
+
+#### 1.0 Plain Default layer
+ ,-----------------------------------------------------------.
+ |Esc| 1| 2| 3| 4| 5| 6| 7| 8| 9| 0| -| =|Backsp |
+ |-----------------------------------------------------------|
+ |Tab | Q| W| E| R| T| Y| U| I| O| P| [| ]| \|
+ |-----------------------------------------------------------|
+ |Caps | A| S| D| F| G| H| J| K| L| ;| '|Return |
+ |-----------------------------------------------------------|
+ |Shift | Z| X| C| V| B| N| M| ,| .| /|Shift |
+ |-----------------------------------------------------------|
+ |Ctrl|Gui |Alt | Space |Alt |Gui |App |Ctrl|
+ `-----------------------------------------------------------'
+
+
+### 3. Hasu
+This is my favorite keymap with HHKB Fn, Vi cursor and Mousekey layer. See [keymap_hasu.c](keymap_hasu.c) for detail.
+
+
+### 4. SpaceFN
+This layout proposed by spiceBar uses space bar to change layer with using Dual role key technique. See [keymap_spacefn.c](keymap_spacefn.c) and [SpaceFN discussion](http://geekhack.org/index.php?topic=51069.0).
+
+#### 4.0 Default layer
+ ,-----------------------------------------------------------.
+ |Esc| 1| 2| 3| 4| 5| 6| 7| 8| 9| 0| -| =|Backsp |
+ |-----------------------------------------------------------|
+ |Tab | Q| W| E| R| T| Y| U| I| O| P| [| ]| \|
+ |-----------------------------------------------------------|
+ |Caps | A| S| D| F| G| H| J| K| L| ;| '|Return |
+ |-----------------------------------------------------------|
+ |Shift | Z| X| C| V| B| N| M| ,| .| /|Shift |
+ |-----------------------------------------------------------|
+ |Ctrl|Gui |Alt | Space/Fn |Alt |Gui |App |Ctrl|
+ `-----------------------------------------------------------'
+#### 4.1 SpaceFN layer
+ ,-----------------------------------------------------------.
+ |` | F1| F2| F3| F4| F5| F6| F7| F8| F9|F10|F11|F12|Delete |
+ |-----------------------------------------------------------|
+ | | | | | | | |Hom|Up |End|Psc|Slk|Pau|Ins |
+ |-----------------------------------------------------------|
+ | | | | | | |PgU|Lef|Dow|Rig| | | |
+ |-----------------------------------------------------------|
+ | | | | | |Spc|PgD|` |~ | | | |
+ |-----------------------------------------------------------|
+ | | | | Fn | | | | |
+ `-----------------------------------------------------------'
+
+
+### 5. HHKB
+[keymap_hhkb.c](keymap_hhkb.c) emulates original HHKB layers.
+#### 5.0: Default layer
+ ,-----------------------------------------------------------.
+ |Esc| 1| 2| 3| 4| 5| 6| 7| 8| 9| 0| -| =| \| `|
+ |-----------------------------------------------------------|
+ |Tab | Q| W| E| R| T| Y| U| I| O| P| [| ]|Bspc |
+ |-----------------------------------------------------------|
+ |Ctrl | A| S| D| F| G| H| J| K| L|Fn3| '|Return |
+ |-----------------------------------------------------------|
+ |Shift | Z| X| C| V| B| N| M| ,| .| /|Shift |Fn |
+ |-----------------------------------------------------------|
+ | |Gui |Alt | Space | |Alt |Gui | |
+ `-----------------------------------------------------------'
+#### 5.1: HHKB Fn layer
+ ,-----------------------------------------------------------.
+ |Pwr| F1| F2| F3| F4| F5| F6| F7| F8| F9|F10|F11|F12|Ins|Del|
+ |-----------------------------------------------------------|
+ |Caps | | | | | | | |Psc|Slk|Pus|Up | | |
+ |-----------------------------------------------------------|
+ | |VoD|VoU|Mut|Ejc| | *| /|Hom|PgU|Lef|Rig|Enter |
+ |-----------------------------------------------------------|
+ | | | | | | | +| -|End|PgD|Dow| | |
+ |-----------------------------------------------------------|
+ | | | | | | | | |
+ `-----------------------------------------------------------'
+
diff --git a/keyboard/atomic_old/config.h b/keyboard/atomic_old/config.h
new file mode 100644
index 0000000000..5ea953805f
--- /dev/null
+++ b/keyboard/atomic_old/config.h
@@ -0,0 +1,70 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef CONFIG_H
+#define CONFIG_H
+
+
+/* USB Device descriptor parameter */
+#define VENDOR_ID 0xFEED
+#define PRODUCT_ID 0x6060
+#define DEVICE_VER 0x0001
+#define MANUFACTURER Ortholinear Keyboards
+#define PRODUCT Atomic Keyboard
+#define DESCRIPTION t.m.k. keyboard firmware for Atomic
+
+/* key matrix size */
+#define MATRIX_ROWS 5
+#define MATRIX_COLS 15
+
+/* define if matrix has ghost */
+//#define MATRIX_HAS_GHOST
+
+/* Set 0 if debouncing isn't needed */
+#define DEBOUNCE 5
+
+/* Mechanical locking support. Use KC_LCAP, KC_LNUM or KC_LSCR instead in keymap */
+#define LOCKING_SUPPORT_ENABLE
+/* Locking resynchronize hack */
+#define LOCKING_RESYNC_ENABLE
+
+/* key combination for command */
+#define IS_COMMAND() ( \
+ keyboard_report->mods == (MOD_BIT(KC_LSHIFT) | MOD_BIT(KC_RSHIFT)) \
+)
+
+
+
+/*
+ * Feature disable options
+ * These options are also useful to firmware size reduction.
+ */
+
+/* disable debug print */
+//#define NO_DEBUG
+
+/* disable print */
+//#define NO_PRINT
+
+/* disable action features */
+//#define NO_ACTION_LAYER
+//#define NO_ACTION_TAPPING
+//#define NO_ACTION_ONESHOT
+//#define NO_ACTION_MACRO
+//#define NO_ACTION_FUNCTION
+
+#endif
diff --git a/keyboard/atomic_old/keymap_common.c b/keyboard/atomic_old/keymap_common.c
new file mode 100644
index 0000000000..fdb1769e1c
--- /dev/null
+++ b/keyboard/atomic_old/keymap_common.c
@@ -0,0 +1,30 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+#include "keymap_common.h"
+
+
+/* translates key to keycode */
+uint8_t keymap_key_to_keycode(uint8_t layer, keypos_t key)
+{
+ return pgm_read_byte(&keymaps[(layer)][(key.row)][(key.col)]);
+}
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint8_t keycode)
+{
+ return (action_t){ .code = pgm_read_word(&fn_actions[FN_INDEX(keycode)]) };
+}
diff --git a/keyboard/atomic_old/keymap_common.h b/keyboard/atomic_old/keymap_common.h
new file mode 100644
index 0000000000..c582c0135f
--- /dev/null
+++ b/keyboard/atomic_old/keymap_common.h
@@ -0,0 +1,87 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+#ifndef KEYMAP_COMMON_H
+#define KEYMAP_COMMON_H
+
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/pgmspace.h>
+#include "keycode.h"
+#include "action.h"
+#include "action_macro.h"
+#include "report.h"
+#include "host.h"
+#include "print.h"
+#include "debug.h"
+#include "keymap.h"
+
+
+extern const uint8_t keymaps[][MATRIX_ROWS][MATRIX_COLS];
+extern const uint16_t fn_actions[];
+
+// JCK: Semi-Standard layout
+#define KEYMAP_JCK( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, K0C, K0E, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, K1C, K1D, K1E, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, K2D, K2E, \
+ K30, K31, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3C, K3D, K3E, \
+ K40, K41, K43, K46, K4A, K4B, K4C, K4D, K4E \
+) { \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B, KC_##K0C, KC_NO, KC_##K0E }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B, KC_##K1C, KC_##K1D, KC_##K1E }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B, KC_NO, KC_##K2D, KC_##K2E }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_##K36, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_NO, KC_##K3C, KC_##K3D, KC_##K3E }, \
+ { KC_##K40, KC_##K41, KC_NO, KC_##K43, KC_NO, KC_NO, KC_##K46, KC_NO, KC_NO, KC_NO, KC_##K4A, KC_##K4B, KC_##K4C, KC_##K4D, KC_##K4E } \
+}
+
+// ASK: Short Space layout
+#define KEYMAP_ASK_MESSY( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, K0C, K0E, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, K1C, K1D, K1E, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, K2D, K2E, \
+ K30, K31, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3C, K3D, K3E, \
+ K40, K41, K43, K44, K46, K48, K49, K4A, K4B, K4C, K4D, K4E \
+) { \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B, KC_##K0C, KC_NO, KC_##K0E }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B, KC_##K1C, KC_##K1D, KC_##K1E }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B, KC_NO, KC_##K2D, KC_##K2E }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_##K36, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_NO, KC_##K3C, KC_##K3D, KC_##K3E }, \
+ { KC_##K40, KC_##K41, KC_NO, KC_##K43, KC_##K44, KC_NO, KC_##K46, KC_NO, KC_##K48, KC_##K49, KC_##K4A, KC_##K4B, KC_##K4C, KC_##K4D, KC_##K4E } \
+}
+
+#define KEYMAP_ASK( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, K0C, K0E, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, K1C, K1D, K1E, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, K2C, K2E, \
+ K30, K31, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3B, K3D, K3E, \
+ K40, K41, K43, K44, K46, K47, K48, K4A, K4B, K4C, K4D, K4E \
+) { \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B, KC_##K0C, KC_NO, KC_##K0E }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B, KC_##K1C, KC_##K1D, KC_##K1E }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B, KC_##K2C, KC_NO, KC_##K2E }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_##K36, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B, KC_NO, KC_##K3D, KC_##K3E }, \
+ { KC_##K40, KC_##K41, KC_NO, KC_##K43, KC_##K44, KC_NO, KC_##K46, KC_##K47, KC_##K48, KC_NO, KC_##K4A, KC_##K4B, KC_##K4C, KC_##K4D, KC_##K4E } \
+}
+
+
+// MLO: Semi-Grid layout
+
+// KLN: Grid layout
+
+// PKR: Standard layout
+
+#endif
diff --git a/keyboard/atomic_old/keymap_plain.c b/keyboard/atomic_old/keymap_plain.c
new file mode 100644
index 0000000000..e7f53649f0
--- /dev/null
+++ b/keyboard/atomic_old/keymap_plain.c
@@ -0,0 +1,46 @@
+#include "keymap_common.h"
+
+// JCK: Semi-Standard layout
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ /* 0: qwerty */
+ [0] = KEYMAP_JCK(GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, MINS, EQL, BSPC, \
+ TAB, Q, W, E, R, T, Y, U, I, O, P, LBRC, RBRC, BSLS, DEL, \
+ ESC, A, S, D, F, G, H, J, K, L, SCLN, QUOT, ENT, MPLY, \
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, RSFT, VOLD, VOLU, \
+ LCTL, LALT, LGUI, SPC, FN1, LEFT, DOWN, UP, RGHT),
+ [1] = KEYMAP_JCK(GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, MINS, EQL, BSPC, \
+ TAB, Q, W, F, P, G, J, L, U, Y, SCLN, LBRC, RBRC, BSLS, DEL, \
+ ESC, A, R, S, T, D, H, N, E, I, O, QUOT, ENT, MPLY, \
+ LSFT, Z, X, C, V, B, K, M, COMM, DOT, SLSH, RSFT, VOLD, VOLU, \
+ LCTL, LALT, LGUI, SPC, FN1, LEFT, DOWN, UP, RGHT),
+ [2] = KEYMAP_JCK(GRV, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12, BSPC, \
+ TAB, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, LBRC, RBRC, BSLS, DEL, \
+ ESC, FN3, FN4, TRNS, TRNS, TRNS, TRNS, MINS, EQL, LBRC, RBRC, BSLS, ENT, MPLY, \
+ LSFT, FN9, X, C, V, B, N, M, COMM, DOT, SLSH, RSFT, VOLD, VOLU, \
+ LCTL, LALT, LGUI, SPC, TRNS, MNXT, VOLD, VOLU, MPLY),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [9] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+};
diff --git a/keyboard/atomic_old/keymap_ricky.c b/keyboard/atomic_old/keymap_ricky.c
new file mode 100644
index 0000000000..fcc91a1fa5
--- /dev/null
+++ b/keyboard/atomic_old/keymap_ricky.c
@@ -0,0 +1,15 @@
+#include "keymap_common.h"
+
+// JCK: Semi-Standard layout
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ /* 0: qwerty */
+ [0] = KEYMAP_JCK(GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, MINS, EQL, BSPC, \
+ TAB, Q, W, E, R, T, Y, U, I, O, P, LBRC, RBRC, BSLS, PSCR, \
+ CAPS, A, S, D, F, G, H, J, K, L, SCLN, QUOT, ENT, INS, \
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, RSFT, UP, DEL, \
+ LCTL, LGUI, LALT, SPC, RALT, RCTL, LEFT, DOWN, RGHT)
+};
+const uint16_t PROGMEM fn_actions[] = {
+};
+
diff --git a/keyboard/atomic_old/keymap_vlad.c b/keyboard/atomic_old/keymap_vlad.c
new file mode 100644
index 0000000000..e56bcf1618
--- /dev/null
+++ b/keyboard/atomic_old/keymap_vlad.c
@@ -0,0 +1,14 @@
+#include "keymap_common.h"
+
+// JCK: Semi-Standard layout
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ /* 0: qwerty */
+ [0] = KEYMAP_ASK(GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, MINS, EQL, BSPC, \
+ TAB, Q, W, E, R, T, Y, U, I, O, P, LBRC, RBRC, BSLS, DEL, \
+ CAPS, A, S, D, F, G, H, J, K, L, SCLN, QUOT, ENT, VOLU, \
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, RSFT, UP, VOLD, \
+ LCTL, LGUI, LALT, LGUI, SPC, RGUI, RALT, RGUI, RCTL, LEFT, DOWN, RGHT)
+};
+const uint16_t PROGMEM fn_actions[] = {
+}; \ No newline at end of file
diff --git a/keyboard/atomic_old/led.c b/keyboard/atomic_old/led.c
new file mode 100644
index 0000000000..2d52fbf1c3
--- /dev/null
+++ b/keyboard/atomic_old/led.c
@@ -0,0 +1,25 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include <avr/io.h>
+#include "stdint.h"
+#include "led.h"
+
+
+void led_set(uint8_t usb_led)
+{
+}
diff --git a/keyboard/atomic_old/matrix.c b/keyboard/atomic_old/matrix.c
new file mode 100644
index 0000000000..98102cb694
--- /dev/null
+++ b/keyboard/atomic_old/matrix.c
@@ -0,0 +1,211 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+/*
+ * scan matrix
+ */
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/io.h>
+#include <util/delay.h>
+#include "action_layer.h"
+#include "print.h"
+#include "debug.h"
+#include "util.h"
+#include "matrix.h"
+
+
+#ifndef DEBOUNCE
+# define DEBOUNCE 10
+#endif
+static uint8_t debouncing = DEBOUNCE;
+
+/* matrix state(1:on, 0:off) */
+static matrix_row_t matrix[MATRIX_ROWS];
+static matrix_row_t matrix_debouncing[MATRIX_ROWS];
+
+static matrix_row_t read_cols(void);
+static void init_cols(void);
+static void unselect_rows(void);
+static void select_row(uint8_t row);
+
+
+inline
+uint8_t matrix_rows(void)
+{
+ return MATRIX_ROWS;
+}
+
+inline
+uint8_t matrix_cols(void)
+{
+ return MATRIX_COLS;
+}
+
+
+void matrix_init(void)
+{
+ // initialize row and col
+ unselect_rows();
+ init_cols();
+
+ // initialize matrix state: all keys off
+ for (uint8_t i=0; i < MATRIX_ROWS; i++) {
+ matrix[i] = 0;
+ matrix_debouncing[i] = 0;
+ }
+}
+
+uint8_t matrix_scan(void)
+{
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ select_row(i);
+ _delay_us(30); // without this wait read unstable value.
+ matrix_row_t cols = read_cols();
+ if (matrix_debouncing[i] != cols) {
+ matrix_debouncing[i] = cols;
+ if (debouncing) {
+ debug("bounce!: "); debug_hex(debouncing); debug("\n");
+ }
+ debouncing = DEBOUNCE;
+ }
+ unselect_rows();
+ }
+
+ if (debouncing) {
+ if (--debouncing) {
+ _delay_ms(1);
+ } else {
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ matrix[i] = matrix_debouncing[i];
+ }
+ }
+ }
+
+
+ return 1;
+}
+
+bool matrix_is_modified(void)
+{
+ if (debouncing) return false;
+ return true;
+}
+
+inline
+bool matrix_is_on(uint8_t row, uint8_t col)
+{
+ return (matrix[row] & ((matrix_row_t)1<<col));
+}
+
+inline
+matrix_row_t matrix_get_row(uint8_t row)
+{
+ return matrix[row];
+}
+
+void matrix_print(void)
+{
+ print("\nr/c 0123456789ABCDEF\n");
+ for (uint8_t row = 0; row < MATRIX_ROWS; row++) {
+ phex(row); print(": ");
+ pbin_reverse16(matrix_get_row(row));
+ print("\n");
+ }
+}
+
+uint8_t matrix_key_count(void)
+{
+ uint8_t count = 0;
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ count += bitpop16(matrix[i]);
+ }
+ return count;
+}
+
+/* Column pin configuration
+ * col: 0 1 2 3 4 5 6 7 8 9 10 11
+ * pin: F0 F1 F4 F5 F6 F7 B6 B5 B4 D7 D5 D4
+ */
+
+static void init_cols(void)
+{
+ DDRC &= ~(1<<6 | 1<<7);
+ PORTC |= (1<<6 | 1<<7);
+ DDRD &= ~(1<<4 | 1<<5 | 1<<6 | 1<<7);
+ PORTD |= (1<<4 | 1<<5 | 1<<6 | 1<<7);
+ DDRB &= ~(1<<4 | 1<<5 | 1<<6);
+ PORTB |= (1<<4 | 1<<5 | 1<<6);
+ DDRF &= ~(1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+ PORTF |= (1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+}
+
+static matrix_row_t read_cols(void)
+{
+ return (PINC&(1<<6) ? 0 : (1<< 0)) |
+ (PINC&(1<<7) ? 0 : (1<< 1)) |
+ (PIND&(1<<5) ? 0 : (1<< 2)) |
+ (PIND&(1<<4) ? 0 : (1<< 3)) |
+ (PIND&(1<<6) ? 0 : (1<< 4)) |
+ (PIND&(1<<7) ? 0 : (1<< 5)) |
+ (PINB&(1<<4) ? 0 : (1<< 6)) |
+ (PINB&(1<<5) ? 0 : (1<< 7)) |
+ (PINB&(1<<6) ? 0 : (1<< 8)) |
+ (PINF&(1<<7) ? 0 : (1<< 9)) |
+ (PINF&(1<<6) ? 0 : (1<<10)) |
+ (PINF&(1<<5) ? 0 : (1<<11)) |
+ (PINF&(1<<4) ? 0 : (1<<12)) |
+ (PINF&(1<<1) ? 0 : (1<<13)) |
+ (PINF&(1<<0) ? 0 : (1<<14));
+}
+
+/* Row pin configuration
+ * row: 0 1 2 3
+ * pin: B0 B1 B2 B3
+ */
+static void unselect_rows(void)
+{
+ // Hi-Z(DDR:0, PORT:0) to unselect
+ DDRB &= ~(1<<0 | 1<<1 | 1<<2 | 1<<3 | 1<<7);
+ PORTB |= (1<<0 | 1<<1 | 1<<2 | 1<<3 | 1<<7);
+}
+
+static void select_row(uint8_t row)
+{
+ switch (row) {
+ case 0:
+ DDRB |= (1<<0);
+ PORTB &= ~(1<<0);
+ break;
+ case 1:
+ DDRB |= (1<<1);
+ PORTB &= ~(1<<1);
+ break;
+ case 2:
+ DDRB |= (1<<2);
+ PORTB &= ~(1<<2);
+ break;
+ case 3:
+ DDRB |= (1<<3);
+ PORTB &= ~(1<<3);
+ break;
+ case 4:
+ DDRB |= (1<<7);
+ PORTB &= ~(1<<7);
+ break;
+ }
+}
diff --git a/keyboard/ergodox_ez/Makefile b/keyboard/ergodox_ez/Makefile
new file mode 100644
index 0000000000..e0d303c9df
--- /dev/null
+++ b/keyboard/ergodox_ez/Makefile
@@ -0,0 +1,114 @@
+#----------------------------------------------------------------------------
+# On command line:
+#
+# make = Make software.
+#
+# make clean = Clean out built project files.
+#
+# That's pretty much all you need. To compile, always go make clean,
+# followed by make.
+#
+# For advanced users only:
+# make teensy = Download the hex file to the device, using teensy_loader_cli.
+# (must have teensy_loader_cli installed).
+#
+#----------------------------------------------------------------------------
+
+# Target file name (without extension).
+TARGET = ergodox_ez
+
+
+# Directory common source filess exist
+TOP_DIR = ../..
+
+# Directory keyboard dependent files exist
+TARGET_DIR = .
+
+# # project specific files
+SRC = ergodox_ez.c \
+ twimaster.c
+
+ifdef KEYMAP
+ SRC := keymaps/keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := keymaps/keymap_default.c $(SRC)
+endif
+
+CONFIG_H = config.h
+
+# MCU name
+#MCU = at90usb1287
+MCU = atmega32u4
+
+# Processor frequency.
+# This will define a symbol, F_CPU, in all source code files equal to the
+# processor frequency in Hz. You can then use this symbol in your source code to
+# calculate timings. Do NOT tack on a 'UL' at the end, this will be done
+# automatically to create a 32-bit value in your source code.
+#
+# This will be an integer division of F_USB below, as it is sourced by
+# F_USB after it has run through any CPU prescalers. Note that this value
+# does not *change* the processor frequency - it should merely be updated to
+# reflect the processor speed set externally so that the code can use accurate
+# software delays.
+F_CPU = 16000000
+
+
+#
+# LUFA specific
+#
+# Target architecture (see library "Board Types" documentation).
+ARCH = AVR8
+
+# Input clock frequency.
+# This will define a symbol, F_USB, in all source code files equal to the
+# input clock frequency (before any prescaling is performed) in Hz. This value may
+# differ from F_CPU if prescaling is used on the latter, and is required as the
+# raw input clock is fed directly to the PLL sections of the AVR for high speed
+# clock generation for the USB and other AVR subsections. Do NOT tack on a 'UL'
+# at the end, this will be done automatically to create a 32-bit value in your
+# source code.
+#
+# If no clock division is performed on the input clock inside the AVR (via the
+# CPU clock adjust registers or the clock division fuses), this will be equal to F_CPU.
+F_USB = $(F_CPU)
+
+# Interrupt driven control endpoint task(+60)
+OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT
+
+
+# Boot Section Size in *bytes*
+# Teensy halfKay 512
+# Teensy++ halfKay 1024
+# Atmel DFU loader 4096
+# LUFA bootloader 4096
+# USBaspLoader 2048
+OPT_DEFS += -DBOOTLOADER_SIZE=4096
+
+
+# Build Options
+# comment out to disable the options.
+#
+BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration(+1000)
+MOUSEKEY_ENABLE = yes # Mouse keys(+4700)
+EXTRAKEY_ENABLE = yes # Audio control and System control(+450)
+CONSOLE_ENABLE = yes # Console for debug(+400)
+COMMAND_ENABLE = yes # Commands for debug and configuration
+# Do not enable SLEEP_LED_ENABLE. it uses the same timer as BACKLIGHT_ENABLE
+# SLEEP_LED_ENABLE = yes # Breathing sleep LED during USB suspend
+# NKRO_ENABLE = yes # USB Nkey Rollover - not yet supported in LUFA
+# BACKLIGHT_ENABLE = yes # Enable keyboard backlight functionality
+# MIDI_ENABLE = YES # MIDI controls
+# UNICODE_ENABLE = YES # Unicode
+# BLUETOOTH_ENABLE = yes # Enable Bluetooth with the Adafruit EZ-Key HID
+
+
+# Optimize size but this may cause error "relocation truncated to fit"
+#EXTRALDFLAGS = -Wl,--relax
+
+# Search Path
+VPATH += $(TARGET_DIR)
+VPATH += $(TOP_DIR)
+
+include $(TOP_DIR)/quantum.mk
+
diff --git a/keyboard/ergodox_ez/README.md b/keyboard/ergodox_ez/README.md
new file mode 100644
index 0000000000..f750d8dbec
--- /dev/null
+++ b/keyboard/ergodox_ez/README.md
@@ -0,0 +1 @@
+// TODO: Make up a proper readme for the ErgoDox EZ.
diff --git a/keyboard/ergodox_ez/config.h b/keyboard/ergodox_ez/config.h
new file mode 100644
index 0000000000..850d245791
--- /dev/null
+++ b/keyboard/ergodox_ez/config.h
@@ -0,0 +1,87 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+Copyright 2013 Oleg Kostyuk <cub.uanic@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef CONFIG_H
+#define CONFIG_H
+
+#include "config_common.h"
+
+/* USB Device descriptor parameter */
+#define VENDOR_ID 0xFEED
+#define PRODUCT_ID 0x1307
+#define DEVICE_VER 0x0001
+#define MANUFACTURER ErgoDox EZ
+#define PRODUCT ErgoDox EZ
+#define DESCRIPTION t.m.k. keyboard firmware for Ergodox
+
+/* key matrix size */
+#define MATRIX_ROWS 14
+#define MATRIX_COLS 6
+
+#define MOUSEKEY_DELAY 100
+#define MOUSEKEY_INTERVAL 20
+#define MOUSEKEY_MAX_SPEED 3
+#define MOUSEKEY_TIME_TO_MAX 10
+
+#define COLS (int []){ F1, F0, B0, C7, F4, F5, F6, F7, D4, D6, B4, D7 }
+#define ROWS (int []){ D0, D5, B5, B6 }
+
+/* COL2ROW or ROW2COL */
+#define DIODE_DIRECTION COL2ROW
+
+/* define if matrix has ghost */
+//#define MATRIX_HAS_GHOST
+
+/* number of backlight levels */
+#define BACKLIGHT_LEVELS 3
+
+/* Set 0 if debouncing isn't needed */
+#define DEBOUNCE 2
+#define TAPPING_TERM 100
+
+/* Mechanical locking support. Use KC_LCAP, KC_LNUM or KC_LSCR instead in keymap */
+#define LOCKING_SUPPORT_ENABLE
+/* Locking resynchronize hack */
+#define LOCKING_RESYNC_ENABLE
+
+/* key combination for command */
+#define IS_COMMAND() ( \
+ keyboard_report->mods == (MOD_BIT(KC_LCTL) | MOD_BIT(KC_RCTL)) || \
+ keyboard_report->mods == (MOD_BIT(KC_LSFT) | MOD_BIT(KC_RSFT)) \
+)
+
+/*
+ * Feature disable options
+ * These options are also useful to firmware size reduction.
+ */
+
+/* disable debug print */
+// #define NO_DEBUG
+
+/* disable print */
+// #define NO_PRINT
+
+/* disable action features */
+//#define NO_ACTION_LAYER
+//#define NO_ACTION_TAPPING
+//#define NO_ACTION_ONESHOT
+//#define NO_ACTION_MACRO
+//#define NO_ACTION_FUNCTION
+//#define DEBUG_MATRIX_SCAN_RATE
+
+#endif
diff --git a/keyboard/ergodox_ez/ergodox_ez.c b/keyboard/ergodox_ez/ergodox_ez.c
new file mode 100644
index 0000000000..f7e156b319
--- /dev/null
+++ b/keyboard/ergodox_ez/ergodox_ez.c
@@ -0,0 +1,123 @@
+#include "ergodox_ez.h"
+#include "i2cmaster.h"
+
+bool i2c_initialized = 0;
+uint8_t mcp23018_status = 0x20;
+
+bool ergodox_left_led_1 = 0; // left top
+bool ergodox_left_led_2 = 0; // left middle
+bool ergodox_left_led_3 = 0; // left bottom
+
+__attribute__ ((weak))
+void * matrix_init_user(void) {
+
+};
+
+__attribute__ ((weak))
+void * matrix_scan_user(void) {
+
+};
+
+void * matrix_init_kb(void) {
+ // keyboard LEDs (see "PWM on ports OC1(A|B|C)" in "teensy-2-0.md")
+ TCCR1A = 0b10101001; // set and configure fast PWM
+ TCCR1B = 0b00001001; // set and configure fast PWM
+
+ // (tied to Vcc for hardware convenience)
+ DDRB &= ~(1<<4); // set B(4) as input
+ PORTB &= ~(1<<4); // set B(4) internal pull-up disabled
+
+ // unused pins - C7, D4, D5, D7, E6
+ // set as input with internal pull-ip enabled
+ DDRC &= ~(1<<7);
+ DDRD &= ~(1<<7 | 1<<5 | 1<<4);
+ DDRE &= ~(1<<6);
+ PORTC |= (1<<7);
+ PORTD |= (1<<7 | 1<<5 | 1<<4);
+ PORTE |= (1<<6);
+
+ ergodox_blink_all_leds();
+
+ if (matrix_init_user) {
+ (*matrix_init_user)();
+ }
+};
+
+void * matrix_scan_kb(void) {
+
+ if (matrix_scan_user) {
+ (*matrix_scan_user)();
+ }
+};
+
+
+void ergodox_blink_all_leds(void)
+{
+ ergodox_led_all_off();
+ ergodox_led_all_set(LED_BRIGHTNESS_HI);
+ ergodox_led_all_on();
+ _delay_ms(333);
+ ergodox_led_all_off();
+}
+
+uint8_t init_mcp23018(void) {
+ mcp23018_status = 0x20;
+
+ // I2C subsystem
+ if (i2c_initialized == 0) {
+ i2c_init(); // on pins D(1,0)
+ i2c_initialized++;
+ _delay_ms(1000);
+ }
+
+ // set pin direction
+ // - unused : input : 1
+ // - input : input : 1
+ // - driving : output : 0
+ mcp23018_status = i2c_start(I2C_ADDR_WRITE); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(IODIRA); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(0b00000000); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(0b00111111); if (mcp23018_status) goto out;
+ i2c_stop();
+
+ // set pull-up
+ // - unused : on : 1
+ // - input : on : 1
+ // - driving : off : 0
+ mcp23018_status = i2c_start(I2C_ADDR_WRITE); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(GPPUA); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(0b00000000); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(0b00111111); if (mcp23018_status) goto out;
+
+out:
+ i2c_stop();
+
+ if (!mcp23018_status) mcp23018_status = ergodox_left_leds_update();
+
+ return mcp23018_status;
+}
+
+uint8_t ergodox_left_leds_update(void) {
+ if (mcp23018_status) { // if there was an error
+ return mcp23018_status;
+ }
+
+ // set logical value (doesn't matter on inputs)
+ // - unused : hi-Z : 1
+ // - input : hi-Z : 1
+ // - driving : hi-Z : 1
+ mcp23018_status = i2c_start(I2C_ADDR_WRITE); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(OLATA); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(0b11111111
+ & ~(ergodox_left_led_3<<LEFT_LED_3_SHIFT)
+ ); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(0b11111111
+ & ~(ergodox_left_led_2<<LEFT_LED_2_SHIFT)
+ & ~(ergodox_left_led_1<<LEFT_LED_1_SHIFT)
+ ); if (mcp23018_status) goto out;
+
+out:
+ i2c_stop();
+ return mcp23018_status;
+}
+
diff --git a/keyboard/ergodox_ez/ergodox_ez.h b/keyboard/ergodox_ez/ergodox_ez.h
new file mode 100644
index 0000000000..9d0691dfe2
--- /dev/null
+++ b/keyboard/ergodox_ez/ergodox_ez.h
@@ -0,0 +1,145 @@
+#ifndef PLANCK_H
+#define PLANCK_H
+
+#include "matrix.h"
+#include "keymap_common.h"
+#include "backlight.h"
+#include <stddef.h>
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/io.h>
+#include "i2cmaster.h"
+#include <util/delay.h>
+
+#define CPU_PRESCALE(n) (CLKPR = 0x80, CLKPR = (n))
+#define CPU_16MHz 0x00
+
+// I2C aliases and register addresses (see "mcp23018.md")
+#define I2C_ADDR 0b0100000
+#define I2C_ADDR_WRITE ( (I2C_ADDR<<1) | I2C_WRITE )
+#define I2C_ADDR_READ ( (I2C_ADDR<<1) | I2C_READ )
+#define IODIRA 0x00 // i/o direction register
+#define IODIRB 0x01
+#define GPPUA 0x0C // GPIO pull-up resistor register
+#define GPPUB 0x0D
+#define GPIOA 0x12 // general purpose i/o port register (write modifies OLAT)
+#define GPIOB 0x13
+#define OLATA 0x14 // output latch register
+#define OLATB 0x15
+
+extern uint8_t mcp23018_status;
+
+void init_ergodox(void);
+void ergodox_blink_all_leds(void);
+uint8_t init_mcp23018(void);
+uint8_t ergodox_left_leds_update(void);
+
+#define LED_BRIGHTNESS_LO 31
+#define LED_BRIGHTNESS_HI 255
+
+#define LEFT_LED_1_SHIFT 7 // in MCP23018 port B
+#define LEFT_LED_2_SHIFT 6 // in MCP23018 port B
+#define LEFT_LED_3_SHIFT 7 // in MCP23018 port A
+
+extern bool ergodox_left_led_1; // left top
+extern bool ergodox_left_led_2; // left middle
+extern bool ergodox_left_led_3; // left bottom
+
+inline void ergodox_board_led_on(void) { DDRD |= (1<<6); PORTD |= (1<<6); }
+inline void ergodox_right_led_1_on(void) { DDRB |= (1<<5); PORTB |= (1<<5); }
+inline void ergodox_right_led_2_on(void) { DDRB |= (1<<6); PORTB |= (1<<6); }
+inline void ergodox_right_led_3_on(void) { DDRB |= (1<<7); PORTB |= (1<<7); }
+inline void ergodox_left_led_1_on(void) { ergodox_left_led_1 = 1; }
+inline void ergodox_left_led_2_on(void) { ergodox_left_led_2 = 1; }
+inline void ergodox_left_led_3_on(void) { ergodox_left_led_3 = 1; }
+
+inline void ergodox_board_led_off(void) { DDRD &= ~(1<<6); PORTD &= ~(1<<6); }
+inline void ergodox_right_led_1_off(void) { DDRB &= ~(1<<5); PORTB &= ~(1<<5); }
+inline void ergodox_right_led_2_off(void) { DDRB &= ~(1<<6); PORTB &= ~(1<<6); }
+inline void ergodox_right_led_3_off(void) { DDRB &= ~(1<<7); PORTB &= ~(1<<7); }
+inline void ergodox_left_led_1_off(void) { ergodox_left_led_1 = 0; }
+inline void ergodox_left_led_2_off(void) { ergodox_left_led_2 = 0; }
+inline void ergodox_left_led_3_off(void) { ergodox_left_led_3 = 0; }
+
+inline void ergodox_led_all_on(void)
+{
+ ergodox_board_led_on();
+ ergodox_right_led_1_on();
+ ergodox_right_led_2_on();
+ ergodox_right_led_3_on();
+ ergodox_left_led_1_on();
+ ergodox_left_led_2_on();
+ ergodox_left_led_3_on();
+ ergodox_left_leds_update();
+}
+
+inline void ergodox_led_all_off(void)
+{
+ ergodox_board_led_off();
+ ergodox_right_led_1_off();
+ ergodox_right_led_2_off();
+ ergodox_right_led_3_off();
+ ergodox_left_led_1_off();
+ ergodox_left_led_2_off();
+ ergodox_left_led_3_off();
+ ergodox_left_leds_update();
+}
+
+inline void ergodox_right_led_1_set(uint8_t n) { OCR1A = n; }
+inline void ergodox_right_led_2_set(uint8_t n) { OCR1B = n; }
+inline void ergodox_right_led_3_set(uint8_t n) { OCR1C = n; }
+
+inline void ergodox_led_all_set(uint8_t n)
+{
+ ergodox_right_led_1_set(n);
+ ergodox_right_led_2_set(n);
+ ergodox_right_led_3_set(n);
+}
+
+#define KEYMAP( \
+ \
+ /* left hand, spatial positions */ \
+ k00,k01,k02,k03,k04,k05,k06, \
+ k10,k11,k12,k13,k14,k15,k16, \
+ k20,k21,k22,k23,k24,k25, \
+ k30,k31,k32,k33,k34,k35,k36, \
+ k40,k41,k42,k43,k44, \
+ k55,k56, \
+ k54, \
+ k53,k52,k51, \
+ \
+ /* right hand, spatial positions */ \
+ k07,k08,k09,k0A,k0B,k0C,k0D, \
+ k17,k18,k19,k1A,k1B,k1C,k1D, \
+ k28,k29,k2A,k2B,k2C,k2D, \
+ k37,k38,k39,k3A,k3B,k3C,k3D, \
+ k49,k4A,k4B,k4C,k4D, \
+ k57,k58, \
+ k59, \
+ k5C,k5B,k5A ) \
+ \
+ /* matrix positions */ \
+ { \
+ { k00, k10, k20, k30, k40, KC_NO }, \
+ { k01, k11, k21, k31, k41, k51 }, \
+ { k02, k12, k22, k32, k42, k52 }, \
+ { k03, k13, k23, k33, k43, k53 }, \
+ { k04, k14, k24, k34, k44, k54 }, \
+ { k05, k15, k25, k35, KC_NO, k55 }, \
+ { k06, k16, KC_NO, k36, KC_NO, k56 }, \
+ \
+ { k07, k17, KC_NO, k37,KC_NO, k57 }, \
+ { k08, k18, k28, k38,KC_NO, k58 }, \
+ { k09, k19, k29, k39, k49, k59 }, \
+ { k0A, k1A, k2A, k3A, k4A, k5A }, \
+ { k0B, k1B, k2B, k3B, k4B, k5B }, \
+ { k0C, k1C, k2C, k3C, k4C, k5C }, \
+ { k0D, k1D, k2D, k3D, k4D, KC_NO } \
+ }
+
+void * matrix_init_user(void);
+void * matrix_scan_user(void);
+
+
+
+#endif \ No newline at end of file
diff --git a/keyboard/ergodox_ez/i2cmaster.h b/keyboard/ergodox_ez/i2cmaster.h
new file mode 100644
index 0000000000..3917b9e6c0
--- /dev/null
+++ b/keyboard/ergodox_ez/i2cmaster.h
@@ -0,0 +1,178 @@
+#ifndef _I2CMASTER_H
+#define _I2CMASTER_H 1
+/*************************************************************************
+* Title: C include file for the I2C master interface
+* (i2cmaster.S or twimaster.c)
+* Author: Peter Fleury <pfleury@gmx.ch> http://jump.to/fleury
+* File: $Id: i2cmaster.h,v 1.10 2005/03/06 22:39:57 Peter Exp $
+* Software: AVR-GCC 3.4.3 / avr-libc 1.2.3
+* Target: any AVR device
+* Usage: see Doxygen manual
+**************************************************************************/
+
+#ifdef DOXYGEN
+/**
+ @defgroup pfleury_ic2master I2C Master library
+ @code #include <i2cmaster.h> @endcode
+
+ @brief I2C (TWI) Master Software Library
+
+ Basic routines for communicating with I2C slave devices. This single master
+ implementation is limited to one bus master on the I2C bus.
+
+ This I2c library is implemented as a compact assembler software implementation of the I2C protocol
+ which runs on any AVR (i2cmaster.S) and as a TWI hardware interface for all AVR with built-in TWI hardware (twimaster.c).
+ Since the API for these two implementations is exactly the same, an application can be linked either against the
+ software I2C implementation or the hardware I2C implementation.
+
+ Use 4.7k pull-up resistor on the SDA and SCL pin.
+
+ Adapt the SCL and SDA port and pin definitions and eventually the delay routine in the module
+ i2cmaster.S to your target when using the software I2C implementation !
+
+ Adjust the CPU clock frequence F_CPU in twimaster.c or in the Makfile when using the TWI hardware implementaion.
+
+ @note
+ The module i2cmaster.S is based on the Atmel Application Note AVR300, corrected and adapted
+ to GNU assembler and AVR-GCC C call interface.
+ Replaced the incorrect quarter period delays found in AVR300 with
+ half period delays.
+
+ @author Peter Fleury pfleury@gmx.ch http://jump.to/fleury
+
+ @par API Usage Example
+ The following code shows typical usage of this library, see example test_i2cmaster.c
+
+ @code
+
+ #include <i2cmaster.h>
+
+
+ #define Dev24C02 0xA2 // device address of EEPROM 24C02, see datasheet
+
+ int main(void)
+ {
+ unsigned char ret;
+
+ i2c_init(); // initialize I2C library
+
+ // write 0x75 to EEPROM address 5 (Byte Write)
+ i2c_start_wait(Dev24C02+I2C_WRITE); // set device address and write mode
+ i2c_write(0x05); // write address = 5
+ i2c_write(0x75); // write value 0x75 to EEPROM
+ i2c_stop(); // set stop conditon = release bus
+
+
+ // read previously written value back from EEPROM address 5
+ i2c_start_wait(Dev24C02+I2C_WRITE); // set device address and write mode
+
+ i2c_write(0x05); // write address = 5
+ i2c_rep_start(Dev24C02+I2C_READ); // set device address and read mode
+
+ ret = i2c_readNak(); // read one byte from EEPROM
+ i2c_stop();
+
+ for(;;);
+ }
+ @endcode
+
+*/
+#endif /* DOXYGEN */
+
+/**@{*/
+
+#if (__GNUC__ * 100 + __GNUC_MINOR__) < 304
+#error "This library requires AVR-GCC 3.4 or later, update to newer AVR-GCC compiler !"
+#endif
+
+#include <avr/io.h>
+
+/** defines the data direction (reading from I2C device) in i2c_start(),i2c_rep_start() */
+#define I2C_READ 1
+
+/** defines the data direction (writing to I2C device) in i2c_start(),i2c_rep_start() */
+#define I2C_WRITE 0
+
+
+/**
+ @brief initialize the I2C master interace. Need to be called only once
+ @param void
+ @return none
+ */
+extern void i2c_init(void);
+
+
+/**
+ @brief Terminates the data transfer and releases the I2C bus
+ @param void
+ @return none
+ */
+extern void i2c_stop(void);
+
+
+/**
+ @brief Issues a start condition and sends address and transfer direction
+
+ @param addr address and transfer direction of I2C device
+ @retval 0 device accessible
+ @retval 1 failed to access device
+ */
+extern unsigned char i2c_start(unsigned char addr);
+
+
+/**
+ @brief Issues a repeated start condition and sends address and transfer direction
+
+ @param addr address and transfer direction of I2C device
+ @retval 0 device accessible
+ @retval 1 failed to access device
+ */
+extern unsigned char i2c_rep_start(unsigned char addr);
+
+
+/**
+ @brief Issues a start condition and sends address and transfer direction
+
+ If device is busy, use ack polling to wait until device ready
+ @param addr address and transfer direction of I2C device
+ @return none
+ */
+extern void i2c_start_wait(unsigned char addr);
+
+
+/**
+ @brief Send one byte to I2C device
+ @param data byte to be transfered
+ @retval 0 write successful
+ @retval 1 write failed
+ */
+extern unsigned char i2c_write(unsigned char data);
+
+
+/**
+ @brief read one byte from the I2C device, request more data from device
+ @return byte read from I2C device
+ */
+extern unsigned char i2c_readAck(void);
+
+/**
+ @brief read one byte from the I2C device, read is followed by a stop condition
+ @return byte read from I2C device
+ */
+extern unsigned char i2c_readNak(void);
+
+/**
+ @brief read one byte from the I2C device
+
+ Implemented as a macro, which calls either i2c_readAck or i2c_readNak
+
+ @param ack 1 send ack, request more data from device<br>
+ 0 send nak, read is followed by a stop condition
+ @return byte read from I2C device
+ */
+extern unsigned char i2c_read(unsigned char ack);
+#define i2c_read(ack) (ack) ? i2c_readAck() : i2c_readNak();
+
+
+/**@}*/
+#endif
diff --git a/keyboard/ergodox_ez/keymaps/keymap_default.c b/keyboard/ergodox_ez/keymaps/keymap_default.c
new file mode 100644
index 0000000000..98cc9c5a6f
--- /dev/null
+++ b/keyboard/ergodox_ez/keymaps/keymap_default.c
@@ -0,0 +1,133 @@
+#include "ergodox_ez.h"
+#include "debug.h"
+#include "action_layer.h"
+
+// TODO: Define layer names that make sense for the ErgoDox EZ.
+#define DEFAULT_LAYER 0
+#define COLEMAK_LAYER 1
+#define DVORAK_LAYER 2
+#define LOWER_LAYER 1
+#define RAISE_LAYER 4
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[DEFAULT_LAYER] = KEYMAP( // layer 0 : default
+ // left hand
+ KC_EQL, KC_1, KC_2, KC_3, KC_4, KC_5, KC_ESC,
+ KC_BSLS,KC_Q, KC_W, KC_E, KC_R, KC_T, KC_FN2,
+ KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G,
+ KC_LSFT,KC_Z, KC_X, KC_C, KC_V, KC_B, KC_FN1,
+ KC_LGUI,KC_GRV, KC_BSLS,KC_LEFT,KC_RGHT,
+ KC_LCTL,KC_LALT,
+ KC_HOME,
+ KC_BSPC,KC_DEL, KC_END,
+ // right hand
+ KC_FN3, KC_6, KC_7, KC_8, KC_9, KC_0, KC_MINS,
+ KC_LBRC,KC_Y, KC_U, KC_I, KC_O, KC_P, KC_RBRC,
+ KC_H, KC_J, KC_K, KC_L, KC_SCLN,KC_QUOT,
+ KC_FN1, KC_N, KC_M, KC_COMM,KC_DOT, KC_SLSH,KC_RSFT,
+ KC_LEFT,KC_DOWN,KC_UP, KC_RGHT,KC_RGUI,
+ KC_RALT,KC_RCTL,
+ KC_PGUP,
+ KC_PGDN,KC_ENT, KC_SPC
+ ),
+[LOWER_LAYER] = KEYMAP( // layer 0 : default
+ // left hand
+ KC_EQL, KC_1, KC_2, KC_3, LALT(KC_TAB), KC_5, KC_ESC,
+ KC_BSLS,KC_Q, S(KC_W), KC_E, KC_R, KC_T, KC_FN2,
+ KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G,
+ KC_LSFT,KC_Z, KC_X, KC_C, KC_V, KC_B, KC_FN1,
+ KC_LGUI,KC_GRV, KC_BSLS,KC_LEFT,KC_RGHT,
+ KC_LCTL,KC_LALT,
+ KC_HOME,
+ KC_BSPC,KC_DEL, KC_END,
+ // right hand
+ KC_FN3, KC_6, KC_7, KC_8, KC_9, KC_0, KC_MINS,
+ KC_LBRC,KC_Y, KC_U, KC_I, KC_O, KC_P, KC_RBRC,
+ KC_H, KC_J, KC_K, KC_L, KC_SCLN,KC_QUOT,
+ KC_FN1, KC_N, KC_M, KC_COMM,KC_DOT, KC_SLSH,KC_RSFT,
+ KC_LEFT,KC_DOWN,KC_UP, KC_RGHT,KC_RGUI,
+ KC_RALT,KC_RCTL,
+ KC_PGUP,
+ KC_PGDN,KC_ENT, KC_SPC
+ )
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+
+ [1] = ACTION_LAYER_MOMENTARY(LOWER_LAYER), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(LOWER_LAYER), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(DEFAULT_LAYER),
+ [4] = ACTION_DEFAULT_LAYER_SET(COLEMAK_LAYER),
+ [5] = ACTION_DEFAULT_LAYER_SET(DVORAK_LAYER),
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ if (record->event.pressed) {
+ register_code(KC_RSFT);
+ } else {
+ unregister_code(KC_RSFT);
+ }
+ break;
+ }
+ return MACRO_NONE;
+};
+
+// Runs just one time when the keyboard initializes.
+void * matrix_init_user(void) {
+
+};
+
+// Runs constantly in the background, in a loop.
+void * matrix_scan_user(void) {
+ uint8_t layer = biton32(layer_state);
+
+ ergodox_board_led_off();
+ ergodox_left_led_1_off();
+ ergodox_left_led_2_off();
+ ergodox_left_led_3_off();
+ switch (layer) {
+ // TODO: Make this relevant to the ErgoDox EZ.
+ case 1:
+ // all
+ ergodox_left_led_1_on();
+ ergodox_left_led_2_on();
+ ergodox_left_led_3_on();
+ break;
+ case 2:
+ // blue
+ ergodox_left_led_2_on();
+ break;
+ case 8:
+ // blue and green
+ ergodox_left_led_2_on();
+ // break missed intentionally
+ case 3:
+ // green
+ ergodox_left_led_3_on();
+ break;
+ case 6:
+ ergodox_board_led_on();
+ // break missed intentionally
+ case 4:
+ case 5:
+ case 7:
+ // white
+ ergodox_left_led_1_on();
+ break;
+ case 9:
+ // white+green
+ ergodox_left_led_1_on();
+ ergodox_left_led_3_on();
+ break;
+ default:
+ // none
+ break;
+ }
+
+ mcp23018_status = ergodox_left_leds_update();
+};
diff --git a/keyboard/ergodox_ez/keymaps/keymap_ergodox_ez.c b/keyboard/ergodox_ez/keymaps/keymap_ergodox_ez.c
new file mode 100644
index 0000000000..bab16ece53
--- /dev/null
+++ b/keyboard/ergodox_ez/keymaps/keymap_ergodox_ez.c
@@ -0,0 +1,211 @@
+// TODO: Move all of this stuff into the default keymap, and then get rid of this file.
+#include "action_util.h"
+#include "action_layer.h"
+#define KC_SW0 KC_FN0
+#define DEBUG_ACTION
+
+static const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+
+ /* Keymap 0: Basic layer
+ *
+ * ,--------------------------------------------------. ,--------------------------------------------------.
+ * | = | 1 | 2 | 3 | 4 | 5 | LEFT | | RIGHT| 6 | 7 | 8 | 9 | 0 | - |
+ * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------|
+ * | Del | Q | W | E | R | T | Up | | Up | Y | U | I | O | P | \ |
+ * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------|
+ * | BkSp | A | S | D | F | G |------| |------| H | J | K | L |; / L2| ' |
+ * |--------+------+------+------+------+------| L1 | | L1 |------+------+------+------+------+--------|
+ * | LShift |Z/Ctrl| X | C | V | B | | | | N | M | , | . |//Ctrl| RShift |
+ * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------'
+ * |Grv/L1| ~L1 | TAB | Left | Right| | Up | Down | [ | ] | ~L1 |
+ * `----------------------------------' `----------------------------------'
+ * ,-------------. ,-------------.
+ * | Rclk | LGui | | Alt |Ctrl/Esc|
+ * ,------|------|------| |------+--------+------.
+ * | | | Home | | PgUp | | |
+ * | Space| Enter|------| |------| Tab |Enter |
+ * | | | End | | PgDn | | |
+ * `--------------------' `----------------------'
+ */
+
+
+ // Basic layer
+
+ KEYMAP(
+ EQL, 1, 2, 3, 4, 5, LEFT,
+ DEL, Q, W, E, R, T, UP,
+ BSPC, A, S, D, F, G,
+ LSFT, FN29, X, C, V, B, FN1,
+ FN30, FN4, TAB, LEFT, RIGHT,
+
+ BTN2,LGUI,
+ HOME,
+ SPC, ENT, END,
+ //RIGHT
+ RIGHT,6, 7, 8, 9, 0, MINS,
+ UP, Y, U, I, O, P, BSLS,
+ H, J, K, L, FN31, QUOT,
+ FN1, N, M, COMM, DOT, FN28, RSFT,
+ UP, DOWN, LBRC, RBRC, FN4,
+ LALT, FN27,
+ PGUP,
+ PGDN, TAB, ENT
+ ),
+
+ /* Keymap 1: Symbol Layer
+ *
+ * ,--------------------------------------------------. ,--------------------------------------------------.
+ * | Flash | F1 | F2 | F3 | F4 | F5 | | | | F6 | F7 | F8 | F9 | F10 | F11 |
+ * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------|
+ * | | ! | @ | { | } | | | | | | Up | 7 | 8 | 9 | * | F12 |
+ * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------|
+ * | : | # | $ | ( | ) | ` |------| |------| Down | 4 | 5 | 6 | + | |
+ * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------|
+ * | | % | ^ | [ | ] | ~ | | | | & | 1 | 2 | 3 | \ | |
+ * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------'
+ * | | | | | | | | . | 0 | = | |
+ * `----------------------------------' `----------------------------------'
+ * ,-------------. ,-------------.
+ * | | | | | |
+ * ,------|------|------| |------+------+------.
+ * | | | | | | | |
+ * | | |------| |------| | |
+ * | | | | | | | |
+ * `--------------------' `--------------------'
+ */
+ // SYMBOLS
+ KEYMAP(
+ FN0, F1, F2, F3, F4, F5, TRNS,
+ TRNS, FN7, FN8, FN23, FN24, FN18, TRNS,
+ FN22, FN9, FN10, FN15, FN16, GRV,
+ TRNS, FN11, FN12, LBRC, RBRC, FN17, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS,
+
+ TRNS, TRNS,
+ TRNS,
+ TRNS, TRNS, TRNS,
+ // right hand
+ TRNS, F6, F7, F8, F9, F10, F11,
+ TRNS, UP, 7, 8, 9, FN14, F12,
+ DOWN, 4, 5, 6, FN26, TRNS,
+ TRNS, FN13, 1, 2, 3, BSLS, TRNS,
+ TRNS,DOT, 0, EQL, TRNS,
+ TRNS, TRNS,
+ TRNS,
+ TRNS, TRNS, TRNS
+ ),
+ /* Keymap 2: Media and mouse keys
+ *
+ * ,--------------------------------------------------. ,--------------------------------------------------.
+ * | | | | | | | | | | | | | | | |
+ * |--------+------+------+------+------+-------------| |------+------+------+------+------+------+--------|
+ * | | | MsUp | | | | | | | | | | | | |
+ * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------|
+ * | |MsLeft|MsDown|MsRght| | |------| |------| | | | Play | | |
+ * |--------+------+------+------+------+------| | | |------+------+------+------+------+--------|
+ * | | | | | | | | | | | | Prev | Next | | |
+ * `--------+------+------+------+------+-------------' `-------------+------+------+------+------+--------'
+ * | | | | Lclk | Rclk | |VolUp |VolDn | | | |
+ * `----------------------------------' `----------------------------------'
+ * ,-------------. ,-------------.
+ * | | | | | |
+ * ,------|------|------| |------+------+------.
+ * | | | | | | | |
+ * | | |------| |------| | |
+ * | | | | | | | |
+ * `--------------------' `--------------------'
+ */
+ // MEDIA AND MOUSE
+ KEYMAP(
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, MS_U, TRNS, TRNS, TRNS, TRNS,
+ TRNS, MS_L, MS_D, MS_R, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, BTN3, BTN2,
+
+ TRNS, TRNS,
+ TRNS,
+ TRNS, TRNS, TRNS,
+ // right hand
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, MPLY, TRNS, TRNS,
+ TRNS, TRNS, TRNS, MPRV, MNXT, TRNS, TRNS,
+ VOLU, VOLD, TRNS, TRNS, TRNS,
+ TRNS, TRNS,
+ TRNS,
+ TRNS, TRNS, WBAK
+ ),
+};
+
+/* id for user defined functions */
+enum function_id {
+ TEENSY_KEY,
+};
+
+/*
+ * Fn action definition
+ */
+static const uint16_t PROGMEM fn_actions[] = {
+ [0] = ACTION_FUNCTION(TEENSY_KEY), // FN0 - Teensy key
+ [1] = ACTION_LAYER_INVERT(1, ON_RELEASE), // FN1 - Toggle 1
+ [2] = ACTION_LAYER_TOGGLE(2), // FN2 - Toggle 2
+ [3] = ACTION_LAYER_TOGGLE(3), // FN3 - Toggle 3
+ [4] = ACTION_LAYER_TAP_TOGGLE(1), // FN4 - Momentary Layer 1
+ [5] = ACTION_LAYER_MOMENTARY(2), // FN5 - Momentary L2
+
+ // SYMBOLS
+ ACTION_MODS_KEY(MOD_LSFT, KC_QUOT), // FN6 - "
+ ACTION_MODS_KEY(MOD_LSFT, KC_1), // FN7 - !
+ ACTION_MODS_KEY(MOD_LSFT, KC_2), // FN8 - @
+ ACTION_MODS_KEY(MOD_LSFT, KC_3), // FN9 - #
+ ACTION_MODS_KEY(MOD_LSFT, KC_4), // FN10 - $
+ ACTION_MODS_KEY(MOD_LSFT, KC_5), // FN11 - %
+ ACTION_MODS_KEY(MOD_LSFT, KC_6), // FN12 - ^
+ ACTION_MODS_KEY(MOD_LSFT, KC_7), // FN13 - &
+ ACTION_MODS_KEY(MOD_LSFT, KC_8), // FN14 - *
+ ACTION_MODS_KEY(MOD_LSFT, KC_9), // FN15 - (
+ ACTION_MODS_KEY(MOD_LSFT, KC_0), // FN16 - )
+ ACTION_MODS_KEY(MOD_LSFT, KC_GRV), // FN17 - ~
+ ACTION_MODS_KEY(MOD_LSFT, KC_BSLS), // FN18 - |
+ ACTION_MODS_KEY(MOD_LSFT, KC_MINS), // FN19 - _
+ ACTION_MODS_KEY(MOD_LSFT, KC_COMM), // FN20 - <
+ ACTION_MODS_KEY(MOD_LSFT, KC_DOT), // FN21 - >
+ ACTION_MODS_KEY(MOD_LSFT, KC_SCLN), // FN22 - :
+ ACTION_MODS_KEY(MOD_LSFT, KC_LBRC), // FN23 - {
+ ACTION_MODS_KEY(MOD_LSFT, KC_RBRC), // FN24 - }
+ ACTION_MODS_KEY(MOD_LSFT, KC_SLSH), // FN25 - ?
+ ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // FN26 - +
+
+ ACTION_MODS_TAP_KEY(MOD_LCTL, KC_ESC), // FN27 - Control/esc on tap
+ ACTION_MODS_TAP_KEY(MOD_LCTL, KC_SLSH), // FN28 - slash becomes Ctrl when held (right pinky)
+ ACTION_MODS_TAP_KEY(MOD_LCTL, KC_Z), // FN29 - z becomes Ctrl when held (left pinky)
+
+ // Fancy tapping/toggling
+ ACTION_LAYER_TAP_KEY(1, KC_GRV), // FN30 - Layer 1 when holding backtick key
+ ACTION_LAYER_TAP_KEY(2, KC_SCLN), // FN31 - Layer 2 when holding semicolon key
+
+
+};
+
+void action_function(keyrecord_t *event, uint8_t id, uint8_t opt)
+{
+ print("action_function called\n");
+ print("id = "); phex(id); print("\n");
+ print("opt = "); phex(opt); print("\n");
+ if (id == TEENSY_KEY) {
+ clear_keyboard();
+ print("\n\nJump to bootloader... ");
+ _delay_ms(250);
+ bootloader_jump(); // should not return
+ print("not supported.\n");
+ }
+}
+
+void * matrix_init_user(void) {
+
+};
+
+void * matrix_scan_user(void) {
+
+};
diff --git a/keyboard/ergodox_ez/matrix.c b/keyboard/ergodox_ez/matrix.c
new file mode 100644
index 0000000000..09380d3083
--- /dev/null
+++ b/keyboard/ergodox_ez/matrix.c
@@ -0,0 +1,348 @@
+/*
+
+Note for ErgoDox EZ customizers: Here be dragons!
+This is not a file you want to be messing with.
+All of the interesting stuff for you is under keymaps/ :)
+Love, Erez
+
+Copyright 2013 Oleg Kostyuk <cub.uanic@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+/*
+ * scan matrix
+ */
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/io.h>
+#include <util/delay.h>
+#include "action_layer.h"
+#include "print.h"
+#include "debug.h"
+#include "util.h"
+#include "matrix.h"
+#include "ergodox_ez.h"
+#include "i2cmaster.h"
+#ifdef DEBUG_MATRIX_SCAN_RATE
+#include "timer.h"
+#endif
+
+#ifndef DEBOUNCE
+# define DEBOUNCE 5
+#endif
+static uint8_t debouncing = DEBOUNCE;
+
+/* matrix state(1:on, 0:off) */
+static matrix_row_t matrix[MATRIX_ROWS];
+static matrix_row_t matrix_debouncing[MATRIX_ROWS];
+
+static matrix_row_t read_cols(uint8_t row);
+static void init_cols(void);
+static void unselect_rows();
+static void select_row(uint8_t row);
+
+static uint8_t mcp23018_reset_loop;
+
+#ifdef DEBUG_MATRIX_SCAN_RATE
+uint32_t matrix_timer;
+uint32_t matrix_scan_count;
+#endif
+
+
+__attribute__ ((weak))
+void * matrix_init_kb(void) {
+};
+
+__attribute__ ((weak))
+void * matrix_scan_kb(void) {
+};
+
+inline
+uint8_t matrix_rows(void)
+{
+ return MATRIX_ROWS;
+}
+
+inline
+uint8_t matrix_cols(void)
+{
+ return MATRIX_COLS;
+}
+
+void matrix_init(void)
+{
+ // initialize row and col
+
+ mcp23018_status = init_mcp23018();
+
+
+ unselect_rows();
+ init_cols();
+
+ // initialize matrix state: all keys off
+ for (uint8_t i=0; i < MATRIX_ROWS; i++) {
+ matrix[i] = 0;
+ matrix_debouncing[i] = 0;
+ }
+
+#ifdef DEBUG_MATRIX_SCAN_RATE
+ matrix_timer = timer_read32();
+ matrix_scan_count = 0;
+#endif
+
+ if (matrix_init_kb) {
+ (*matrix_init_kb)();
+ }
+
+}
+
+uint8_t matrix_scan(void)
+{
+ if (mcp23018_status) { // if there was an error
+ if (++mcp23018_reset_loop == 0) {
+ // since mcp23018_reset_loop is 8 bit - we'll try to reset once in 255 matrix scans
+ // this will be approx bit more frequent than once per second
+ print("trying to reset mcp23018\n");
+ mcp23018_status = init_mcp23018();
+ if (mcp23018_status) {
+ print("left side not responding\n");
+ } else {
+ print("left side attached\n");
+ ergodox_blink_all_leds();
+ }
+ }
+ }
+
+#ifdef DEBUG_MATRIX_SCAN_RATE
+ matrix_scan_count++;
+
+ uint32_t timer_now = timer_read32();
+ if (TIMER_DIFF_32(timer_now, matrix_timer)>1000) {
+ print("matrix scan frequency: ");
+ pdec(matrix_scan_count);
+ print("\n");
+
+ matrix_timer = timer_now;
+ matrix_scan_count = 0;
+ }
+#endif
+
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ select_row(i);
+ matrix_row_t cols = read_cols(i);
+ if (matrix_debouncing[i] != cols) {
+ matrix_debouncing[i] = cols;
+ if (debouncing) {
+ debug("bounce!: "); debug_hex(debouncing); debug("\n");
+ }
+ debouncing = DEBOUNCE;
+ }
+ unselect_rows();
+ }
+
+ if (debouncing) {
+ if (--debouncing) {
+ _delay_ms(1);
+ } else {
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ matrix[i] = matrix_debouncing[i];
+ }
+ }
+ }
+
+
+ if (matrix_scan_kb) {
+ (*matrix_scan_kb)();
+ }
+
+ return 1;
+}
+
+bool matrix_is_modified(void)
+{
+ if (debouncing) return false;
+ return true;
+}
+
+inline
+bool matrix_is_on(uint8_t row, uint8_t col)
+{
+ return (matrix[row] & ((matrix_row_t)1<<col));
+}
+
+inline
+matrix_row_t matrix_get_row(uint8_t row)
+{
+ return matrix[row];
+}
+
+void matrix_print(void)
+{
+ print("\nr/c 0123456789ABCDEF\n");
+ for (uint8_t row = 0; row < MATRIX_ROWS; row++) {
+ phex(row); print(": ");
+ pbin_reverse16(matrix_get_row(row));
+ print("\n");
+ }
+}
+
+uint8_t matrix_key_count(void)
+{
+ uint8_t count = 0;
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ count += bitpop16(matrix[i]);
+ }
+ return count;
+}
+
+/* Column pin configuration
+ *
+ * Teensy
+ * col: 0 1 2 3 4 5
+ * pin: F0 F1 F4 F5 F6 F7
+ *
+ * MCP23018
+ * col: 0 1 2 3 4 5
+ * pin: B5 B4 B3 B2 B1 B0
+ */
+static void init_cols(void)
+{
+ // init on mcp23018
+ // not needed, already done as part of init_mcp23018()
+
+ // init on teensy
+ // Input with pull-up(DDR:0, PORT:1)
+ DDRF &= ~(1<<7 | 1<<6 | 1<<5 | 1<<4 | 1<<1 | 1<<0);
+ PORTF |= (1<<7 | 1<<6 | 1<<5 | 1<<4 | 1<<1 | 1<<0);
+}
+
+static matrix_row_t read_cols(uint8_t row)
+{
+ if (row < 7) {
+ if (mcp23018_status) { // if there was an error
+ return 0;
+ } else {
+ uint8_t data = 0;
+ mcp23018_status = i2c_start(I2C_ADDR_WRITE); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(GPIOB); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_start(I2C_ADDR_READ); if (mcp23018_status) goto out;
+ data = i2c_readNak();
+ data = ~data;
+ out:
+ i2c_stop();
+ return data;
+ }
+ } else {
+ _delay_us(30); // without this wait read unstable value.
+ // read from teensy
+ return
+ (PINF&(1<<0) ? 0 : (1<<0)) |
+ (PINF&(1<<1) ? 0 : (1<<1)) |
+ (PINF&(1<<4) ? 0 : (1<<2)) |
+ (PINF&(1<<5) ? 0 : (1<<3)) |
+ (PINF&(1<<6) ? 0 : (1<<4)) |
+ (PINF&(1<<7) ? 0 : (1<<5)) ;
+ }
+}
+
+/* Row pin configuration
+ *
+ * Teensy
+ * row: 7 8 9 10 11 12 13
+ * pin: B0 B1 B2 B3 D2 D3 C6
+ *
+ * MCP23018
+ * row: 0 1 2 3 4 5 6
+ * pin: A0 A1 A2 A3 A4 A5 A6
+ */
+static void unselect_rows(void)
+{
+ // unselect on mcp23018
+ if (mcp23018_status) { // if there was an error
+ // do nothing
+ } else {
+ // set all rows hi-Z : 1
+ mcp23018_status = i2c_start(I2C_ADDR_WRITE); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(GPIOA); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write( 0xFF
+ & ~(ergodox_left_led_3<<LEFT_LED_3_SHIFT)
+ ); if (mcp23018_status) goto out;
+ out:
+ i2c_stop();
+ }
+
+ // unselect on teensy
+ // Hi-Z(DDR:0, PORT:0) to unselect
+ DDRB &= ~(1<<0 | 1<<1 | 1<<2 | 1<<3);
+ PORTB &= ~(1<<0 | 1<<1 | 1<<2 | 1<<3);
+ DDRD &= ~(1<<2 | 1<<3);
+ PORTD &= ~(1<<2 | 1<<3);
+ DDRC &= ~(1<<6);
+ PORTC &= ~(1<<6);
+}
+
+static void select_row(uint8_t row)
+{
+ if (row < 7) {
+ // select on mcp23018
+ if (mcp23018_status) { // if there was an error
+ // do nothing
+ } else {
+ // set active row low : 0
+ // set other rows hi-Z : 1
+ mcp23018_status = i2c_start(I2C_ADDR_WRITE); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write(GPIOA); if (mcp23018_status) goto out;
+ mcp23018_status = i2c_write( 0xFF & ~(1<<row)
+ & ~(ergodox_left_led_3<<LEFT_LED_3_SHIFT)
+ ); if (mcp23018_status) goto out;
+ out:
+ i2c_stop();
+ }
+ } else {
+ // select on teensy
+ // Output low(DDR:1, PORT:0) to select
+ switch (row) {
+ case 7:
+ DDRB |= (1<<0);
+ PORTB &= ~(1<<0);
+ break;
+ case 8:
+ DDRB |= (1<<1);
+ PORTB &= ~(1<<1);
+ break;
+ case 9:
+ DDRB |= (1<<2);
+ PORTB &= ~(1<<2);
+ break;
+ case 10:
+ DDRB |= (1<<3);
+ PORTB &= ~(1<<3);
+ break;
+ case 11:
+ DDRD |= (1<<2);
+ PORTD &= ~(1<<3);
+ break;
+ case 12:
+ DDRD |= (1<<3);
+ PORTD &= ~(1<<3);
+ break;
+ case 13:
+ DDRC |= (1<<6);
+ PORTC &= ~(1<<6);
+ break;
+ }
+ }
+}
+
diff --git a/keyboard/ergodox_ez/twimaster.c b/keyboard/ergodox_ez/twimaster.c
new file mode 100644
index 0000000000..f91c08e6e4
--- /dev/null
+++ b/keyboard/ergodox_ez/twimaster.c
@@ -0,0 +1,208 @@
+/*************************************************************************
+* Title: I2C master library using hardware TWI interface
+* Author: Peter Fleury <pfleury@gmx.ch> http://jump.to/fleury
+* File: $Id: twimaster.c,v 1.3 2005/07/02 11:14:21 Peter Exp $
+* Software: AVR-GCC 3.4.3 / avr-libc 1.2.3
+* Target: any AVR device with hardware TWI
+* Usage: API compatible with I2C Software Library i2cmaster.h
+**************************************************************************/
+#include <inttypes.h>
+#include <compat/twi.h>
+
+#include <i2cmaster.h>
+
+
+/* define CPU frequency in Mhz here if not defined in Makefile */
+#ifndef F_CPU
+#define F_CPU 16000000UL
+#endif
+
+/* I2C clock in Hz */
+#define SCL_CLOCK 400000L
+
+
+/*************************************************************************
+ Initialization of the I2C bus interface. Need to be called only once
+*************************************************************************/
+void i2c_init(void)
+{
+ /* initialize TWI clock
+ * minimal values in Bit Rate Register (TWBR) and minimal Prescaler
+ * bits in the TWI Status Register should give us maximal possible
+ * I2C bus speed - about 444 kHz
+ *
+ * for more details, see 20.5.2 in ATmega16/32 secification
+ */
+
+ TWSR = 0; /* no prescaler */
+ TWBR = 10; /* must be >= 10 for stable operation */
+
+}/* i2c_init */
+
+
+/*************************************************************************
+ Issues a start condition and sends address and transfer direction.
+ return 0 = device accessible, 1= failed to access device
+*************************************************************************/
+unsigned char i2c_start(unsigned char address)
+{
+ uint8_t twst;
+
+ // send START condition
+ TWCR = (1<<TWINT) | (1<<TWSTA) | (1<<TWEN);
+
+ // wait until transmission completed
+ while(!(TWCR & (1<<TWINT)));
+
+ // check value of TWI Status Register. Mask prescaler bits.
+ twst = TW_STATUS & 0xF8;
+ if ( (twst != TW_START) && (twst != TW_REP_START)) return 1;
+
+ // send device address
+ TWDR = address;
+ TWCR = (1<<TWINT) | (1<<TWEN);
+
+ // wail until transmission completed and ACK/NACK has been received
+ while(!(TWCR & (1<<TWINT)));
+
+ // check value of TWI Status Register. Mask prescaler bits.
+ twst = TW_STATUS & 0xF8;
+ if ( (twst != TW_MT_SLA_ACK) && (twst != TW_MR_SLA_ACK) ) return 1;
+
+ return 0;
+
+}/* i2c_start */
+
+
+/*************************************************************************
+ Issues a start condition and sends address and transfer direction.
+ If device is busy, use ack polling to wait until device is ready
+
+ Input: address and transfer direction of I2C device
+*************************************************************************/
+void i2c_start_wait(unsigned char address)
+{
+ uint8_t twst;
+
+
+ while ( 1 )
+ {
+ // send START condition
+ TWCR = (1<<TWINT) | (1<<TWSTA) | (1<<TWEN);
+
+ // wait until transmission completed
+ while(!(TWCR & (1<<TWINT)));
+
+ // check value of TWI Status Register. Mask prescaler bits.
+ twst = TW_STATUS & 0xF8;
+ if ( (twst != TW_START) && (twst != TW_REP_START)) continue;
+
+ // send device address
+ TWDR = address;
+ TWCR = (1<<TWINT) | (1<<TWEN);
+
+ // wail until transmission completed
+ while(!(TWCR & (1<<TWINT)));
+
+ // check value of TWI Status Register. Mask prescaler bits.
+ twst = TW_STATUS & 0xF8;
+ if ( (twst == TW_MT_SLA_NACK )||(twst ==TW_MR_DATA_NACK) )
+ {
+ /* device busy, send stop condition to terminate write operation */
+ TWCR = (1<<TWINT) | (1<<TWEN) | (1<<TWSTO);
+
+ // wait until stop condition is executed and bus released
+ while(TWCR & (1<<TWSTO));
+
+ continue;
+ }
+ //if( twst != TW_MT_SLA_ACK) return 1;
+ break;
+ }
+
+}/* i2c_start_wait */
+
+
+/*************************************************************************
+ Issues a repeated start condition and sends address and transfer direction
+
+ Input: address and transfer direction of I2C device
+
+ Return: 0 device accessible
+ 1 failed to access device
+*************************************************************************/
+unsigned char i2c_rep_start(unsigned char address)
+{
+ return i2c_start( address );
+
+}/* i2c_rep_start */
+
+
+/*************************************************************************
+ Terminates the data transfer and releases the I2C bus
+*************************************************************************/
+void i2c_stop(void)
+{
+ /* send stop condition */
+ TWCR = (1<<TWINT) | (1<<TWEN) | (1<<TWSTO);
+
+ // wait until stop condition is executed and bus released
+ while(TWCR & (1<<TWSTO));
+
+}/* i2c_stop */
+
+
+/*************************************************************************
+ Send one byte to I2C device
+
+ Input: byte to be transfered
+ Return: 0 write successful
+ 1 write failed
+*************************************************************************/
+unsigned char i2c_write( unsigned char data )
+{
+ uint8_t twst;
+
+ // send data to the previously addressed device
+ TWDR = data;
+ TWCR = (1<<TWINT) | (1<<TWEN);
+
+ // wait until transmission completed
+ while(!(TWCR & (1<<TWINT)));
+
+ // check value of TWI Status Register. Mask prescaler bits
+ twst = TW_STATUS & 0xF8;
+ if( twst != TW_MT_DATA_ACK) return 1;
+ return 0;
+
+}/* i2c_write */
+
+
+/*************************************************************************
+ Read one byte from the I2C device, request more data from device
+
+ Return: byte read from I2C device
+*************************************************************************/
+unsigned char i2c_readAck(void)
+{
+ TWCR = (1<<TWINT) | (1<<TWEN) | (1<<TWEA);
+ while(!(TWCR & (1<<TWINT)));
+
+ return TWDR;
+
+}/* i2c_readAck */
+
+
+/*************************************************************************
+ Read one byte from the I2C device, read is followed by a stop condition
+
+ Return: byte read from I2C device
+*************************************************************************/
+unsigned char i2c_readNak(void)
+{
+ TWCR = (1<<TWINT) | (1<<TWEN);
+ while(!(TWCR & (1<<TWINT)));
+
+ return TWDR;
+
+}/* i2c_readNak */
diff --git a/keyboard/gh60/Makefile b/keyboard/gh60/Makefile
index 083b87c30a..6b0f1a0e8d 100644
--- a/keyboard/gh60/Makefile
+++ b/keyboard/gh60/Makefile
@@ -55,7 +55,7 @@ SRC = keymap_common.c \
ifdef KEYMAP
SRC := keymap_$(KEYMAP).c $(SRC)
else
- SRC := keymap_poker.c $(SRC)
+ SRC := keymap_planck.c $(SRC)
endif
CONFIG_H = config.h
diff --git a/keyboard/gh60/keymap_common.h b/keyboard/gh60/keymap_common.h
index 896badd748..7c95fb8e7c 100644
--- a/keyboard/gh60/keymap_common.h
+++ b/keyboard/gh60/keymap_common.h
@@ -38,47 +38,15 @@ extern const uint16_t fn_actions[];
* K2C, K31 and K3C are extra keys for ISO
*/
#define KEYMAP( \
- K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, K0C, K0D, \
- K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, K1C, K1D, \
- K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, K2C, K2D, \
- K30, K31, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3B, K3C, K3D, \
- K40, K41, K42, K45, K49, K4A, K4B, K4C, K4D \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K36, K37, K38, K39, K3A, K3B \
) { \
- { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B, KC_##K0C, KC_##K0D }, \
- { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B, KC_##K1C, KC_##K1D }, \
- { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B, KC_##K2C, KC_##K2D }, \
- { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_##K36, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B, KC_##K3C, KC_##K3D }, \
- { KC_##K40, KC_##K41, KC_##K42, KC_NO, KC_NO, KC_##K45, KC_NO, KC_NO, KC_NO, KC_##K49, KC_##K4A, KC_##K4B, KC_##K4C, KC_##K4D } \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_NO, KC_##K36, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B } \
}
-/* ANSI valiant. No extra keys for ISO */
-#define KEYMAP_ANSI( \
- K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, K0C, K0D, \
- K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, K1C, K1D, \
- K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, K2D, \
- K30, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3B, K3D, \
- K40, K41, K42, K45, K4A, K4B, K4C, K4D \
-) KEYMAP( \
- K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, K0C, K0D, \
- K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, K1C, K1D, \
- K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, NO, K2D, \
- K30, NO, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3B, NO, K3D, \
- K40, K41, K42, K45, NO, K4A, K4B, K4C, K4D \
-)
-
-
-#define KEYMAP_HHKB( \
- K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, K0C, K0D, K49,\
- K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, K1C, K1D, \
- K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, K2D, \
- K30, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3B, K3D, K3C, \
- K40, K41, K42, K45, K4A, K4B, K4C, K4D \
-) KEYMAP( \
- K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, K0C, K0D, \
- K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, K1C, K1D, \
- K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, NO, K2D, \
- K30, NO, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3B, K3C, K3D, \
- K40, K41, K42, K45, K49, K4A, K4B, K4C, K4D \
-)
-
#endif
diff --git a/keyboard/gh60/led.c b/keyboard/gh60/led.c
index 62abcd79da..7c98510801 100644
--- a/keyboard/gh60/led.c
+++ b/keyboard/gh60/led.c
@@ -22,13 +22,13 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
void led_set(uint8_t usb_led)
{
- if (usb_led & (1<<USB_LED_CAPS_LOCK)) {
- // output low
- DDRB |= (1<<2);
- PORTB &= ~(1<<2);
+ if (usb_led & (1<<USB_LED_FUNCTION)) {
+ // Output high.
+ DDRF |= (1<<0);
+ PORTF |= (1<<0);
} else {
- // Hi-Z
- DDRB &= ~(1<<2);
- PORTB &= ~(1<<2);
+ // Output low.
+ DDRF &= ~(1<<0);
+ PORTF &= ~(1<<0);
}
}
diff --git a/keyboard/gh60/matrix.c b/keyboard/gh60/matrix.c
index a61215152c..720ac30043 100644
--- a/keyboard/gh60/matrix.c
+++ b/keyboard/gh60/matrix.c
@@ -22,6 +22,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
#include <stdbool.h>
#include <avr/io.h>
#include <util/delay.h>
+#include "action_layer.h"
#include "print.h"
#include "debug.h"
#include "util.h"
@@ -29,7 +30,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
#ifndef DEBOUNCE
-# define DEBOUNCE 5
+# define DEBOUNCE 10
#endif
static uint8_t debouncing = DEBOUNCE;
@@ -94,6 +95,19 @@ uint8_t matrix_scan(void)
}
}
+ uint8_t layer = biton32(layer_state);
+ switch (layer) {
+ case 1:
+ case 2:
+ DDRC |= (1<<7);
+ PORTC |= (1<<7);
+ break;
+ case 0:
+ DDRC &= ~(1<<7);
+ PORTC &= ~(1<<7);
+ break;
+ }
+
return 1;
}
@@ -135,77 +149,67 @@ uint8_t matrix_key_count(void)
}
/* Column pin configuration
- * col: 0 1 2 3 4 5 6 7 8 9 10 11 12 13
- * pin: F0 F1 E6 C7 C6 B6 D4 B1 B0 B5 B4 D7 D6 B3 (Rev.A)
- * pin: B7 (Rev.B)
+ * col: 0 1 2 3 4 5 6 7 8 9 10 11
+ * pin: F0 F1 F4 F5 F6 F7 B6 B5 B4 D7 D5 D4
*/
-static void init_cols(void)
+
+static void init_cols(void)
{
- // Input with pull-up(DDR:0, PORT:1)
- DDRF &= ~(1<<0 | 1<<1);
- PORTF |= (1<<0 | 1<<1);
- DDRE &= ~(1<<6);
- PORTE |= (1<<6);
- DDRD &= ~(1<<7 | 1<<6 | 1<<4);
- PORTD |= (1<<7 | 1<<6 | 1<<4);
- DDRC &= ~(1<<7 | 1<<6);
- PORTC |= (1<<7 | 1<<6);
- DDRB &= ~(1<<7 | 1<<6 | 1<< 5 | 1<<4 | 1<<3 | 1<<1 | 1<<0);
- PORTB |= (1<<7 | 1<<6 | 1<< 5 | 1<<4 | 1<<3 | 1<<1 | 1<<0);
+ DDRF &= ~(1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+ PORTF |= (1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+ DDRD &= ~(1<<0);
+ PORTD |= (1<<0);
+ DDRB &= ~(1<<0 | 1<<1 | 1<<2 | 1<<3 | 1<<7);
+ PORTB |= (1<<0 | 1<<1 | 1<<2 | 1<<3 | 1<<7);
}
static matrix_row_t read_cols(void)
{
- return (PINF&(1<<0) ? 0 : (1<<0)) |
- (PINF&(1<<1) ? 0 : (1<<1)) |
- (PINE&(1<<6) ? 0 : (1<<2)) |
- (PINC&(1<<7) ? 0 : (1<<3)) |
- (PINC&(1<<6) ? 0 : (1<<4)) |
- (PINB&(1<<6) ? 0 : (1<<5)) |
- (PIND&(1<<4) ? 0 : (1<<6)) |
- (PINB&(1<<1) ? 0 : (1<<7)) |
- ((PINB&(1<<0) && PINB&(1<<7)) ? 0 : (1<<8)) | // Rev.A and B
- (PINB&(1<<5) ? 0 : (1<<9)) |
- (PINB&(1<<4) ? 0 : (1<<10)) |
- (PIND&(1<<7) ? 0 : (1<<11)) |
- (PIND&(1<<6) ? 0 : (1<<12)) |
- (PINB&(1<<3) ? 0 : (1<<13));
+ return (PINB&(1<<0) ? 0 : (1<< 0)) |
+ (PINB&(1<<1) ? 0 : (1<< 1)) |
+ (PINB&(1<<2) ? 0 : (1<< 2)) |
+ (PINB&(1<<3) ? 0 : (1<< 3)) |
+ (PINB&(1<<7) ? 0 : (1<< 4)) |
+ (PIND&(1<<0) ? 0 : (1<< 5)) |
+ (PINF&(1<<7) ? 0 : (1<< 6)) |
+ (PINF&(1<<6) ? 0 : (1<< 7)) |
+ (PINF&(1<<5) ? 0 : (1<< 8)) |
+ (PINF&(1<<4) ? 0 : (1<< 9)) |
+ (PINF&(1<<1) ? 0 : (1<<10)) |
+ (PINF&(1<<0) ? 0 : (1<<11));
}
/* Row pin configuration
- * row: 0 1 2 3 4
- * pin: D0 D1 D2 D3 D5
+ * row: 0 1 2 3
+ * pin: B0 B1 B2 B3
*/
static void unselect_rows(void)
{
// Hi-Z(DDR:0, PORT:0) to unselect
- DDRD &= ~0b00101111;
- PORTD &= ~0b00101111;
+ DDRB &= ~0b01110000;
+ PORTB &= ~0b01110000;
+ DDRD &= ~0b10000000;
+ PORTD &= ~0b10000000;
}
static void select_row(uint8_t row)
{
- // Output low(DDR:1, PORT:0) to select
switch (row) {
case 0:
- DDRD |= (1<<0);
- PORTD &= ~(1<<0);
+ DDRB |= (1<<6);
+ PORTB &= ~(1<<6);
break;
case 1:
- DDRD |= (1<<1);
- PORTD &= ~(1<<1);
+ DDRB |= (1<<5);
+ PORTB &= ~(1<<5);
break;
case 2:
- DDRD |= (1<<2);
- PORTD &= ~(1<<2);
+ DDRB |= (1<<4);
+ PORTB &= ~(1<<4);
break;
case 3:
- DDRD |= (1<<3);
- PORTD &= ~(1<<3);
- break;
- case 4:
- DDRD |= (1<<5);
- PORTD &= ~(1<<5);
+ DDRD |= (1<<7);
+ PORTD &= ~(1<<7);
break;
}
}
diff --git a/keyboard/planck/Makefile b/keyboard/planck/Makefile
new file mode 100644
index 0000000000..fc26905d80
--- /dev/null
+++ b/keyboard/planck/Makefile
@@ -0,0 +1,140 @@
+#----------------------------------------------------------------------------
+# On command line:
+#
+# make all = Make software.
+#
+# make clean = Clean out built project files.
+#
+# make coff = Convert ELF to AVR COFF.
+#
+# make extcoff = Convert ELF to AVR Extended COFF.
+#
+# make program = Download the hex file to the device.
+# Please customize your programmer settings(PROGRAM_CMD)
+#
+# make teensy = Download the hex file to the device, using teensy_loader_cli.
+# (must have teensy_loader_cli installed).
+#
+# make dfu = Download the hex file to the device, using dfu-programmer (must
+# have dfu-programmer installed).
+#
+# make flip = Download the hex file to the device, using Atmel FLIP (must
+# have Atmel FLIP installed).
+#
+# make dfu-ee = Download the eeprom file to the device, using dfu-programmer
+# (must have dfu-programmer installed).
+#
+# make flip-ee = Download the eeprom file to the device, using Atmel FLIP
+# (must have Atmel FLIP installed).
+#
+# make debug = Start either simulavr or avarice as specified for debugging,
+# with avr-gdb or avr-insight as the front end for debugging.
+#
+# make filename.s = Just compile filename.c into the assembler code only.
+#
+# make filename.i = Create a preprocessed source file for use in submitting
+# bug reports to the GCC project.
+#
+# To rebuild project do "make clean" then "make all".
+#----------------------------------------------------------------------------
+
+# Target file name (without extension).
+TARGET = planck
+
+
+# Directory common source filess exist
+TOP_DIR = ../..
+TMK_DIR = ../../tmk_core
+
+# Directory keyboard dependent files exist
+TARGET_DIR = .
+
+# # project specific files
+SRC = planck.c \
+ backlight.c
+
+ifdef KEYMAP
+ SRC := keymaps/keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := keymaps/keymap_default.c $(SRC)
+endif
+
+CONFIG_H = config.h
+
+# MCU name
+#MCU = at90usb1287
+MCU = atmega32u4
+
+# Processor frequency.
+# This will define a symbol, F_CPU, in all source code files equal to the
+# processor frequency in Hz. You can then use this symbol in your source code to
+# calculate timings. Do NOT tack on a 'UL' at the end, this will be done
+# automatically to create a 32-bit value in your source code.
+#
+# This will be an integer division of F_USB below, as it is sourced by
+# F_USB after it has run through any CPU prescalers. Note that this value
+# does not *change* the processor frequency - it should merely be updated to
+# reflect the processor speed set externally so that the code can use accurate
+# software delays.
+F_CPU = 16000000
+
+
+#
+# LUFA specific
+#
+# Target architecture (see library "Board Types" documentation).
+ARCH = AVR8
+
+# Input clock frequency.
+# This will define a symbol, F_USB, in all source code files equal to the
+# input clock frequency (before any prescaling is performed) in Hz. This value may
+# differ from F_CPU if prescaling is used on the latter, and is required as the
+# raw input clock is fed directly to the PLL sections of the AVR for high speed
+# clock generation for the USB and other AVR subsections. Do NOT tack on a 'UL'
+# at the end, this will be done automatically to create a 32-bit value in your
+# source code.
+#
+# If no clock division is performed on the input clock inside the AVR (via the
+# CPU clock adjust registers or the clock division fuses), this will be equal to F_CPU.
+F_USB = $(F_CPU)
+
+# Interrupt driven control endpoint task(+60)
+OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT
+
+
+# Boot Section Size in *bytes*
+# Teensy halfKay 512
+# Teensy++ halfKay 1024
+# Atmel DFU loader 4096
+# LUFA bootloader 4096
+# USBaspLoader 2048
+OPT_DEFS += -DBOOTLOADER_SIZE=4096
+
+
+# Build Options
+# comment out to disable the options.
+#
+BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration(+1000)
+MOUSEKEY_ENABLE = yes # Mouse keys(+4700)
+EXTRAKEY_ENABLE = yes # Audio control and System control(+450)
+CONSOLE_ENABLE = yes # Console for debug(+400)
+COMMAND_ENABLE = yes # Commands for debug and configuration
+# Do not enable SLEEP_LED_ENABLE. it uses the same timer as BACKLIGHT_ENABLE
+# SLEEP_LED_ENABLE = yes # Breathing sleep LED during USB suspend
+# NKRO_ENABLE = yes # USB Nkey Rollover - not yet supported in LUFA
+BACKLIGHT_ENABLE = yes # Enable keyboard backlight functionality
+MIDI_ENABLE = YES # MIDI controls
+# UNICODE_ENABLE = YES # Unicode
+BLUETOOTH_ENABLE = yes # Enable Bluetooth with the Adafruit EZ-Key HID
+
+
+# Optimize size but this may cause error "relocation truncated to fit"
+#EXTRALDFLAGS = -Wl,--relax
+
+# Search Path
+VPATH += $(TARGET_DIR)
+VPATH += $(TOP_DIR)
+VPATH += $(TMK_DIR)
+
+include $(TOP_DIR)/quantum.mk
+
diff --git a/keyboard/planck/PCB_GUIDE.md b/keyboard/planck/PCB_GUIDE.md
new file mode 100644
index 0000000000..10b86bb3b2
--- /dev/null
+++ b/keyboard/planck/PCB_GUIDE.md
@@ -0,0 +1,114 @@
+# Planck Firmware Guide
+
+## Setting up the environment
+
+### Windows
+1. Install [WinAVR Tools](http://sourceforge.net/projects/winavr/) for AVR GCC compiler.
+2. Install [DFU-Programmer][dfu-prog] (the -win one).
+3. Start DFU bootloader on the chip first time you will see 'Found New Hardware Wizard' to install driver. If you install device driver properly you can find chip name like 'ATmega32U4' under 'LibUSB-Win32 Devices' tree on 'Device Manager'. If not you will need to update its driver on 'Device Manager' to the `dfu-programmer` driver.
+
+### Mac
+1. Install Xcode from the App Store.
+2. Install the Command Line Tools from `Xcode->Preferences->Downloads`.
+3. Install [DFU-Programmer][dfu-prog].
+
+### Linux
+1. Install AVR GCC with your favorite package manager.
+2. Install [DFU-Programmer][dfu-prog].
+
+## Verify Your Installation
+1. Clone the following repository: https://github.com/jackhumbert/qmk_firmware
+2. Open a Terminal and `cd` into `qmk_firmware/keyboard/planck`
+3. Run `make`. This should output a lot of information about the build process.
+
+## Using the built-in functions
+
+Here is a list of some of the functions available from the command line:
+
+* `make clean`: clean the environment - may be required in-between builds
+* `make`: compile the code
+* `make KEYMAP=<keymap>`: compile with the extended keymap file `extended_keymaps/extended_keymap_<keymap>.c`
+* `make dfu`: build and flash the layout to the PCB
+* `make dfu-force`: build and force-flash the layout to the PCB (may be require for first flash)
+
+Generally, the instructions to flash the PCB are as follows:
+
+1. Make changes to the appropriate keymap file
+2. Save the file
+3. `make clean`
+4. Press the reset button on the PCB/press the key with the `RESET` keycode
+5. `make <arguments> dfu` - use the necessary `KEYMAP=<keymap>` and/or `COMMON=true` arguments here.
+
+## Quantum MK Firmware
+
+### Keymap
+
+Unlike the other keymaps, prefixing the keycodes with `KC_` is required. A full list of the keycodes is available [here](https://github.com/jackhumbert/qmk_firmware/blob/master/doc/keycode.txt). For the keycodes available only in the extended keymap, see this [header file](https://github.com/jackhumbert/qmk_firmware/blob/master/quantum/keymap_common.h).
+
+You can use modifiers with keycodes like this:
+
+ LCTL(KC_C)
+
+Which will generate Ctrl+c. These are daisy-chainable, meaning you can do things like:
+
+ LCTL(LALT(KC_C))
+
+That will generate Ctrl+Alt+c. The entire list of these functions is here:
+
+* `LCTL()`: Left control
+* `LSFT()` / `S()`: Left shift
+* `LALT()`: Left alt/opt
+* `LGUI()`: Left win/cmd
+* `RCTL()`: Right control
+* `RSFT()`: Right shift
+* `RALT()`: Right alt/opt
+* `RGUI()`: Right win/cmd
+
+`S(KC_1)`-like entries are useful in writing keymaps for the Planck.
+
+### Other keycodes
+
+A number of other keycodes have been added that you may find useful:
+
+* `CM_<key>`: the Colemak equivalent of a key (in place of `KC_<key>`), when using Colemak in software (`CM_O` generates `KC_SCLN`)
+* `RESET`: jump to bootloader for flashing (same as press the reset button)
+* `BL_STEP`: step through the backlight brightnesses
+* `BL_<0-15>`: set backlight brightness to 0-15
+* `BL_DEC`: lower the backlight brightness
+* `BL_INC`: raise the backlight brightness
+* `BL_TOGG`: toggle the backlight on/off
+
+### Function layers
+
+The extended keymap extends the number of function layers from 32 to the near-infinite value of 256. Rather than using `FN<num>` notation (still available, but limited to `FN0`-`FN31`), you can use the `FUNC(<num>)` notation. `F(<num>)` is a shortcut for this.
+
+The function actions are unchanged, and you can see the full list of them [here](https://github.com/jackhumbert/tmk_keyboard/blob/master/common/action_code.h). They are explained in detail [here](https://github.com/jackhumbert/tmk_keyboard/blob/master/doc/keymap.md#2-action).
+
+### Macros
+
+Macros have been setup in the `keymaps/keymap_default.c` file so that you can use `M(<num>)` to access a macro in the `action_get_macro` section on your keymap. The switch/case structure you see here is required, and is setup for `M(0)` - you'll need to copy and paste the code to look like this (e.g. to support `M(3)`):
+
+ switch(id) {
+ case 0:
+ return MACRODOWN(TYPE(KC_A), END);
+ break;
+ case 1:
+ return MACRODOWN(TYPE(KC_B), END);
+ break;
+ case 2:
+ return MACRODOWN(TYPE(KC_C), END);
+ break;
+ case 3:
+ return MACRODOWN(TYPE(KC_D), END);
+ break;
+ }
+ return MACRO_NONE;
+
+`MACRODOWN()` is a shortcut for `(record->event.pressed ? MACRO(__VA_ARGS__) : MACRO_NONE)` which tells the macro to execute when the key is pressed. Without this, the macro will be executed on both the down and up stroke.
+
+[cygwin]: https://www.cygwin.com/
+[mingw]: http://www.mingw.org/
+[mhv]: https://infernoembedded.com/products/avr-tools
+[winavr]: http://winavr.sourceforge.net/
+[crosspack]: http://www.obdev.at/products/crosspack/index.html
+[dfu-prog]: http://dfu-programmer.sourceforge.net/
diff --git a/keyboard/planck/README.md b/keyboard/planck/README.md
new file mode 100644
index 0000000000..a733f07937
--- /dev/null
+++ b/keyboard/planck/README.md
@@ -0,0 +1,48 @@
+Planck keyboard firmware
+======================
+DIY/Assembled compact ortholinear 40% keyboard by [Ortholinear Keyboards](http://ortholinearkeyboards.com).
+
+## Quantum MK Firmware
+You have access to a bunch of goodies:
+
+- Use `LSFT()`, `LCTL()`, et. al. (listed in keymap_common.h) as modifiers for keys (daisy-chain-able)
+- Use `FUNC(1)` instead of `FN1` (etc.) to access the function layers beyond the 32 function layer limit
+- Use `CM_F` instead of `KC_F` to get the ColeMak equivilent for shortcuts (maps backwards)
+- Use `MACRODOWN()` instead of `MACRO()` to easily make a keydown macro (`CM_*` works here too)
+
+### Some notes on usage:
+
+- The `KEYMAP()` macro is unable to be used due to the bitwise modifications that take place - refer to extended_keymap_jack.c to see how to set things up with the `KC_` prefix
+- Keep an eye on the Makefile - this needs to include the correct files to work
+- Don't forget to use `const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {` instead of the 8bit equivilent
+
+## Build
+
+Follow [this guide](http://deskthority.net/workshop-f7/how-to-build-your-very-own-keyboard-firmware-t7177.html) to setup your development environment before anything else. Abbreviated instructions are provide at the [bottom of this document](https://github.com/rswiernik/tmk_keyboard/tree/rswiernik_dev/keyboard/planck#environment-setup)
+
+Download the whole firmware [here](https://github.com/jackhumbert/tmk_keyboard/archive/master.zip) and navigate to the keyboard/planck folder. Once your dev env is setup, you'll be able to type `make` to generate your .hex that you can load with the Teensy app onto your Planck (once you've hit reset/shorted GND & RST).
+
+Depending on which keymap you would like to use, you will have to compile slightly differently.
+
+####Default
+To build with the default keymap, simply move to the tmk\_keyboard/keyboard/planck/ and run `make` as follows:
+```
+$ make
+```
+
+## Keymap
+Several version of keymap are available in advance but you are recommended to define your favorite layout yourself. To define your own keymap create file named `keymap_<name>.c` and see keymap document (you can find in top README.md) and existent keymap files.
+
+####**Keymaps**
+
+To build the firmware binary hex file with an extended keymap just do `make` with `KEYMAP` option like:
+```
+$ make KEYMAP=[default|jack|<name>]
+```
+_The only applicable keymaps will work with this option._ Keymaps follow the format **__keymap\_\<name\>.c__** and are stored in the `keymaps` folder.
+
+## Notable TMK forks (which some of the keymap files are from)
+- [Shane's Fork](https://github.com/shanecelis/tmk_keyboard/tree/master/keyboard/planck)
+- [Pierre's Fork](https://github.com/pcarrier/tmk_keyboard/blob/pcarrier/planck/keyboard/gh60/keymap_planck.c)
+- [Nathan's Fork](https://github.com/nathanrosspowell/tmk_keyboard/tree/planck-jack/keyboard/planck)
+- [Matthew's Fork](https://github.com/pepers/tmk_keyboard/tree/master/keyboard/planck_grid)
diff --git a/keyboard/planck/backlight.c b/keyboard/planck/backlight.c
new file mode 100644
index 0000000000..f69364b2af
--- /dev/null
+++ b/keyboard/planck/backlight.c
@@ -0,0 +1,61 @@
+
+#include <avr/io.h>
+#include "backlight.h"
+
+#define CHANNEL OCR1C
+
+void backlight_init_ports()
+{
+
+ // Setup PB7 as output and output low.
+ DDRB |= (1<<7);
+ PORTB &= ~(1<<7);
+
+ // Use full 16-bit resolution.
+ ICR1 = 0xFFFF;
+
+ // I could write a wall of text here to explain... but TL;DW
+ // Go read the ATmega32u4 datasheet.
+ // And this: http://blog.saikoled.com/post/43165849837/secret-konami-cheat-code-to-high-resolution-pwm-on
+
+ // Pin PB7 = OCR1C (Timer 1, Channel C)
+ // Compare Output Mode = Clear on compare match, Channel C = COM1C1=1 COM1C0=0
+ // (i.e. start high, go low when counter matches.)
+ // WGM Mode 14 (Fast PWM) = WGM13=1 WGM12=1 WGM11=1 WGM10=0
+ // Clock Select = clk/1 (no prescaling) = CS12=0 CS11=0 CS10=1
+
+ TCCR1A = _BV(COM1C1) | _BV(WGM11); // = 0b00001010;
+ TCCR1B = _BV(WGM13) | _BV(WGM12) | _BV(CS10); // = 0b00011001;
+
+ backlight_init();
+}
+
+void backlight_set(uint8_t level)
+{
+ if ( level == 0 )
+ {
+ // Turn off PWM control on PB7, revert to output low.
+ TCCR1A &= ~(_BV(COM1C1));
+ CHANNEL = 0x0;
+ // Prevent backlight blink on lowest level
+ PORTB &= ~(_BV(PORTB7));
+ }
+ else if ( level == BACKLIGHT_LEVELS )
+ {
+ // Prevent backlight blink on lowest level
+ PORTB &= ~(_BV(PORTB7));
+ // Turn on PWM control of PB7
+ TCCR1A |= _BV(COM1C1);
+ // Set the brightness
+ CHANNEL = 0xFFFF;
+ }
+ else
+ {
+ // Prevent backlight blink on lowest level
+ PORTB &= ~(_BV(PORTB7));
+ // Turn on PWM control of PB7
+ TCCR1A |= _BV(COM1C1);
+ // Set the brightness
+ CHANNEL = 0xFFFF >> ((BACKLIGHT_LEVELS - level) * ((BACKLIGHT_LEVELS + 1) / 2));
+ }
+} \ No newline at end of file
diff --git a/keyboard/planck/config.h b/keyboard/planck/config.h
new file mode 100644
index 0000000000..a4c711db82
--- /dev/null
+++ b/keyboard/planck/config.h
@@ -0,0 +1,79 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef CONFIG_H
+#define CONFIG_H
+
+#include "config_common.h"
+
+/* USB Device descriptor parameter */
+#define VENDOR_ID 0xFEED
+#define PRODUCT_ID 0x6060
+#define DEVICE_VER 0x0001
+#define MANUFACTURER Ortholinear Keyboards
+#define PRODUCT The Planck Keyboard
+#define DESCRIPTION A compact ortholinear keyboard
+
+/* key matrix size */
+#define MATRIX_ROWS 4
+#define MATRIX_COLS 12
+
+/* Planck PCB default pin-out */
+#define COLS (int []){ F1, F0, B0, C7, F4, F5, F6, F7, D4, D6, B4, D7 }
+#define ROWS (int []){ D0, D5, B5, B6 }
+
+/* COL2ROW or ROW2COL */
+#define DIODE_DIRECTION COL2ROW
+
+/* define if matrix has ghost */
+//#define MATRIX_HAS_GHOST
+
+/* number of backlight levels */
+#define BACKLIGHT_LEVELS 3
+
+/* Set 0 if debouncing isn't needed */
+#define DEBOUNCE 5
+
+/* Mechanical locking support. Use KC_LCAP, KC_LNUM or KC_LSCR instead in keymap */
+#define LOCKING_SUPPORT_ENABLE
+/* Locking resynchronize hack */
+#define LOCKING_RESYNC_ENABLE
+
+/* key combination for command */
+#define IS_COMMAND() ( \
+ keyboard_report->mods == (MOD_BIT(KC_LSHIFT) | MOD_BIT(KC_RSHIFT)) \
+)
+
+/*
+ * Feature disable options
+ * These options are also useful to firmware size reduction.
+ */
+
+/* disable debug print */
+#define NO_DEBUG
+
+/* disable print */
+#define NO_PRINT
+
+/* disable action features */
+//#define NO_ACTION_LAYER
+//#define NO_ACTION_TAPPING
+//#define NO_ACTION_ONESHOT
+//#define NO_ACTION_MACRO
+//#define NO_ACTION_FUNCTION
+
+#endif
diff --git a/keyboard/planck/flash-pcb.sh b/keyboard/planck/flash-pcb.sh
new file mode 100755
index 0000000000..2ae15458c0
--- /dev/null
+++ b/keyboard/planck/flash-pcb.sh
@@ -0,0 +1,3 @@
+dfu-programmer atmega32u4 erase --force
+dfu-programmer atmega32u4 flash planck_pcb.hex
+dfu-programmer atmega32u4 reset \ No newline at end of file
diff --git a/keyboard/planck/keymaps/keymap_angerthosenear.c b/keyboard/planck/keymaps/keymap_angerthosenear.c
new file mode 100644
index 0000000000..cdf60632e4
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_angerthosenear.c
@@ -0,0 +1,50 @@
+#include "keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_ENT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_QUOT},
+ {KC_LCTL, KC_LGUI, KC_LALT, BL_STEP, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* WASD + NumPad */
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_P7, KC_P8, KC_P9, KC_PSLS, KC_PMNS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_P4, KC_P5, KC_P6, KC_PAST, KC_PPLS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_P1, KC_P2, KC_P3, KC_PDOT, KC_PENT, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_SPC, KC_P0, FUNC(1), KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS}
+},
+[2] = { /* RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_TRNS},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F11, KC_F12, KC_F13, KC_F14, KC_F15, KC_F16, KC_F17, KC_F18, KC_F19, KC_F20, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_MPRV, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* LOWER */
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_DEL},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), KC_TRNS, KC_TRNS, KC_TRNS, S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), S(KC_BSLS)},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_HOME, KC_PGDN, KC_PGUP, KC_END}
+}
+};
+
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/planck/keymaps/keymap_austin.c b/keyboard/planck/keymaps/keymap_austin.c
new file mode 100644
index 0000000000..49fc98a587
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_austin.c
@@ -0,0 +1,50 @@
+#include "keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {BL_STEP, KC_LGUI, KC_LALT, KC_LCTL, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Colemak */
+ {KC_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN3, KC_LGUI, KC_LALT, KC_LCTL, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F11, KC_F12, KC_F13, KC_F14, KC_F15, KC_F16, KC_F17, KC_F18, KC_F19, KC_F20, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* LOWER */
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), KC_TRNS, KC_TRNS, KC_TRNS, S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), S(KC_BSLS)},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+}
+};
+
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/planck/keymaps/keymap_charlie.c b/keyboard/planck/keymaps/keymap_charlie.c
new file mode 100644
index 0000000000..88f454d789
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_charlie.c
@@ -0,0 +1,54 @@
+#include "keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = { /* Native */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, FUNC(2)},
+ {KC_BSPC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_TAB, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_DEL, KC_LCTL, KC_NO, KC_LSFT, KC_LALT, KC_SPC, KC_NO, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+ [1] = { /* QWERTY->PHOTOSHOP */
+ {KC_DELETE, KC_0, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, FUNC(1)},
+ {KC_O, KC_G, KC_S, KC_U, KC_T, FUNC(27), KC_F21, KC_F10, KC_F11, KC_F7, KC_F8, KC_F9},
+ {KC_TAB, FUNC(4), FUNC(5), FUNC(6), KC_F1, FUNC(7), KC_F18, KC_F19, KC_F23, KC_F20, KC_F22, FUNC(9)},
+ {KC_COMM, KC_DOT, KC_R, FUNC(11), FUNC(3), KC_SPC, FUNC(12), KC_F2, FUNC(8), KC_F3, KC_F14}
+ },
+ [2] = { /* 2: FUNC(3 PHOTOSHOP */
+ {KC_ESC, FUNC(25), FUNC(26), KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO},
+ {KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, FUNC(19), FUNC(20), FUNC(21)},
+ {KC_C, KC_NO, FUNC(22), FUNC(5), KC_NO, FUNC(23), KC_NO, KC_NO, KC_NO, KC_NO, FUNC(13), KC_NO},
+ {FUNC(14), FUNC(15), FUNC(16), FUNC(17), FUNC(3), KC_SPC, FUNC(18), KC_NO, KC_NO, KC_F24, KC_NO}
+ }
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_DEFAULT_LAYER_SET(0), // set Qwerty layout
+ [2] = ACTION_DEFAULT_LAYER_SET(1), // set Photoshop presets
+ [3] = ACTION_LAYER_MOMENTARY(2), // Photoshop function layer
+
+ [4] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F9), // photo folder AHK
+ [5] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_I), // select inverse
+ [6] = ACTION_MODS_KEY(MOD_LSFT, KC_M), // marquee select
+ [7] = ACTION_MODS_KEY(MOD_LALT, KC_BSPC), // fill
+ [8] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_X), // warp
+ [9] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT | MOD_LSFT, KC_F12), // merge all new layer
+ [10] = ACTION_MODS_KEY(MOD_LCTL, KC_MINS), // zoom out
+ [11] = ACTION_MODS_KEY(MOD_LCTL, KC_H), // RBG sliders
+ [12] = ACTION_MODS_KEY(MOD_LCTL, KC_S), // save
+ [13] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_F5), // layer mask from transparancy
+ [14] = ACTION_MODS_KEY(MOD_LCTL, KC_F2), // stroke
+ [15] = ACTION_MODS_KEY(MOD_LCTL | MOD_LSFT, KC_F2), // stroke layer
+ [16] = ACTION_MODS_KEY(MOD_LCTL, KC_0), // zoom 0
+ [17] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_H), // HSV sliders
+ [18] = ACTION_MODS_KEY(MOD_LCTL | MOD_LSFT, KC_S), // save as
+ [19] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F7), // gaussian blur
+ [20] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F8), // motion blur
+ [21] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_X), // liquify filter
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS), // prev layer blending
+ [23] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_BSPC), // KC_NOrmal layer blending
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // next layer blending
+ [25] = ACTION_MODS_KEY(MOD_LCTL, KC_Z), // step back
+ [26] = ACTION_MODS_KEY(MOD_LCTL, KC_Y), // step forward
+ [27] = ACTION_MODS_KEY(MOD_LCTL, KC_R), // rasterize
+
+};
diff --git a/keyboard/planck/keymaps/keymap_daniel.c b/keyboard/planck/keymaps/keymap_daniel.c
new file mode 100644
index 0000000000..234e48ff4a
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_daniel.c
@@ -0,0 +1,48 @@
+#include "keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_RSFT},
+ {FUNC(3), KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* RAISE */
+ {KC_GRV, S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_EQL},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_LBRC, KC_RBRC},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, S(KC_MINS), KC_BSLS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[2] = { /* LOWER */
+ {S(KC_GRV), KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, S(KC_EQL)},
+ {KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12},
+ {KC_CAPS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_ENT},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* Qwerty */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_DEL},
+ {KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_RSFT},
+ {KC_TRNS, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+}
+};
+
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(2), // to LOWER
+ [3] = ACTION_LAYER_MOMENTARY(3) // to LOWER
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/planck/keymaps/keymap_david.c b/keyboard/planck/keymaps/keymap_david.c
new file mode 100644
index 0000000000..f483084801
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_david.c
@@ -0,0 +1,76 @@
+#include "keymap_common.h"
+#include "beeps.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_Q, KC_W, KC_E, KC_R, KC_T, KC_BSPC, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_A, KC_S, KC_D, KC_F, KC_G, KC_ENT, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_Z, KC_X, KC_C, KC_V, KC_B, KC_ESC, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {M(10), KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Colemak */
+ {KC_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN3, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), RESET, M(0), M(1), M(2), KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F11, KC_F12, M(0), M(1), M(2), M(3), M(4), M(5), M(6), M(7), KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* LOWER */
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), RESET, M(0), M(1), M(2), S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), S(KC_BSLS)},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ if (record->event.pressed) {
+ switch(id) {
+ case 0:
+ true_note(12, 12, 20);
+ break;
+ case 1:
+ true_note(14, 14, 20);
+ break;
+ case 2:
+ true_note(16, 16, 20);
+ break;
+ case 3:
+ true_note(17, 17, 20);
+ break;
+ case 4:
+ true_note(19, 19, 20);
+ break;
+ case 5:
+ true_note(21, 21, 20);
+ break;
+ case 6:
+ true_note(23, 23, 20);
+ break;
+ case 7:
+ true_note(24, 24, 20);
+ break;
+ case 10:
+
+ break;
+ }
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/planck/keymaps/keymap_default.c b/keyboard/planck/keymaps/keymap_default.c
new file mode 100644
index 0000000000..49670dafd3
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_default.c
@@ -0,0 +1,68 @@
+// This is the canonical layout file for the Quantum project. If you want to add another keyboard,
+// this is the style you want to emulate.
+
+#include "planck.h"
+#include "backlight.h"
+
+// Each layer gets a name for readability, which is then used in the keymap matrix below.
+// The underscores don't mean anything - you can have a layer called STUFF or any other name.
+// Layer names don't all need to be of the same length, obviously, and you can also skip them
+// entirely and just use numbers.
+#define _QW 0
+#define _CM 1
+#define _DV 2
+#define _LW 3
+#define _RS 4
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[_QW] = { /* Qwerty */
+ {KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT },
+ {M(0), KC_LCTL, KC_LALT, KC_LGUI, MO(_LW), KC_SPC, KC_SPC, MO(_RS), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[_CM] = { /* Colemak */
+ {KC_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT },
+ {M(0), KC_LCTL, KC_LALT, KC_LGUI, MO(_LW), KC_SPC, KC_SPC, MO(_RS), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[_DV] = { /* Dvorak */
+ {KC_TAB, KC_QUOT, KC_COMM, KC_DOT, KC_P, KC_Y, KC_F, KC_G, KC_C, KC_R, KC_L, KC_BSPC},
+ {KC_ESC, KC_A, KC_O, KC_E, KC_U, KC_I, KC_D, KC_H, KC_T, KC_N, KC_S, KC_SLSH},
+ {KC_LSFT, KC_SCLN, KC_Q, KC_J, KC_K, KC_X, KC_B, KC_M, KC_W, KC_V, KC_Z, KC_ENT },
+ {M(0), KC_LCTL, KC_LALT, KC_LGUI, MO(_LW), KC_SPC, KC_SPC, MO(_RS), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[_RS] = { /* RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12, DF(_QW), DF(_CM), DF(_DV), RESET, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[_LW] = { /* LOWER */
+ {KC_TILD, KC_EXLM, KC_AT, KC_HASH, KC_DLR, KC_PERC, KC_CIRC, KC_AMPR, KC_ASTR, KC_LPRN, KC_RPRN, KC_BSPC},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_UNDS, KC_PLUS, KC_LCBR, KC_RCBR, KC_PIPE},
+ {KC_TRNS, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12, DF(_QW), DF(_CM), DF(_DV), RESET, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ if (record->event.pressed) {
+ register_code(KC_RSFT);
+ backlight_step();
+ } else {
+ unregister_code(KC_RSFT);
+ }
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/planck/keymaps/keymap_dzobert.c b/keyboard/planck/keymaps/keymap_dzobert.c
new file mode 100644
index 0000000000..665e9c20b6
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_dzobert.c
@@ -0,0 +1,49 @@
+#include "keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_TAB},
+ {KC_LCTL, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_BSPC},
+ {KC_LALT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN4, KC_RSFT, KC_LGUI, KC_LSFT, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Colemak */
+ {KC_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_TAB},
+ {KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_BSPC},
+ {KC_LALT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN3, KC_RSFT, KC_LGUI, KC_LSFT, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* RAISE */
+ {KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12},
+ {KC_TRNS, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_DEL},
+ {KC_TRNS, KC_GRV, KC_MINS, KC_EQL, KC_QUOT, S(KC_QUOT), S(KC_LBRC), S(KC_RBRC), KC_LBRC, KC_RBRC, KC_BSLS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_HOME, KC_PGUP, KC_PGDN, KC_END}
+},
+[3] = { /* LOWER */
+ {KC_POWER,KC_PSCR, KC_SLCK, KC_PAUSE, KC_NLCK, KC_EXECUTE, KC_MENU, KC_APP, KC_7, KC_8, KC_9, KC_KP_SLASH},
+ {KC_TRNS, KC_VOLD, KC_VOLU, KC_MUTE, KC_CAPS, KC_CANCEL, KC_UNDO, KC_AGAIN, KC_4, KC_5, KC_6, KC_KP_ASTERISK},
+ {KC_TRNS, KC_INSERT,KC_CUT, KC_COPY, KC_PASTE, KC_BSLS, KC_9, KC_0, KC_1, KC_2, KC_3, KC_KP_MINUS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_0, KC_KP_DOT, KC_KP_ENTER, KC_KP_PLUS}
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+}; \ No newline at end of file
diff --git a/keyboard/planck/keymaps/keymap_jack.c b/keyboard/planck/keymaps/keymap_jack.c
new file mode 100644
index 0000000000..0b93bba33f
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_jack.c
@@ -0,0 +1,50 @@
+#include "keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Jack soft-coded colemak */
+ {KC_TAB, CM_Q, CM_W, CM_F, CM_P, CM_G, CM_J, CM_L, CM_U, CM_Y, CM_SCLN, KC_BSPC},
+ {KC_ESC, CM_A, CM_R, CM_S, CM_T, CM_D, CM_H, CM_N, CM_E, CM_I, CM_O, KC_QUOT},
+ {KC_LSFT, CM_Z, CM_X, CM_C, CM_V, CM_B, CM_K, CM_M, CM_COMM, CM_DOT, CM_SLSH, KC_ENT},
+ {BL_STEP, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Jack hard-coded colemak */
+ {KC_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN3, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* Jack RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F11, KC_F12, KC_F13, KC_F14, KC_F15, KC_F16, KC_F17, KC_F18, KC_F19, KC_F20, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* Jack LOWER */
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), KC_TRNS, KC_TRNS, KC_TRNS, S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), S(KC_BSLS)},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+}
+};
+
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/planck/keymaps/keymap_joe.c b/keyboard/planck/keymaps/keymap_joe.c
new file mode 100644
index 0000000000..5b7bbe2bbb
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_joe.c
@@ -0,0 +1,88 @@
+#include "keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = { /* Joe colemak */
+ {F(3), KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_MINS},
+ {KC_BSPC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_ENT },
+ {F(15), KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_UP, KC_QUOT},
+ {KC_LCTL, KC_LGUI, KC_LALT, KC_LSFT, F(1), KC_SPC, KC_SPC, F(2), KC_SLSH, KC_LEFT, KC_DOWN, KC_RGHT}
+ },
+ [1] = { /* Joe soft Colemak */
+ {F(3), CM_Q, CM_W, CM_F, CM_P, CM_G, CM_J, CM_L, CM_U, CM_Y, CM_SCLN, KC_MINS},
+ {KC_BSPC, CM_A, CM_R, CM_S, CM_T, CM_D, CM_H, CM_N, CM_E, CM_I, CM_O, KC_ENT },
+ {F(15), CM_Z, CM_X, CM_C, CM_V, CM_B, CM_K, CM_M, KC_COMM, KC_DOT, KC_UP, KC_QUOT},
+ {KC_LCTL, KC_LGUI, KC_LALT, KC_LSFT, F(1), KC_SPC, KC_SPC, F(2), KC_SLSH, KC_LEFT, KC_DOWN, KC_RGHT}
+ },
+ [2] = { /* Joe NUMPAD */
+ {F(3), KC_NO, KC_UP, KC_NO, KC_NO, KC_NO, LSFT(KC_9), LSFT(KC_0), KC_PSLS, KC_P7, KC_P8, KC_P9 },
+ {KC_BSPC, KC_LEFT, KC_DOWN, KC_RGHT, KC_NO, KC_NO, LSFT(KC_5), KC_PEQL, KC_PAST, KC_P4, KC_P5, KC_P6 },
+ {F(15), KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_PCMM, KC_PMNS, KC_P1, KC_P2, KC_P3 },
+ {KC_LCTL, KC_LGUI, KC_LALT, KC_LSFT, F(1), KC_TRNS, KC_TRNS, F(2), KC_PPLS, KC_P0, KC_PDOT, KC_PENT}
+ },
+ [3] = { /* Joe 1337 haxOr5*/
+ {F(3), KC_Q, KC_W, KC_F, KC_P, KC_6, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_MINS},
+ {KC_BSPC, KC_4, KC_R, KC_5, KC_7, KC_D, KC_H, KC_N, KC_3, KC_1, KC_0, KC_ENT },
+ {F(15), KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_UP, KC_QUOT},
+ {KC_LCTL, KC_LGUI, KC_LALT, KC_LSFT, F(1), KC_SPC, KC_SPC, F(2), KC_SLSH, KC_LEFT, KC_DOWN, KC_RGHT}
+ },
+ [4] = { /* Joe LOWER fn1 */
+ {KC_GRV, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, M(3), M(2), M(1), M(0) },
+ {KC_BSPC, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_TRNS},
+ {KC_BSLS, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_LBRC, KC_RBRC, KC_PGUP, KC_EQL },
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, F(1), KC_TRNS, KC_TRNS, F(2), KC_NO, KC_HOME, KC_PGDN, KC_END }
+ },
+ [5] = { /* Joe UPPER fn2 */
+ {KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12 },
+ {KC_DEL, KC_BTN1, KC_MS_U, KC_BTN2, KC_BTN3, KC_WH_U, KC_BTN4, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT, KC_NO },
+ {KC_TRNS, KC_MS_L, KC_MS_D, KC_MS_R, KC_WH_L, KC_WH_D, KC_WH_R, KC_NO, KC_NO, LCTL(KC_PGUP), LCTL(LALT(KC_UP)), LCTL(KC_PGDN) },
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, F(1), KC_NO, KC_NO, F(2), KC_NO, LCTL(LALT(KC_LEFT)), LCTL(LALT(KC_DOWN)), LCTL(LALT(KC_RGHT))}
+ },
+ [6] = { /* Joe SPECIAL fn3 */
+ {KC_TRNS, KC_MUTE, KC_VOLD, KC_VOLU, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO },
+ {KC_NO, KC_MPLY, KC_MPRV, KC_MNXT, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, RESET },
+ {KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO, KC_NO },
+ {F(6), F(7), F(8), F(9), F(1), KC_TRNS, KC_TRNS, F(2), KC_POWER, KC_WAKE, KC_SLEP, LCTL(LALT(KC_L))}
+ }
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(4), // fn1
+ [2] = ACTION_LAYER_MOMENTARY(5), // fn2
+
+ /* ESC on tap, fn3 on hold */
+ [3] = ACTION_LAYER_TAP_KEY(6, KC_ESC),
+
+ /* toggle layers */
+ [6] = ACTION_DEFAULT_LAYER_SET(0),
+ [7] = ACTION_DEFAULT_LAYER_SET(1),
+ [8] = ACTION_DEFAULT_LAYER_SET(2),
+ [9] = ACTION_DEFAULT_LAYER_SET(3),
+
+ /* tab on tap, shift on hold */
+ [15] = ACTION_MODS_TAP_KEY(MOD_LSFT, KC_TAB),
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ switch (id) {
+ case 0:
+ /* :) */
+ return MACRODOWN( DOWN(KC_LSFT), TYPE(KC_SCLN), TYPE(KC_0), UP(KC_LSFT), END );
+ break;
+ case 1:
+ /* :( */
+ return MACRODOWN( DOWN(KC_LSFT), TYPE(KC_SCLN), TYPE(KC_9), UP(KC_LSFT), END );
+ break;
+ case 2:
+ /* (: | :) */
+ return MACRODOWN( DOWN(KC_LSFT), TYPE(KC_9), TYPE(KC_SCLN), TYPE(KC_SPC), TYPE(KC_SPC), TYPE(KC_SCLN), TYPE(KC_0), UP(KC_LSFT), TYPE(KC_LEFT), TYPE(KC_LEFT), TYPE(KC_LEFT), END );
+ break;
+ case 3:
+ /* :( | ): */
+ return MACRODOWN( DOWN(KC_LSFT), TYPE(KC_SCLN), TYPE(KC_9), TYPE(KC_SPC), TYPE(KC_SPC), TYPE(KC_0), TYPE(KC_SCLN), UP(KC_LSFT), TYPE(KC_LEFT), TYPE(KC_LEFT), TYPE(KC_LEFT), END );
+ break;
+ default:
+ break;
+ }
+ return MACRO_NONE;
+}
diff --git a/keyboard/planck/keymaps/keymap_kyle.c b/keyboard/planck/keymaps/keymap_kyle.c
new file mode 100644
index 0000000000..da32b74f96
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_kyle.c
@@ -0,0 +1,49 @@
+#include "keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_RCTL, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Colemak */
+ {KC_ESC, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_TAB, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN3, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F11, KC_F12, KC_F13, KC_F14, KC_F15, KC_F16, KC_F17, KC_F18, KC_F19, KC_F20, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* LOWER */
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), LSFT(RSFT(KC_PAUSE)), LSFT(RSFT(KC_D)), KC_TRNS, KC_TRNS, S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), S(KC_BSLS)},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_TRNS},
+ {BL_STEP, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/planck/keymaps/keymap_leo.c b/keyboard/planck/keymaps/keymap_leo.c
new file mode 100644
index 0000000000..6d66441822
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_leo.c
@@ -0,0 +1,46 @@
+#include "keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* BASE */
+ {KC_ESC, KC_LBRC, KC_QUOT, KC_SCLN, KC_P, KC_Y, KC_F, KC_G, KC_C, KC_R, KC_L, KC_BSPC},
+ {KC_TAB, KC_A, KC_O, KC_E, KC_U, KC_I, KC_D, KC_H, KC_T, KC_N, KC_S, KC_ENT},
+ {KC_LSFT, KC_DOT, KC_Q, KC_J, KC_K, KC_X, KC_B, KC_M, KC_W, KC_V, KC_Z, KC_COMM},
+ {KC_LCTL, KC_LALT, KC_LGUI, FUNC(3), FUNC(2), KC_SPC, KC_SPC, FUNC(1), FUNC(3), KC_RGUI, KC_RALT, KC_RCTL}
+},
+[2] = { /* RAISE */
+ {RALT(KC_RBRC), KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, S(KC_RBRC)},
+ {KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_F11, KC_F12},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS}
+},
+[3] = { /* LOWER */
+ {S(KC_EQL),S(KC_1),S(KC_2),S(KC_3),RALT(KC_5),S(KC_5), S(KC_6), S(KC_7),RALT(KC_7),RALT(KC_0),S(KC_0), KC_MINS},
+ {KC_TRNS,RALT(KC_2),S(KC_SLSH),KC_NUBS,S(KC_NUBS),RALT(KC_MINS),RALT(KC_NUBS), KC_NUHS, S(KC_8), S(KC_9), S(KC_MINS), KC_SLSH},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, RALT(KC_8), RALT(KC_9), KC_TRNS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS}
+},
+[4] = { /* META */
+ {KC_TRNS, KC_HOME, KC_UP, KC_END, KC_TRNS, KC_TRNS, KC_TRNS, KC_HOME, KC_UP, KC_END, KC_TRNS, KC_DEL},
+ {KC_TRNS, KC_RGHT, KC_DOWN, KC_LEFT, KC_PGUP, KC_TRNS, KC_PGUP, KC_LEFT, KC_DOWN, KC_RGHT, KC_TRNS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_PGDN, KC_TRNS, KC_PGDN, KC_TRNS, KC_VOLD, KC_VOLU, KC_TRNS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS}
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+ [3] = ACTION_LAYER_MOMENTARY(4), // to META
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/planck/keymaps/keymap_lock.c b/keyboard/planck/keymaps/keymap_lock.c
new file mode 100644
index 0000000000..cc9be55f64
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_lock.c
@@ -0,0 +1,121 @@
+#include "keymap_common.h"
+#include "backlight.h"
+#include "action_layer.h"
+#include "keymap_midi.h"
+#include <avr/boot.h>
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {M(0), KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Colemak */
+ {KC_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN3, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), RESET, KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F11, KC_F12, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* LOWER */
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), RESET, KC_TRNS, KC_TRNS, KC_TRNS, S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), S(KC_BSLS)},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[4] = { /* TENKEY */
+ {KC_TAB, N_C5, N_D5, N_E5, N_F5, N_G5, N_A5, KC_KP_7, KC_KP_8, KC_KP_9, KC_P, KC_BSPC},
+ {KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_KP_4, KC_KP_5, KC_KP_6, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_KP_1, KC_KP_2, KC_KP_3, KC_SLSH, KC_ENT},
+ {KC_TRNS, KC_LCTL, KC_LALT, KC_LGUI, KC_TRNS, KC_SPC, KC_SPC, KC_KP_0, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[5] = {
+ { MIDI12 },
+ { MIDI12 },
+ { MIDI12 },
+ {M(0), KC_MS_L, KC_MS_D, KC_MS_U, KC_MS_R, KC_SPC, KC_SPC, FUNC(1), MIDI, MIDI, MIDI, MIDI}
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+uint16_t hextokeycode(int hex) {
+ if (hex == 0x0) {
+ return KC_0;
+ } else if (hex < 0xA) {
+ return KC_1 + (hex - 0x1);
+ } else {
+ return KC_A + (hex - 0xA);
+ }
+}
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ if (record->event.pressed) {
+ // play_note(440, 20);
+ // register_code(KC_RSFT);
+ backlight_set(BACKLIGHT_LEVELS);
+ default_layer_and(0);
+ default_layer_or((1<<5));
+
+ // uint8_t low = boot_lock_fuse_bits_get(0x0000);
+ // uint8_t high = boot_lock_fuse_bits_get(0x0003);
+ // uint8_t ext = boot_lock_fuse_bits_get(0x0002);
+ // uint8_t lock = boot_lock_fuse_bits_get(0x0001);
+
+ // register_code(hextokeycode((low & 0xF0) >> 4));
+ // unregister_code(hextokeycode((low & 0xF0) >> 4));
+ // register_code(hextokeycode((low & 0x0F)));
+ // unregister_code(hextokeycode((low & 0x0F)));
+
+
+ // register_code(hextokeycode((high & 0xF0) >> 4));
+ // unregister_code(hextokeycode((high & 0xF0) >> 4));
+ // register_code(hextokeycode((high & 0x0F)));
+ // unregister_code(hextokeycode((high & 0x0F)));
+
+
+ // register_code(hextokeycode((ext & 0xF0) >> 4));
+ // unregister_code(hextokeycode((ext & 0xF0) >> 4));
+ // register_code(hextokeycode((ext & 0x0F)));
+ // unregister_code(hextokeycode((ext & 0x0F)));
+
+
+ // register_code(hextokeycode((lock & 0xF0) >> 4));
+ // unregister_code(hextokeycode((lock & 0xF0) >> 4));
+ // register_code(hextokeycode((lock & 0x0F)));
+ // unregister_code(hextokeycode((lock & 0x0F)));
+
+ // note(0+12, 20);
+ // note(0+24, 20);
+ } else {
+ // unregister_code(KC_RSFT);
+ // stop_note();
+ backlight_set(0);
+ default_layer_and(0);
+ default_layer_or(0);
+ // note(0+24, 20);
+ // note(0, 20);
+ // play_note(4, 20);
+ }
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/planck/keymaps/keymap_max.c b/keyboard/planck/keymaps/keymap_max.c
new file mode 100644
index 0000000000..7fb29bc7a4
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_max.c
@@ -0,0 +1,49 @@
+#include "keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_ENT },
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_QUOT},
+ {KC_LCTL, BL_STEP, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Colemak */
+ {KC_ESC, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_TAB, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_ENT },
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_QUOT},
+ {KC_LCTL, BL_STEP, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), RESET, KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_TRNS},
+ {KC_TRNS, KC_F11, KC_F12, KC_F13, KC_F14, KC_F15, KC_F16, KC_F17, KC_F18, KC_F19, KC_F20, KC_BSLS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* LOWER */
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), RESET, KC_TRNS, KC_TRNS, KC_TRNS, S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), KC_TRNS},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, S(KC_BSLS)},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/planck/keymaps/keymap_monkey.c b/keyboard/planck/keymaps/keymap_monkey.c
new file mode 100644
index 0000000000..21a2c146ab
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_monkey.c
@@ -0,0 +1,76 @@
+#include "keymap_common.h"
+#include "backlight.h"
+#include "debug.h"
+
+#define COLEMAK_LAYER 0
+#define QWERTY_LAYER 1
+#define LOWER_LAYER 2
+#define UPPER_LAYER 3
+#define SPACEFN_LAYER 4
+#define TENKEY_LAYER 5
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[COLEMAK_LAYER] = { /* Colemak */
+ {KC_TAB, UNI(0x1961), KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_LCTL, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {FUNC(5), KC_ESC, KC_LGUI, KC_LALT, FUNC(1), FUNC(6), FUNC(6), FUNC(2), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[QWERTY_LAYER] = { /* Qwerty */
+ {KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_LCTL, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {FUNC(5), KC_ESC, KC_LGUI, KC_LALT, FUNC(1), FUNC(6), FUNC(6), FUNC(2), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[LOWER_LAYER] = { /* LOWER */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_DELETE},
+ {KC_TRNS, FUNC(3), FUNC(4), RESET, DEBUG, KC_TRNS, KC_TRNS, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F11, KC_F12, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_HOME, KC_PGDN, KC_PGUP, KC_END}
+},
+[UPPER_LAYER] = { /* RAISE */
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_DELETE},
+ {KC_CALC, FUNC(3), FUNC(4), RESET, DEBUG, KC_TRNS, KC_TRNS, S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), S(KC_BSLS)},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[SPACEFN_LAYER] = { /* SpaceFN */
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_HOME, KC_UP, KC_END, KC_TRNS, KC_TRNS},
+ {KC_TRNS, FUNC(3), FUNC(4), KC_TRNS, KC_TRNS, KC_TRNS, KC_PGUP, KC_LEFT, KC_DOWN, KC_RIGHT, KC_TRNS, KC_TRNS},
+ {KC_TRNS, KC_F11, KC_F12, KC_TRNS, KC_TRNS, KC_TRNS, KC_PGDN, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS}
+},
+[TENKEY_LAYER] = { /* TENKEY */
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_KP_7, KC_KP_8, KC_KP_9, KC_PMNS, KC_BSPC},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_KP_4, KC_KP_5, KC_KP_6, KC_PPLS, KC_NLCK},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_KP_1, KC_KP_2, KC_KP_3, KC_PDOT, KC_ENT},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_SPC, KC_SPC, KC_KP_0, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS}
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_TAP_KEY(LOWER_LAYER, KC_BSPC), // Tap for backspace, hold for LOWER
+ [2] = ACTION_LAYER_TAP_KEY(UPPER_LAYER, KC_ENT), // Tap for enter, hold for RAISE
+
+ [3] = ACTION_DEFAULT_LAYER_SET(COLEMAK_LAYER),
+ [4] = ACTION_DEFAULT_LAYER_SET(QWERTY_LAYER),
+ [5] = ACTION_LAYER_TOGGLE(TENKEY_LAYER),
+
+ [6] = ACTION_LAYER_TAP_KEY(SPACEFN_LAYER, KC_SPC), // Tap for space, hold for SpaceFN
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ if (record->event.pressed) {
+ register_code(KC_RSFT);
+ backlight_step();
+ } else {
+ unregister_code(KC_RSFT);
+ }
+ break;
+ }
+ return MACRO_NONE;
+}; \ No newline at end of file
diff --git a/keyboard/planck/keymaps/keymap_numpad.c b/keyboard/planck/keymaps/keymap_numpad.c
new file mode 100644
index 0000000000..7de4372ab0
--- /dev/null
+++ b/keyboard/planck/keymaps/keymap_numpad.c
@@ -0,0 +1,26 @@
+#include "keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_KP_MINUS, KC_KP_PLUS, KC_KP_PLUS, KC_KP_ENTER, KC_KP_ENTER},
+ {KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_KP_ASTERISK, KC_KP_9, KC_KP_6, KC_KP_3, KC_KP_DOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_KP_SLASH, KC_KP_8, KC_KP_5, KC_KP_2, KC_KP_0},
+ {BL_STEP, KC_LCTL, KC_LALT, KC_LGUI, KC_NO, KC_SPC, KC_SPC, KC_NUMLOCK, KC_KP_7, KC_KP_4, KC_KP_1, KC_KP_0}
+ // Space is repeated to accommadate for both spacebar wiring positions
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRODOWN(T(CM_T), END);
+ break;
+ }
+ return MACRO_NONE;
+}; \ No newline at end of file
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_brett.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_brett.c
new file mode 100644
index 0000000000..97d832b47a
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_brett.c
@@ -0,0 +1,42 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP(
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ LCTL, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, RSFT,
+ TAB, LGUI, RSFT, LALT, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* RAISE */
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, DEL,
+ TRNS, F1, F2, F3, F4, F5, F6, 4, 5, 6, QUOT, TRNS,
+ TRNS, F7, F8, F9, F10, F11, F12, 1, 2, 3, TRNS, PGUP,
+ MPRV, MNXT, TRNS, MUTE, TRNS, TRNS, FN1, 0, 0, TRNS, PGDN),
+[2] = KEYMAP( /* LOWER */
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MINS,
+ TRNS, TRNS, TRNS, PAUSE, TRNS, TRNS, TRNS, TRNS, LBRC, RBRC, BSLS, EQL,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ MPLY, MSTP, VOLU, VOLD, FN2, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_dotcom.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_dotcom.c
new file mode 100644
index 0000000000..347f6dea91
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_dotcom.c
@@ -0,0 +1,34 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP(
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ FN1, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, LBRC,
+ LCTL, BSLS, QUOT, LALT, FN22, SPC, LEFT, UP, DOWN, RGHT, RBRC),
+[1] = KEYMAP(
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, DEL,
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, TRNS, TRNS, TRNS,
+ TRNS, FN18, FN19, FN22, EQL, MINS, FN20, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, TRNS, VOLD, VOLU, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to Fn overlay
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+};
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_jack.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_jack.c
new file mode 100644
index 0000000000..c74812121f
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_jack.c
@@ -0,0 +1,50 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Jack */
+ TAB, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ ESC, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ RSFT, LCTL, LALT, LGUI, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* Jack colemak */
+ TAB, Q, W, F, P, G, J, L, U, Y, SCLN, BSPC,
+ ESC, A, R, S, T, D, H, N, E, I, O, QUOT,
+ LSFT, Z, X, C, V, B, K, M, COMM, DOT, SLSH, ENT,
+ FN3, LCTL, LALT, LGUI, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[2] = KEYMAP( /* Jack RAISE */
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, BSPC,
+ TRNS, FN3, FN4, PAUSE, TRNS, TRNS, TRNS, MINS, EQL, LBRC, RBRC, BSLS,
+ TRNS, F11, F12, F13, F14, F15, F16, F17, F18, F19, F20, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, MNXT, VOLD, VOLU, MPLY),
+[3] = KEYMAP( /* Jack LOWER */
+ FN22, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, BSPC,
+ TRNS, FN3, FN4, PAUSE, TRNS, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, MNXT, VOLD, VOLU, MPLY),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_joe.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_joe.c
new file mode 100644
index 0000000000..598b0c455c
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_joe.c
@@ -0,0 +1,83 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Joe qwerty */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, MINS,
+ BSPC, A, S, D, F, G, H, J, K, L, SCLN, ENTER,
+ FN7, Z, X, C, V, B, N, M, COMM, DOT, SLSH, QUOT,
+ LCTL, LGUI, LALT, LSFT, FN1, SPC, FN0, LEFT, UP, DOWN, RGHT),
+[1] = KEYMAP( /* Joe colemak */
+ ESC, Q, W, F, P, G, J, L, U, Y, SCLN, MINS,
+ BSPC, A, R, S, T, D, H, N, E, I, O, ENTER,
+ FN7, Z, X, C, V, B, K, M, COMM, DOT, SLSH, QUOT,
+ LCTL, LGUI, LALT, LSFT, FN1, SPC, FN0, LEFT, UP, DOWN, RGHT),
+[2] = KEYMAP( /* Joe UPPER */
+ F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12,
+ DEL, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, MENU, CAPS, INS, PSCR, TRNS, FN5, FN6,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, FN0, FN26, FN27, FN28, FN29),
+[3] = KEYMAP( /* Joe LOWER */
+ GRV, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN8, FN9, FN30,
+ BSPC, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, TRNS,
+ BSLS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, LBRC, RBRC, TRNS, EQL,
+ TRNS, TRNS, TRNS, TRNS, FN1, TRNS, FN2, HOME, PGUP, PGDN, END),
+[4] = KEYMAP( /* Joe LOWER + UPPER */
+ FN3, FN4, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, SLEP,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MUTE, VOLD, VOLU, MPLY),
+};
+
+enum macro_id {
+ M_Q0,
+ M_Q1,
+ M_Q2
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [0] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [1] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(4), // to Fn overlay
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [5] = ACTION_MODS_KEY(MOD_LCTL, KC_PGUP),
+ [6] = ACTION_MODS_KEY(MOD_LCTL, KC_PGDN),
+
+ /* tab on tap, shift on hold */
+ [7] = ACTION_MODS_TAP_KEY(MOD_LSFT, KC_TAB),
+
+ [8] = ACTION_MACRO(M_Q0),
+ [9] = ACTION_MACRO(M_Q1),
+
+ [26] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_LEFT),
+ [27] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_UP),
+ [28] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_DOWN),
+ [29] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_RGHT),
+
+ [30] = ACTION_MACRO(M_Q2),
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ keyevent_t event = record->event;
+ switch (id) {
+ case M_Q0:
+ /* :( | ): */
+ return event.pressed ?
+ MACRO( D(LSFT), T(P), T(9), T(SPC), T(SPC), T(0), T(P), U(LSFT), T(LEFT), T(LEFT), T(LEFT), END ) :
+ MACRO_NONE;
+ case M_Q1:
+ /* (: | :) */
+ return event.pressed ?
+ MACRO( D(LSFT), T(9), T(P), T(SPC), T(SPC), T(P), T(0), U(LSFT), T(LEFT), T(LEFT), T(LEFT), END ) :
+ MACRO_NONE;
+ case M_Q2:
+ /* :) */
+ return event.pressed ?
+ MACRO( D(LSFT), T(P), T(0), U(LSFT), END ) :
+ MACRO_NONE;
+ }
+ return MACRO_NONE;
+}
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_matthew.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_matthew.c
new file mode 100644
index 0000000000..56e7003a97
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_matthew.c
@@ -0,0 +1,70 @@
+// by Matthew Pepers - https://github.com/pepers
+
+/* grid planck layout - modified programmer dvorak
+,-----------------------------------------------------------------------------------------------.
+| pause | @ | | | ^ | | | | | * | # | $ | del |
+| esc | ; : | , < | . > | P | Y | F | G | G | C | R | bkspc |
+| F1 | F2 | F3 | F4 | F5 | F6 | F7 | F8 | F9 | F10 | F11 | F12 |
+|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|
+| & | / | { | ( | [ | = | ! | ] | ) | } | \ | + |
+| ` ~ | A | O | E | U | I | D | H | T | N | S | - _ |
+| % | 7 | 5 | 3 | 1 | 9 | 0 | 2 | 4 | 6 | 8 | ? |
+|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|
+| | | | | | | | | | | | prtsc |
+| tab | ' " | Q | J | K | X | B | M | W | V | Z | retrn |
+| | | | | | | | | | | | insrt |
+|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|
+| | | | | | | | | | | | |
+| lctrl | lgui | lalt | ralt | lower | shift | space | raise | left | down | up | right |
+| | | | | | | | | home | pgdn | pgup | end |
+`-----------------------------------------------------------------------------------------------'
+*/
+
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ /* 0: dvorak */
+ [0] = KEYMAP_GRID( ESC, SCLN, COMM, DOT, P, Y, F, G, C, R, L, BSPC, \
+ GRV, A, O, E, U, I, D, H, T, N, S, MINS, \
+ TAB, QUOT, Q, J, K, X, B, M, W, V, Z, ENT, \
+ LCTL, LGUI, LALT, RALT, FN1, LSFT, SPC, FN2, LEFT, DOWN, UP, RGHT),
+
+ /* 1: lower (FN1) */
+ [1] = KEYMAP_GRID( F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12, \
+ FN17, 7, 5, 3, 1, 9, 0, 2, 4, 6, 8, FN18, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, INS, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, HOME, PGDN, PGUP, END),
+
+ /* 2: raise (FN2) */
+ [2] = KEYMAP_GRID(PAUS, FN19, FN20, FN21, TRNS, TRNS, TRNS, TRNS, FN22, FN23, FN24, DEL, \
+ FN10, SLSH, FN11, FN12, LBRC, EQL, FN13, RBRC, FN14, FN15, BSLS, FN16, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, PSCR, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // lower Fn layer
+ [2] = ACTION_LAYER_MOMENTARY(2), // raise Fn layer
+
+ // lower row1
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_5), // %
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_SLASH), // ?
+
+ // raise row0
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_2), // @
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLASH), // |
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_6), // ^
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_8), // *
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_3), // #
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_4), // $
+
+ // raise row1
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_7), // &
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRACKET), // {
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_9), // (
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_1), // !
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_0), // )
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRACKET), // }
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_EQUAL), // +
+};
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_nathan.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_nathan.c
new file mode 100644
index 0000000000..5a0900b66d
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_nathan.c
@@ -0,0 +1,153 @@
+// Author: Nathan Ross Powell <nathanrospowell@gmail.com>
+// https://github.com/nathanrosspowell/tmk_keyboard/blob/planck-jack/keyboard/planck/keymap_nathan.c
+
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ /* 0: main layer
+ * ,-----------------------------------------------------------------------.
+ * |Tab | q | w | e | r | t | y | u | i | o | p | BS |
+ * |-----------------------------------------------------------------------|
+ * |Ctrl | a | s | d | f | g | h | j | k | l | ; | Ret |
+ * |-----------------------------------------------------------------------|
+ * |Shift| z | x | c | v | b | n | m | [ | ( | { | < |
+ * |-----------------------------------------------------------------------|
+ * |Meta | \ | / | Alt |Lower|Space|Space|Upper|Left |Down | Up |Right|
+ * `-----------------------------------------------------------------------'
+ */
+ [0] = KEYMAP_GRID(
+ TAB, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ LCTL, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ RSFT, Z, X, C, V, B, N, M, LBRC, FN10, FN11, FN12,
+ LGUI, BSLS, SLSH, LALT, FN0, SPC, SPC, FN1, LEFT, DOWN, UP, RGHT),
+
+ /* 1: fn left/lower layer
+ * The top row are Visual Studio combos:
+ * 'Run', 'Breakpoint', 'Step over', 'Step into', 'Set cursor to line'
+ * 2nd row are key combos:
+ * 'ctrl-alt-delete', 'ctrl-shift-escape'
+ * 3rd row are macros keys:
+ * 'P0' - 'P5' execute a script on Windows machines
+ * ,-----------------------------------------------------------------------.
+ * | ESC | F5 | F9 | F10 | F11 |S+F11|CSF10|NLock|Num7 |Num8 |Num9 | Del |
+ * |-----------------------------------------------------------------------|
+ * | |C/A/D|C/S/E| Ins |Print|Pause|SLock|Num0 |Num4 |Num5 |Num6 |Num= |
+ * |-----------------------------------------------------------------------|
+ * | | P0 | P1 | P2 | P3 | P4 | P5 |Num. |Num1 |Num2 |Num3 |Num/ |
+ * |-----------------------------------------------------------------------|
+ * | |User | | | | | | |Home |PgDn |PgUp | End |
+ * `-----------------------------------------------------------------------'
+ */
+ [1] = KEYMAP_GRID(
+ ESC, F5, F9, F10, F11, FN30, FN31, NLCK, P7, P8, P9, DEL,
+ TRNS, FN16, FN17, INS, PSCR, PAUS, SLCK, P0, P4, P5, P6, PEQL,
+ TRNS, FN2, FN3, FN4, FN5, FN6, FN7, PDOT, P1, P2, P3, PSLS,
+ TRNS, FN8, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, HOME, PGDN, PGUP, END ),
+
+ /* 2: fn right/raise layer
+ * ,-----------------------------------------------------------------------.
+ * | F1 | F2 | F3 | F4 |F5 | F6 | F7 | F8 | F9 | F10 | F11 | F12 |
+ * |-----------------------------------------------------------------------|
+ * | | ! | @ | # | $ | % | ^ | & | * | - | + | = |
+ * |-----------------------------------------------------------------------|
+ * | | _ | ' | " | ` | ~ | , | . | ] | ) | } | > |
+ * |-----------------------------------------------------------------------|
+ * | |NextT|PrevT| | | | Esc | |Mute |Vol- |Vol+ | P/P |
+ * `-----------------------------------------------------------------------'
+ */
+ [2] = KEYMAP_GRID(
+ F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12,
+ TRNS, FN18, FN19, FN20, FN21, FN22, FN23, FN24, FN25, MINS, FN26, PAST,
+ TRNS, FN27, QUOT, FN28, GRV, FN29, COMM, DOT, RBRC, FN13, FN14, FN15,
+ TRNS, MNXT, MPRV, TRNS, TRNS, TRNS, ESC, TRNS, MUTE, VOLD, VOLU, MPLY ),
+};
+
+enum macro_id {
+ M_P0,
+ M_P1,
+ M_P2,
+ M_P3,
+ M_P4,
+ M_P5,
+ M_USERNAME
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [0] = ACTION_LAYER_MOMENTARY(1), // left/lower layer
+ [1] = ACTION_LAYER_MOMENTARY(2), // right/raise layer
+ // Program macros
+ [2] = ACTION_MACRO(M_P0),
+ [3] = ACTION_MACRO(M_P1),
+ [4] = ACTION_MACRO(M_P2),
+ [5] = ACTION_MACRO(M_P3),
+ [6] = ACTION_MACRO(M_P4),
+ [7] = ACTION_MACRO(M_P5),
+ [8] = ACTION_MACRO(M_USERNAME),
+ // Braces
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_9), // (
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC), // {
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_COMMA), // <
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_0), // )
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC), // }
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_DOT), // >
+ // Combo
+ [16] = ACTION_MODS_KEY(MOD_LALT | MOD_LCTL, KC_DEL), // Ctrl+Alt+Delete
+ [17] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_ESC), // Ctrl+Shft+Escape
+ // Symbols
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_1), // !
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_2), // @
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_3), // #
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_4), // $
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_5), // %
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_6), // ^
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_7), // &
+ [25] = ACTION_MODS_KEY(MOD_LSFT, KC_8), // *
+ [26] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // +
+ [27] = ACTION_MODS_KEY(MOD_LSFT, KC_MINUS), // _
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_QUOTE), // "
+ [29] = ACTION_MODS_KEY(MOD_LSFT, KC_GRAVE), // ~
+ // Debugging
+ [30] = ACTION_MODS_KEY(MOD_LSFT, KC_F11), // Step into
+ [31] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_F10), // Set cursor to line
+ };
+
+// Run a script and pass a key number to it. This is Windows specific and the script needs to be on your path.
+// *open run dialog* keypress.py [PRG_NUM]
+#define ADD_PYTHON_PROGRAM_ON_WIN( PRG_NUM ) MACRO( D(LGUI), T(R), U(LGUI), W(100), T(K), T(E), T(Y), T(P), T(R), T(E), T(S), T(S), T(DOT), T(P), T(Y), T(SPC), T(PRG_NUM), END )
+// *return*
+#define RUN_PYTHON_PROGRAM_ON_WIN MACRO( T(ENT), END )
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt) {
+ keyevent_t event = record->event;
+ switch (id) {
+ case M_P0:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 0 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P1:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 1 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P2:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 2 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P3:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 3 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P4:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 4 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P5:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 5 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_USERNAME:
+ return event.pressed ?
+ MACRO( T(N), T(A), T(T), T(H), T(A), T(N), T(R), T(O), T(S), T(S), T(P), T(O), T(W), T(E), T(L), T(L), END ) :
+ MACRO_NONE;
+ }
+ return MACRO_NONE;
+}
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_paul.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_paul.c
new file mode 100644
index 0000000000..49c90e0196
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_paul.c
@@ -0,0 +1,49 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Paul */
+ TAB, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ FN1, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ ESC, LCTL, LALT, LGUI, FN2, SPC, FN3, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* Paul FN */
+ TRNS, TRNS, TRNS, FN8, FN9, TRNS, TRNS, TRNS, TRNS, MUTE, VOLD, VOLU,
+ FN1, TRNS, TRNS, HOME, END, TRNS, TRNS, TRNS, TRNS, MPRV, MPLY, MNXT,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, UP, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, LEFT, DOWN, RGHT),
+[2] = KEYMAP( /* Paul LOWER */
+ FN22, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, BSPC,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+[3] = KEYMAP( /* Paul RAISE */
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, BSPC,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MINS, EQL, LBRC, RBRC, BSLS,
+ TRNS, F11, F12, F13, F14, F15, F16, F17, F18, F19, F20, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN3, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to Fn1 overlay (FN)
+ [2] = ACTION_LAYER_MOMENTARY(2), // to Fn2 overlay (LOWER)
+ [3] = ACTION_LAYER_MOMENTARY(3), // to Fn3 overlay (RAISE)
+
+ [8] = ACTION_MODS_KEY(MOD_LSFT, KC_HOME),
+ [9] = ACTION_MODS_KEY(MOD_LSFT, KC_END),
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+};
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_peasant.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_peasant.c
new file mode 100644
index 0000000000..ddacb614e6
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_peasant.c
@@ -0,0 +1,51 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = KEYMAP( /* Native */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, FN2,
+ BSPC, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ TAB, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ DEL, LCTL, NO, LSFT, LALT, SPC, NO, LEFT, DOWN, UP, RGHT),
+ [1] = KEYMAP( /* QWERTY->PHOTOSHOP */
+ DELETE, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, FN1,
+ O, G, S, U, T, FN27, F21, F10, F11, F7, F8, F9,
+ TAB, FN4, FN5, FN6, F1, FN7, F18, F19, F23, F20, F22, FN9,
+ COMM, DOT, FN10, FN11, FN3, SPC, FN12, F2, FN8, F3, F14),
+ [2] = KEYMAP( /* 2: FN3 PHOTOSHOP */
+ ESC, FN25, FN26, NO, NO, NO, NO, NO, NO, NO, NO, NO,
+ NO, NO, NO, NO, NO, NO, NO, NO, NO, FN19, FN20, FN21,
+ C, NO, FN22, FN5, NO, FN23, NO, NO, NO, NO, FN13, NO,
+ FN14, FN15, FN16, FN17, FN3, SPC, FN18, NO, NO, F24, NO),
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_DEFAULT_LAYER_SET(0), // set Qwerty layout
+ [2] = ACTION_DEFAULT_LAYER_SET(1), // set Photoshop presets
+ [3] = ACTION_LAYER_ON_OFF(2), // Photoshop function layer
+
+ [4] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F9), // photo folder AHK
+ [5] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_I), // select inverse
+ [6] = ACTION_MODS_KEY(MOD_LSFT, KC_M), // marquee select
+ [7] = ACTION_MODS_KEY(MOD_LALT, KC_BSPC), // fill
+ [8] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_X), // warp
+ [9] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT | MOD_LSFT, KC_F12), // merge all new layer
+ [10] = ACTION_MODS_KEY(MOD_LCTL, KC_MINS), // zoom out
+ [11] = ACTION_MODS_KEY(MOD_LCTL, KC_H), // RBG sliders
+ [12] = ACTION_MODS_KEY(MOD_LCTL, KC_S), // save
+ [13] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_F5), // layer mask from transparancy
+ [14] = ACTION_MODS_KEY(MOD_LALT, KC_LBRC), // prev layer
+ [15] = ACTION_MODS_KEY(MOD_LALT, KC_RBRC), // next layer
+ [16] = ACTION_MODS_KEY(MOD_LCTL, KC_EQL), // zoom in
+ [17] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_H), // HSV sliders
+ [18] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F11), // save as PNG
+ [19] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F7), // gaussian blur
+ [20] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F8), // motion blur
+ [21] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_X), // liquify filter
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS), // prev layer blending
+ [23] = ACTION_MODS_KEY(MOD_LSFT | MOD_LALT, KC_N), // normal layer blending
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // next layer blending
+ [25] = ACTION_MODS_KEY(MOD_LCTL, KC_Z), // step back
+ [26] = ACTION_MODS_KEY(MOD_LCTL, KC_Y), // step forward
+ [27] = ACTION_MODS_KEY(MOD_LCTL, KC_R), // rasterize
+
+};
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_reed.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_reed.c
new file mode 100644
index 0000000000..1aa24e10de
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_reed.c
@@ -0,0 +1,74 @@
+#include "keymap_common.h"
+
+/*
+ * BUILD:
+ * Simply run the command below in the keyboard/planck directory
+ * to build against this keymap
+ *
+ * make KEYMAP=reed COMMON_KEYMAP=true
+ *
+ *
+ * DETAILS:
+ *
+ * This layout works off of Jack's layout, making some changes that I
+ * feel significantly improve the function of the keyboard. Major changes
+ * include adding a "gaming mode" that will allow users to still access
+ * the number keys 1 through 4 easily for games that require it. Also
+ * included is the ability to use the tap/hold function for easy use of
+ * right shift and thumb shift with their tapped companions.
+ *
+ */
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP_GRID( /* Reed */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, FN5,
+ LCTL, CAPS, LALT, LGUI, FN2, FN7, SPC, FN1, LEFT, DOWN, UP, RGHT),
+
+[1] = KEYMAP_GRID( /* Reed EXTREME GAMING */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, FN5,
+ LCTL, 1, 2, 3, 4, SPC, FN2, FN1, LEFT, DOWN, UP, RGHT),
+
+[2] = KEYMAP_GRID( /* Reed RAISE */
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, BSPC,
+ TRNS, FN3, FN4, PAUSE, TRNS, TRNS, TRNS, MINS, EQL, LBRC, RBRC, BSLS,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, MNXT, VOLD, VOLU, MPLY),
+
+[3] = KEYMAP_GRID( /* Reed LOWER */
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, DEL,
+ TRNS, TRNS, INS, HOME, PGUP, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, TRNS, DEL, END, PGDN, F11, F12, F13, TRNS, VOLD, VOLU, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, TRNS, MPRV, MUTE, MPLY, MNXT),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay - RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay - LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+ // Actions for the tap/hold modifiers listed above
+ [5] = ACTION_MODS_TAP_KEY(MOD_RSFT, KC_ENT),
+ [7] = ACTION_MODS_TAP_KEY(MOD_LSFT, KC_BSPC),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_sean.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_sean.c
new file mode 100644
index 0000000000..cb2ef8f138
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_sean.c
@@ -0,0 +1,53 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = KEYMAP( /* Matrix Dvorak */
+ QUOT, COMM, DOT, P, Y, SLSH, EQL, F, G, C, R, L,
+ A, O, E, U, I, ESC, BSPC, D, H, T, N, S,
+ SCLN, Q, J, K, X, TAB, ENT, B, M, W, V, Z,
+ LSFT, LCTL, LALT, LGUI, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+
+ [1] = KEYMAP( /* Matrix Qwerty */
+ Q, W, E, R, T, QUOT, EQL, Y, U, I, O, P,
+ A, S, D, F, G, ESC, BSPC, H, J, K, L, SCLN,
+ Z, X, C, V, B, TAB, ENT, N, M, COMM, DOT, SLSH,
+ LSFT, LCTL, LALT, LGUI, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+
+ [2] = KEYMAP( /* fn1 lower */
+ F1, F2, F3, F4, F5, NO, NO, F6, F7, F8, F9, F10,
+ 1, 2, 3, 4, 5, F18, DEL, 6, 7, 8, 9, 0,
+ FN3, FN4, FN28, GRV, MINS, TRNS, INS, BSLS, LBRC, RBRC, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, HOME, PGDN, PGUP, END),
+
+ [3] = KEYMAP( /* fn2 raise */
+ MRWD, MPLY, MFFD, NO, NO, FN21, FN22, EJCT, PWR, LSFT,PAUSE, RSFT,
+ FN11, FN12, FN13, FN14, FN15, F18, DEL, FN16, FN17, FN18, FN19, FN20,
+ FN3, FN4, FN28, FN23, FN24, TRNS, INS, FN25, FN26, FN27, MPRV, MNXT,
+ TRNS, TRNS, TRNS, TRNS, FN1, TRNS, FN2, NO, VOLD, VOLU, MUTE),
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay LOWER
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay RAISE
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_SLSH),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [25] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+ [26] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [27] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_shane.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_shane.c
new file mode 100644
index 0000000000..8d5ad68753
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_shane.c
@@ -0,0 +1,98 @@
+#include "keymap_common.h"
+#include "action_layer.h"
+#include "action.h"
+#include "action_util.h"
+
+/*
+ Shane's Planck Layout
+ http://www.keyboard-layout-editor.com/#/layouts/015d9011102619d7695c86ffe57cf441
+*/
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = KEYMAP_AND_SWAP( /* Base */
+ TAB, Q, W, E, R, T, Y, U, I, O, P, MINS,
+ LCTL, A, S, D, F, G, H, J, K, L, SCLN, BSPC,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, FN5,
+ /*ALPHA*/FN3, /*HYPER*/ /*SUPER*/LGUI, /*META*/LALT, LCTL, FN2, FN6, FN1, LEFT, DOWN, UP, RGHT),
+ [2] = KEYMAP_AND_SWAP( /* More modifiers */
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, RCTL, RALT, RGUI, TRNS),
+ [4] = KEYMAP_AND_SWAP( /* WASD */
+ TRNS, TRNS, UP, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, LEFT, DOWN, RIGHT, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+ [6] = KEYMAP_AND_SWAP( /* Raise/FN1 */
+ FN23, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, EQL,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, ENT,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, BSLS, TRNS,
+ PAUS, TRNS, TRNS, TRNS, TRNS, BSPC, TRNS, MUTE, PGUP, PGDN, MNXT),
+ [8] = KEYMAP_AND_SWAP( /* Lower/FN2 */
+ ESC, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN19, FN20, TRNS,
+ TRNS, TRNS, TRNS, TRNS, CAPS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, QUOT,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN24, FN25, LBRC, RBRC, TRNS, TRNS,
+ FN4, TRNS, TRNS, TRNS, TRNS, ENT, TRNS, MPLY, VOLD, VOLU, MPRV),
+};
+
+enum function_id {
+ SPACE_FN,
+};
+
+void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ switch (id) {
+ case SPACE_FN:
+ if (record->event.pressed) {
+ // Change the keyboard maps.
+ // Whatever even layer's are on, turn on the odd one's too.
+ for (uint8_t i = 0; i < 9; i += 2) {
+ if (layer_state & (1UL << i))
+ layer_on(i + 1);
+ }
+ layer_on(1);
+ } else {
+ // turn off all the even layers.
+ for (uint8_t i = 0; i < 9; i += 2)
+ layer_off(i + 1);
+
+ if (record->tap.count != 0) {
+ // Space was tapped rather than used like a modifier.
+ // So send a space up and down event.
+ add_key(KC_SPC);
+ send_keyboard_report();
+ del_key(KC_SPC);
+ send_keyboard_report();
+ }
+ }
+ break;
+ }
+}
+
+
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(6), // to fist Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(8), // to second Fn overlay
+ [3] = ACTION_LAYER_TOGGLE(2), // toggle more modifiers
+ [4] = ACTION_LAYER_TOGGLE(4), // toggle wasd
+ [5] = ACTION_MODS_TAP_KEY(MOD_RSFT, KC_ENT),
+ [6] = ACTION_FUNCTION_TAP(SPACE_FN),
+
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [25] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [26] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+}; \ No newline at end of file
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_simon.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_simon.c
new file mode 100644
index 0000000000..37951364be
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_simon.c
@@ -0,0 +1,44 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Jack */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, DOT, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SCLN, DEL,
+ LCTL, ENT, LALT, CAPS, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* Jack RAISE */
+ TRNS, F1, F2, F3, F4, NO, FN11, FN9, FN12, NO, FN14, TRNS,
+ TRNS, F5, F6, F7, F8, FN16, SLSH, MINS, EQL, LBRC, FN8, TRNS,
+ TRNS, F9, F10, F11, F12, F15, F16, FN22, SCLN, MINS, QUOT, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+[2] = KEYMAP( /* Jack LOWER */
+ FN22, 1, 2, 3, FN13, FN14, FN15, FN16, FN17, FN18, FN19, BSPC,
+ TRNS, 4, 5, 6, TRNS, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, 7, 8, 9, 0, FN28, FN15, F7, F8, F9, F10, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+
+ [8] = ACTION_MODS_KEY(MOD_LSFT, KC_SLSH),
+ [9] = ACTION_MODS_KEY(MOD_LSFT, KC_QUOT),
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_tim.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_tim.c
new file mode 100644
index 0000000000..7444f3877b
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_tim.c
@@ -0,0 +1,44 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP(
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, RSFT,
+ LCTL, LALT, DEL, LGUI, FN2, SPC, FN1, F2, F5, F9, F12),
+[2] = KEYMAP( /* RAISE */
+ TRNS, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, BSPC,
+ GRV, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MINS, EQL, LBRC, RBRC, BSLS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, QUOT, FN29, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, TRNS, TRNS, TRNS, TRNS),
+[3] = KEYMAP( /* LOWER */
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, BSPC,
+ FN22, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, QUOT, FN29, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+ [29] = ACTION_MODS_KEY(MOD_LSFT, KC_QUOT),
+};
diff --git a/keyboard/planck/old_keymap_files/common_keymaps/keymap_wilba.c b/keyboard/planck/old_keymap_files/common_keymaps/keymap_wilba.c
new file mode 100644
index 0000000000..9781f8fcd8
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/common_keymaps/keymap_wilba.c
@@ -0,0 +1,56 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Wilba */
+ FN27, FN28, FN29, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ LCTL, LGUI, LALT, RSFT, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* Wilba Alternate */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ LCTL, LGUI, LALT, RSFT, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+[2] = KEYMAP( /* Wilba LOWER */
+ TRNS, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, TRNS,
+ TRNS, F11, F12, LBRC, RBRC, FN20, EQL, FN23, FN24, MINS, FN21, TRNS,
+ TRNS, BSLS, GRV, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN1, TRNS, TRNS, MNXT, VOLD, VOLU, MPLY),
+[3] = KEYMAP( /* Wilba RAISE */
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, TRNS,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, TRNS,
+ TRNS, FN25, FN22, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // LOWER
+ [2] = ACTION_LAYER_MOMENTARY(3), // RAISE
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1), // !
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2), // @
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3), // #
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4), // $
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5), // %
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6), // ^
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7), // &
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8), // *
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9), // (
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0), // )
+
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS), // _
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // +
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV), // ~
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC), // {
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC), // }
+ [25] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS), // |
+
+ [26] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+
+ [27] = ACTION_BACKLIGHT_TOGGLE(),
+ [28] = ACTION_BACKLIGHT_INCREASE(),
+ [29] = ACTION_BACKLIGHT_DECREASE()
+
+};
diff --git a/keyboard/planck/old_keymap_files/keymap_common.c b/keyboard/planck/old_keymap_files/keymap_common.c
new file mode 100644
index 0000000000..fdb1769e1c
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/keymap_common.c
@@ -0,0 +1,30 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+#include "keymap_common.h"
+
+
+/* translates key to keycode */
+uint8_t keymap_key_to_keycode(uint8_t layer, keypos_t key)
+{
+ return pgm_read_byte(&keymaps[(layer)][(key.row)][(key.col)]);
+}
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint8_t keycode)
+{
+ return (action_t){ .code = pgm_read_word(&fn_actions[FN_INDEX(keycode)]) };
+}
diff --git a/keyboard/planck/old_keymap_files/keymap_common.h b/keyboard/planck/old_keymap_files/keymap_common.h
new file mode 100644
index 0000000000..d46df92876
--- /dev/null
+++ b/keyboard/planck/old_keymap_files/keymap_common.h
@@ -0,0 +1,129 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+#ifndef KEYMAP_COMMON_H
+#define KEYMAP_COMMON_H
+
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/pgmspace.h>
+#include "keycode.h"
+#include "action.h"
+#include "action_macro.h"
+#include "report.h"
+#include "host.h"
+// #include "print.h"
+#include "debug.h"
+#include "keymap.h"
+
+
+extern const uint8_t keymaps[][MATRIX_ROWS][MATRIX_COLS];
+extern const uint16_t fn_actions[];
+
+
+// MIT Layout
+/*
+ * ,-----------------------------------------------------------------------.
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | |
+ * `-----------------------------------------------------------------------'
+ */
+#define KEYMAP( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K35, K37, K38, K39, K3A, K3B \
+) { \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_##K35, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B } \
+}
+
+// Grid Layout
+/*
+ * ,-----------------------------------------------------------------------.
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * `-----------------------------------------------------------------------'
+ */
+#define KEYMAP_GRID( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3B \
+) { \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_##K36, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B } \
+}
+
+#define KEYMAP_REVERSE( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K35, K37, K38, K39, K3A, K3B \
+ ) { \
+ { KC_##K0B, KC_##K0A, KC_##K09, KC_##K08, KC_##K07, KC_##K06, KC_##K05, KC_##K04, KC_##K03, KC_##K02, KC_##K01, KC_##K00 }, \
+ { KC_##K1B, KC_##K1A, KC_##K19, KC_##K18, KC_##K17, KC_##K16, KC_##K15, KC_##K14, KC_##K13, KC_##K12, KC_##K11, KC_##K10 }, \
+ { KC_##K2B, KC_##K2A, KC_##K29, KC_##K28, KC_##K27, KC_##K26, KC_##K25, KC_##K24, KC_##K23, KC_##K22, KC_##K21, KC_##K20 }, \
+ { KC_##K3B, KC_##K3A, KC_##K39, KC_##K38, KC_##K37, KC_##K35, KC_##K35, KC_##K34, KC_##K33, KC_##K32, KC_##K31, KC_##K30 }, \
+ }
+
+#define KEYMAP_AND_REVERSE(args...) KEYMAP(args), KEYMAP_REVERSE(args)
+
+#define KEYMAP_SWAP( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K35, K37, K38, K39, K3A, K3B \
+ ) { \
+ { KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B, KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05 }, \
+ { KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B, KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15 }, \
+ { KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B, KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25 }, \
+ { KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B, KC_##K35, KC_##K35, KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34 }, \
+}
+
+#define KEYMAP_AND_SWAP(args...) KEYMAP(args), KEYMAP_SWAP(args)
+
+/*
+ Keymap for the Planck 48 key variant.
+ */
+#define KEYMAP_48( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3B \
+) { \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_##K36, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B }, \
+}
+
+
+#endif
diff --git a/keyboard/planck/planck.c b/keyboard/planck/planck.c
new file mode 100644
index 0000000000..b62862af04
--- /dev/null
+++ b/keyboard/planck/planck.c
@@ -0,0 +1,31 @@
+#include "planck.h"
+
+__attribute__ ((weak))
+void * matrix_init_user(void) {
+
+};
+
+__attribute__ ((weak))
+void * matrix_scan_user(void) {
+
+};
+
+void * matrix_init_kb(void) {
+ #ifdef BACKLIGHT_ENABLE
+ backlight_init_ports();
+ #endif
+
+ // Turn status LED on
+ DDRE |= (1<<6);
+ PORTE |= (1<<6);
+
+ if (matrix_init_user) {
+ (*matrix_init_user)();
+ }
+};
+
+void * matrix_scan_kb(void) {
+ if (matrix_scan_user) {
+ (*matrix_scan_user)();
+ }
+}; \ No newline at end of file
diff --git a/keyboard/planck/planck.h b/keyboard/planck/planck.h
new file mode 100644
index 0000000000..4e59aef566
--- /dev/null
+++ b/keyboard/planck/planck.h
@@ -0,0 +1,38 @@
+#ifndef PLANCK_H
+#define PLANCK_H
+
+#include "matrix.h"
+#include "keymap_common.h"
+#include "backlight.h"
+#include <stddef.h>
+
+#define PLANCK_MIT( \
+ k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b, \
+ k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b, \
+ k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b, \
+ k30, k31, k32, k33, k34, k35, k37, k38, k39, k3a, k3b \
+) \
+{ \
+ { k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b }, \
+ { k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b }, \
+ { k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b }, \
+ { k30, k31, k32, k33, k34, k35, k35, k37, k38, k39, k3a, k3b } \
+}
+
+#define PLANCK_GRID( \
+ k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b, \
+ k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b, \
+ k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b, \
+ k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b \
+) \
+{ \
+ { k00, k01, k02, k03, k04, k05, k06, k07, k08, k09, k0a, k0b }, \
+ { k10, k11, k12, k13, k14, k15, k16, k17, k18, k19, k1a, k1b }, \
+ { k20, k21, k22, k23, k24, k25, k26, k27, k28, k29, k2a, k2b }, \
+ { k30, k31, k32, k33, k34, k35, k36, k37, k38, k39, k3a, k3b } \
+}
+
+void * matrix_init_user(void);
+void * matrix_scan_user(void);
+
+#endif \ No newline at end of file
diff --git a/keyboard/planck/planck_pcb.hex b/keyboard/planck/planck_pcb.hex
new file mode 100644
index 0000000000..11f523c058
--- /dev/null
+++ b/keyboard/planck/planck_pcb.hex
@@ -0,0 +1,1544 @@
+:100000000C949D020C94E1020C94E1020C94E10228
+:100010000C94E1020C94E1020C94E1020C94E102D4
+:100020000C94E1020C94E1020C941C120C94EE125C
+:100030000C948D240C94E1020C94E1020C94E102E6
+:100040000C94E1020C94E1020C94E1020C94E102A4
+:100050000C94E1020C94FA240C94E1020C94E10259
+:100060000C94E1020C94E1020C94E1020C94E10284
+:100070000C94E1020C94E1020C94E1020C94E10274
+:100080000C94860A0C94E1020C94E1020C94E102B7
+:100090000C94E1020C94E1020C94E1020C94E10254
+:1000A0000C94E1020C94E1020C94E10207634236E5
+:1000B000B79BD8A71A39685618AEBAAB558C1D3CF9
+:1000C000B7CC5763BD6DEDFD753EF6177231BF00BD
+:1000D0000000803F08000000BE922449123EABAAF7
+:1000E000AA2ABECDCCCC4C3E00000080BEABAAAA52
+:1000F000AA3E00000000BF000000803F000000009A
+:1001000000084178D3BB4387D1133D190E3CC3BDD2
+:100110004282AD2B3E68EC8276BED98FE1A93E4C7F
+:1001200080EFFFBE01C4FF7F3F0000000000000021
+:10013000F1A4F1A3018C028C048C2B0014001A0092
+:100140000800150017001C0018000C001200130016
+:100150002A00290004001600070009000A000B000D
+:100160000D000E000F0033003400E1001D001B00E5
+:100170000600190005001100100036003700380095
+:1001800028000030E000E200E30002202C002C00F8
+:1001900001205000510052004F002B0014001A00A3
+:1001A000090013000A000D000F0018001C003300A6
+:1001B0002A002900040015001600170007000B0094
+:1001C000110008000C0012003400E1001D001B00AB
+:1001D0000600190005000E00100036003700380038
+:1001E00028000030E000E200E30002202C002C0098
+:1001F00001205000510052004F002B003400360007
+:10020000370013001C0009000A00060015000F004B
+:100210002A00290004001200080018000C00070042
+:100220000B001700110016003800E1003300140025
+:100230000D000E001B00050010001A0019001D0023
+:1002400028000030E000E200E30002202C002C0037
+:1002500001205000510052004F0035021E021F02C3
+:100260002002210222022302240225022602270262
+:100270002A0001003A003B003C003D003E003F00E8
+:100280002D022E022F0230023102010040004100F7
+:100290004200430044004500032004200520005094
+:1002A0000100010001000100010002200100010025
+:1002B0000100AB00AA00A900AE0035001E001F001F
+:1002C0002000210022002300240025002600270012
+:1002D0002A0001003A003B003C003D003E003F0088
+:1002E0002D002E002F0030003100010040004100A1
+:1002F0004200430044004500032004200520005034
+:1003000001000100010001000100010001000100E5
+:100310000120AB00AA00A900AE0028035400680029
+:100320006500200050006C0061006E0063006B00EF
+:1003300020004B006500790062006F0061007200D0
+:10034000640000002C034F007200740068006F000E
+:100350006C0069006E0065006100720020004B00B7
+:100360006500790062006F00610072006400730034
+:100370000000040309040902D000060100A03209AC
+:100380000400000103010100092111010001223FC5
+:10039000000705810308000A0904010001030102A6
+:1003A00000092111010001224D0007058203080008
+:1003B0000A090402000103000000092111010001E3
+:1003C0002236000705830308000A0904030002031C
+:1003D000000000092111010001222000070584030B
+:1003E00020000107050403200001090404000001A6
+:1003F00001000009240100010900010509040500AC
+:10040000020103000007240100014100062402014B
+:100410000100062402020200092403010301020173
+:10042000000924030204010101000905060240003D
+:1004300005000005250101010905850240000500B0
+:100440000005250101031201100100000008EDFE66
+:1004500060600100010200010631FF0974A1010979
+:1004600075150025FF952075088102097615002570
+:10047000FF952075089102C005010980A101850240
+:1004800016010026B7001A01002AB7007510950161
+:100490008100C0050C0901A1018503160100269CFD
+:1004A000021A01002A9C02751095018100C0050105
+:1004B0000902A1010901A100050919012905150079
+:1004C00025019505750181029501750381010501DD
+:1004D000093009311581257F950275088106093893
+:1004E0001581257F950175088106050C0A380215CE
+:1004F00081257F950175088106C0C005010906A107
+:1005000001050719E029E715002501950875018106
+:1005100002950175088101050819012905950575E0
+:100520000191029501750391010507190029FF1535
+:100530000025FF950675088100C011241FBECFEF6E
+:10054000DAE0DEBFCDBF04B603FE24C0809178039D
+:1005500090917903A0917A03B0917B038730904BFF
+:10056000A740B04BB9F4109278031092790310921F
+:100570007A0310927B0314BE84B7877F84BF88E11F
+:100580000FB6F89480936000109260000FBEE0E018
+:10059000F8E3099511E0A0E0B1E0E2EAFFE502C06E
+:1005A00005900D92A63BB107D9F713E0A6EBB1E099
+:1005B00001C01D92A837B107E1F70E94F90E0C9413
+:1005C000CF2F0C9400000895089561110DC0FC0117
+:1005D0008281882331F085EE0E949D190E94B62BFE
+:1005E00003C085EE0E94651A80E090E008958B3B81
+:1005F000910568F4883A910530F5853A9105C0F483
+:100600008430910598F4019709F06FC071C0803E65
+:10061000910508F46AC0883E910540F09C01205F76
+:1006200031092031310508F060C05CC09C01A1C0D7
+:10063000853A910509F45FC0863A910509F45EC0D8
+:1006400023E830E496C0883A910509F45AC0893A03
+:10065000910509F459C08A3A910509F458C08B3ABA
+:10066000910509F457C08C3A910509F456C08D3AAA
+:10067000910509F455C0803B910509F454C08E3AA8
+:10068000910509F453C08F3A910509F452C0813B9A
+:10069000910509F451C0823B910509F450C0833B98
+:1006A000910509F44FC0843B910509F44EC0853B88
+:1006B000910509F44DC0863B910509F44CC0873B78
+:1006C000910509F44BC0883B910509F44AC0893B68
+:1006D000910509F449C08A3B910509F048C02AE216
+:1006E00036E447C09C01306544C020E030E041C0A2
+:1006F00021E030E03EC021E830E43BC022E830E4B5
+:1007000038C022EE34E435C029EE34E432C02AEE9B
+:1007100034E42FC025EB34E42CC026EB34E429C0AC
+:1007200027EB34E426C02CEC34E423C02DEC34E475
+:1007300020C023E835E41DC02AE835E41AC022E9C8
+:1007400035E417C024E935E414C021E236E411C0D1
+:1007500023E236E40EC024E236E40BC025E236E4A0
+:1007600008C026E236E405C027E236E402C020E0F5
+:1007700034E4C90108959CE0799FF001112490E3CD
+:10078000899FE00DF11D1124E60FF11DEE0FFF1FF3
+:10079000E65CFE4F25913491C9010895880F991F99
+:1007A00082559040FC0125913491C9010895880F2C
+:1007B000991F825D9E4FFC0125913491C9010895D6
+:1007C0000E94BB039C013A9521153F4108F4DFC00C
+:1007D0009C0130522115304120F49F700E94D703B4
+:1007E00008959C0130532115304118F49927906CDD
+:1007F00008959C0130542031310520F48F709927E1
+:10080000946D0895803120E4920719F480E091ED11
+:100810000895813140E4940719F480E090ED089543
+:10082000823120E4920719F480E092ED089583313B
+:1008300040E4940719F480E093ED0895811520E5D4
+:10084000920711F40C941F25813040E5940731F490
+:100850008091680281608093680208959C013056FF
+:100860002115304108F402C097FF02C0906F08952F
+:10087000803E9105E0F4803C910568F58133910557
+:1008800009F474C048F48932910509F46AC08A32C7
+:10089000910509F07AC074C089339105F9F0823866
+:1008A0009105E1F08533910509F06FC050C0833E9A
+:1008B0009105A9F140F4803E9105C9F0823E910571
+:1008C00009F063C01BC0863E910571F1873E91051A
+:1008D00009F05BC037C00E94CE03089520917B02CF
+:1008E00020FD02C021FF51C080EE90E04EC08091FB
+:1008F0007B0280FFF9CF89E390E047C080917B02C3
+:1009000082FF0AC080917B0284FF03C080E090E0F8
+:100910003CC083EE90E039C082EE90E036C080911A
+:100920007B0282FFEFCFF8CF80917B0283FF07C06D
+:1009300080917B0284FDEACF87EE90E026C086EEB0
+:1009400090E023C080917B0283FFF2CFF8CF8091AB
+:100950007B0285FF03C089E290E017C085E390E049
+:1009600014C080917B0285FDF9CFF5CF80917B0289
+:1009700086FF03C08AE290E008C081E390E005C0F2
+:1009800080917B0286FDF9CFF5CF0E94F702089592
+:100990005F926F927F928F929F92AF92BF92CF920F
+:1009A000DF92EF92FF920F931F93CF93DF93CDB718
+:1009B000DEB728970FB6F894DEBF0FBECDBF9E01FD
+:1009C0002F5F3F4F4E0189E0880E911C60E070E080
+:1009D00000E010E0E12CF12CC12CD12CA12CB12C89
+:1009E00088E0782E622E532E41E050E0E3E2F1E001
+:1009F000A62DB52D872D01900D928A95E1F7F9016D
+:100A0000819191919F01FC01E07FFF27E032F10588
+:100A100059F48F709927FA0102C0EE0FFF1F8A95D3
+:100A2000E2F7AE2ABF2A37C0E033F10559F48F70E0
+:100A30009927FA0102C0EE0FFF1F8A95E2F7CE2A2E
+:100A4000DF2A29C0E034F10559F48F709927FA01A3
+:100A500002C0EE0FFF1F8A95E2F7EE2AFF2A1BC0A5
+:100A6000E035F10559F48F709927FA0102C0EE0FB5
+:100A7000FF1F8A95E2F70E2B1F2B0DC0E036F10504
+:100A800051F48F709927FA0102C0EE0FFF1F8A956B
+:100A9000E2F76E2B7F2B2815390509F0A7CF94B10B
+:100AA0008A2D8095892384B985B18A2985B997B122
+:100AB0008C2D8095892387B988B18C2988B99AB102
+:100AC0008E2D809589238AB98BB18E298BB99DB1E2
+:100AD000802F809589238DB98EB1802B8EB990B3EC
+:100AE000862F8095892380BB81B3862B81BB289676
+:100AF0000FB6F894DEBF0FBECDBFDF91CF911F912F
+:100B00000F91FF90EF90DF90CF90BF90AF909F90AC
+:100B10008F907F906F905F9008955F926F927F9219
+:100B20008F929F92AF92BF92CF92DF92EF92FF92FD
+:100B30000F931F93CF93DF93CDB7DEB768970FB6B0
+:100B4000F894DEBF0FBECDBF85B7806885BF85B77F
+:100B5000806885BF0E94CF076E9A769A0E94C8046B
+:100B60009E012F5F3F4F4E0189E1880E911C60E08E
+:100B700070E000E010E0E12CF12CC12CD12CA12C74
+:100B8000B12C98E1792E622E532E41E050E0EBE239
+:100B9000F1E0A62DB52D872D01900D928A95E1F7F4
+:100BA000F901819191919F01FC01E07FFF27E032E3
+:100BB000F10559F48F709927FA0102C0EE0FFF1F5B
+:100BC0008A95E2F7AE2ABF2A37C0E033F10559F41F
+:100BD0008F709927FA0102C0EE0FFF1F8A95E2F786
+:100BE000CE2ADF2A29C0E034F10559F48F70992705
+:100BF000FA0102C0EE0FFF1F8A95E2F7EE2AFF2AE4
+:100C00001BC0E035F10559F48F709927FA0102C035
+:100C1000EE0FFF1F8A95E2F70E2B1F2B0DC0E0365B
+:100C2000F10551F48F709927FA0102C0EE0FFF1FF2
+:100C30008A95E2F76E2B7F2B2815390509F0A7CF8F
+:100C400094B18A2D8095892384B985B18A2985B983
+:100C500097B18C2D8095892387B988B18C2988B963
+:100C60009AB18E2D809589238AB98BB18E298BB943
+:100C70009DB1802F809589238DB98EB1802B8EB93F
+:100C800090B3862F8095892380BB81B3862B81BB4F
+:100C90001092B7011092B6011092BF011092BE01DE
+:100CA0001092B9011092B8011092C1011092C001C6
+:100CB0001092BB011092BA011092C3011092C201AE
+:100CC0001092BD011092BC011092C5011092C40196
+:100CD00068960FB6F894DEBF0FBECDBFDF91CF91FF
+:100CE0001F910F91FF90EF90DF90CF90BF90AF904A
+:100CF0009F908F907F906F905F9008955F926F921A
+:100D00007F928F929F92AF92BF92CF92DF92EF929B
+:100D1000FF920F931F93CF93DF93CDB7DEB7A097CA
+:100D20000FB6F894DEBF0FBECDBF7E0149E1E40EE1
+:100D3000F11C2EEBC22E21E0D22E5E0151E2A50E57
+:100D4000B11C38E0532E470101E010E048E1642E69
+:100D500055E0752EE3E2F1E0D401852D01900D926E
+:100D60008A95E1F7F701819191917F019C01207FA4
+:100D700033272032310589F424B18F709927A801D7
+:100D800002C0440F551F8A95E2F7CA01242B24B9EB
+:100D900095B18095892385B94FC02033310589F4F9
+:100DA00027B18F709927F80102C0EE0FFF1F8A95B7
+:100DB000E2F7CF012E2B27B998B18095892388B906
+:100DC0003BC02034310589F42AB18F709927A801DE
+:100DD00002C0440F551F8A95E2F7CA01242B2AB995
+:100DE0009BB1809589238BB927C02035310589F4C3
+:100DF0002DB18F709927F80102C0EE0FFF1F8A9561
+:100E0000E2F7CF012E2B2DB99EB1809589238EB9A3
+:100E100013C02036310581F420B38F709927A801C3
+:100E200002C0440F551F8A95E2F7CA01242B20BB4C
+:100E300091B38095892381BB50EA5A95F1F7BE01A1
+:100E40006F5F7F4F80E090E020E030E0EBE2F1E088
+:100E5000DE011196462D01900D924A95E1F7FB01B6
+:100E600041915191BF01FA01E07FFF27E032F10586
+:100E700011F4E3B113C0E033F10511F4E6B10EC093
+:100E8000E034F10511F4E9B109C0E035F10511F4E0
+:100E9000ECB104C0E036F105B9F4EFB1F0E04F7009
+:100EA000552702C0F595E7954A95E2F7E0FD08C0A1
+:100EB000A801022E02C0440F551F0A94E2F702C097
+:100EC00040E050E0842B952B2F5F3F4F2C303105B5
+:100ED00009F0BCCFF601208131812817390721F0B4
+:100EE00091838083709200010E94C804F2E0CF0ECB
+:100EF000D11CEA14FB0409F02DCF80910001882356
+:100F000061F1815080930001811121C08091BE0167
+:100F10009091BF019093B7018093B6018091C00179
+:100F20009091C1019093B9018093B8018091C20161
+:100F30009091C3019093BB018093BA018091C40149
+:100F40009091C5019093BD018093BC0106C08FE9CB
+:100F50009FE00197F1F700C0000081E0A0960FB676
+:100F6000F894DEBF0FBECDBFDF91CF911F910F91DF
+:100F7000FF90EF90DF90CF90BF90AF909F908F90B9
+:100F80007F906F905F900895E82FF0E0EE0FFF1FC5
+:100F9000EA54FE4F80819181089508950895279A1B
+:100FA0002F988FEF9FEF90938700809386008AE0C1
+:100FB0008093800089E1809381000C945F2B8111E4
+:100FC0000BC080918000877F8093800010928D00FD
+:100FD00010928C002F9808952F98833041F48091BF
+:100FE00080008860809380008FEF9FEF12C0909107
+:100FF000800098609093800023E030E0281B310946
+:10100000220F331F8FEF9FEF02C0969587952A9589
+:10101000E2F790938D0080938C0008950F931F93B7
+:10102000CF93DF93CDB7DEB7CC58D1090FB6F89484
+:10103000DEBF0FBECDBF8C01862F642F882379F0D1
+:10104000F80192812FE7482F992329F08DE792E04C
+:101050000E94F81404C08DE792E00E940815F80180
+:1010600080818B3061F49181933009F068C0828176
+:10107000882309F4CDC0809103018F5F0EC08A30B0
+:10108000E1F5F8019181933009F059C082818823FC
+:1010900009F4BEC08091030181508093030120E0D8
+:1010A0004BE760E08DE792E00E94E81420E04BE718
+:1010B00061E08DE792E00E94E81420E04BE762E0F7
+:1010C0008DE792E00E94E81420E04BE763E08DE7B3
+:1010D00092E00E94E81420E04BE764E08DE792E0A4
+:1010E000C457DF4F0FB6F894DEBF0FBECDBFDF9100
+:1010F000CF911F910F910C94E814893069F4F80195
+:1011000091819330E1F492819923C9F0809101019A
+:101110009091020101960EC0883089F4F801918106
+:10112000933069F49281992351F08091010190915B
+:10113000020101979093020180930101B0CFF80161
+:10114000928140910301992391F196E4E3E4F1E067
+:10115000DE01A95BBF4F01900D929A95E1F7405DCA
+:10116000F8019181FCE09F9F40191124E091010159
+:10117000F0910201E80FF11DEE0FFF1F87E490E0F0
+:101180008C0F9D1FE80FF91F8081480F2FE760E04B
+:101190008DE792E0C457DF4F0FB6F894DEBF0FBE65
+:1011A000CDBFDF91CF911F910F910C94F81496E46D
+:1011B000E3E4F1E0DE01119601900D929A95E1F7DA
+:1011C000405DF8019181FCE09F9F40191124E0915E
+:1011D0000101F0910201E80FF11DEE0FFF1F81E008
+:1011E00090E08C0F9D1FE80FF91F8081480F2FE7BB
+:1011F00060E08DE792E0C457DF4F0FB6F894DEBF92
+:101200000FBECDBFDF91CF911F910F910C940815A8
+:10121000C457DF4F0FB6F894DEBF0FBECDBFDF91CE
+:10122000CF911F910F910895CF93DF93EA019B0116
+:10123000AC0160E074E284E79BE40E945F2C0E94B2
+:10124000C72C709397006093960020E130E02C1B30
+:101250003D0B02C0759567952A95E2F7709399004A
+:1012600060939800DF91CF9108951092020210923E
+:10127000010210929000109291001092FD011092C4
+:10128000FE011092FF01109200021092FC011092D8
+:10129000FB01E9EDF1E0A9ECB1E01192119211929C
+:1012A00011921D921D9281E0E93FF807B1F7089570
+:1012B000AF92BF92CF92DF92EF92FF920F931F9364
+:1012C000CF93DF936B017C0109EF11E047EDA42E72
+:1012D00041E0B42EC7E0D0E0A7019601F801929159
+:1012E0008291729162918F010E945B2C882349F058
+:1012F0002197F2E0AF1AB108CF3F8FEFD80761F71F
+:1013000034C0F8011082118212821382F501118219
+:101310001082FE01EE0FFF1FEE0FFF1FE752FE4F80
+:10132000DE01AA0FBB1FA753BE4FCE011AC0019604
+:1013300044815581668177814083518362837383C1
+:10134000148215821682178212962D913C91139762
+:1013500011963C932E9313961C921E9212973496DC
+:1013600012968730910519F7C3CF809101029091B1
+:101370000202019797FD05C090930202809301023B
+:1013800004C01092020210920102E0910102F09159
+:101390000202309789F410929000109291001092FE
+:1013A000FD011092FE011092FF01109200021092B6
+:1013B000FC011092FB019EC03197DF01AA0FBB1FF9
+:1013C000AA0FBB1FA752BE4FCD90DD90ED90FC90B1
+:1013D000EE0FFF1FE753FE4FC081D181A090FD01AA
+:1013E000B090FE010091FF0110910002A70196014B
+:1013F0006A2D7B2D802F912F0E945B2C87FF2FC0A1
+:1014000081E08093C801AE016A2D7B2D802F912F42
+:101410000E9414092091FD013091FE014091FF01CD
+:1014200050910002C701B6010E94F62B20E030E087
+:101430004AEF53E40E945F2C9B01AC016A2D7B2D87
+:10144000802F912F0E94F72B5B018C01A701960141
+:101450007B2D912F0E945B2C1816ACF638C0A7018B
+:1014600096016A2D7B2D802F912F0E94AA2D181690
+:1014700084F581E08093C801AE016A2D7B2D802F19
+:10148000912F0E941409A70196016091FD017091AE
+:10149000FE018091FF01909100020E94F62B20E056
+:1014A00030E04AEF53E40E945F2C9B01AC016A2DAF
+:1014B0007B2D802F912F0E94F62B5B018C01A701C1
+:1014C00096017B2D912F0E94AA2D87FFD5CF1092D8
+:1014D000C801AE01C701B6010E941409C092FD0106
+:1014E000D092FE01E092FF01F0920002D093FC0145
+:1014F000C093FB01DF91CF911F910F91FF90EF906F
+:10150000DF90CF90BF90AF90089508951F920F92F3
+:101510000FB60F9211242F933F934F935F936F93C6
+:101520007F938F939F93AF93BF93EF93FF9380919C
+:10153000960090919700892B09F455C08091C801BD
+:10154000811151C08091F9019091FA01813091058A
+:1015500071F082309105C1F0892BC1F52091FD0118
+:101560003091FE014091FF01509100021DC0609139
+:10157000FD017091FE018091FF01909100029B019D
+:10158000AC010E94F72B0EC020E030E040E450E4B4
+:101590006091FD017091FE018091FF019091000228
+:1015A0000E94AE2D9B01AC0160E074E284E79BE4F5
+:1015B0000E945F2C0E94C72C709397006093960046
+:1015C0007595679570939900609398008091F901E3
+:1015D0009091FA01019663E070E00E948A2F909347
+:1015E000FA018093F901FF91EF91BF91AF919F9123
+:1015F0008F917F916F915F914F913F912F910F90BC
+:101600000FBE0F901F901895AF92BF92CF92DF92AE
+:10161000EF92FF920F931F93CF93DF936B017C01A7
+:10162000EA0120E030E0A9010E94AA2D18160CF072
+:10163000B4C03E9A82E8809390008AE18093910042
+:10164000A090FD01B090FE010091FF0110910002F9
+:1016500020E030E0A9016A2D7B2D802F912F0E9480
+:101660005B2C81112DC0AE01C701B6010E94140987
+:10167000C092FD01D092FE01E092FF01F0920002C3
+:10168000D093FC01C093FB01809101029091020272
+:10169000FC01EE0FFF1FEE0FFF1FE752FE4FC0824F
+:1016A000D182E282F382FC01EE0FFF1FE753FE4F6F
+:1016B000D183C083019690930202809301026DC092
+:1016C000A70196016A2D7B2D802F912F0E945B2C04
+:1016D00087FF2CC0AE016A2D7B2D802F912F0E9499
+:1016E00014092091FD013091FE014091FF015091BC
+:1016F0000002C701B6010E94F62B20E030E04AEF5D
+:1017000053E40E945F2C9B01AC016A2D7B2D802F3E
+:10171000912F0E94F72B5B018C01A70196017B2D75
+:10172000912F0E945B2C1816ACF69DCFA701960155
+:101730006A2D7B2D802F912F0E94AA2D18160CF058
+:1017400092CFAE016A2D7B2D802F912F0E9414091C
+:10175000A70196016091FD017091FE018091FF014A
+:10176000909100020E94F62B20E030E04AEF53E413
+:101770000E945F2C9B01AC016A2D7B2D802F912F45
+:101780000E94F62B5B018C01A70196017B2D912F06
+:101790000E94AA2D87FFD5CF66CFDF91CF911F91F1
+:1017A0000F91FF90EF90DF90CF90BF90AF90089592
+:1017B00080910C020895CF93DF9300D01F92CDB794
+:1017C000DEB720916E03243021F523E029839B832B
+:1017D0008A832093E9008FEF06C095ED9A95F1F783
+:1017E0000000882329F09091E800815095FFF5CF03
+:1017F0008091E80085FF0DC040E050E063E070E0BC
+:10180000CE0101960E94BA0F8091E8008E778093F6
+:10181000E8000F900F900F90DF91CF910895CF9334
+:10182000DF9300D01F92CDB7DEB720916E03243036
+:1018300029F522E029839B838A8383E08093E90052
+:101840008FEF06C095ED9A95F1F70000882329F0F7
+:101850009091E800815095FFF5CF8091E80085FFD9
+:101860000DC040E050E063E070E0CE0101960E94C0
+:10187000BA0F8091E8008E778093E8000F900F9068
+:101880000F90DF91CF91089520916E032430F9F4E9
+:1018900022E02093E9002FEF06C035ED3A95F1F7ED
+:1018A0000000222329F03091E800215035FFF5CFC8
+:1018B0002091E80025FF0BC040E050E065E070E0BB
+:1018C0000E94BA0F8091E8008E778093E800089517
+:1018D000CF93DF93EC0180916E03843041F581E07A
+:1018E0008093E9008FEF06C095ED9A95F1F700001F
+:1018F000882329F09091E800815095FFF5CF8091E1
+:10190000E80085FF14C040E050E068E070E0CE01E0
+:101910000E94BA0F8091E8008E778093E80088E0FB
+:10192000FE01A4E0B2E001900D928A95E1F7DF910B
+:10193000CF910895BF92CF92DF92EF92FF920F93D3
+:101940001F93CF93DF937C01B62EE90100E010E0F6
+:10195000C42ED12C0BC04991202F2B0D2F774F7700
+:101960006FE0C7010E94E8140F5F1F4F0C151D05A3
+:1019700094F3DF91CF911F910F91FF90EF90DF9043
+:10198000CF90BF90089570E06F5F7F4F6F707727A3
+:101990000C94E8140F931F93CF93C42F63307105F9
+:1019A00009F04AC0842F807F803849F1803909F0DE
+:1019B00043C0622F6F7770E080E090E00E94FA2CC5
+:1019C00020E030E040E451E40E945F2C9B01AC0138
+:1019D00060E070E080E090E40E94112E0F7710E04C
+:1019E00023E0159507952A95E1F72DEC3CEC42E0B4
+:1019F00053E40E94AE2DA8010E94040B1DC0622F6B
+:101A00006F7770E080E090E00E94FA2C20E030E0F8
+:101A100040E451E40E945F2C9B01AC0160E070E067
+:101A200080E090E40E94112E2DEC3CEC42E053E467
+:101A30000E94AE2D0E945809CC3F29F4CF911F91EE
+:101A40000F910C943509CF911F910F9108950F9329
+:101A50001F93CF93DF93CDB7DEB727970FB6F894D8
+:101A6000DEBF0FBECDBF8C0114C08A810E94C2149C
+:101A70009A819D839B819E839C819F8381111EC03F
+:101A800089818430B1F08730A1F08630A1F08530B3
+:101A9000A1F0BE016F5F7F4F84E091E00E942F189C
+:101AA0008111E3CF84E091E00E9420180E949B14F2
+:101AB0000DC083E003C082E001C081E0AE014B5F56
+:101AC0005F4F682FC8010E945515E3CF27960FB6C8
+:101AD000F894DEBF0FBECDBFDF91CF911F910F9164
+:101AE0000895EF92FF920F93CF93DF9300D000D031
+:101AF00000D0CDB7DEB77B014A832B830C83842FC4
+:101B00002E834D830E94C2142E814D8181111BC0F2
+:101B100082E0E816F10479F083E0E816F10421F0A0
+:101B2000EA94EF2821F50BC0073F11F487E001C0CC
+:101B300084E089830BC0273FD9F786E0FACF473F7F
+:101B4000B9F785E0F6CF42954F704983BE016F5FCC
+:101B50007F4F84E091E00E94E51784E091E00E94CD
+:101B6000031884E091E00E9420180E949B1426969E
+:101B70000FB6F894DEBF0FBECDBFDF91CF910F91AE
+:101B8000FF90EF90089580916D03811109C00E942C
+:101B9000A1110E94FE118091E20084608093E20016
+:101BA000089510926D03089508950C94E4020C9426
+:101BB000892480916E03843049F58091E9008F700B
+:101BC0009091EC0090FF02C090E801C090E0982B4B
+:101BD00084E08093E9008091EB0080FF14C0809145
+:101BE000EE0087FD03C00FC01092F1008091E80065
+:101BF00085FDFACF8091E80080FF05C08091E80064
+:101C00008E778093E8009F709093E900089542E0FA
+:101C100061EC81E00E94171142E061EC82E00E94D9
+:101C2000171142E061EC83E00E94171146E261EC7B
+:101C300084E00E94171142E361E885E00E941711D9
+:101C400042E360E886E00C941711809170038330C2
+:101C500009F454C030F4813071F0823009F0AAC028
+:101C600091C08A3009F47EC08B3009F45FC089309E
+:101C700009F0A0C020C080916F03813A09F09AC09A
+:101C80008091E800877F8093E800809173039091B2
+:101C90007403892B21F060E080E090E003C068E0ED
+:101CA00084E092E070E00E9458108091E8008B7709
+:101CB0008093E800089580916F03813209F07AC023
+:101CC0008091730390917403892B09F073C0809104
+:101CD000E800877F8093E80005C080916E03882329
+:101CE00009F468C08091E80082FFF7CF8091F1008D
+:101CF00080930C028091E8008B7758C080916F032D
+:101D0000813A09F057C08091730390917403892B35
+:101D100009F050C08091E800877F8093E8008091AF
+:101D2000E80080FFFCCF80911A013BC080916F03D7
+:101D3000813209F03FC08091730390917403892B25
+:101D4000C9F58091E800877F8093E8000E944E11DA
+:101D50009091710381E0911101C080E080931A019C
+:101D60000C948C1E80916F03813221F58091E800E4
+:101D7000877F8093E8000E944E11809172038093C8
+:101D80000302089580916F03813AA1F48091E800E5
+:101D9000877F8093E8008091E80080FFFCCF8091EE
+:101DA00003028093F1008091E8008E778093E80031
+:101DB0000C944E11089584B7877F84BF88E10FB6D5
+:101DC000F89480936000109260000FBE90E080E86D
+:101DD0000FB6F89480936100909361000FBE0E944B
+:101DE000A1110E94FE11E2EEF0E080818460808308
+:101DF00008958DE792E00E94241561E77DE08DE76C
+:101E000092E00E947A1567E27DE08DE792E00E9401
+:101E10007E150E94DB0E78946AEC7CE08DE792E000
+:101E20000E94201563EC7CE08DE792E00E9418157B
+:101E30006AE97CE08DE792E00E941C150E94850A09
+:101E40000E949B140E94AC1880E191E00E945418FB
+:101E50000BC00E944E2480916C03882329F00E94BD
+:101E6000742481110E94A40F80916E03853089F340
+:101E70008DE792E00E942D170E94B618F5CF292F0A
+:101E8000332723303105B1F04CF42130310509F40A
+:101E90004DC02230310509F04EC007C02132310556
+:101EA00041F12232310591F146C0E0EDF0E086E7E4
+:101EB00093E045C099278130910569F08230910502
+:101EC00089F0892B09F037C0E2E7F3E0E491F0E014
+:101ED00082E793E034C0E4E4F3E0E491F0E084E4EA
+:101EE00093E02DC0EAE1F3E0E491F0E08AE193E0D1
+:101EF00026C0643000F5E62FF0E0EE0FFF1FE75735
+:101F0000FE4F80819181E9E0F0E019C0643098F4DF
+:101F1000E62FF0E0DF01AA0FBB1FAF56BE4F8D9139
+:101F20009C91E756FE4FE081F0E009C0E2E1F0E06D
+:101F300086E494E004C0E0E0F0E080E090E0DA01C4
+:101F40008D939C93CF01089580E189BD82E189BD85
+:101F500009B400FEFDCF8091D8008F7D8093D8001A
+:101F60008091E00082608093E0008091E00081FD3C
+:101F7000FCCF0895BF92CF92DF92EF92FF920F9322
+:101F80001F93CF93DF937C018B01EA010E946F11B5
+:101F9000B82E811133C0209731F028813981021B7E
+:101FA000130BE20EF31EC12CD12C23C08091E8004C
+:101FB00085FD15C08091E8008E778093E80020971A
+:101FC00049F0888199818C0D9D1D9983888325E036
+:101FD000B22E14C00E946F11882359F00EC0F70171
+:101FE00081917F018093F10001501109FFEFCF1A19
+:101FF000DF0A01151105D1F601C0B82E8B2DDF9136
+:10200000CF911F910F91FF90EF90DF90CF90BF90F5
+:102010000895BF92CF92DF92EF92FF920F931F939A
+:10202000CF93DF937C018B01EA010E946F11B82EE0
+:10203000811133C0209731F028813981021B130BA5
+:10204000E20EF31EC12CD12C23C08091E80085FD47
+:1020500015C08091E8008B778093E800209749F0C5
+:10206000888199818C0D9D1D9983888345E0B42ECC
+:1020700014C00E946F11882359F00EC08091F100A6
+:10208000F70181937F0101501109FFEFCF1ADF0A99
+:1020900001151105D1F601C0B82E8B2DDF91CF911E
+:1020A0001F910F91FF90EF90DF90CF90BF90089518
+:1020B00040917503509176034617570748F0611514
+:1020C000710539F44091E8004E774093E80001C073
+:1020D000BA01FC0140E033C080916E03882309F40B
+:1020E00042C0853009F441C08091E80083FD39C0C9
+:1020F0008091E80082FD2FC08091E80080FF1FC022
+:102100009091F3008091F200392F20E0A901482B33
+:10211000CA0106C041914093F100615071090196D6
+:102120006115710519F088309105A0F341E0089719
+:1021300009F040E08091E8008E778093E800611517
+:10214000710551F64111C8CF06C080916E038823F6
+:1021500051F0853051F08091E80082FFF6CF80E0A9
+:10216000089581E0089582E0089583E00895409104
+:102170007503509176034617570748F061157105AE
+:1021800039F44091E8004E774093E80001C0BA016D
+:10219000FC0140E034C080916E03882309F443C001
+:1021A000853009F442C08091E80083FD3AC08091F7
+:1021B000E80082FD30C08091E80080FF20C090914F
+:1021C000F3008091F200392F20E0A901482BCA01C9
+:1021D00007C044914093F100319661507109019616
+:1021E0006115710519F08830910598F341E0089761
+:1021F00009F040E08091E8008E778093E800611557
+:10220000710549F64111C7CF06C080916E0388233E
+:1022100051F0853051F08091E80082FFF6CF80E0E8
+:10222000089581E0089582E0089583E00895982F4D
+:102230002CC09093E900981739F07091EC00209130
+:10224000ED005091F00003C0242F762F50E021FDC7
+:1022500002C09F5F1AC03091EB003E7F3093EB00CD
+:102260003091ED003D7F3093ED003091EB00316017
+:102270003093EB007093EC002093ED005093F0004E
+:102280002091EE0027FDE5CF07C0973090F28F70C8
+:102290008093E90081E0089580E0089580916F03C4
+:1022A00087FD05C08091E80080FF0EC012C08091BC
+:1022B000E80082FD05C080916E038111F8CF08957A
+:1022C0008091E8008B7708C080916E038111EACF7E
+:1022D00008958091E8008E778093E80008958091BA
+:1022E000E4009091E50045E62091EC0020FD1FC040
+:1022F00023C020916E03222391F0253091F020918C
+:10230000EB0025FD10C02091E4003091E500281776
+:10231000390751F34150C90139F784E0089582E04B
+:10232000089583E0089581E0089580E00895209164
+:10233000E80020FFDECFF9CF2091E80022FFD9CFBF
+:10234000F4CF0E940F120E941712E0EEF0E080819D
+:1023500081608083E8EDF0E080818F77808319BC15
+:10236000A7EDB0E08C918E7F8C9380818F7E8083EF
+:1023700010926D0308950F931F93CF93DF930E94E4
+:102380000F120E941712C8EDD0E088818F778883E2
+:1023900088818068888388818F7D888319BC1092AA
+:1023A0006E0310926A0310926C0310926B0300EE9E
+:1023B00010E0F80180818B7F808388818160888331
+:1023C00042E060E080E00E941711E1EEF0E08081E1
+:1023D0008E7F8083E2EEF0E0808181608083808167
+:1023E00088608083F80180818E7F8083888180610E
+:1023F0008883DF91CF911F910F910895E8EDF0E070
+:1024000080818F7E8083E7EDF0E080818160808332
+:1024100084E082BF81E080936D030C94BB11E8EDF2
+:10242000F0E080818E7F80831092E2000895109208
+:10243000DA001092E10008951F920F920FB60F92EA
+:1024400011242F933F934F935F936F937F938F93B9
+:102450009F93AF93BF93EF93FF938091E10082FF2F
+:102460000BC08091E20082FF07C08091E1008B7F6A
+:102470008093E1000E94D90D8091DA0080FF1FC097
+:102480008091D80080FF1BC08091DA008E7F8093FE
+:10249000DA008091D90080FF0DC080E189BD82E122
+:1024A00089BD09B400FEFDCF81E080936E030E94D8
+:1024B000C30D05C019BC10926E030E94D10D80910E
+:1024C000E10080FF19C08091E20080FF15C080917B
+:1024D000E2008E7F8093E2008091E2008061809331
+:1024E000E2008091D80080628093D80019BC85E01A
+:1024F00080936E030E94D50D8091E10084FF30C06F
+:102500008091E20084FF2CC080E189BD82E189BD19
+:1025100009B400FEFDCF8091D8008F7D8093D80054
+:102520008091E1008F7E8093E1008091E2008F7EB8
+:102530008093E2008091E20081608093E2008091CC
+:102540006A03882311F084E007C08091E30087FFCD
+:1025500002C083E001C081E080936E030E94D70D2A
+:102560008091E10083FF29C08091E20083FF25C0B4
+:102570008091E100877F8093E10082E080936E0389
+:1025800010926A038091E1008E7F8093E100809138
+:10259000E2008E7F8093E2008091E2008061809370
+:1025A000E20042E060E080E00E9417118091F000BC
+:1025B00088608093F0000E94D40DFF91EF91BF914D
+:1025C000AF919F918F917F916F915F914F913F91CB
+:1025D0002F910F900FBE0F901F9018951F920F9282
+:1025E0000FB60F9211242F933F934F935F936F93E6
+:1025F0007F938F939F93AF93BF93CF93EF93FF936B
+:102600008091E9008F709091EC0090FF02C090E8FB
+:1026100001C090E0C92FC82B1092E9008091F00012
+:10262000877F8093F00078940E9432131092E90023
+:102630008091F00088608093F000CF70C093E90033
+:10264000FF91EF91CF91BF91AF919F918F917F912A
+:102650006F915F914F913F912F910F900FBE0F900F
+:102660001F9018951F93CF93DF93CDB7DEB7AC972C
+:102670000FB6F894DEBF0FBECDBFEFE6F3E080915A
+:10268000F100819323E0E737F207C9F70E94250E96
+:102690008091E80083FF37C180916F0390917003B0
+:1026A000953009F488C038F49130B1F170F093306E
+:1026B00009F029C131C0983009F4F8C0993009F403
+:1026C00004C1963009F01FC19DC0803821F08238C6
+:1026D00009F019C108C080916B0390916C03992394
+:1026E00089F082600FC080917303909174038F70A2
+:1026F00099278093E9008091EB0085FB882780F97A
+:102700001092E9009091E800977F9093E800809301
+:10271000F1001092F100D5C0882319F0823009F041
+:10272000F2C08F7121F0823009F0EDC00BC08091B2
+:102730007103813009F0E7C0933009F080E08093A5
+:102740006C032FC08091710381112BC080917303A2
+:10275000909174038F709927009709F4D4C08093E7
+:10276000E9002091EB0020FF1CC020917003233072
+:1027700021F48091EB00806212C09091EB00906197
+:102780009093EB0021E030E001C0220F8A95EAF738
+:102790002093EA001092EA008091EB008860809319
+:1027A000EB001092E9008091E800877F8093E800B9
+:1027B0000E944E11A8C08111A6C080917103909112
+:1027C00072038F779927182F9091E3009078982BB8
+:1027D0009093E3008091E800877F8093E8000E9457
+:1027E0004E118091E80080FFFCCF8091E30080686B
+:1027F0008093E300112311F083E001C082E0809315
+:102800006E0381C08058823008F07DC080917103D2
+:10281000909172038C3D23E0920779F583E08A83DF
+:102820008AE289834FB7F894DE01139620E03EE0F8
+:1028300051E2E32FF0E050935700E49120FF03C0F2
+:10284000E295EF703F5FEF708E2F90E0EA3010F06E
+:10285000C79601C0C0968D939D932F5F243149F791
+:102860004FBF8091E800877F8093E8006AE270E0C4
+:10287000CE0101960E94581013C0AE01455D5F4F16
+:10288000609173030E943F0F0097E9F12091E800E7
+:10289000277F2093E800BC018BA59CA50E94B71060
+:1028A0008091E8008B778093E8002DC0803859F53F
+:1028B0008091E800877F8093E80080916A0380938D
+:1028C000F1008091E8008E7771CF81111CC090914A
+:1028D00071039230C0F48091E800877F8093E80014
+:1028E00090936A030E944E1180916A03811104C083
+:1028F0008091E30087FF02C084E001C081E0809303
+:102900006E030E94070E8091E80083FF0AC0809149
+:10291000E800877F8093E8008091EB0080628093DD
+:10292000EB00AC960FB6F894DEBF0FBECDBFDF91C3
+:10293000CF911F910895CF9380916E038823B1F0BA
+:102940008091E9008F709091EC0090FF02C090E8B8
+:1029500001C090E0C92FC82B1092E9008091E800D7
+:1029600083FD0E943213CF70C093E900CF91089588
+:10297000881F8827881F089591E0883F08F490E019
+:10298000892F0895982F907F903B99F038F49039D3
+:1029900081F0903A71F09038C9F40BC0903DA1F0ED
+:1029A00018F4903C99F410C0903E19F0903F71F4E7
+:1029B00002C083E00895E82FE15FEF3038F4F0E0E3
+:1029C000E356FE4F8081089582E0089580E00895E7
+:1029D0000F932F774F776F70606BDC01ED91FC9157
+:1029E000022F242F462F63E070E009950F91089580
+:1029F0000F932F774F776F706069DC01ED91FC9139
+:102A0000022F242F462F63E070E009950F9108955F
+:102A10000F932F774F776F706068DC01ED91FC9119
+:102A2000022F242F462F63E070E009950F9108953F
+:102A3000FC01738362830895FC01738F628F089594
+:102A4000FC01758F648F0895CF93DF93EC011DA275
+:102A50001FA21EA2BC01685D7F4F40EC88519F4FB2
+:102A60000E9461171B821A821D821C821F821E8295
+:102A7000198618861B861A861D861C861F861E864A
+:102A8000198A188A1B8A1A8A1D8A1C8A1F8A1E8A1A
+:102A9000198E188E1B8E1A8E1D8E1C8E1F8E1E8EEA
+:102AA00019A218A2DF91CF910895CF92DF92FF92E1
+:102AB0000F931F93CF93DF931F92CDB7DEB7F62E00
+:102AC0006A018C0108511F4F08C0F60161916F0126
+:102AD000C80149830E94681749818C2D841B8F157A
+:102AE000A0F30F90DF91CF911F910F91FF90DF9096
+:102AF000CF900895FC01718360830895FC0171A358
+:102B000060A30895AF92BF92CF92DF92EF92FF92AF
+:102B10000F931F93CF93DF9300D01F92CDB7DEB7F3
+:102B20007C016B01142FB22EA02EDC0195968C91A6
+:102B300095978430F1F45A96ED91FC915B9730971C
+:102B400009F4D8C0CB01019763E070E00E94762FB2
+:102B5000DB01AA0FBB1FA60FB71F49832A830B8374
+:102B60004C2D4A1B9E012F5F3F4FBD01C7010995A8
+:102B7000B1C06230710509F453C06330710529F0AA
+:102B80006130710509F09CC083C0842F807F803A3A
+:102B900001F130F48038B9F0803909F0ABC00DC0D4
+:102BA000803EE9F0803F09F1803B09F0A3C0D701E6
+:102BB0001296ED91FC91139723C0D7011496ED91D5
+:102BC000FC9115971DC0D7011696ED91FC911797B2
+:102BD00017C0D7011896ED91FC91199711C0D70134
+:102BE0001A96ED91FC911B970BC0423F09F082C0F1
+:102BF000D7011C96ED91FC911D97309731F47AC066
+:102C0000309709F477C0123F21F42A2D4B2D62EF43
+:102C100004C0612F6F702A2D4B2DC70109955AC032
+:102C2000842F807F803D59F0803F79F0803C09F00F
+:102C300061C0D7011E96ED91FC911F9719C0D70175
+:102C40005096ED91FC91519713C0433F31F4D70159
+:102C50005296ED91FC91539708C0413F09F04AC04C
+:102C6000D7015496ED91FC915597309741F442C0AD
+:102C7000309709F43FC0133F11F0113F19F44B2D69
+:102C8000612F03C0612F6F704B2DC701099522C0C2
+:102C9000842F0E94BC14882331F0D7015696ED9101
+:102CA000FC91579707C0163F29F5D7015896ED912B
+:102CB000FC9159973097F1F0612FC70109950AC02F
+:102CC00064307105A8F416C00A2D2B2D412FB601D2
+:102CD000C7010995D7015E96ED91FC915F973097FA
+:102CE00089F00A2D2B2D412FB601C70109950AC085
+:102CF000C12CD12CD7015C96ED91FC915D9730975A
+:102D000019F7E8CF0F900F900F90DF91CF911F919F
+:102D10000F91FF90EF90DF90CF90BF90AF9008950C
+:102D2000EF92FF920F931F93CF93DF93EC01162F37
+:102D3000862F0E94BC14882369F0FDA081E08DA33A
+:102D400000E020E0412F61E070E0CE010E9482159A
+:102D5000FDA27CC0812F0E94B8144DA1882309F4E4
+:102D600040C0443029F01AA321E030E03FA32EA355
+:102D7000812F0E94C214813031F070F0823051F006
+:102D8000833059F507C08DA300E020E0412F61E0BA
+:102D900070E01EC08DA35AC0103F19F0173FE9F430
+:102DA00004C084E08DA31AA33FC02EA13FA1C90196
+:102DB00063E070E00E94762F8C0F9D1FFC0112A330
+:102DC000B9016F5F7F4F7FA36EA30CA12BA14AA116
+:102DD000CE010E9482151DA239C01DA21FA21EA2F3
+:102DE00035C0442399F12EA13FA1C90163E070E0F1
+:102DF0000E94762F7C01FE01E80FF91F12A3B90192
+:102E00006F5F7F4F7FA36EA38130910591F082E0C9
+:102E1000E816F104D9F40CA12BA14AA1CE010E941D
+:102E200082158DA1843091F081E090E09FA38EA364
+:102E30000DC0423059F400E02BA14AA1CE010E94FE
+:102E400082158DA1843011F0FFA2EEA2DF91CF9107
+:102E50001F910F91FF90EF900895CF92DF92EF9224
+:102E6000FF920F931F93CF93DF93EC01E8A1F9A199
+:102E7000309709F009958E0108511F4FC8010E9433
+:102E80009A17E12CF12CC82ED12C0FC060E0C8019C
+:102E90000E94AE17682FCE010E94901661E0C80113
+:102EA0000E94BF178FEFE81AF80AEC14FD0470F3C4
+:102EB000DF91CF911F910F91FF90EF90DF90CF9016
+:102EC0000895FC0142837483638311821082089504
+:102ED0000F931F93CF93DF93EC01062F0E94E0170F
+:102EE000182F298130E0C90101966A8170E00E94A3
+:102EF0008A2F488150E08417950729F4812F0E947A
+:102F0000E31780E012C0EB81FC81E20FF31F008326
+:102F10002981822F90E001966A8170E00E948A2FB9
+:102F20008983812F0E94E31781E0DF91CF911F9168
+:102F30000F910895CF93DF93EC010E94E017298150
+:102F40009881291710F0C22F02C0CA81C20FC91B75
+:102F50000E94E3178C2FDF91CF910895FC0120810F
+:102F6000862F90E0820F911D628170E00E948A2F6F
+:102F70000380F481E02DE80FF91F808108950F93FD
+:102F80001F93CF93DF931F92CDB7DEB78C01698378
+:102F90000E94E017482FF80180816981262F30E0D8
+:102FA000280F311D6281C90170E00E948A2F808341
+:102FB000842F0F90DF91CF911F910F910C94E31705
+:102FC0008FB7F89408958FBF0895FC01CB0120912D
+:102FD0006E032430B1F421812F702093E90040E08A
+:102FE00050E064E070E00E94BA0F81110BC0909134
+:102FF000E80095FD07C09091E8009E779093E80067
+:10300000089582E0089520916E032430A9F4FC0114
+:1030100081818F708093E9003091F3002091F2005C
+:10302000932F80E0822B892B49F08091E8008E77E6
+:103030008093E8000C946F1182E0089580E0089579
+:1030400020916E03243051F4FC0121812F702093D4
+:10305000E9002091E80020FD0C9403180895FC017C
+:10306000CB0120916E03243011F080E00895268179
+:103070002F702093E9002091E80022FFF6CF2091E5
+:10308000E80025FFF2CF40E050E064E070E00E94ED
+:1030900009108091E80085FD05C08091E8008B77DC
+:1030A0008093E80081E0089590930F0280930E02D0
+:1030B000089580910E0290910F020895E0910E0202
+:1030C000F0910F02309721F00190F081E02D0994EA
+:1030D00080E00895E0910E02F0910F02309721F008
+:1030E0000280F381E02D09940895E0910E02F091A1
+:1030F0000F02309721F00480F581E02D09940895A6
+:1031000020911002309111028217930771F0909371
+:10311000110280931002E0910E02F0910F0230979D
+:1031200021F00680F781E02D099408952091120284
+:10313000309113028217930771F0909313028093DA
+:103140001202E0910E02F0910F02309721F00084FC
+:10315000F185E02D099408950E94B6240E948D0502
+:103160000E948A250C945F2B0C94CE075F926F927D
+:103170007F928F929F92AF92BF92CF92DF92EF9207
+:10318000FF920F931F93CF93DF93CDB7DEB72A97AC
+:103190000FB6F894DEBF0FBECDBF0E947E0694E14D
+:1031A000C92E92E0D92E00E010E0AA24A394B12CFD
+:1031B000502E802F0E94C4073C01F601E190F1904F
+:1031C0006F01E826F926E114F10431F40F5F1F4F77
+:1031D0000430110569F73AC08091680281FD0E94B0
+:1031E000CD0720E030E04501022E02C0880C991C7A
+:1031F0000A94E2F7C4018E219F21892B09F12E83C5
+:103200005F826820792081E0672809F480E0888760
+:103210000E94BF248160782F9A8789874E815F81C1
+:1032200068858A850E946F19F801EE0FFF1FEC5E1A
+:10323000FD4F80819181882599259183808316C0D7
+:103240002F5F3F4F2C30310571F6C0CF8FEF898350
+:103250008A831B820E94BF248160782F9D838C8388
+:1032600049815A816B818D810E946F190E94772854
+:1032700010911C020E945E181817D9F00E945E1867
+:1032800080931C022A960FB6F894DEBF0FBECDBF06
+:10329000DF91CF911F910F91FF90EF90DF90CF9032
+:1032A000BF90AF909F908F907F906F905F900C94A5
+:1032B000B4182A960FB6F894DEBF0FBECDBFDF91CB
+:1032C000CF911F910F91FF90EF90DF90CF90BF9023
+:1032D000AF909F908F907F906F905F900895CF9365
+:1032E000DF93CDB7DEB72B970FB6F894DEBF0FBED6
+:1032F000CDBF4F83588769877A878B87DE01119608
+:1033000086E0FD0111928A95E9F785E0FE01379686
+:1033100001900D928A95E1F749815A816B817C81F8
+:103320008D819E810E9447212B960FB6F894DEBFB7
+:103330000FBECDBFDF91CF910895CF93C82F8823C3
+:1033400009F4C1C0823859F40E945E1881FDBBC0E7
+:1033500089E30E94AC230E94282489E30CC08338AF
+:1033600079F40E945E1880FDAEC083E50E94AC2314
+:103370000E94282483E50E94CE23CF910C94282418
+:10338000843859F40E945E1882FD9DC087E40E9433
+:10339000AC230E94282487E4EECF8450813A48F47D
+:1033A0008C2F0E94C72A81118EC08C2F0E94AC23C3
+:1033B000E4CF8C2F805E883050F4C77081E090E0BD
+:1033C00001C0880FCA95EAF70E94EF23D6CF8C2F51
+:1033D000855A833078F4C53A29F0C63A31F482E848
+:1033E00090E005C081E890E002C083E890E0CF91D2
+:1033F0000C9480188C2F885A833108F064C0C83A26
+:1034000039F1C93A41F1CA3A49F1CB3A51F1CC3AD2
+:1034100059F1CD3A61F1C03B69F1CE3A71F1CF3A41
+:1034200079F1C13B81F1C23B89F1C33B91F1C43BCE
+:1034300099F1C53BA1F1C63BA9F1C73BB1F1C83B2E
+:10344000B9F1C93BC1F1CA3BC9F58AE292E038C083
+:1034500082EE90E035C089EE90E032C08AEE90E0D6
+:103460002FC085EB90E02CC086EB90E029C087EB65
+:1034700090E026C08CEC90E023C08DEC90E020C062
+:1034800083E891E01DC08AE891E01AC082E991E0EA
+:1034900017C084E991E014C081E292E011C083E298
+:1034A00092E00EC084E292E00BC085E292E008C098
+:1034B00086E292E005C087E292E002C080E090E000
+:1034C000CF910C949618CF910895882309F44DC09C
+:1034D000823859F40E945E1881FF47C089E30E9438
+:1034E000AC230E94282489E30CC0833871F40E9425
+:1034F0005E1880FF3AC083E50E94AC230E94282416
+:1035000083E50E94CE230C942824843859F40E9429
+:103510005E1882FF2AC087E40E94AC230E94282400
+:1035200087E4EFCF982F9450913A08F4EACF982F80
+:10353000905E983058F4282F277081E090E001C009
+:10354000880F2A95EAF70E94F523DDCF982F955A28
+:10355000933020F480E090E00C948018885A8331F6
+:1035600020F480E090E00C9496180895882321F0D0
+:103570000E94EF230C9428240895882321F00E94B0
+:10358000F5230C9428240895BF92CF92DF92EF92F6
+:10359000FF920F931F93CF93DF93CDB7DEB727979B
+:1035A0000FB6F894DEBF0FBECDBF8C0185E0F801E9
+:1035B000DE01119601900D928A95E1F7F8013081B4
+:1035C0002181F280558152955F7083819481892B8E
+:1035D00039F02F3F41F481E090E03F3F31F003C0EC
+:1035E00081E090E002C080E090E080FD73C3398309
+:1035F0002A8389819A815E830E946923B92E8F83F1
+:103600000E9468230E9490222B2D22952F7030E07B
+:103610005E816F812530310509F4E6C06CF42430F9
+:1036200031050CF0A2C04B2D407F8B2D8F702230C6
+:1036300031050CF045C017C02C3031054CF42A3050
+:1036400031050CF0E7C12830310509F043C3E5C06E
+:103650002D30310509F4BAC20CF4A2C22F30310565
+:1036600009F038C323C3182F411101C002C01295BD
+:10367000107FFF2059F0112309F46BC2812F6F8353
+:103680000E94FF230E9428246F8163C2862F0E941C
+:10369000651A112309F41EC3812F0E940524279661
+:1036A0000FB6F894DEBF0FBECDBFDF91CF911F9153
+:1036B0000F91FF90EF90DF90CF90BF900C94282453
+:1036C000403211F08295807F662319F0613071F5E8
+:1036D00023C0FF20B1F0511101C032C0513081F53B
+:1036E00027960FB6F894DEBF0FBECDBFDF91CF9106
+:1036F0001F910F91FF90EF90DF90CF90BF900C94AF
+:103700000F24511101C003C0513009F4E3C28E836C
+:103710000E9412248E819AC1FF2021F0563008F0B9
+:10372000D9C20EC0553008F0D5C290C1FF20C9F0F3
+:10373000552331F0F801958190FF0BC29F7095835E
+:1037400027960FB6F894DEBF0FBECDBFDF91CF91A5
+:103750001F910F91FF90EF90DF90CF90BF900C944E
+:10376000B61A552309F472C109C22B2D2695269548
+:10377000237030E02115310529F02130310509F0A1
+:10378000A9C219C0FF2021F0862F9B2D937002C083
+:1037900080E090E027960FB6F894DEBF0FBECDBF55
+:1037A000DF91CF911F910F91FF90EF90DF90CF901D
+:1037B000BF900C948018FF2021F0862F9B2D9370D2
+:1037C00002C080E090E027960FB6F894DEBF0FBEEF
+:1037D000CDBFDF91CF911F910F91FF90EF90DF90C0
+:1037E000CF90BF900C949618862FFF2019F00E945E
+:1037F0007D2702C00E94E52727960FB6F894DEBF0A
+:103800000FBECDBFDF91CF911F910F91FF90EF9031
+:10381000DF90CF90BF900C946C288B2D837009F0B3
+:1038200079C0F11057C2262F229526952770220FB6
+:10383000220F862F8F70C82ED12CE12CF12C022E56
+:1038400004C0CC0CDD1CEE1CFF1C0A94D2F764FFF4
+:1038500010C06FE070E080E090E004C0660F771F5A
+:10386000881F991F2A95D2F760957095809590953D
+:1038700003C060E070E0CB012B2D269526952370C8
+:10388000422F50E042305105D9F04330510569F1E3
+:103890006C297D298E299F294130510551F12796A8
+:1038A0000FB6F894DEBF0FBECDBFDF91CF911F9151
+:1038B0000F91FF90EF90DF90CF90BF900C94A522D6
+:1038C0006C297D298E299F2927960FB6F894DEBF93
+:1038D0000FBECDBFDF91CF911F910F91FF90EF9061
+:1038E000DF90CF90BF900C94B7220E94A522C70111
+:1038F000B60127960FB6F894DEBF0FBECDBFDF919D
+:10390000CF911F910F91FF90EF90DF90CF90BF90DC
+:103910000C949322FF2019F08B2D817001C08695A5
+:10392000882309F4D7C1262F229526952770220FC8
+:10393000220F862F8F70C82ED12CE12CF12C022E55
+:1039400004C0CC0CDD1CEE1CFF1C0A94D2F764FFF3
+:1039500010C06FE070E080E090E004C0660F771F59
+:10396000881F991F2A95D2F760957095809590953C
+:1039700003C060E070E0CB012B2D269526952370C7
+:10398000422F50E042305105D9F04330510569F1E2
+:103990006C297D298E299F294130510551F12796A7
+:1039A0000FB6F894DEBF0FBECDBFDF91CF911F9150
+:1039B0000F91FF90EF90DF90CF90BF900C94442335
+:1039C0006C297D298E299F2927960FB6F894DEBF92
+:1039D0000FBECDBFDF91CF911F910F91FF90EF9060
+:1039E000DF90CF90BF900C9456230E944423C701D0
+:1039F000B60127960FB6F894DEBF0FBECDBFDF919C
+:103A0000CF911F910F91FF90EF90DF90CF90BF90DB
+:103A10000C943223603F59F120F4603E08F494C0C6
+:103A200008C0623F09F467C0F0F1633F09F08CC041
+:103A300065C0162F1F708B2D8F71FF2021F00E9403
+:103A4000DD22812F7DCE0E94F822812F27960FB68E
+:103A5000F894DEBF0FBECDBFDF91CF911F910F91C4
+:103A6000FF90EF90DF90CF90BF900C94BD1AFF2095
+:103A7000B1F0553008F02EC18B2D8F7127960FB6FF
+:103A8000F894DEBF0FBECDBFDF91CF911F910F9194
+:103A9000FF90EF90DF90CF90BF900C94172356309B
+:103AA00008F018C1E9CFFF2099F08B2D8F71279670
+:103AB0000FB6F894DEBF0FBECDBFDF91CF911F913F
+:103AC0000F91FF90EF90DF90CF90BF900C94DD228C
+:103AD0008B2D8F7127960FB6F894DEBF0FBECDBF2A
+:103AE000DF91CF911F910F91FF90EF90DF90CF90DA
+:103AF000BF900C94F822F110EBCFD7CFFF2099F0B4
+:103B00008B2D8F7127960FB6F894DEBF0FBECDBFF9
+:103B1000DF91CF911F910F91FF90EF90DF90CF90A9
+:103B2000BF900C94CE2227960FB6F894DEBF0FBE3E
+:103B3000CDBFDF91CF911F910F91FF90EF90DF905C
+:103B4000CF90BF900C94C922FF20A9F0552309F40F
+:103B5000ACCF862F27960FB6F894DEBF0FBECDBF31
+:103B6000DF91CF911F910F91FF90EF90DF90CF9059
+:103B7000BF900C949D19552309F4AACF862F279640
+:103B80000FB6F894DEBF0FBECDBFDF91CF911F916E
+:103B90000F91FF90EF90DF90CF90BF900C94651A3B
+:103BA0004B2D4F70C8010E94E50227960FB6F8947E
+:103BB000DEBF0FBECDBFDF91CF911F910F91FF9060
+:103BC000EF90DF90CF90BF900C94FD21F11082C058
+:103BD0009B2D9F70492F50E04230510599F144F4DC
+:103BE0004115510569F04130510509F073C019C004
+:103BF00043305105C1F14430510509F06BC044C058
+:103C000027960FB6F894DEBF0FBECDBFDF91CF91E0
+:103C10001F910F91FF90EF90DF90CF90BF900C9489
+:103C2000702B27960FB6F894DEBF0FBECDBFDF9185
+:103C3000CF911F910F91FF90EF90DF90CF90BF90A9
+:103C40000C94872B27960FB6F894DEBF0FBECDBF1E
+:103C5000DF91CF911F910F91FF90EF90DF90CF9068
+:103C6000BF900C94A32B27960FB6F894DEBF0FBE1F
+:103C7000CDBFDF91CF911F910F91FF90EF90DF901B
+:103C8000CF90BF900C94B62B862F27960FB6F89442
+:103C9000DEBF0FBECDBFDF91CF911F910F91FF907F
+:103CA000EF90DF90CF90BF900C94DA2B4B2D4F709C
+:103CB000C80127960FB6F894DEBF0FBECDBFDF91C7
+:103CC000CF911F910F91FF90EF90DF90CF90BF9019
+:103CD0000C940E0827960FB6F894DEBF0FBECDBF2A
+:103CE000DF91CF911F910F91FF90EF90DF90CF90D8
+:103CF000BF9008950E940C240E94E1230E94282472
+:103D00000E9418290E946C2880E090E00E94801890
+:103D100080E090E00C9496180E94FC230C947A1E8C
+:103D20000E946923292F22952F7030E02C30310515
+:103D30004CF42A3031056CF422503109223031051F
+:103D400070F407C02C30310531F02F30310539F4D3
+:103D500002C081E0089593FB882780F9089580E0F0
+:103D60000895CF93DF9300D000D01F92CDB7DEB778
+:103D70000F900F900F900F900F90DF91CF910895BB
+:103D8000CF93DF9300D000D000D0CDB7DEB726961A
+:103D90000FB6F894DEBF0FBECDBFDF91CF9108956F
+:103DA0001F93CF93DF93C091530216E012C0D0E06F
+:103DB0001C9FF0011D9FF00D1124ED5DFD4F408112
+:103DC000518162817381848195810E94C01E2196F8
+:103DD000C77080915402C813EACFDF91CF911F9131
+:103DE000089540911D0250911E0260911F02709132
+:103DF000200280912102909122020C94C01E0F9308
+:103E00001F93CF93DF938091220282958F7009F0E8
+:103E100069C080911F02882309F464C0A0915302F5
+:103E2000D0915402B0911D02C0911E0280912002D7
+:103E30009091210221E030E0BF3F11F020E030E01E
+:103E4000122FBC016095709506E04AC0009721F0E2
+:103E5000CF3F29F4212F05C021E030E002C020E04F
+:103E600030E020FD3BC04A2F50E0049FF001059F49
+:103E7000F00D1124ED5DFD4F2181C2132FC0208173
+:103E8000B2132CC02281211129C02381348128172B
+:103E9000390718F0281B390B02C0260F371F283CA2
+:103EA0003105E0F4809122028F70806180932202BC
+:103EB00086E0849FF001859FF00D1124E85DFD4FA1
+:103EC00080818F70806180838DE192E00E94C41AAE
+:103ED000DF91CF911F910F910C94D01EAF5FA7700F
+:103EE000AD13B4CFDF91CF911F910F910895EF9251
+:103EF000FF920F931F93CF93DF93CDB7DEB76297F7
+:103F00000FB6F894DEBF0FBECDBF8C0185E0F8017F
+:103F1000DE011D9601900D928A95E1F7D8014C9132
+:103F200011965C91119712966C9112971396ED90E1
+:103F3000FC90149770911D02E0911E028091200266
+:103F400090912102009739F0EF3F41F421E030E0F9
+:103F50007F3F31F003C021E030E002C020E030E0DC
+:103F600020FD5CC120911F02222309F4F1C0E81654
+:103F7000F90628F09701281B390BC90104C0809568
+:103F800090958E0D9F1D883C910508F098C08091FA
+:103F90002202982F907F09F064C0E51314C07413B7
+:103FA00012C0611110C08F708061809322020E9444
+:103FB000F11E8DE192E00E94C41A80912202D80184
+:103FC00015968C9343C1EF2839F05F3F41F481E0AF
+:103FD00090E04F3F31F003C081E090E002C080E00C
+:103FE00090E080FD03C081E0862702C080E090E081
+:103FF00080FF2EC0809153022091540236E013C0FE
+:1040000090E0389FF001399FF00D1124ED5DFD4FD8
+:104010007181571306C07081471303C07281671303
+:1040200017C0019687708213EBCF12C19F7059F0B1
+:10403000882309F40BC107C09F7029F0F80195810E
+:10404000907F09F403C1805E883008F4FFC0D2C0BD
+:10405000662309F4FBC080912202816080932202D2
+:10406000F5C0E51308C0741306C0611104C0D8017F
+:1040700015968C939DC04D875E878D859E856A8B36
+:104080000E94901E6A89882309F4B4C0662309F44B
+:10409000B1C020912202822F82958F7090E002970A
+:1040A0000CF4C6C080911D0290911E0298878F83E8
+:1040B0001986FB86EA862C87CE01079646C080913A
+:1040C0002202982F907F59F47E2DF98AE88A8989F7
+:1040D0000E94B11E8DE192E00E94C41A95C0E513C2
+:1040E00011C074130FC061110DC0F8018583C801A0
+:1040F0000E94C41AEDE1F2E086E0DF011D928A958C
+:10410000E9F7A2C04D875E878D859E856A8B0E94E8
+:10411000901E6A89882309F46DC0662309F46AC079
+:1041200020912202822F82958F7090E002970CF4EA
+:104130007FC080911D0290911E029A8389831B8209
+:10414000FD82EC822E83CE0101960E94C41A70C0BB
+:10415000E816F90628F09701281B390BC90104C09D
+:10416000809590958E0D9F1D883C910508F046C066
+:10417000662309F43FC0E51330C074132EC02091AC
+:10418000220220FD21C0322F32953F70832F90E014
+:104190000097D1F0D80115962C9315970F9741F001
+:1041A000832F8F5F8295807F2F70282B15962C93FD
+:1041B000C8010E94C41A86E0F801ADE1B2E00190A6
+:1041C0000D928A95E1F73EC086E0F801ADE1B2E0DC
+:1041D00001900D928A95E1F737C04D875E878D85F6
+:1041E0009E850E94901E811123C0809122028160D1
+:1041F00080932202C8010E94C41A26C07E2DF98A2B
+:10420000E88A89890E94B11EEDE1F2E086E0DF01D3
+:104210001D928A95E9F70E94F11E18C0662351F39A
+:104220004D875E878D859E850E94901E882311F3A1
+:1042300086E0F801ADE1B2E001900D928A95E1F7D8
+:104240000E94FF1E0E94F11E81E014C080E012C097
+:104250004D875E878D859E850E946923292F229533
+:104260002F7030E0223031050CF4E0CE24303105DF
+:104270000CF6E2CE62960FB6F894DEBF0FBECDBF4D
+:10428000DF91CF911F910F91FF90EF9008951F93B1
+:10429000CF93DF93CDB7DEB72C970FB6F894DEBF80
+:1042A0000FBECDBF4F83588769877A878B879C87DE
+:1042B000CE0107960E94771F8823D9F02F81388579
+:1042C0008A859B85892B39F03F3F19F080E090E08B
+:1042D00004C02F3FD9F781E090E0892B09F06DC031
+:1042E0004F81588569857A858B859C850E94C01E83
+:1042F00064C086E0FE013796DE01119601900D92B2
+:104300008A95E1F7FF81E8854A855B85411551056E
+:1043100039F0EF3F41F481E090E0FF3F31F003C01E
+:1043200081E090E002C080E090E080FD46C02091F6
+:10433000540230E0C90101968770992760915302B9
+:1043400070E08617970709F440C0F983EA835D831C
+:104350004C8396E0929FD001939FB00D1124AD5DE8
+:10436000BD4FFE01319601900D929A95E1F7809331
+:1043700054020E94D01E21C0189FC00111248D5DDF
+:104380009D4F0E94771F882371F1E09153021E9F79
+:10439000F0011124ED5DFD4F4081518162817381F7
+:1043A000848195810E94C01E8091530290E0019605
+:1043B000877099278093530201C016E080915302C1
+:1043C000909154028913D8CF0EC00E948C1E109277
+:1043D000540210925302EDE1F2E086E0DF011D92FB
+:1043E0008A95E9F7EACF2C960FB6F894DEBF0FBE98
+:1043F000CDBFDF91CF911F910895DF92EF92FF9291
+:104400000F931F93CF93DF93EC01009709F46CC0D7
+:10441000D12CEE24E394F12C8E010F5F1F4FFE018F
+:104420008491843748F4843008F04AC0813071F0B8
+:10443000823009F059C01EC0853709F43DC070F1C3
+:10444000982F9458903708F04FC03DC02296F8013D
+:104450008491982F905E983050F48770FE2D01C0A3
+:10446000FF0F8A95EAF78F2F0E94FF2330C00E942A
+:104470009D192DC02296F8018491982F905E983056
+:1044800050F48770FE2D01C0FF0F8A95EAF78F2F39
+:104490000E9405241CC00E94651A19C02296F801CA
+:1044A000049107C08FE99FE00197F1F700C0000079
+:1044B00001500111F7CF0BC02296F801D49007C02C
+:1044C0000E949D1903C08F770E94651AE8018D2D07
+:1044D00007C08150EFE9FFE03197F1F700C000001D
+:1044E000882309F499CFF5CFDF91CF911F910F91D8
+:1044F000FF90EF90DF9008956093590270935A02F5
+:1045000080935B0290935C020C947A1E6093550238
+:104510007093560280935702909358020C947A1E1F
+:1045200008950C947C220F931F93009159021091CF
+:104530005A0220915B0230915C02602B712B822B1E
+:10454000932B1F910F910C947C220F931F9300913A
+:10455000590210915A0220915B0230915C02602353
+:104560007123822393231F910F910C947C220F932C
+:104570001F930091590210915A0220915B023091D1
+:104580005C0260277127822793271F910F910C945B
+:104590007C2260E070E0CB010C94862241E050E088
+:1045A00060E070E004C0440F551F661F771F8A95B6
+:1045B000D2F7CB01BA010C94862241E050E060E0D2
+:1045C00070E004C0440F551F661F771F8A95D2F70D
+:1045D0008091550290915602A0915702B0915802D5
+:1045E000482B592B6A2B7B2BCB01BA010C948622CA
+:1045F00041E050E060E070E004C0440F551F661FCA
+:10460000771F8A95D2F74095509560957095809167
+:10461000550290915602A0915702B091580248233A
+:1046200059236A237B23CB01BA010C94862241E0F3
+:1046300050E060E070E004C0440F551F661F771F14
+:104640008A95D2F78091550290915602A091570217
+:10465000B0915802482759276A277B27CB01BA0116
+:104660000C9486220F931F930091550210915602CD
+:104670002091570230915802602B712B822B932B83
+:104680001F910F910C9486220F931F930091550256
+:1046900010915602209157023091580260237123E5
+:1046A000822393231F910F910C9486220F931F93C3
+:1046B00000915502109156022091570230915802F4
+:1046C00060277127822793271F910F910C948622D0
+:1046D0000895CF92DF92EF92FF920F931F93CF93A3
+:1046E000DF93EC01C0905902D0905A02E0905B0237
+:1046F000F0905C028091550290915602A091570271
+:10470000B0915802C82AD92AEA2AFB2A0FE110E000
+:10471000B701A601002E04C0769567955795479579
+:104720000A94D2F740FF08C0BE01802F0E94E00328
+:104730008130910509F007C00150110948F7BE0109
+:1047400080E00E94E003DF91CF911F910F91FF90D5
+:10475000EF90DF90CF90089540911B0150911C0184
+:1047600020E030E09FEFFA01E20FF31F628168174B
+:10477000A1F09F3F19F4611101C0922F2F5F3F4FAD
+:104780002630310581F707C0FA01E90FF11D97FDC9
+:10479000FA95828308959F3FB9F7089540911B01D0
+:1047A00050911C0120E030E0FA01E20FF31F9281EA
+:1047B000981301C012822F5F3F4F26303105A1F7B9
+:1047C000089581E090E0E0911B01F0911C01E80F59
+:1047D000F91F1082019688309105A9F708959091EC
+:1047E0005D02982B90935D020895809590915D02F3
+:1047F000982390935D02089510925D020895909120
+:104800005E02982B90935E020895809590915E02CF
+:10481000982390935E02089510925E02089580930B
+:104820005F02089510925F02089540911B0150911C
+:104830001C0120E030E080E0FA01E20FF31F9181DB
+:1048400091118F5F2F5F3F4F27303105A9F70895F2
+:10485000E0911B01F0911C0180915D028083E09149
+:104860001B01F0911C01808190915E02892B808355
+:1048700090915F02992361F0E0911B01F0911C017E
+:104880008081892B80830E94152481110E9412242B
+:1048900080911B0190911C010C946A1880916E0309
+:1048A000843009F11092690220E488E190E00FB6AB
+:1048B000F894A895809360000FBE2093600083B7A2
+:1048C000817F846083BF83B7816083BF789488953C
+:1048D00083B78E7F83BF88E10FB6F8948093600022
+:1048E000109260000FBE0895CF930E94E3020E94D1
+:1048F0007E060E94E402C0E08C2F0E94C407892B30
+:1049000029F4CF5FC430C1F780E001C081E0CF91CE
+:1049100008950E948C1E0C945F2B1F920F920FB66D
+:104920000F9211248F939F93AF93BF93809169024D
+:10493000811113C080916A0290916B02A0916C0268
+:10494000B0916D024196A11DB11D80936A029093B2
+:104950006B02A0936C02B0936D02BF91AF919F91D7
+:104960008F910F900FBE0F901F90189582E084BD1D
+:1049700093E095BD9AEF97BD80936E0008958FB731
+:10498000F89440916A0250916B0260916C027091B0
+:104990006D028FBFCA010895CF92DF92EF92FF920E
+:1049A0000F931F932FB7F89440916A0250916B02B6
+:1049B00060916C0270916D022FBF6A017B01EE2441
+:1049C000FF248C0120E030E0C016D106E206F30699
+:1049D00020F09A01281B390B05C09C0120953095C9
+:1049E000240F351FC9011F910F91FF90EF90DF90A9
+:1049F000CF9008951F920F920FB60F9211248F93AC
+:104A00009F93AF93BF9380916A0290916B02A091A4
+:104A10006C02B0916D020196A11DB11D80936A02D6
+:104A200090936B02A0936C02B0936D02BF91AF9113
+:104A30009F918F910F900FBE0F901F9018950E941D
+:104A4000A111F8942FEF87EA91E621508040904021
+:104A5000E1F700C0000087E090EBDC018093780371
+:104A600090937903A0937A03B0937B032CE088E1C1
+:104A700090E00FB6F894A895809360000FBE209345
+:104A80006000FFCFCF92DF92EF92FF920F931F93C0
+:104A9000CF93DF93C82ED12C01E010E08D2D0E9422
+:104AA000C4077C01C0E0D0E098010C2E02C0220FA8
+:104AB000331F0A94E2F72E213F21232B29F421965C
+:104AC000CC30D10589F708C06C2F7D2D80E00E9485
+:104AD000BB03C812F4CF06C0D39484E0D812DECF53
+:104AE00080E001C081E0DF91CF911F910F91FF9095
+:104AF000EF90DF90CF900895CF93C82F8CE20E9463
+:104B00004225882321F08C2FCF910C94422580E000
+:104B1000CF910895CF930E94CD26811102C00E94AB
+:104B2000AE26C5E608C00E947E068FE39CE9019789
+:104B3000F1F700C00000C150B1F789E20E947C2566
+:104B400081110AC18AE20E947C2581110E94AE2651
+:104B500085E00E947C2581110E941F250E94D82695
+:104B60008093680287E00E947C25882399F18BE17D
+:104B70000E947C25882351F09091680291FB882740
+:104B800080F921E0822780FB91F922C08EE00E940B
+:104B90007C25882351F09091680292FB882780F948
+:104BA00021E0822780FB92F913C080E10E947C25DE
+:104BB00090916802882341F093FB882780F921E0D7
+:104BC000822780FB93F904C0892F809580FB90F9A0
+:104BD00090936802809168020E94DC260E94EA2677
+:104BE00080937B0280EE0E947C25882341F0809197
+:104BF0007B02982F909590FB80F980937B0289E34C
+:104C00000E947C25882359F090917B0291FB882794
+:104C100080F921E0822780FB91F990937B0282EE5C
+:104C20000E947C25882359F090917B0292FB882773
+:104C300080F921E0822780FB92F990937B0286EE37
+:104C40000E947C25882359F090917B0293FB882752
+:104C500080F921E0822780FB93F990937B0283EE19
+:104C60000E947C25882359F090917B0294FB882731
+:104C700080F921E0822780FB94F990937B0285E301
+:104C80000E947C25882359F090917B0295FB882710
+:104C900080F921E0822780FB95F990937B0281E3E4
+:104CA0000E947C25882359F090917B0296FB8827EF
+:104CB00080F921E0822780FB96F990937B0281E1C5
+:104CC0000E947C25882359F090917B0297FB8827CE
+:104CD00080F921E0822780FB97F990937B028091F5
+:104CE0007B020E94EE2687E20E947C25C82F8EE17F
+:104CF0000E947C258111C2608FE10E947C25811178
+:104D0000C46080E20E947C258111C86081E20E941B
+:104D10007C258111C06182E20E947C258111C062E4
+:104D200083E20E947C258111C06484E20E947C257C
+:104D3000882311F0C06802C0CC2329F08C2F0E9478
+:104D4000E5266C2F03C00E94E126682F70E080E00A
+:104D500090E0CF910C949122CF9108956DEE7EEF6B
+:104D600080E090E00E94BA2F60E082E090E00E9434
+:104D7000AC2F60E083E090E00E94AC2F60E084E024
+:104D800090E00E94AC2F60E085E090E00E94AC2FA4
+:104D900060E086E090E00C94AC2F80E090E00E9410
+:104DA000A62F21E08D3E9E4F09F020E0822F08952E
+:104DB00082E090E00C949E2F682F82E090E00C94AB
+:104DC000AC2F83E090E00C949E2F682F83E090E05E
+:104DD0000C94AC2F84E090E00C949E2F682F84E01C
+:104DE00090E00C94AC2F86E090E00C949E2F682FFE
+:104DF00086E090E00C94AC2F8091760280FF0BC08F
+:104E00006091200185E0689FB00111247595679538
+:104E1000759567952AC081FF09C06091200185E0E2
+:104E2000689FB0011124759567951FC082FF07C068
+:104E30006091200185E0689FB001112416C0409167
+:104E400070024423C9F060911F01461788F7209132
+:104E5000200185E0289F90011124429FC001439FBB
+:104E6000900D112470E00E948A2F6038710540F483
+:104E70006115710539F002C065E070E0862F089574
+:104E80008FE7089581E008958091760280FF08C041
+:104E900060911E0170E0759567957595679521C0C5
+:104EA00081FF06C060911E0170E07595679519C07D
+:104EB00082FF04C060911E0170E010C080917002FA
+:104EC0008823C1F060911D018617A0F790911E0103
+:104ED000989FC001112470E00E948A2F60387105EC
+:104EE00028F46115710521F0862F08958FE7089544
+:104EF00081E0089561E070E0F4CF803F21F40E94EA
+:104F0000FC26819504C0813F29F40E94FC268093F1
+:104F100073020895823F21F40E94FC26819504C00B
+:104F2000833F29F40E94FC26809372020895893FF2
+:104F300019F40E94442705C08A3F31F40E94442797
+:104F400081958093740208958B3F21F40E94442739
+:104F5000819504C08C3F29F40E94442780937502F8
+:104F60000895843F21F480917102816017C0853FCC
+:104F700021F480917102826011C0863F21F48091FA
+:104F8000710284600BC0873F21F4809171028860B8
+:104F900005C0883F31F48091710280618093710275
+:104FA00008958D3F21F48091760281600BC08E3F81
+:104FB00021F480917602826005C08F3F29F48091B0
+:104FC00076028460809376020895803F29F4809170
+:104FD000730287FF6EC007C0813F41F48091730266
+:104FE00018160CF066C01092730263C090917202A2
+:104FF000823F19F497FF5DC005C0833F31F4191655
+:105000000CF057C01092720254C0893F31F4809165
+:10501000740218160CF04DC006C08A3F39F4809116
+:10502000740287FF46C01092740243C08B3F29F47C
+:105030008091750287FF3DC006C08C3F39F4809196
+:1050400075021816B4F51092750233C0843F21F42E
+:10505000809171028E7F05C0853F31F4809171028D
+:105060008D7F8093710225C0863F21F4809171026B
+:105070008B7FF7CF873F21F480917102877FF1CF3B
+:10508000883F21F4809171028F7EEBCF8D3F21F418
+:10509000809176028E7F0BC08E3F21F48091760244
+:1050A0008D7F05C08F3F29F4809176028B7F80939E
+:1050B00076028091720281110EC08091730281117B
+:1050C0000AC080917402811106C08091750281111D
+:1050D00002C010927002089581E792E00E94751854
+:1050E0000E94BF2490936F0280936E020895CF9325
+:1050F00080916E0290916F020E94CC2440917002C8
+:10510000442321F02091210130E006C020912201AA
+:105110005AE0259F900111248217930708F486C056
+:105120008091720281110DC090917302911109C09A
+:1051300090917402911105C090917502992309F420
+:1051400075C04F3F19F04F5F40937002181624F45A
+:105150000E94FC26809372028091720287FF05C034
+:105160000E94FC268195809372028091730218162A
+:1051700024F40E94FC26809373028091730287FFBF
+:1051800005C00E94FC268195809373026091720293
+:10519000662339F1C0917302CC2319F1772767FD9B
+:1051A0007095872F972F0E94FA2C23E333E343E374
+:1051B0005FE30E94AE2D0E94C72C609372026C2F99
+:1051C000772767FD7095872F972F0E94FA2C23E38E
+:1051D00033E343E35FE30E94AE2D0E94C72C60934C
+:1051E000730280917402181624F40E94442780935D
+:1051F00074028091740287FF05C00E944427819544
+:105200008093740280917502181624F40E9444273A
+:10521000809375028091750287FF05C00E94442724
+:10522000819580937502CF910C946C28CF9108954D
+:10523000E1E7F2E085E0DF011D928A95E9F710923F
+:105240007002109276020895833089F130F4813033
+:1052500061F0823009F06EC019C0853009F449C090
+:10526000B8F1863009F066C055C020912201862F22
+:1052700090E0820F911D8F3F910520F4620F6093A3
+:10528000220108958FEF809322010895209121013A
+:10529000862F90E0820F911D8F3F910520F4620FC1
+:1052A0006093210108958FEF80932101089520914B
+:1052B0002001862F90E0820F911D8F3F910520F4F1
+:1052C000620F6093200108958FEF8093200108956D
+:1052D00020911F01862F90E0820F911D8F3F910535
+:1052E00020F4620F60931F0108958FEF80931F01D8
+:1052F000089520911E01862F90E0820F911D8F3F0F
+:10530000910520F4620F60931E0108958FEF809342
+:105310001E01089520911D01862F90E0820F911D9E
+:105320008F3F910520F4620F60931D0108958FEF68
+:1053300080931D010895833021F130F4813059F0BC
+:10534000823009F049C012C0853089F128F18630D9
+:1053500009F042C037C080912201681720F4861BF3
+:1053600080932201089510922201089580912101D5
+:10537000681720F4861B8093210108951092210163
+:10538000089580912001681720F4861B80932001E6
+:10539000089510922001089580911F01681720F44C
+:1053A000861B80931F01089510921F01089580911C
+:1053B0001E01681720F4861B80931E010895109229
+:1053C0001E01089580911D01681720F4861B8093AB
+:1053D0001D01089510921D01089541E050E060E024
+:1053E00070E004C0440F551F661F771F8A95D2F7DF
+:1053F000CB01BA010E9491220C948C1E873208F5D1
+:105400008E3108F0B9C08E3009F47EC060F4873068
+:1054100009F465C018F4863059F549C0883051F157
+:105420008B3031F5AEC0883130F4863108F0A9C038
+:105430008031F1F473C0893109F4A3C08B31C1F418
+:1054400059C08933F1F068F4893209F493C018F433
+:10545000873271F48FC0853309F48CC0883341F4EE
+:1054600090C0863409F46BC008F488C0883449F1D0
+:1054700080E008950E94D8260E94EA260E94F32622
+:1054800080C00E945918892B59F00E945918909396
+:105490007902809378020E948C1E80E090E004C024
+:1054A00080917802909179020E9454186AC080918C
+:1054B0006802817F8E7F8093680281E0809377020B
+:1054C00008950E948C1E2FEF83ED90E321508040C1
+:1054D0009040E1F700C000000E941F2552C080915B
+:1054E000680280FF03C0817F8E7F01C0816080934E
+:1054F000680247C09091680291FB882780F921E0FB
+:10550000822780FB91F913C09091680292FB882753
+:1055100080F921E0822780FB92F909C0909168020E
+:1055200093FB882780F921E0822780FB93F99093F1
+:105530006802882331F191609093680222C081E86B
+:1055400090E00E9480182FEF81EE94E0215080407F
+:105550009040E1F700C0000080E090E00E948018D9
+:105560002FEF89E698E1215080409040E1F700C09C
+:10557000000007C080E003C08D5101C089530E9424
+:10558000ED2981E0089580E0089580E00895CF93AB
+:10559000C82F80917702813071F020F0823009F0BD
+:1055A00083C037C0A0911B01B0911C018C91823245
+:1055B00009F07CC007C0A0911B01B0911C018C9127
+:1055C000823249F48C2F0E94C32A81111EC08C2F75
+:1055D0000E94FE291CC08C2F0E94C52A811115C073
+:1055E000C43169F030F4CB3081F0C03109F062C0D1
+:1055F00009C0C93221F0C83309F05CC006C010925E
+:10560000770258C082E08093770281E090E0817059
+:1056100054C0C932C1F060F4C431A9F020F4C730DD
+:1056200009F046C02EC0CE51CA3008F041C011C0AA
+:10563000CE3409F118F4CB34D9F517C0C13599F03F
+:10564000C235B1F50EC010927A0281E080937702E4
+:1056500034C0EC2FF0E0E455FE4F808180937A0255
+:1056600027C061E003C061E007C06AE080917A0270
+:105670000E9424291DC06AE080917A020E949B2921
+:1056800017C08EE18093220182E3809321018AE09A
+:105690008093200184E180931F0188E080931E01A4
+:1056A00088E280931D0104C01092770280E005C05B
+:1056B00081E003C080E090E0AACFCF9108950E94DE
+:1056C000CD26811102C00E94AE260E94F32680934F
+:1056D000770380FF02C0869501C080E00C94DF074D
+:1056E00080917703982F9695292F30E0233031054C
+:1056F0004CF49F5F990F8170892B816080937703B1
+:105700000E94F7268091770386950C94DF0780919D
+:105710007703982F969591F09158990F8170892B66
+:10572000809377038E7F91E009F490E08091770376
+:1057300090FB80F9809377030E94F726809177038E
+:1057400086950C94DF0780917703982F909590FBB6
+:1057500080F9809377030E94F7268091770380FF7A
+:1057600002C0869501C080E00C94DF07309177037A
+:10577000232F26952F5F2F77822F90E0317004978B
+:105780002CF4220F232B2093770302C0309377034E
+:1057900080917703282F2E7F91E009F490E090FB11
+:1057A00080F9809377030E94F7268091770386958E
+:1057B0000C94DF0720917703922F96959827990FE5
+:1057C000822F8170892B809377038E7F91E009F47B
+:1057D00090E08091770390FB80F9809377030E949B
+:1057E000F7268091770386950C94DF075058BB27E6
+:1057F000AA270ED075C166D130F06BD120F031F4FC
+:105800009F3F11F41EF45BC10EF4E095E7FB51C11C
+:10581000E92F77D180F3BA176207730784079507DA
+:1058200018F071F49EF58FC10EF4E0950B2EBA2F8F
+:10583000A02D0B01B90190010C01CA01A001112496
+:10584000FF27591B99F0593F50F4503E68F11A1642
+:10585000F040A22F232F342F4427585FF3CF4695D3
+:1058600037952795A795F0405395C9F77EF41F16F5
+:10587000BA0B620B730B840BBAF09150A1F0FF0FBF
+:10588000BB1F661F771F881FC2F70EC0BA0F621FAB
+:10589000731F841F48F4879577956795B795F7959B
+:1058A0009E3F08F0B3CF9395880F08F09927EE0F2D
+:1058B000979587950895D9D008F481E008950CD084
+:1058C0000FC107D140F0FED030F021F45F3F19F056
+:1058D000F0C0511139C1F3C014D198F39923C9F321
+:1058E0005523B1F3951B550BBB27AA2762177307E6
+:1058F000840738F09F5F5F4F220F331F441FAA1F9A
+:10590000A9F333D00E2E3AF0E0E830D09150504059
+:10591000E695001CCAF729D0FE2F27D0660F771F07
+:10592000881FBB1F261737074807AB07B0E809F0E9
+:10593000BB0B802DBF01FF2793585F4F2AF09E3F7E
+:10594000510568F0B6C000C15F3FECF3983EDCF350
+:10595000869577956795B795F7959F5FC9F7880FF7
+:10596000911D9695879597F90895E1E0660F771F49
+:10597000881FBB1F621773078407BA0720F0621BDA
+:10598000730B840BBA0BEE1F88F7E095089504D0D3
+:105990006894B111D9C00895BCD088F09F5790F099
+:1059A000B92F9927B751A0F0D1F0660F771F881F44
+:1059B000991F1AF0BA95C9F712C0B13081F0C3D05F
+:1059C000B1E00895C0C0672F782F8827B85F39F0FD
+:1059D000B93FCCF3869577956795B395D9F73EF4A3
+:1059E00090958095709561957F4F8F4F9F4F08954B
+:1059F000E89409C097FB3EF4909580957095619569
+:105A00007F4F8F4F9F4F9923A9F0F92F96E9BB271E
+:105A10009395F695879577956795B795F111F8CF9A
+:105A2000FAF4BB0F11F460FF1BC06F5F7F4F8F4F05
+:105A30009F4F16C0882311F096E911C0772321F0FB
+:105A40009EE8872F762F05C0662371F096E8862F93
+:105A500070E060E02AF09A95660F771F881FDAF7EA
+:105A6000880F9695879597F90895990F0008550F17
+:105A7000AA0BE0E8FEEF16161706E807F907C0F0D4
+:105A800012161306E407F50798F0621B730B840BDC
+:105A9000950B39F40A2661F0232B242B252B21F4B6
+:105AA00008950A2609F4A140A6958FEF811D811D56
+:105AB000089597F99F6780E870E060E008959FEF90
+:105AC00080EC089500240A94161617061806090695
+:105AD000089500240A941216130614060506089564
+:105AE000092E0394000C11F4882352F0BB0F40F4EC
+:105AF000BF2B11F460FF04C06F5F7F4F8F4F9F4F2C
+:105B0000089557FD9058440F551F59F05F3F71F0AD
+:105B10004795880F97FB991F61F09F3F79F0879514
+:105B20000895121613061406551FF2CF4695F1DF9D
+:105B300008C0161617061806991FF1CF869571052D
+:105B4000610508940895E894BB2766277727CB0161
+:105B500097F908958ADF08F48FEF08950BD0C0CF2E
+:105B6000B1DF28F0B6DF18F0952309F0A2CFA7CF58
+:105B70001124EACFC6DFA0F3959FD1F3950F50E033
+:105B8000551F629FF001729FBB27F00DB11D639FEF
+:105B9000AA27F00DB11DAA1F649F6627B00DA11D95
+:105BA000661F829F2227B00DA11D621F739FB00D3B
+:105BB000A11D621F839FA00D611D221F749F3327AB
+:105BC000A00D611D231F849F600D211D822F762F44
+:105BD0006A2F11249F5750408AF0E1F088234AF041
+:105BE000EE0FFF1FBB1F661F771F881F915050408D
+:105BF000A9F79E3F510570F05CCFA6CF5F3FECF355
+:105C0000983EDCF3869577956795B795F795E79578
+:105C10009F5FC1F7FE2B880F911D9695879597F989
+:105C20000895FA01EE0FFF1F30962105310599F115
+:105C30006115710561F48038BFE39B0749F16894F1
+:105C40009038810561F08038BFEF9B0741F09923C0
+:105C500042F5FF3FE1053105210511F1E894089473
+:105C6000E795D901AA2329F4AB2FBE2FF85FD0F313
+:105C700010C0FF5F70F4A695E0F7F73950F019F007
+:105C8000FF3A38F49F779F930CD00F9007FC905801
+:105C900008953EF014CF60E070E080E89FE308953F
+:105CA0004FE79F775F934F933F932F939ED02F9112
+:105CB0003F914F915F9152DF05C019F40EF0F9CE7C
+:105CC00042CFFDCE26DFC8F39638C0F707F80F9213
+:105CD000E8942BE33AEA48EB5FE74EDF0F920F922E
+:105CE0000F924DB75EB70F92C0D0ECEAF0E016D03D
+:105CF0004F915F91EF91FF91E595EE1FFF1F49F0E6
+:105D0000FE57E0684427EE0F441FFA95E1F74195EE
+:105D1000550B32D00F9007FE26C00895DF93CF9326
+:105D20001F930F93FF92EF92DF927B018C01689497
+:105D300005C0DA2EEF011EDFFE01E894A591259142
+:105D4000359145915591AEF3EF0162DDFE0197016A
+:105D5000A801DA9479F7DF90EF90FF900F911F91EF
+:105D6000CF91DF9108959B01AC0160E070E080E885
+:105D70009FE3A5CD9ECEACC0CCDEE8F39923D9F34A
+:105D8000940F511DBBF39150504094F059F088236B
+:105D900032F0660F771F881F91505040C1F79E3F29
+:105DA000510544F7880F911D9695879597F90895A9
+:105DB0005F3FACF0983E9CF0BB2786957795679542
+:105DC000B79508F4B1609395C1F7BB0F58F711F47C
+:105DD00060FFE8CF6F5F7F4F8F4F9F4FE3CFB4CE11
+:105DE0000EF076C06CCE689464CE93DEC8F399232F
+:105DF000D1F3C6F3DF93CF931F930F93FF92C92F75
+:105E0000DD2788232AF02197660F771F881FDAF78E
+:105E100020E030E040E85FEB9FE3883920F0803EEF
+:105E200030F021968F77E3DCE4EDF0E003C0DFDCB7
+:105E3000E1E0F1E073DF8B01BE01EC01FB2E6F5757
+:105E400071097595771F880B990BD4DD28E132E72E
+:105E500041E35FE38FDEAF2D9801AE01FF900F911C
+:105E60001F91CF91DF91D4DC3BCEFA01DC01AA0F68
+:105E7000BB1F9B01AC01BF5728F4222733274427BF
+:105E800050781FC0B75188F4AB2F00244695379542
+:105E90002795011CA395D2F3002069F0220F331F30
+:105EA000441FB395DAF30DD0A1CC61307105A0E8A1
+:105EB0008A07B94630F49B01AC016627772788270B
+:105EC0009078309621F02083318342835383089564
+:105ED0009F3F31F0915020F4879577956795B7955E
+:105EE000880F911D9695879597F90895AA1BBB1B5E
+:105EF00051E107C0AA1FBB1FA617B70710F0A61BCA
+:105F0000B70B881F991F5A95A9F780959095BC01EA
+:105F1000CD01089597FB072E16F4009407D077FD66
+:105F200009D00E94762F07FC05D03EF4909581950C
+:105F30009F4F0895709561957F4F0895F999FECF11
+:105F400092BD81BDF89A992780B50895A8E1B0E087
+:105F500042E050E00C94C12F262FF999FECF1FBAD2
+:105F600092BD81BD20BD0FB6F894FA9AF99A0FBE82
+:105F7000019608950E94AC2F272F0C94AD2FDC01C1
+:105F8000CB01FC01F999FECF06C0F2BDE1BDF89A44
+:105F9000319600B40D9241505040B8F70895F894EE
+:025FA000FFCF31
+:105FA2000507000C058540000001064000000100C5
+:105FB200D80B680C440C0F0CDB0B01600228081490
+:105FC2000A321E40004500250026006100600020C4
+:105FD2000037006400650066006700440046002444
+:105FE2000047000000020004000500070009000B42
+:105FF200000C000E0010001100130015001700180D
+:10600200001A001C001D001F00210023002400268E
+:1060120000280029002B002D002F00300032003410
+:10602200003500370039003B008803A103BA03D3CF
+:1060320003FB04AE04780458043F4D3620020302E9
+:10604200000001000101010101000101010203043C
+:0660520005060708090025
+:00000001FF
diff --git a/keyboard/planck/planck_with_bootloader.hex b/keyboard/planck/planck_with_bootloader.hex
new file mode 100755
index 0000000000..c61dfb743a
--- /dev/null
+++ b/keyboard/planck/planck_with_bootloader.hex
@@ -0,0 +1,1796 @@
+:020000020000FC
+:047000000C948D3E21
+:047028000C94B73DD0
+:10702F0012010002FF010020EB03F42F0000010208
+:10703F00030109021200010100803209040000005F
+:10704F00000000000C03410054004D0045004C00AF
+:10705F001603410054006D00330032005500340018
+:10706F004400460055000C0331002E0030002E0066
+:10707F0030000403090416010C0100000C0000018C
+:02708F006C7F14
+:1070920012BD01BDF89A00B5089501E00895F9996D
+:1070A200FECF12BD01BD20BDFA9AF99AF6CFF99929
+:1070B200FECF0C944938F80104910895F8013491F7
+:1070C20031962491890108950091610000930C0189
+:1070D20000E80093610001E00093610005BF02E057
+:1070E20005BF0C9486380091D70001600093D70049
+:1070F200A89507EF04BF0091600000610093600053
+:1071020000E00093600001E008950E94AA3D0E9401
+:10711200B53DFDCF0CD00F7708D0006806D00061D6
+:1071220004D0016028D0789408950093D80000918B
+:10713200D8000895FCDF00621ED04CD009B500FFD4
+:10714200FDCFF5DF0F7D17D00091E0000E7F009399
+:10715200E0000091E000077F0093E0000091E20070
+:1071620001600093E2000091E20008600093E200F7
+:1071720078940C94743B0093D800089500910D010B
+:10718200002359F40091D90000FF07C0D0DF006846
+:10719200F2DF01E000930D01CDDFE0E2F2E00081D9
+:1071A200018100FF0DC0008111811E7F11830083C8
+:1071B20001E00093EA0000E00093EA0000931E025F
+:1071C20000E00093E9000091E80003FF02C00E9482
+:1071D200F23B0895A89539D000E40093600000E0E6
+:1071E200009381000093800010E0009385000093DB
+:1071F200840001E006BB00918100036000938100DE
+:107202000091600007FFFCCF00E80093600010933C
+:107212008100A89507EF04BF18D010936000209159
+:1072220084003091850010938100109380001093A8
+:1072320085001093840001E006BB2D3D354010F01F
+:1072420002E101C002E009BD089500916000006101
+:107252000093600008950E94AD3E239741D100E063
+:1072620000930901B5D104811581012B51F437D165
+:1072720000910701002309F4B9C000E0009307015F
+:10728200B5C058D102FFFDCF37D1068335D1009367
+:107292000F0132D1009310012FD1009311012CD193
+:1072A2000093120129D10093130102852091130149
+:1072B20030911201409111015091100116811A95DD
+:1072C20041F01250A9F01A9599F11A9509F473C078
+:1072D2008BC010910F01113011F411E001C010E0C8
+:1072E200138799D00C3F11F414D17FC077D17DC0A0
+:1072F20092D010910F01112329F01A9549F01A9595
+:10730200A9F073C010E013870C3F09F06EC0ECCFF8
+:1073120056D103C04CD109F468C00D911C9144D1DF
+:107322000F3FC1F305E0009309015FC011E0EBCF0D
+:10733200D2D029F00250E1F10A9541F056C0FDD0B9
+:107342000E94A33F0FEF00930A014FC0552319F08B
+:107352005A9579F04AC04ED00DEF04BF74D0EAD0EE
+:1073620003FFFDCF67D051D04AD008E00093600000
+:10737200FFCF40D068D0DED003FFFDCF5BD03FD03F
+:1073820044D00FEF1FE004C009811A810150104060
+:1073920009831A8309811A81012BB1F700E800934E
+:1073A200610000910C01009361000C940000FFCF7A
+:1073B20001E003871AC08FD019F00A9539F015C081
+:1073C200535098F4BAD002E000870FC0505339F0FE
+:1073D2005A9541F05F52B1F35A95A1F306C002E00B
+:1073E2000883F0CF01E0FCCFA8D079D02396E4E067
+:1073F2000C94BA3E01E005BF00E005BF089500917C
+:10740200D8000F770093D800089509B50D7F09BD04
+:1074120000E009BD08955183408333832283109194
+:10742200E8001B7F1093E8001091E8001F7710938B
+:10743200E80008955DD053D0F8940091E000016017
+:107442000093E000089579D04AC0219749D0009175
+:107452000601035019F00250B9F00BC03CD021F0E4
+:107462000A9559F00A9529F400910A010C3F19F482
+:1074720050D02196089567D0FCCF0091010100936E
+:10748200F100009100010AC01091100124D019F0FE
+:107492000A9549F0EECF135018F400E00093F10082
+:1074A2001ED044D0E6CF105339F01A9539F01F524E
+:1074B20041F01A9541F0F4CF08E5F0CF00E006D094
+:1074C200EDCF02E0FCCF04E001D0E8CF10E020E0F5
+:1074D20030E00C94113F00910F010023089521C068
+:1074E2000BD008D007D00093040106D00093050109
+:1074F20021D00BC000D008830091F10008950091C3
+:10750200EB0000620093EB0015D0077F0093E800C8
+:107512000895F5DF02E00093080103E000930901FA
+:10752200089559D007D000FFFDCF089503D002FF80
+:10753200FDCF03C00091E8000895FCDF0B7FE6DF7A
+:10754200F9DF0F77E3CF0E94AC3E42D038D006C0BD
+:107552002BD00093F1002BD059F43DD0082F092BEA
+:10756200A9F0E8DF02FD12C0E5DF00FFFDCF4424F1
+:10757200042D4394003289F300910B0100230D91F5
+:107582001C9131F311970E945838E3CFD3DF00FFEB
+:10759200FDCF21D0CFDF00FFFDCFCCDF02FFFDCF3B
+:1075A200CCDFE5E00C94B93E11970C945C380D9158
+:1075B2001C910F5F1F4F1C930E93019708958281B8
+:1075C200938100811181801B910B0196DF01089547
+:1075D200E0E0F1E00895AEDF0E7F98CF0E94A93E71
+:1075E200F7DF80819181A081B181AF710481158122
+:1075F20000521040048315830AC000910B0100233E
+:1076020031F4A301920103E911E00E943B3F47D00C
+:10761200B8F1662477242C0111C06EDFF301ED5618
+:10762200FE4F008301E0600E00E0701E01960091A3
+:10763200F200002311F033D0B8F47FDF30D0E8F24B
+:10764200F301B096E238F040C0F674DF02FFFDCFDE
+:107652000091F200BDDF24813581201B304024835C
+:107662003583E5CF49DFAA95AA23E1F700910B0103
+:10767200013099F62091F1008C010E945038D6CF4A
+:1076820004811581012B21F055DF02FFFDCF55DF6B
+:10769200A2DF50DF00FFFDCFE8E00C94B63EE0E051
+:1076A200F1E0028113810817190708952091EB0078
+:1076B20021602093EB000093EC000091ED0002703A
+:1076C200012B0093ED000091ED0002600093ED00AC
+:1076D2001091EE00012F000F00E0001F0895412FCE
+:1076E2000093E900089500E009D000FD05C000E024
+:1076F200F7DF10E202E0DACF00E00895F1DF009157
+:10770200EB0008950F770132A9F5112369F11A955B
+:1077120059F01A9561F01A9569F01A95F9F01A95CF
+:10772200C1F01A95D9F024C00E942C3920C00E94C1
+:10773200263A1DC029D00091090123D001E01FD0B3
+:1077420020D0009108011BD00E94923A0E94973AE1
+:107752000EC01AD00091080114D007C002E00093B5
+:10776200080100E0009309010FD00E94923A03C081
+:107772000E94803A02C001E0089500E0089501D01D
+:1077820000E00093F10008950091E800077F009364
+:10779200E800089508950350F9F4112339F01A9579
+:1077A20051F01A9581F01A9599F016C004E016D09E
+:1077B20001E810E703C011D003E510E7E7E1F2E0CA
+:1077C20000831183D8CF06E109D00FE510E7F6CF89
+:1077D20004D005E710E7F2CFD0CF0CE000931A02F5
+:1077E200089527D120D100931D02E1D0212F11232A
+:1077F20029F12A95E9F02250F1F0225099F02A95C8
+:1078020049F0225061F02A9581F02A95E1F02A95FB
+:10781200E9F023C0003809F44FC00C94833B0038D0
+:10782200E1F7C8C00023C9F71EC00023B1F72DC07D
+:10783200033098F744C1033080F70BC1003868F376
+:10784200033858F7C9C0013841F77BC1013051F400
+:10785200FCD0BFD000FD06C0FCCF0E94833B0023BA
+:1078620009F41ED008951091E3001078DCD00F7750
+:10787200012B0093E300E9D0ACD000FFFDCF0091D3
+:10788200E30000680093E300089591D0123040F4C1
+:107892000FD010931E02DAD000911E020C94CB3B43
+:1078A2000091EB0001D004C000620093EB00089548
+:1078B2000091E800077FC0C0BA93AA93229700E024
+:1078C2000093190274D0AFD0202F2A9519F02A956F
+:1078D200E9F022C002E100931A020FE210E7E7E1A9
+:1078E200F2E0008311839DD008839DD00983E0DFFD
+:1078F20000911A0210E02881398102171307A8F4B7
+:107902000F7181F401E00093190211C002E10093AA
+:107912001A0201E410E7E3CF0E94CC3B002319F7DF
+:107922008ED040C01093190202C020931A027ED05A
+:10793200A7E1B2E001C08AD000911A02002309F146
+:1079420048D004FD1EC045D000FD03C042D004FF54
+:10795200FACF10E0012F1395003281F0ED91FC91E6
+:107962001197049133D02D913C912F5F3F4F3C935F
+:107972002E93FD0103810A95038361F72AD004FF48
+:10798200DACF00911902013039F423D004FD04C08A
+:1079920020D000FFFDCF5AD01CD004FFFDCF46D02F
+:1079A20018D00B7F49D02296A991B99108951091D0
+:1079B200F10008957DDF00911E0208D047D009D062
+:1079C2000F773AD006D002FFFDCFBFC00093F1007F
+:1079D20008950091E800089524D010911D021058D6
+:1079E20029F01A9589F01A9591F019C061DF00917A
+:1079F2001C02ECDF00E0EADF29D0EBDF02FFFDCF63
+:107A020018D0E7DF0F770CC053DF00E0F2CF51D080
+:107A12000F7710E0F801E55EFD4F0081EACF0FD04D
+:107A22000BC001D000D00091F1000895D2DF0F7E8B
+:107A320003C00091E8000B7F0093E80008950091D5
+:107A4200EB0032DFC6DF077F089532DFC2DF0E7F31
+:107A5200F3CF00911D02002329F00A9509F10A953E
+:107A620031F01EC0E0DF0A9561D0D9F41AC061D0AE
+:107A7200B9F4D9DF0F7711F416D01BD00093E900C7
+:107A82001091EB0010FF0BC00ED010E01093E90034
+:107A920021E0F801E55EFD4F20834FD003C042D0C4
+:107AA20045D0CFDFC9CF1091EB0010621093EB00ED
+:107AB20008951091E800177F1093E800089500914F
+:107AC2001D02002311F4AFDF02C0013011F4B7DF51
+:107AD200B3CF023031F52DD019F52091F1002F7777
+:107AE2002093E90023D000FF19C081F01FD000616C
+:107AF200DCDE01E010E0422F0E949F3E0093EA008C
+:107B020000E00093EA0012D00860CFDE0BD030E034
+:107B1200F901E55EFD4F008310D0DACF03D0D7CF55
+:107B2200BFDE089500E00093E90008950091EB00A4
+:107B3200089579DF3CDF00230895BADE4ADF0E7F25
+:107B4200089583DF46DF02FFFDCF73DF42DF0F7749
+:107B520073CF0091D70001600093D7000E948B3849
+:107B620000E000931F0208950C94BF388A93FA93A1
+:107B7200EA933A922A921A920A927A936A935A93BF
+:107B82004A933A932A931A930A938FB70091DA0091
+:107B920000FF24C00091D80000FF20C00EEF009328
+:107BA200DA000091D90000FF11C001E000930D013D
+:107BB200ABD0026096D09AD00860A2D00E949B38C7
+:107BC2000091E0000E7F0093E00008C000E0009307
+:107BD2000D0100931E0298D0046083D07FD002FF73
+:107BE20005C084D002FF02C00BEF75D077D000FF32
+:107BF2001BC07CD000FF18C001E000930E016AD0C8
+:107C020083D000626ED00EEF6FD0006179D06ED05B
+:107C12000F7D76D00091D80000620093D80009B59C
+:107C22000D7F09BD00E009BD59D004FF20C05ED020
+:107C320004FF1DC009B500FD05C00E94EB3809B55F
+:107C420000FFFDCF0091D8000F7D0093D80042D0F5
+:107C520000910E01002359F04CD00FEE45D00F7E5B
+:107C620052D000643ED042D001604AD042D036D0D9
+:107C720005FF0FC03BD005FF0CC000E000930E01D2
+:107C820035D00F7E3DD00FED2FD00F7D3CD0006858
+:107C920028D024D003FF0DC029D003FF0AC000E082
+:107CA20000931F0207EF17D00E94743B2DD0116082
+:107CB20018D08FBF09911991299139914991599100
+:107CC200699179910990199029903990E991F991E6
+:107CD200899118950FEE0093E10008950091E1005B
+:107CE20008951183008308950093E1000091E2005A
+:107CF20008950091E200006203D00091E200086062
+:107D02000093E2000895FCDFE0E2F2E000811181DD
+:107D1200089500008895FECF01E60DBF02E00EBF78
+:107D2200C2EED2E00E947438002311F00E94D33ECA
+:107D32000E9465380E948A3E0C948A3E4A951AF047
+:107D4200000F111FFBCF0895BA92AA929A928A92BB
+:107D52007A926A925A924A92BA93AA939A938A937D
+:107D62000895BB84AA84998488847F806E805D8014
+:107D72004C80BB81AA8199818881F0E00FB6F8948A
+:107D8200CE0FDF1F0FBE089520E006D0E9F7089559
+:107D9200259102D0E9F708952D9301501040202F2C
+:107DA200212B089585E890E7FC0105911491FC01CF
+:107DB2003296A591B491FC01349625913491422FCB
+:107DC200432B19F0F901E4DF01C0DEDF069610E76C
+:107DD2008139910748F308952F930CD02F9101D048
+:107DE20008953CD0F12FE02F45E047BFE89536D00B
+:107DF20012D0089533D0F12FE02F43E047BFE8952A
+:107E02002DD008952BD0F12FE02F43E047BFE89506
+:107E120025D001D0089522D041E147BFE8951EC088
+:107E22001DD0F12FE02F41E247BFC895002D16C0AB
+:107E320015D0F12FE02F49E047BFC895002D0EC0A5
+:107E4200F32FE22F012E102E41E047BFE89506C026
+:107E520005D0002E29E027BFE89500C0022E27B7E3
+:107E620020FDFCCF202D0895022E27B726FDFCCF42
+:107E7200202D08950E94A53E22974801C901DA01EA
+:107E820010C05BD001E0A00E00E0B01E00E4A0161E
+:107E920000E0B00608F440C0830120E030E00E9418
+:107EA200F23E0A2F0B2B09F440C0082F0F7710E087
+:107EB2002C01401A510A320100E4A02E03C00A2FFD
+:107EC2000B2BE1F04816590680F0F40101914F01A5
+:107ED2000983119729F001914F010883119711C06D
+:107EE200F2013196049108830CC0F20104910983D6
+:107EF2003196E817F907A1F7F401EDCF1BD00883FB
+:107F020019839201088119810E94213F16D0AA94F7
+:107F1200B1F62301AA24BB240DD0312F0F3F3F4FCE
+:107F220009F4AFCF83011DD0B7CF01E02296ECE078
+:107F32000C94B23E82010C945F3802E0400E00E0E5
+:107F4200501E08959A938A9380E090E08C0109D0A4
+:107F520080589F4F8F3F0FE69007C0F38991999108
+:107F6200089520E030E00C94FB3E00000000000089
+:067F720000000000FC000D
+:107FE4000C94ED3E0C94113F0C94193F0C94213FDA
+:0C7FF4000C94F23E0C94033F0C94293FC7
+:040000030000700089
+:100000000C949D020C94E1020C94E1020C94E10228
+:100010000C94E1020C94E1020C94E1020C94E102D4
+:100020000C94E1020C94E1020C941C120C94EE125C
+:100030000C948D240C94E1020C94E1020C94E102E6
+:100040000C94E1020C94E1020C94E1020C94E102A4
+:100050000C94E1020C94FA240C94E1020C94E10259
+:100060000C94E1020C94E1020C94E1020C94E10284
+:100070000C94E1020C94E1020C94E1020C94E10274
+:100080000C94860A0C94E1020C94E1020C94E102B7
+:100090000C94E1020C94E1020C94E1020C94E10254
+:1000A0000C94E1020C94E1020C94E10207634236E5
+:1000B000B79BD8A71A39685618AEBAAB558C1D3CF9
+:1000C000B7CC5763BD6DEDFD753EF6177231BF00BD
+:1000D0000000803F08000000BE922449123EABAAF7
+:1000E000AA2ABECDCCCC4C3E00000080BEABAAAA52
+:1000F000AA3E00000000BF000000803F000000009A
+:1001000000084178D3BB4387D1133D190E3CC3BDD2
+:100110004282AD2B3E68EC8276BED98FE1A93E4C7F
+:1001200080EFFFBE01C4FF7F3F0000000000000021
+:10013000F1A4F1A3018C028C048C2B0014001A0092
+:100140000800150017001C0018000C001200130016
+:100150002A00290004001600070009000A000B000D
+:100160000D000E000F0033003400E1001D001B00E5
+:100170000600190005001100100036003700380095
+:1001800028000030E000E200E30002202C002C00F8
+:1001900001205000510052004F002B0014001A00A3
+:1001A000090013000A000D000F0018001C003300A6
+:1001B0002A002900040015001600170007000B0094
+:1001C000110008000C0012003400E1001D001B00AB
+:1001D0000600190005000E00100036003700380038
+:1001E00028000030E000E200E30002202C002C0098
+:1001F00001205000510052004F002B003400360007
+:10020000370013001C0009000A00060015000F004B
+:100210002A00290004001200080018000C00070042
+:100220000B001700110016003800E1003300140025
+:100230000D000E001B00050010001A0019001D0023
+:1002400028000030E000E200E30002202C002C0037
+:1002500001205000510052004F0035021E021F02C3
+:100260002002210222022302240225022602270262
+:100270002A0001003A003B003C003D003E003F00E8
+:100280002D022E022F0230023102010040004100F7
+:100290004200430044004500032004200520005094
+:1002A0000100010001000100010002200100010025
+:1002B0000100AB00AA00A900AE0035001E001F001F
+:1002C0002000210022002300240025002600270012
+:1002D0002A0001003A003B003C003D003E003F0088
+:1002E0002D002E002F0030003100010040004100A1
+:1002F0004200430044004500032004200520005034
+:1003000001000100010001000100010001000100E5
+:100310000120AB00AA00A900AE0028035400680029
+:100320006500200050006C0061006E0063006B00EF
+:1003300020004B006500790062006F0061007200D0
+:10034000640000002C034F007200740068006F000E
+:100350006C0069006E0065006100720020004B00B7
+:100360006500790062006F00610072006400730034
+:100370000000040309040902D000060100A03209AC
+:100380000400000103010100092111010001223FC5
+:10039000000705810308000A0904010001030102A6
+:1003A00000092111010001224D0007058203080008
+:1003B0000A090402000103000000092111010001E3
+:1003C0002236000705830308000A0904030002031C
+:1003D000000000092111010001222000070584030B
+:1003E00020000107050403200001090404000001A6
+:1003F00001000009240100010900010509040500AC
+:10040000020103000007240100014100062402014B
+:100410000100062402020200092403010301020173
+:10042000000924030204010101000905060240003D
+:1004300005000005250101010905850240000500B0
+:100440000005250101031201100100000008EDFE66
+:1004500060600100010200010631FF0974A1010979
+:1004600075150025FF952075088102097615002570
+:10047000FF952075089102C005010980A101850240
+:1004800016010026B7001A01002AB7007510950161
+:100490008100C0050C0901A1018503160100269CFD
+:1004A000021A01002A9C02751095018100C0050105
+:1004B0000902A1010901A100050919012905150079
+:1004C00025019505750181029501750381010501DD
+:1004D000093009311581257F950275088106093893
+:1004E0001581257F950175088106050C0A380215CE
+:1004F00081257F950175088106C0C005010906A107
+:1005000001050719E029E715002501950875018106
+:1005100002950175088101050819012905950575E0
+:100520000191029501750391010507190029FF1535
+:100530000025FF950675088100C011241FBECFEF6E
+:10054000DAE0DEBFCDBF04B603FE24C0809178039D
+:1005500090917903A0917A03B0917B038730904BFF
+:10056000A740B04BB9F4109278031092790310921F
+:100570007A0310927B0314BE84B7877F84BF88E11F
+:100580000FB6F89480936000109260000FBEE0E018
+:10059000F8E3099511E0A0E0B1E0E2EAFFE502C06E
+:1005A00005900D92A63BB107D9F713E0A6EBB1E099
+:1005B00001C01D92A837B107E1F70E94F90E0C9413
+:1005C000CF2F0C9400000895089561110DC0FC0117
+:1005D0008281882331F085EE0E949D190E94B62BFE
+:1005E00003C085EE0E94651A80E090E008958B3B81
+:1005F000910568F4883A910530F5853A9105C0F483
+:100600008430910598F4019709F06FC071C0803E65
+:10061000910508F46AC0883E910540F09C01205F76
+:1006200031092031310508F060C05CC09C01A1C0D7
+:10063000853A910509F45FC0863A910509F45EC0D8
+:1006400023E830E496C0883A910509F45AC0893A03
+:10065000910509F459C08A3A910509F458C08B3ABA
+:10066000910509F457C08C3A910509F456C08D3AAA
+:10067000910509F455C0803B910509F454C08E3AA8
+:10068000910509F453C08F3A910509F452C0813B9A
+:10069000910509F451C0823B910509F450C0833B98
+:1006A000910509F44FC0843B910509F44EC0853B88
+:1006B000910509F44DC0863B910509F44CC0873B78
+:1006C000910509F44BC0883B910509F44AC0893B68
+:1006D000910509F449C08A3B910509F048C02AE216
+:1006E00036E447C09C01306544C020E030E041C0A2
+:1006F00021E030E03EC021E830E43BC022E830E4B5
+:1007000038C022EE34E435C029EE34E432C02AEE9B
+:1007100034E42FC025EB34E42CC026EB34E429C0AC
+:1007200027EB34E426C02CEC34E423C02DEC34E475
+:1007300020C023E835E41DC02AE835E41AC022E9C8
+:1007400035E417C024E935E414C021E236E411C0D1
+:1007500023E236E40EC024E236E40BC025E236E4A0
+:1007600008C026E236E405C027E236E402C020E0F5
+:1007700034E4C90108959CE0799FF001112490E3CD
+:10078000899FE00DF11D1124E60FF11DEE0FFF1FF3
+:10079000E65CFE4F25913491C9010895880F991F99
+:1007A00082559040FC0125913491C9010895880F2C
+:1007B000991F825D9E4FFC0125913491C9010895D6
+:1007C0000E94BB039C013A9521153F4108F4DFC00C
+:1007D0009C0130522115304120F49F700E94D703B4
+:1007E00008959C0130532115304118F49927906CDD
+:1007F00008959C0130542031310520F48F709927E1
+:10080000946D0895803120E4920719F480E091ED11
+:100810000895813140E4940719F480E090ED089543
+:10082000823120E4920719F480E092ED089583313B
+:1008300040E4940719F480E093ED0895811520E5D4
+:10084000920711F40C941F25813040E5940731F490
+:100850008091680281608093680208959C013056FF
+:100860002115304108F402C097FF02C0906F08952F
+:10087000803E9105E0F4803C910568F58133910557
+:1008800009F474C048F48932910509F46AC08A32C7
+:10089000910509F07AC074C089339105F9F0823866
+:1008A0009105E1F08533910509F06FC050C0833E9A
+:1008B0009105A9F140F4803E9105C9F0823E910571
+:1008C00009F063C01BC0863E910571F1873E91051A
+:1008D00009F05BC037C00E94CE03089520917B02CF
+:1008E00020FD02C021FF51C080EE90E04EC08091FB
+:1008F0007B0280FFF9CF89E390E047C080917B02C3
+:1009000082FF0AC080917B0284FF03C080E090E0F8
+:100910003CC083EE90E039C082EE90E036C080911A
+:100920007B0282FFEFCFF8CF80917B0283FF07C06D
+:1009300080917B0284FDEACF87EE90E026C086EEB0
+:1009400090E023C080917B0283FFF2CFF8CF8091AB
+:100950007B0285FF03C089E290E017C085E390E049
+:1009600014C080917B0285FDF9CFF5CF80917B0289
+:1009700086FF03C08AE290E008C081E390E005C0F2
+:1009800080917B0286FDF9CFF5CF0E94F702089592
+:100990005F926F927F928F929F92AF92BF92CF920F
+:1009A000DF92EF92FF920F931F93CF93DF93CDB718
+:1009B000DEB728970FB6F894DEBF0FBECDBF9E01FD
+:1009C0002F5F3F4F4E0189E0880E911C60E070E080
+:1009D00000E010E0E12CF12CC12CD12CA12CB12C89
+:1009E00088E0782E622E532E41E050E0E3E2F1E001
+:1009F000A62DB52D872D01900D928A95E1F7F9016D
+:100A0000819191919F01FC01E07FFF27E032F10588
+:100A100059F48F709927FA0102C0EE0FFF1F8A95D3
+:100A2000E2F7AE2ABF2A37C0E033F10559F48F70E0
+:100A30009927FA0102C0EE0FFF1F8A95E2F7CE2A2E
+:100A4000DF2A29C0E034F10559F48F709927FA01A3
+:100A500002C0EE0FFF1F8A95E2F7EE2AFF2A1BC0A5
+:100A6000E035F10559F48F709927FA0102C0EE0FB5
+:100A7000FF1F8A95E2F70E2B1F2B0DC0E036F10504
+:100A800051F48F709927FA0102C0EE0FFF1F8A956B
+:100A9000E2F76E2B7F2B2815390509F0A7CF94B10B
+:100AA0008A2D8095892384B985B18A2985B997B122
+:100AB0008C2D8095892387B988B18C2988B99AB102
+:100AC0008E2D809589238AB98BB18E298BB99DB1E2
+:100AD000802F809589238DB98EB1802B8EB990B3EC
+:100AE000862F8095892380BB81B3862B81BB289676
+:100AF0000FB6F894DEBF0FBECDBFDF91CF911F912F
+:100B00000F91FF90EF90DF90CF90BF90AF909F90AC
+:100B10008F907F906F905F9008955F926F927F9219
+:100B20008F929F92AF92BF92CF92DF92EF92FF92FD
+:100B30000F931F93CF93DF93CDB7DEB768970FB6B0
+:100B4000F894DEBF0FBECDBF85B7806885BF85B77F
+:100B5000806885BF0E94CF076E9A769A0E94C8046B
+:100B60009E012F5F3F4F4E0189E1880E911C60E08E
+:100B700070E000E010E0E12CF12CC12CD12CA12C74
+:100B8000B12C98E1792E622E532E41E050E0EBE239
+:100B9000F1E0A62DB52D872D01900D928A95E1F7F4
+:100BA000F901819191919F01FC01E07FFF27E032E3
+:100BB000F10559F48F709927FA0102C0EE0FFF1F5B
+:100BC0008A95E2F7AE2ABF2A37C0E033F10559F41F
+:100BD0008F709927FA0102C0EE0FFF1F8A95E2F786
+:100BE000CE2ADF2A29C0E034F10559F48F70992705
+:100BF000FA0102C0EE0FFF1F8A95E2F7EE2AFF2AE4
+:100C00001BC0E035F10559F48F709927FA0102C035
+:100C1000EE0FFF1F8A95E2F70E2B1F2B0DC0E0365B
+:100C2000F10551F48F709927FA0102C0EE0FFF1FF2
+:100C30008A95E2F76E2B7F2B2815390509F0A7CF8F
+:100C400094B18A2D8095892384B985B18A2985B983
+:100C500097B18C2D8095892387B988B18C2988B963
+:100C60009AB18E2D809589238AB98BB18E298BB943
+:100C70009DB1802F809589238DB98EB1802B8EB93F
+:100C800090B3862F8095892380BB81B3862B81BB4F
+:100C90001092B7011092B6011092BF011092BE01DE
+:100CA0001092B9011092B8011092C1011092C001C6
+:100CB0001092BB011092BA011092C3011092C201AE
+:100CC0001092BD011092BC011092C5011092C40196
+:100CD00068960FB6F894DEBF0FBECDBFDF91CF91FF
+:100CE0001F910F91FF90EF90DF90CF90BF90AF904A
+:100CF0009F908F907F906F905F9008955F926F921A
+:100D00007F928F929F92AF92BF92CF92DF92EF929B
+:100D1000FF920F931F93CF93DF93CDB7DEB7A097CA
+:100D20000FB6F894DEBF0FBECDBF7E0149E1E40EE1
+:100D3000F11C2EEBC22E21E0D22E5E0151E2A50E57
+:100D4000B11C38E0532E470101E010E048E1642E69
+:100D500055E0752EE3E2F1E0D401852D01900D926E
+:100D60008A95E1F7F701819191917F019C01207FA4
+:100D700033272032310589F424B18F709927A801D7
+:100D800002C0440F551F8A95E2F7CA01242B24B9EB
+:100D900095B18095892385B94FC02033310589F4F9
+:100DA00027B18F709927F80102C0EE0FFF1F8A95B7
+:100DB000E2F7CF012E2B27B998B18095892388B906
+:100DC0003BC02034310589F42AB18F709927A801DE
+:100DD00002C0440F551F8A95E2F7CA01242B2AB995
+:100DE0009BB1809589238BB927C02035310589F4C3
+:100DF0002DB18F709927F80102C0EE0FFF1F8A9561
+:100E0000E2F7CF012E2B2DB99EB1809589238EB9A3
+:100E100013C02036310581F420B38F709927A801C3
+:100E200002C0440F551F8A95E2F7CA01242B20BB4C
+:100E300091B38095892381BB50EA5A95F1F7BE01A1
+:100E40006F5F7F4F80E090E020E030E0EBE2F1E088
+:100E5000DE011196462D01900D924A95E1F7FB01B6
+:100E600041915191BF01FA01E07FFF27E032F10586
+:100E700011F4E3B113C0E033F10511F4E6B10EC093
+:100E8000E034F10511F4E9B109C0E035F10511F4E0
+:100E9000ECB104C0E036F105B9F4EFB1F0E04F7009
+:100EA000552702C0F595E7954A95E2F7E0FD08C0A1
+:100EB000A801022E02C0440F551F0A94E2F702C097
+:100EC00040E050E0842B952B2F5F3F4F2C303105B5
+:100ED00009F0BCCFF601208131812817390721F0B4
+:100EE00091838083709200010E94C804F2E0CF0ECB
+:100EF000D11CEA14FB0409F02DCF80910001882356
+:100F000061F1815080930001811121C08091BE0167
+:100F10009091BF019093B7018093B6018091C00179
+:100F20009091C1019093B9018093B8018091C20161
+:100F30009091C3019093BB018093BA018091C40149
+:100F40009091C5019093BD018093BC0106C08FE9CB
+:100F50009FE00197F1F700C0000081E0A0960FB676
+:100F6000F894DEBF0FBECDBFDF91CF911F910F91DF
+:100F7000FF90EF90DF90CF90BF90AF909F908F90B9
+:100F80007F906F905F900895E82FF0E0EE0FFF1FC5
+:100F9000EA54FE4F80819181089508950895279A1B
+:100FA0002F988FEF9FEF90938700809386008AE0C1
+:100FB0008093800089E1809381000C945F2B8111E4
+:100FC0000BC080918000877F8093800010928D00FD
+:100FD00010928C002F9808952F98833041F48091BF
+:100FE00080008860809380008FEF9FEF12C0909107
+:100FF000800098609093800023E030E0281B310946
+:10100000220F331F8FEF9FEF02C0969587952A9589
+:10101000E2F790938D0080938C0008950F931F93B7
+:10102000CF93DF93CDB7DEB7CC58D1090FB6F89484
+:10103000DEBF0FBECDBF8C01862F642F882379F0D1
+:10104000F80192812FE7482F992329F08DE792E04C
+:101050000E94F81404C08DE792E00E940815F80180
+:1010600080818B3061F49181933009F068C0828176
+:10107000882309F4CDC0809103018F5F0EC08A30B0
+:10108000E1F5F8019181933009F059C082818823FC
+:1010900009F4BEC08091030181508093030120E0D8
+:1010A0004BE760E08DE792E00E94E81420E04BE718
+:1010B00061E08DE792E00E94E81420E04BE762E0F7
+:1010C0008DE792E00E94E81420E04BE763E08DE7B3
+:1010D00092E00E94E81420E04BE764E08DE792E0A4
+:1010E000C457DF4F0FB6F894DEBF0FBECDBFDF9100
+:1010F000CF911F910F910C94E814893069F4F80195
+:1011000091819330E1F492819923C9F0809101019A
+:101110009091020101960EC0883089F4F801918106
+:10112000933069F49281992351F08091010190915B
+:10113000020101979093020180930101B0CFF80161
+:10114000928140910301992391F196E4E3E4F1E067
+:10115000DE01A95BBF4F01900D929A95E1F7405DCA
+:10116000F8019181FCE09F9F40191124E091010159
+:10117000F0910201E80FF11DEE0FFF1F87E490E0F0
+:101180008C0F9D1FE80FF91F8081480F2FE760E04B
+:101190008DE792E0C457DF4F0FB6F894DEBF0FBE65
+:1011A000CDBFDF91CF911F910F910C94F81496E46D
+:1011B000E3E4F1E0DE01119601900D929A95E1F7DA
+:1011C000405DF8019181FCE09F9F40191124E0915E
+:1011D0000101F0910201E80FF11DEE0FFF1F81E008
+:1011E00090E08C0F9D1FE80FF91F8081480F2FE7BB
+:1011F00060E08DE792E0C457DF4F0FB6F894DEBF92
+:101200000FBECDBFDF91CF911F910F910C940815A8
+:10121000C457DF4F0FB6F894DEBF0FBECDBFDF91CE
+:10122000CF911F910F910895CF93DF93EA019B0116
+:10123000AC0160E074E284E79BE40E945F2C0E94B2
+:10124000C72C709397006093960020E130E02C1B30
+:101250003D0B02C0759567952A95E2F7709399004A
+:1012600060939800DF91CF9108951092020210923E
+:10127000010210929000109291001092FD011092C4
+:10128000FE011092FF01109200021092FC011092D8
+:10129000FB01E9EDF1E0A9ECB1E01192119211929C
+:1012A00011921D921D9281E0E93FF807B1F7089570
+:1012B000AF92BF92CF92DF92EF92FF920F931F9364
+:1012C000CF93DF936B017C0109EF11E047EDA42E72
+:1012D00041E0B42EC7E0D0E0A7019601F801929159
+:1012E0008291729162918F010E945B2C882349F058
+:1012F0002197F2E0AF1AB108CF3F8FEFD80761F71F
+:1013000034C0F8011082118212821382F501118219
+:101310001082FE01EE0FFF1FEE0FFF1FE752FE4F80
+:10132000DE01AA0FBB1FA753BE4FCE011AC0019604
+:1013300044815581668177814083518362837383C1
+:10134000148215821682178212962D913C91139762
+:1013500011963C932E9313961C921E9212973496DC
+:1013600012968730910519F7C3CF809101029091B1
+:101370000202019797FD05C090930202809301023B
+:1013800004C01092020210920102E0910102F09159
+:101390000202309789F410929000109291001092FE
+:1013A000FD011092FE011092FF01109200021092B6
+:1013B000FC011092FB019EC03197DF01AA0FBB1FF9
+:1013C000AA0FBB1FA752BE4FCD90DD90ED90FC90B1
+:1013D000EE0FFF1FE753FE4FC081D181A090FD01AA
+:1013E000B090FE010091FF0110910002A70196014B
+:1013F0006A2D7B2D802F912F0E945B2C87FF2FC0A1
+:1014000081E08093C801AE016A2D7B2D802F912F42
+:101410000E9414092091FD013091FE014091FF01CD
+:1014200050910002C701B6010E94F62B20E030E087
+:101430004AEF53E40E945F2C9B01AC016A2D7B2D87
+:10144000802F912F0E94F72B5B018C01A701960141
+:101450007B2D912F0E945B2C1816ACF638C0A7018B
+:1014600096016A2D7B2D802F912F0E94AA2D181690
+:1014700084F581E08093C801AE016A2D7B2D802F19
+:10148000912F0E941409A70196016091FD017091AE
+:10149000FE018091FF01909100020E94F62B20E056
+:1014A00030E04AEF53E40E945F2C9B01AC016A2DAF
+:1014B0007B2D802F912F0E94F62B5B018C01A701C1
+:1014C00096017B2D912F0E94AA2D87FFD5CF1092D8
+:1014D000C801AE01C701B6010E941409C092FD0106
+:1014E000D092FE01E092FF01F0920002D093FC0145
+:1014F000C093FB01DF91CF911F910F91FF90EF906F
+:10150000DF90CF90BF90AF90089508951F920F92F3
+:101510000FB60F9211242F933F934F935F936F93C6
+:101520007F938F939F93AF93BF93EF93FF9380919C
+:10153000960090919700892B09F455C08091C801BD
+:10154000811151C08091F9019091FA01813091058A
+:1015500071F082309105C1F0892BC1F52091FD0118
+:101560003091FE014091FF01509100021DC0609139
+:10157000FD017091FE018091FF01909100029B019D
+:10158000AC010E94F72B0EC020E030E040E450E4B4
+:101590006091FD017091FE018091FF019091000228
+:1015A0000E94AE2D9B01AC0160E074E284E79BE4F5
+:1015B0000E945F2C0E94C72C709397006093960046
+:1015C0007595679570939900609398008091F901E3
+:1015D0009091FA01019663E070E00E948A2F909347
+:1015E000FA018093F901FF91EF91BF91AF919F9123
+:1015F0008F917F916F915F914F913F912F910F90BC
+:101600000FBE0F901F901895AF92BF92CF92DF92AE
+:10161000EF92FF920F931F93CF93DF936B017C01A7
+:10162000EA0120E030E0A9010E94AA2D18160CF072
+:10163000B4C03E9A82E8809390008AE18093910042
+:10164000A090FD01B090FE010091FF0110910002F9
+:1016500020E030E0A9016A2D7B2D802F912F0E9480
+:101660005B2C81112DC0AE01C701B6010E94140987
+:10167000C092FD01D092FE01E092FF01F0920002C3
+:10168000D093FC01C093FB01809101029091020272
+:10169000FC01EE0FFF1FEE0FFF1FE752FE4FC0824F
+:1016A000D182E282F382FC01EE0FFF1FE753FE4F6F
+:1016B000D183C083019690930202809301026DC092
+:1016C000A70196016A2D7B2D802F912F0E945B2C04
+:1016D00087FF2CC0AE016A2D7B2D802F912F0E9499
+:1016E00014092091FD013091FE014091FF015091BC
+:1016F0000002C701B6010E94F62B20E030E04AEF5D
+:1017000053E40E945F2C9B01AC016A2D7B2D802F3E
+:10171000912F0E94F72B5B018C01A70196017B2D75
+:10172000912F0E945B2C1816ACF69DCFA701960155
+:101730006A2D7B2D802F912F0E94AA2D18160CF058
+:1017400092CFAE016A2D7B2D802F912F0E9414091C
+:10175000A70196016091FD017091FE018091FF014A
+:10176000909100020E94F62B20E030E04AEF53E413
+:101770000E945F2C9B01AC016A2D7B2D802F912F45
+:101780000E94F62B5B018C01A70196017B2D912F06
+:101790000E94AA2D87FFD5CF66CFDF91CF911F91F1
+:1017A0000F91FF90EF90DF90CF90BF90AF90089592
+:1017B00080910C020895CF93DF9300D01F92CDB794
+:1017C000DEB720916E03243021F523E029839B832B
+:1017D0008A832093E9008FEF06C095ED9A95F1F783
+:1017E0000000882329F09091E800815095FFF5CF03
+:1017F0008091E80085FF0DC040E050E063E070E0BC
+:10180000CE0101960E94BA0F8091E8008E778093F6
+:10181000E8000F900F900F90DF91CF910895CF9334
+:10182000DF9300D01F92CDB7DEB720916E03243036
+:1018300029F522E029839B838A8383E08093E90052
+:101840008FEF06C095ED9A95F1F70000882329F0F7
+:101850009091E800815095FFF5CF8091E80085FFD9
+:101860000DC040E050E063E070E0CE0101960E94C0
+:10187000BA0F8091E8008E778093E8000F900F9068
+:101880000F90DF91CF91089520916E032430F9F4E9
+:1018900022E02093E9002FEF06C035ED3A95F1F7ED
+:1018A0000000222329F03091E800215035FFF5CFC8
+:1018B0002091E80025FF0BC040E050E065E070E0BB
+:1018C0000E94BA0F8091E8008E778093E800089517
+:1018D000CF93DF93EC0180916E03843041F581E07A
+:1018E0008093E9008FEF06C095ED9A95F1F700001F
+:1018F000882329F09091E800815095FFF5CF8091E1
+:10190000E80085FF14C040E050E068E070E0CE01E0
+:101910000E94BA0F8091E8008E778093E80088E0FB
+:10192000FE01A4E0B2E001900D928A95E1F7DF910B
+:10193000CF910895BF92CF92DF92EF92FF920F93D3
+:101940001F93CF93DF937C01B62EE90100E010E0F6
+:10195000C42ED12C0BC04991202F2B0D2F774F7700
+:101960006FE0C7010E94E8140F5F1F4F0C151D05A3
+:1019700094F3DF91CF911F910F91FF90EF90DF9043
+:10198000CF90BF90089570E06F5F7F4F6F707727A3
+:101990000C94E8140F931F93CF93C42F63307105F9
+:1019A00009F04AC0842F807F803849F1803909F0DE
+:1019B00043C0622F6F7770E080E090E00E94FA2CC5
+:1019C00020E030E040E451E40E945F2C9B01AC0138
+:1019D00060E070E080E090E40E94112E0F7710E04C
+:1019E00023E0159507952A95E1F72DEC3CEC42E0B4
+:1019F00053E40E94AE2DA8010E94040B1DC0622F6B
+:101A00006F7770E080E090E00E94FA2C20E030E0F8
+:101A100040E451E40E945F2C9B01AC0160E070E067
+:101A200080E090E40E94112E2DEC3CEC42E053E467
+:101A30000E94AE2D0E945809CC3F29F4CF911F91EE
+:101A40000F910C943509CF911F910F9108950F9329
+:101A50001F93CF93DF93CDB7DEB727970FB6F894D8
+:101A6000DEBF0FBECDBF8C0114C08A810E94C2149C
+:101A70009A819D839B819E839C819F8381111EC03F
+:101A800089818430B1F08730A1F08630A1F08530B3
+:101A9000A1F0BE016F5F7F4F84E091E00E942F189C
+:101AA0008111E3CF84E091E00E9420180E949B14F2
+:101AB0000DC083E003C082E001C081E0AE014B5F56
+:101AC0005F4F682FC8010E945515E3CF27960FB6C8
+:101AD000F894DEBF0FBECDBFDF91CF911F910F9164
+:101AE0000895EF92FF920F93CF93DF9300D000D031
+:101AF00000D0CDB7DEB77B014A832B830C83842FC4
+:101B00002E834D830E94C2142E814D8181111BC0F2
+:101B100082E0E816F10479F083E0E816F10421F0A0
+:101B2000EA94EF2821F50BC0073F11F487E001C0CC
+:101B300084E089830BC0273FD9F786E0FACF473F7F
+:101B4000B9F785E0F6CF42954F704983BE016F5FCC
+:101B50007F4F84E091E00E94E51784E091E00E94CD
+:101B6000031884E091E00E9420180E949B1426969E
+:101B70000FB6F894DEBF0FBECDBFDF91CF910F91AE
+:101B8000FF90EF90089580916D03811109C00E942C
+:101B9000A1110E94FE118091E20084608093E20016
+:101BA000089510926D03089508950C94E4020C9426
+:101BB000892480916E03843049F58091E9008F700B
+:101BC0009091EC0090FF02C090E801C090E0982B4B
+:101BD00084E08093E9008091EB0080FF14C0809145
+:101BE000EE0087FD03C00FC01092F1008091E80065
+:101BF00085FDFACF8091E80080FF05C08091E80064
+:101C00008E778093E8009F709093E900089542E0FA
+:101C100061EC81E00E94171142E061EC82E00E94D9
+:101C2000171142E061EC83E00E94171146E261EC7B
+:101C300084E00E94171142E361E885E00E941711D9
+:101C400042E360E886E00C941711809170038330C2
+:101C500009F454C030F4813071F0823009F0AAC028
+:101C600091C08A3009F47EC08B3009F45FC089309E
+:101C700009F0A0C020C080916F03813A09F09AC09A
+:101C80008091E800877F8093E800809173039091B2
+:101C90007403892B21F060E080E090E003C068E0ED
+:101CA00084E092E070E00E9458108091E8008B7709
+:101CB0008093E800089580916F03813209F07AC023
+:101CC0008091730390917403892B09F073C0809104
+:101CD000E800877F8093E80005C080916E03882329
+:101CE00009F468C08091E80082FFF7CF8091F1008D
+:101CF00080930C028091E8008B7758C080916F032D
+:101D0000813A09F057C08091730390917403892B35
+:101D100009F050C08091E800877F8093E8008091AF
+:101D2000E80080FFFCCF80911A013BC080916F03D7
+:101D3000813209F03FC08091730390917403892B25
+:101D4000C9F58091E800877F8093E8000E944E11DA
+:101D50009091710381E0911101C080E080931A019C
+:101D60000C948C1E80916F03813221F58091E800E4
+:101D7000877F8093E8000E944E11809172038093C8
+:101D80000302089580916F03813AA1F48091E800E5
+:101D9000877F8093E8008091E80080FFFCCF8091EE
+:101DA00003028093F1008091E8008E778093E80031
+:101DB0000C944E11089584B7877F84BF88E10FB6D5
+:101DC000F89480936000109260000FBE90E080E86D
+:101DD0000FB6F89480936100909361000FBE0E944B
+:101DE000A1110E94FE11E2EEF0E080818460808308
+:101DF00008958DE792E00E94241561E77DE08DE76C
+:101E000092E00E947A1567E27DE08DE792E00E9401
+:101E10007E150E94DB0E78946AEC7CE08DE792E000
+:101E20000E94201563EC7CE08DE792E00E9418157B
+:101E30006AE97CE08DE792E00E941C150E94850A09
+:101E40000E949B140E94AC1880E191E00E945418FB
+:101E50000BC00E944E2480916C03882329F00E94BD
+:101E6000742481110E94A40F80916E03853089F340
+:101E70008DE792E00E942D170E94B618F5CF292F0A
+:101E8000332723303105B1F04CF42130310509F40A
+:101E90004DC02230310509F04EC007C02132310556
+:101EA00041F12232310591F146C0E0EDF0E086E7E4
+:101EB00093E045C099278130910569F08230910502
+:101EC00089F0892B09F037C0E2E7F3E0E491F0E014
+:101ED00082E793E034C0E4E4F3E0E491F0E084E4EA
+:101EE00093E02DC0EAE1F3E0E491F0E08AE193E0D1
+:101EF00026C0643000F5E62FF0E0EE0FFF1FE75735
+:101F0000FE4F80819181E9E0F0E019C0643098F4DF
+:101F1000E62FF0E0DF01AA0FBB1FAF56BE4F8D9139
+:101F20009C91E756FE4FE081F0E009C0E2E1F0E06D
+:101F300086E494E004C0E0E0F0E080E090E0DA01C4
+:101F40008D939C93CF01089580E189BD82E189BD85
+:101F500009B400FEFDCF8091D8008F7D8093D8001A
+:101F60008091E00082608093E0008091E00081FD3C
+:101F7000FCCF0895BF92CF92DF92EF92FF920F9322
+:101F80001F93CF93DF937C018B01EA010E946F11B5
+:101F9000B82E811133C0209731F028813981021B7E
+:101FA000130BE20EF31EC12CD12C23C08091E8004C
+:101FB00085FD15C08091E8008E778093E80020971A
+:101FC00049F0888199818C0D9D1D9983888325E036
+:101FD000B22E14C00E946F11882359F00EC0F70171
+:101FE00081917F018093F10001501109FFEFCF1A19
+:101FF000DF0A01151105D1F601C0B82E8B2DDF9136
+:10200000CF911F910F91FF90EF90DF90CF90BF90F5
+:102010000895BF92CF92DF92EF92FF920F931F939A
+:10202000CF93DF937C018B01EA010E946F11B82EE0
+:10203000811133C0209731F028813981021B130BA5
+:10204000E20EF31EC12CD12C23C08091E80085FD47
+:1020500015C08091E8008B778093E800209749F0C5
+:10206000888199818C0D9D1D9983888345E0B42ECC
+:1020700014C00E946F11882359F00EC08091F100A6
+:10208000F70181937F0101501109FFEFCF1ADF0A99
+:1020900001151105D1F601C0B82E8B2DDF91CF911E
+:1020A0001F910F91FF90EF90DF90CF90BF90089518
+:1020B00040917503509176034617570748F0611514
+:1020C000710539F44091E8004E774093E80001C073
+:1020D000BA01FC0140E033C080916E03882309F40B
+:1020E00042C0853009F441C08091E80083FD39C0C9
+:1020F0008091E80082FD2FC08091E80080FF1FC022
+:102100009091F3008091F200392F20E0A901482B33
+:10211000CA0106C041914093F100615071090196D6
+:102120006115710519F088309105A0F341E0089719
+:1021300009F040E08091E8008E778093E800611517
+:10214000710551F64111C8CF06C080916E038823F6
+:1021500051F0853051F08091E80082FFF6CF80E0A9
+:10216000089581E0089582E0089583E00895409104
+:102170007503509176034617570748F061157105AE
+:1021800039F44091E8004E774093E80001C0BA016D
+:10219000FC0140E034C080916E03882309F443C001
+:1021A000853009F442C08091E80083FD3AC08091F7
+:1021B000E80082FD30C08091E80080FF20C090914F
+:1021C000F3008091F200392F20E0A901482BCA01C9
+:1021D00007C044914093F100319661507109019616
+:1021E0006115710519F08830910598F341E0089761
+:1021F00009F040E08091E8008E778093E800611557
+:10220000710549F64111C7CF06C080916E0388233E
+:1022100051F0853051F08091E80082FFF6CF80E0E8
+:10222000089581E0089582E0089583E00895982F4D
+:102230002CC09093E900981739F07091EC00209130
+:10224000ED005091F00003C0242F762F50E021FDC7
+:1022500002C09F5F1AC03091EB003E7F3093EB00CD
+:102260003091ED003D7F3093ED003091EB00316017
+:102270003093EB007093EC002093ED005093F0004E
+:102280002091EE0027FDE5CF07C0973090F28F70C8
+:102290008093E90081E0089580E0089580916F03C4
+:1022A00087FD05C08091E80080FF0EC012C08091BC
+:1022B000E80082FD05C080916E038111F8CF08957A
+:1022C0008091E8008B7708C080916E038111EACF7E
+:1022D00008958091E8008E778093E80008958091BA
+:1022E000E4009091E50045E62091EC0020FD1FC040
+:1022F00023C020916E03222391F0253091F020918C
+:10230000EB0025FD10C02091E4003091E500281776
+:10231000390751F34150C90139F784E0089582E04B
+:10232000089583E0089581E0089580E00895209164
+:10233000E80020FFDECFF9CF2091E80022FFD9CFBF
+:10234000F4CF0E940F120E941712E0EEF0E080819D
+:1023500081608083E8EDF0E080818F77808319BC15
+:10236000A7EDB0E08C918E7F8C9380818F7E8083EF
+:1023700010926D0308950F931F93CF93DF930E94E4
+:102380000F120E941712C8EDD0E088818F778883E2
+:1023900088818068888388818F7D888319BC1092AA
+:1023A0006E0310926A0310926C0310926B0300EE9E
+:1023B00010E0F80180818B7F808388818160888331
+:1023C00042E060E080E00E941711E1EEF0E08081E1
+:1023D0008E7F8083E2EEF0E0808181608083808167
+:1023E00088608083F80180818E7F8083888180610E
+:1023F0008883DF91CF911F910F910895E8EDF0E070
+:1024000080818F7E8083E7EDF0E080818160808332
+:1024100084E082BF81E080936D030C94BB11E8EDF2
+:10242000F0E080818E7F80831092E2000895109208
+:10243000DA001092E10008951F920F920FB60F92EA
+:1024400011242F933F934F935F936F937F938F93B9
+:102450009F93AF93BF93EF93FF938091E10082FF2F
+:102460000BC08091E20082FF07C08091E1008B7F6A
+:102470008093E1000E94D90D8091DA0080FF1FC097
+:102480008091D80080FF1BC08091DA008E7F8093FE
+:10249000DA008091D90080FF0DC080E189BD82E122
+:1024A00089BD09B400FEFDCF81E080936E030E94D8
+:1024B000C30D05C019BC10926E030E94D10D80910E
+:1024C000E10080FF19C08091E20080FF15C080917B
+:1024D000E2008E7F8093E2008091E2008061809331
+:1024E000E2008091D80080628093D80019BC85E01A
+:1024F00080936E030E94D50D8091E10084FF30C06F
+:102500008091E20084FF2CC080E189BD82E189BD19
+:1025100009B400FEFDCF8091D8008F7D8093D80054
+:102520008091E1008F7E8093E1008091E2008F7EB8
+:102530008093E2008091E20081608093E2008091CC
+:102540006A03882311F084E007C08091E30087FFCD
+:1025500002C083E001C081E080936E030E94D70D2A
+:102560008091E10083FF29C08091E20083FF25C0B4
+:102570008091E100877F8093E10082E080936E0389
+:1025800010926A038091E1008E7F8093E100809138
+:10259000E2008E7F8093E2008091E2008061809370
+:1025A000E20042E060E080E00E9417118091F000BC
+:1025B00088608093F0000E94D40DFF91EF91BF914D
+:1025C000AF919F918F917F916F915F914F913F91CB
+:1025D0002F910F900FBE0F901F9018951F920F9282
+:1025E0000FB60F9211242F933F934F935F936F93E6
+:1025F0007F938F939F93AF93BF93CF93EF93FF936B
+:102600008091E9008F709091EC0090FF02C090E8FB
+:1026100001C090E0C92FC82B1092E9008091F00012
+:10262000877F8093F00078940E9432131092E90023
+:102630008091F00088608093F000CF70C093E90033
+:10264000FF91EF91CF91BF91AF919F918F917F912A
+:102650006F915F914F913F912F910F900FBE0F900F
+:102660001F9018951F93CF93DF93CDB7DEB7AC972C
+:102670000FB6F894DEBF0FBECDBFEFE6F3E080915A
+:10268000F100819323E0E737F207C9F70E94250E96
+:102690008091E80083FF37C180916F0390917003B0
+:1026A000953009F488C038F49130B1F170F093306E
+:1026B00009F029C131C0983009F4F8C0993009F403
+:1026C00004C1963009F01FC19DC0803821F08238C6
+:1026D00009F019C108C080916B0390916C03992394
+:1026E00089F082600FC080917303909174038F70A2
+:1026F00099278093E9008091EB0085FB882780F97A
+:102700001092E9009091E800977F9093E800809301
+:10271000F1001092F100D5C0882319F0823009F041
+:10272000F2C08F7121F0823009F0EDC00BC08091B2
+:102730007103813009F0E7C0933009F080E08093A5
+:102740006C032FC08091710381112BC080917303A2
+:10275000909174038F709927009709F4D4C08093E7
+:10276000E9002091EB0020FF1CC020917003233072
+:1027700021F48091EB00806212C09091EB00906197
+:102780009093EB0021E030E001C0220F8A95EAF738
+:102790002093EA001092EA008091EB008860809319
+:1027A000EB001092E9008091E800877F8093E800B9
+:1027B0000E944E11A8C08111A6C080917103909112
+:1027C00072038F779927182F9091E3009078982BB8
+:1027D0009093E3008091E800877F8093E8000E9457
+:1027E0004E118091E80080FFFCCF8091E30080686B
+:1027F0008093E300112311F083E001C082E0809315
+:102800006E0381C08058823008F07DC080917103D2
+:10281000909172038C3D23E0920779F583E08A83DF
+:102820008AE289834FB7F894DE01139620E03EE0F8
+:1028300051E2E32FF0E050935700E49120FF03C0F2
+:10284000E295EF703F5FEF708E2F90E0EA3010F06E
+:10285000C79601C0C0968D939D932F5F243149F791
+:102860004FBF8091E800877F8093E8006AE270E0C4
+:10287000CE0101960E94581013C0AE01455D5F4F16
+:10288000609173030E943F0F0097E9F12091E800E7
+:10289000277F2093E800BC018BA59CA50E94B71060
+:1028A0008091E8008B778093E8002DC0803859F53F
+:1028B0008091E800877F8093E80080916A0380938D
+:1028C000F1008091E8008E7771CF81111CC090914A
+:1028D00071039230C0F48091E800877F8093E80014
+:1028E00090936A030E944E1180916A03811104C083
+:1028F0008091E30087FF02C084E001C081E0809303
+:102900006E030E94070E8091E80083FF0AC0809149
+:10291000E800877F8093E8008091EB0080628093DD
+:10292000EB00AC960FB6F894DEBF0FBECDBFDF91C3
+:10293000CF911F910895CF9380916E038823B1F0BA
+:102940008091E9008F709091EC0090FF02C090E8B8
+:1029500001C090E0C92FC82B1092E9008091E800D7
+:1029600083FD0E943213CF70C093E900CF91089588
+:10297000881F8827881F089591E0883F08F490E019
+:10298000892F0895982F907F903B99F038F49039D3
+:1029900081F0903A71F09038C9F40BC0903DA1F0ED
+:1029A00018F4903C99F410C0903E19F0903F71F4E7
+:1029B00002C083E00895E82FE15FEF3038F4F0E0E3
+:1029C000E356FE4F8081089582E0089580E00895E7
+:1029D0000F932F774F776F70606BDC01ED91FC9157
+:1029E000022F242F462F63E070E009950F91089580
+:1029F0000F932F774F776F706069DC01ED91FC9139
+:102A0000022F242F462F63E070E009950F9108955F
+:102A10000F932F774F776F706068DC01ED91FC9119
+:102A2000022F242F462F63E070E009950F9108953F
+:102A3000FC01738362830895FC01738F628F089594
+:102A4000FC01758F648F0895CF93DF93EC011DA275
+:102A50001FA21EA2BC01685D7F4F40EC88519F4FB2
+:102A60000E9461171B821A821D821C821F821E8295
+:102A7000198618861B861A861D861C861F861E864A
+:102A8000198A188A1B8A1A8A1D8A1C8A1F8A1E8A1A
+:102A9000198E188E1B8E1A8E1D8E1C8E1F8E1E8EEA
+:102AA00019A218A2DF91CF910895CF92DF92FF92E1
+:102AB0000F931F93CF93DF931F92CDB7DEB7F62E00
+:102AC0006A018C0108511F4F08C0F60161916F0126
+:102AD000C80149830E94681749818C2D841B8F157A
+:102AE000A0F30F90DF91CF911F910F91FF90DF9096
+:102AF000CF900895FC01718360830895FC0171A358
+:102B000060A30895AF92BF92CF92DF92EF92FF92AF
+:102B10000F931F93CF93DF9300D01F92CDB7DEB7F3
+:102B20007C016B01142FB22EA02EDC0195968C91A6
+:102B300095978430F1F45A96ED91FC915B9730971C
+:102B400009F4D8C0CB01019763E070E00E94762FB2
+:102B5000DB01AA0FBB1FA60FB71F49832A830B8374
+:102B60004C2D4A1B9E012F5F3F4FBD01C7010995A8
+:102B7000B1C06230710509F453C06330710529F0AA
+:102B80006130710509F09CC083C0842F807F803A3A
+:102B900001F130F48038B9F0803909F0ABC00DC0D4
+:102BA000803EE9F0803F09F1803B09F0A3C0D701E6
+:102BB0001296ED91FC91139723C0D7011496ED91D5
+:102BC000FC9115971DC0D7011696ED91FC911797B2
+:102BD00017C0D7011896ED91FC91199711C0D70134
+:102BE0001A96ED91FC911B970BC0423F09F082C0F1
+:102BF000D7011C96ED91FC911D97309731F47AC066
+:102C0000309709F477C0123F21F42A2D4B2D62EF43
+:102C100004C0612F6F702A2D4B2DC70109955AC032
+:102C2000842F807F803D59F0803F79F0803C09F00F
+:102C300061C0D7011E96ED91FC911F9719C0D70175
+:102C40005096ED91FC91519713C0433F31F4D70159
+:102C50005296ED91FC91539708C0413F09F04AC04C
+:102C6000D7015496ED91FC915597309741F442C0AD
+:102C7000309709F43FC0133F11F0113F19F44B2D69
+:102C8000612F03C0612F6F704B2DC701099522C0C2
+:102C9000842F0E94BC14882331F0D7015696ED9101
+:102CA000FC91579707C0163F29F5D7015896ED912B
+:102CB000FC9159973097F1F0612FC70109950AC02F
+:102CC00064307105A8F416C00A2D2B2D412FB601D2
+:102CD000C7010995D7015E96ED91FC915F973097FA
+:102CE00089F00A2D2B2D412FB601C70109950AC085
+:102CF000C12CD12CD7015C96ED91FC915D9730975A
+:102D000019F7E8CF0F900F900F90DF91CF911F919F
+:102D10000F91FF90EF90DF90CF90BF90AF9008950C
+:102D2000EF92FF920F931F93CF93DF93EC01162F37
+:102D3000862F0E94BC14882369F0FDA081E08DA33A
+:102D400000E020E0412F61E070E0CE010E9482159A
+:102D5000FDA27CC0812F0E94B8144DA1882309F4E4
+:102D600040C0443029F01AA321E030E03FA32EA355
+:102D7000812F0E94C214813031F070F0823051F006
+:102D8000833059F507C08DA300E020E0412F61E0BA
+:102D900070E01EC08DA35AC0103F19F0173FE9F430
+:102DA00004C084E08DA31AA33FC02EA13FA1C90196
+:102DB00063E070E00E94762F8C0F9D1FFC0112A330
+:102DC000B9016F5F7F4F7FA36EA30CA12BA14AA116
+:102DD000CE010E9482151DA239C01DA21FA21EA2F3
+:102DE00035C0442399F12EA13FA1C90163E070E0F1
+:102DF0000E94762F7C01FE01E80FF91F12A3B90192
+:102E00006F5F7F4F7FA36EA38130910591F082E0C9
+:102E1000E816F104D9F40CA12BA14AA1CE010E941D
+:102E200082158DA1843091F081E090E09FA38EA364
+:102E30000DC0423059F400E02BA14AA1CE010E94FE
+:102E400082158DA1843011F0FFA2EEA2DF91CF9107
+:102E50001F910F91FF90EF900895CF92DF92EF9224
+:102E6000FF920F931F93CF93DF93EC01E8A1F9A199
+:102E7000309709F009958E0108511F4FC8010E9433
+:102E80009A17E12CF12CC82ED12C0FC060E0C8019C
+:102E90000E94AE17682FCE010E94901661E0C80113
+:102EA0000E94BF178FEFE81AF80AEC14FD0470F3C4
+:102EB000DF91CF911F910F91FF90EF90DF90CF9016
+:102EC0000895FC0142837483638311821082089504
+:102ED0000F931F93CF93DF93EC01062F0E94E0170F
+:102EE000182F298130E0C90101966A8170E00E94A3
+:102EF0008A2F488150E08417950729F4812F0E947A
+:102F0000E31780E012C0EB81FC81E20FF31F008326
+:102F10002981822F90E001966A8170E00E948A2FB9
+:102F20008983812F0E94E31781E0DF91CF911F9168
+:102F30000F910895CF93DF93EC010E94E017298150
+:102F40009881291710F0C22F02C0CA81C20FC91B75
+:102F50000E94E3178C2FDF91CF910895FC0120810F
+:102F6000862F90E0820F911D628170E00E948A2F6F
+:102F70000380F481E02DE80FF91F808108950F93FD
+:102F80001F93CF93DF931F92CDB7DEB78C01698378
+:102F90000E94E017482FF80180816981262F30E0D8
+:102FA000280F311D6281C90170E00E948A2F808341
+:102FB000842F0F90DF91CF911F910F910C94E31705
+:102FC0008FB7F89408958FBF0895FC01CB0120912D
+:102FD0006E032430B1F421812F702093E90040E08A
+:102FE00050E064E070E00E94BA0F81110BC0909134
+:102FF000E80095FD07C09091E8009E779093E80067
+:10300000089582E0089520916E032430A9F4FC0114
+:1030100081818F708093E9003091F3002091F2005C
+:10302000932F80E0822B892B49F08091E8008E77E6
+:103030008093E8000C946F1182E0089580E0089579
+:1030400020916E03243051F4FC0121812F702093D4
+:10305000E9002091E80020FD0C9403180895FC017C
+:10306000CB0120916E03243011F080E00895268179
+:103070002F702093E9002091E80022FFF6CF2091E5
+:10308000E80025FFF2CF40E050E064E070E00E94ED
+:1030900009108091E80085FD05C08091E8008B77DC
+:1030A0008093E80081E0089590930F0280930E02D0
+:1030B000089580910E0290910F020895E0910E0202
+:1030C000F0910F02309721F00190F081E02D0994EA
+:1030D00080E00895E0910E02F0910F02309721F008
+:1030E0000280F381E02D09940895E0910E02F091A1
+:1030F0000F02309721F00480F581E02D09940895A6
+:1031000020911002309111028217930771F0909371
+:10311000110280931002E0910E02F0910F0230979D
+:1031200021F00680F781E02D099408952091120284
+:10313000309113028217930771F0909313028093DA
+:103140001202E0910E02F0910F02309721F00084FC
+:10315000F185E02D099408950E94B6240E948D0502
+:103160000E948A250C945F2B0C94CE075F926F927D
+:103170007F928F929F92AF92BF92CF92DF92EF9207
+:10318000FF920F931F93CF93DF93CDB7DEB72A97AC
+:103190000FB6F894DEBF0FBECDBF0E947E0694E14D
+:1031A000C92E92E0D92E00E010E0AA24A394B12CFD
+:1031B000502E802F0E94C4073C01F601E190F1904F
+:1031C0006F01E826F926E114F10431F40F5F1F4F77
+:1031D0000430110569F73AC08091680281FD0E94B0
+:1031E000CD0720E030E04501022E02C0880C991C7A
+:1031F0000A94E2F7C4018E219F21892B09F12E83C5
+:103200005F826820792081E0672809F480E0888760
+:103210000E94BF248160782F9A8789874E815F81C1
+:1032200068858A850E946F19F801EE0FFF1FEC5E1A
+:10323000FD4F80819181882599259183808316C0D7
+:103240002F5F3F4F2C30310571F6C0CF8FEF898350
+:103250008A831B820E94BF248160782F9D838C8388
+:1032600049815A816B818D810E946F190E94772854
+:1032700010911C020E945E181817D9F00E945E1867
+:1032800080931C022A960FB6F894DEBF0FBECDBF06
+:10329000DF91CF911F910F91FF90EF90DF90CF9032
+:1032A000BF90AF909F908F907F906F905F900C94A5
+:1032B000B4182A960FB6F894DEBF0FBECDBFDF91CB
+:1032C000CF911F910F91FF90EF90DF90CF90BF9023
+:1032D000AF909F908F907F906F905F900895CF9365
+:1032E000DF93CDB7DEB72B970FB6F894DEBF0FBED6
+:1032F000CDBF4F83588769877A878B87DE01119608
+:1033000086E0FD0111928A95E9F785E0FE01379686
+:1033100001900D928A95E1F749815A816B817C81F8
+:103320008D819E810E9447212B960FB6F894DEBFB7
+:103330000FBECDBFDF91CF910895CF93C82F8823C3
+:1033400009F4C1C0823859F40E945E1881FDBBC0E7
+:1033500089E30E94AC230E94282489E30CC08338AF
+:1033600079F40E945E1880FDAEC083E50E94AC2314
+:103370000E94282483E50E94CE23CF910C94282418
+:10338000843859F40E945E1882FD9DC087E40E9433
+:10339000AC230E94282487E4EECF8450813A48F47D
+:1033A0008C2F0E94C72A81118EC08C2F0E94AC23C3
+:1033B000E4CF8C2F805E883050F4C77081E090E0BD
+:1033C00001C0880FCA95EAF70E94EF23D6CF8C2F51
+:1033D000855A833078F4C53A29F0C63A31F482E848
+:1033E00090E005C081E890E002C083E890E0CF91D2
+:1033F0000C9480188C2F885A833108F064C0C83A26
+:1034000039F1C93A41F1CA3A49F1CB3A51F1CC3AD2
+:1034100059F1CD3A61F1C03B69F1CE3A71F1CF3A41
+:1034200079F1C13B81F1C23B89F1C33B91F1C43BCE
+:1034300099F1C53BA1F1C63BA9F1C73BB1F1C83B2E
+:10344000B9F1C93BC1F1CA3BC9F58AE292E038C083
+:1034500082EE90E035C089EE90E032C08AEE90E0D6
+:103460002FC085EB90E02CC086EB90E029C087EB65
+:1034700090E026C08CEC90E023C08DEC90E020C062
+:1034800083E891E01DC08AE891E01AC082E991E0EA
+:1034900017C084E991E014C081E292E011C083E298
+:1034A00092E00EC084E292E00BC085E292E008C098
+:1034B00086E292E005C087E292E002C080E090E000
+:1034C000CF910C949618CF910895882309F44DC09C
+:1034D000823859F40E945E1881FF47C089E30E9438
+:1034E000AC230E94282489E30CC0833871F40E9425
+:1034F0005E1880FF3AC083E50E94AC230E94282416
+:1035000083E50E94CE230C942824843859F40E9429
+:103510005E1882FF2AC087E40E94AC230E94282400
+:1035200087E4EFCF982F9450913A08F4EACF982F80
+:10353000905E983058F4282F277081E090E001C009
+:10354000880F2A95EAF70E94F523DDCF982F955A28
+:10355000933020F480E090E00C948018885A8331F6
+:1035600020F480E090E00C9496180895882321F0D0
+:103570000E94EF230C9428240895882321F00E94B0
+:10358000F5230C9428240895BF92CF92DF92EF92F6
+:10359000FF920F931F93CF93DF93CDB7DEB727979B
+:1035A0000FB6F894DEBF0FBECDBF8C0185E0F801E9
+:1035B000DE01119601900D928A95E1F7F8013081B4
+:1035C0002181F280558152955F7083819481892B8E
+:1035D00039F02F3F41F481E090E03F3F31F003C0EC
+:1035E00081E090E002C080E090E080FD73C3398309
+:1035F0002A8389819A815E830E946923B92E8F83F1
+:103600000E9468230E9490222B2D22952F7030E07B
+:103610005E816F812530310509F4E6C06CF42430F9
+:1036200031050CF0A2C04B2D407F8B2D8F702230C6
+:1036300031050CF045C017C02C3031054CF42A3050
+:1036400031050CF0E7C12830310509F043C3E5C06E
+:103650002D30310509F4BAC20CF4A2C22F30310565
+:1036600009F038C323C3182F411101C002C01295BD
+:10367000107FFF2059F0112309F46BC2812F6F8353
+:103680000E94FF230E9428246F8163C2862F0E941C
+:10369000651A112309F41EC3812F0E940524279661
+:1036A0000FB6F894DEBF0FBECDBFDF91CF911F9153
+:1036B0000F91FF90EF90DF90CF90BF900C94282453
+:1036C000403211F08295807F662319F0613071F5E8
+:1036D00023C0FF20B1F0511101C032C0513081F53B
+:1036E00027960FB6F894DEBF0FBECDBFDF91CF9106
+:1036F0001F910F91FF90EF90DF90CF90BF900C94AF
+:103700000F24511101C003C0513009F4E3C28E836C
+:103710000E9412248E819AC1FF2021F0563008F0B9
+:10372000D9C20EC0553008F0D5C290C1FF20C9F0F3
+:10373000552331F0F801958190FF0BC29F7095835E
+:1037400027960FB6F894DEBF0FBECDBFDF91CF91A5
+:103750001F910F91FF90EF90DF90CF90BF900C944E
+:10376000B61A552309F472C109C22B2D2695269548
+:10377000237030E02115310529F02130310509F0A1
+:10378000A9C219C0FF2021F0862F9B2D937002C083
+:1037900080E090E027960FB6F894DEBF0FBECDBF55
+:1037A000DF91CF911F910F91FF90EF90DF90CF901D
+:1037B000BF900C948018FF2021F0862F9B2D9370D2
+:1037C00002C080E090E027960FB6F894DEBF0FBEEF
+:1037D000CDBFDF91CF911F910F91FF90EF90DF90C0
+:1037E000CF90BF900C949618862FFF2019F00E945E
+:1037F0007D2702C00E94E52727960FB6F894DEBF0A
+:103800000FBECDBFDF91CF911F910F91FF90EF9031
+:10381000DF90CF90BF900C946C288B2D837009F0B3
+:1038200079C0F11057C2262F229526952770220FB6
+:10383000220F862F8F70C82ED12CE12CF12C022E56
+:1038400004C0CC0CDD1CEE1CFF1C0A94D2F764FFF4
+:1038500010C06FE070E080E090E004C0660F771F5A
+:10386000881F991F2A95D2F760957095809590953D
+:1038700003C060E070E0CB012B2D269526952370C8
+:10388000422F50E042305105D9F04330510569F1E3
+:103890006C297D298E299F294130510551F12796A8
+:1038A0000FB6F894DEBF0FBECDBFDF91CF911F9151
+:1038B0000F91FF90EF90DF90CF90BF900C94A522D6
+:1038C0006C297D298E299F2927960FB6F894DEBF93
+:1038D0000FBECDBFDF91CF911F910F91FF90EF9061
+:1038E000DF90CF90BF900C94B7220E94A522C70111
+:1038F000B60127960FB6F894DEBF0FBECDBFDF919D
+:10390000CF911F910F91FF90EF90DF90CF90BF90DC
+:103910000C949322FF2019F08B2D817001C08695A5
+:10392000882309F4D7C1262F229526952770220FC8
+:10393000220F862F8F70C82ED12CE12CF12C022E55
+:1039400004C0CC0CDD1CEE1CFF1C0A94D2F764FFF3
+:1039500010C06FE070E080E090E004C0660F771F59
+:10396000881F991F2A95D2F760957095809590953C
+:1039700003C060E070E0CB012B2D269526952370C7
+:10398000422F50E042305105D9F04330510569F1E2
+:103990006C297D298E299F294130510551F12796A7
+:1039A0000FB6F894DEBF0FBECDBFDF91CF911F9150
+:1039B0000F91FF90EF90DF90CF90BF900C94442335
+:1039C0006C297D298E299F2927960FB6F894DEBF92
+:1039D0000FBECDBFDF91CF911F910F91FF90EF9060
+:1039E000DF90CF90BF900C9456230E944423C701D0
+:1039F000B60127960FB6F894DEBF0FBECDBFDF919C
+:103A0000CF911F910F91FF90EF90DF90CF90BF90DB
+:103A10000C943223603F59F120F4603E08F494C0C6
+:103A200008C0623F09F467C0F0F1633F09F08CC041
+:103A300065C0162F1F708B2D8F71FF2021F00E9403
+:103A4000DD22812F7DCE0E94F822812F27960FB68E
+:103A5000F894DEBF0FBECDBFDF91CF911F910F91C4
+:103A6000FF90EF90DF90CF90BF900C94BD1AFF2095
+:103A7000B1F0553008F02EC18B2D8F7127960FB6FF
+:103A8000F894DEBF0FBECDBFDF91CF911F910F9194
+:103A9000FF90EF90DF90CF90BF900C94172356309B
+:103AA00008F018C1E9CFFF2099F08B2D8F71279670
+:103AB0000FB6F894DEBF0FBECDBFDF91CF911F913F
+:103AC0000F91FF90EF90DF90CF90BF900C94DD228C
+:103AD0008B2D8F7127960FB6F894DEBF0FBECDBF2A
+:103AE000DF91CF911F910F91FF90EF90DF90CF90DA
+:103AF000BF900C94F822F110EBCFD7CFFF2099F0B4
+:103B00008B2D8F7127960FB6F894DEBF0FBECDBFF9
+:103B1000DF91CF911F910F91FF90EF90DF90CF90A9
+:103B2000BF900C94CE2227960FB6F894DEBF0FBE3E
+:103B3000CDBFDF91CF911F910F91FF90EF90DF905C
+:103B4000CF90BF900C94C922FF20A9F0552309F40F
+:103B5000ACCF862F27960FB6F894DEBF0FBECDBF31
+:103B6000DF91CF911F910F91FF90EF90DF90CF9059
+:103B7000BF900C949D19552309F4AACF862F279640
+:103B80000FB6F894DEBF0FBECDBFDF91CF911F916E
+:103B90000F91FF90EF90DF90CF90BF900C94651A3B
+:103BA0004B2D4F70C8010E94E50227960FB6F8947E
+:103BB000DEBF0FBECDBFDF91CF911F910F91FF9060
+:103BC000EF90DF90CF90BF900C94FD21F11082C058
+:103BD0009B2D9F70492F50E04230510599F144F4DC
+:103BE0004115510569F04130510509F073C019C004
+:103BF00043305105C1F14430510509F06BC044C058
+:103C000027960FB6F894DEBF0FBECDBFDF91CF91E0
+:103C10001F910F91FF90EF90DF90CF90BF900C9489
+:103C2000702B27960FB6F894DEBF0FBECDBFDF9185
+:103C3000CF911F910F91FF90EF90DF90CF90BF90A9
+:103C40000C94872B27960FB6F894DEBF0FBECDBF1E
+:103C5000DF91CF911F910F91FF90EF90DF90CF9068
+:103C6000BF900C94A32B27960FB6F894DEBF0FBE1F
+:103C7000CDBFDF91CF911F910F91FF90EF90DF901B
+:103C8000CF90BF900C94B62B862F27960FB6F89442
+:103C9000DEBF0FBECDBFDF91CF911F910F91FF907F
+:103CA000EF90DF90CF90BF900C94DA2B4B2D4F709C
+:103CB000C80127960FB6F894DEBF0FBECDBFDF91C7
+:103CC000CF911F910F91FF90EF90DF90CF90BF9019
+:103CD0000C940E0827960FB6F894DEBF0FBECDBF2A
+:103CE000DF91CF911F910F91FF90EF90DF90CF90D8
+:103CF000BF9008950E940C240E94E1230E94282472
+:103D00000E9418290E946C2880E090E00E94801890
+:103D100080E090E00C9496180E94FC230C947A1E8C
+:103D20000E946923292F22952F7030E02C30310515
+:103D30004CF42A3031056CF422503109223031051F
+:103D400070F407C02C30310531F02F30310539F4D3
+:103D500002C081E0089593FB882780F9089580E0F0
+:103D60000895CF93DF9300D000D01F92CDB7DEB778
+:103D70000F900F900F900F900F90DF91CF910895BB
+:103D8000CF93DF9300D000D000D0CDB7DEB726961A
+:103D90000FB6F894DEBF0FBECDBFDF91CF9108956F
+:103DA0001F93CF93DF93C091530216E012C0D0E06F
+:103DB0001C9FF0011D9FF00D1124ED5DFD4F408112
+:103DC000518162817381848195810E94C01E2196F8
+:103DD000C77080915402C813EACFDF91CF911F9131
+:103DE000089540911D0250911E0260911F02709132
+:103DF000200280912102909122020C94C01E0F9308
+:103E00001F93CF93DF938091220282958F7009F0E8
+:103E100069C080911F02882309F464C0A0915302F5
+:103E2000D0915402B0911D02C0911E0280912002D7
+:103E30009091210221E030E0BF3F11F020E030E01E
+:103E4000122FBC016095709506E04AC0009721F0E2
+:103E5000CF3F29F4212F05C021E030E002C020E04F
+:103E600030E020FD3BC04A2F50E0049FF001059F49
+:103E7000F00D1124ED5DFD4F2181C2132FC0208173
+:103E8000B2132CC02281211129C02381348128172B
+:103E9000390718F0281B390B02C0260F371F283CA2
+:103EA0003105E0F4809122028F70806180932202BC
+:103EB00086E0849FF001859FF00D1124E85DFD4FA1
+:103EC00080818F70806180838DE192E00E94C41AAE
+:103ED000DF91CF911F910F910C94D01EAF5FA7700F
+:103EE000AD13B4CFDF91CF911F910F910895EF9251
+:103EF000FF920F931F93CF93DF93CDB7DEB76297F7
+:103F00000FB6F894DEBF0FBECDBF8C0185E0F8017F
+:103F1000DE011D9601900D928A95E1F7D8014C9132
+:103F200011965C91119712966C9112971396ED90E1
+:103F3000FC90149770911D02E0911E028091200266
+:103F400090912102009739F0EF3F41F421E030E0F9
+:103F50007F3F31F003C021E030E002C020E030E0DC
+:103F600020FD5CC120911F02222309F4F1C0E81654
+:103F7000F90628F09701281B390BC90104C0809568
+:103F800090958E0D9F1D883C910508F098C08091FA
+:103F90002202982F907F09F064C0E51314C07413B7
+:103FA00012C0611110C08F708061809322020E9444
+:103FB000F11E8DE192E00E94C41A80912202D80184
+:103FC00015968C9343C1EF2839F05F3F41F481E0AF
+:103FD00090E04F3F31F003C081E090E002C080E00C
+:103FE00090E080FD03C081E0862702C080E090E081
+:103FF00080FF2EC0809153022091540236E013C0FE
+:1040000090E0389FF001399FF00D1124ED5DFD4FD8
+:104010007181571306C07081471303C07281671303
+:1040200017C0019687708213EBCF12C19F7059F0B1
+:10403000882309F40BC107C09F7029F0F80195810E
+:10404000907F09F403C1805E883008F4FFC0D2C0BD
+:10405000662309F4FBC080912202816080932202D2
+:10406000F5C0E51308C0741306C0611104C0D8017F
+:1040700015968C939DC04D875E878D859E856A8B36
+:104080000E94901E6A89882309F4B4C0662309F44B
+:10409000B1C020912202822F82958F7090E002970A
+:1040A0000CF4C6C080911D0290911E0298878F83E8
+:1040B0001986FB86EA862C87CE01079646C080913A
+:1040C0002202982F907F59F47E2DF98AE88A8989F7
+:1040D0000E94B11E8DE192E00E94C41A95C0E513C2
+:1040E00011C074130FC061110DC0F8018583C801A0
+:1040F0000E94C41AEDE1F2E086E0DF011D928A958C
+:10410000E9F7A2C04D875E878D859E856A8B0E94E8
+:10411000901E6A89882309F46DC0662309F46AC079
+:1041200020912202822F82958F7090E002970CF4EA
+:104130007FC080911D0290911E029A8389831B8209
+:10414000FD82EC822E83CE0101960E94C41A70C0BB
+:10415000E816F90628F09701281B390BC90104C09D
+:10416000809590958E0D9F1D883C910508F046C066
+:10417000662309F43FC0E51330C074132EC02091AC
+:10418000220220FD21C0322F32953F70832F90E014
+:104190000097D1F0D80115962C9315970F9741F001
+:1041A000832F8F5F8295807F2F70282B15962C93FD
+:1041B000C8010E94C41A86E0F801ADE1B2E00190A6
+:1041C0000D928A95E1F73EC086E0F801ADE1B2E0DC
+:1041D00001900D928A95E1F737C04D875E878D85F6
+:1041E0009E850E94901E811123C0809122028160D1
+:1041F00080932202C8010E94C41A26C07E2DF98A2B
+:10420000E88A89890E94B11EEDE1F2E086E0DF01D3
+:104210001D928A95E9F70E94F11E18C0662351F39A
+:104220004D875E878D859E850E94901E882311F3A1
+:1042300086E0F801ADE1B2E001900D928A95E1F7D8
+:104240000E94FF1E0E94F11E81E014C080E012C097
+:104250004D875E878D859E850E946923292F229533
+:104260002F7030E0223031050CF4E0CE24303105DF
+:104270000CF6E2CE62960FB6F894DEBF0FBECDBF4D
+:10428000DF91CF911F910F91FF90EF9008951F93B1
+:10429000CF93DF93CDB7DEB72C970FB6F894DEBF80
+:1042A0000FBECDBF4F83588769877A878B879C87DE
+:1042B000CE0107960E94771F8823D9F02F81388579
+:1042C0008A859B85892B39F03F3F19F080E090E08B
+:1042D00004C02F3FD9F781E090E0892B09F06DC031
+:1042E0004F81588569857A858B859C850E94C01E83
+:1042F00064C086E0FE013796DE01119601900D92B2
+:104300008A95E1F7FF81E8854A855B85411551056E
+:1043100039F0EF3F41F481E090E0FF3F31F003C01E
+:1043200081E090E002C080E090E080FD46C02091F6
+:10433000540230E0C90101968770992760915302B9
+:1043400070E08617970709F440C0F983EA835D831C
+:104350004C8396E0929FD001939FB00D1124AD5DE8
+:10436000BD4FFE01319601900D929A95E1F7809331
+:1043700054020E94D01E21C0189FC00111248D5DDF
+:104380009D4F0E94771F882371F1E09153021E9F79
+:10439000F0011124ED5DFD4F4081518162817381F7
+:1043A000848195810E94C01E8091530290E0019605
+:1043B000877099278093530201C016E080915302C1
+:1043C000909154028913D8CF0EC00E948C1E109277
+:1043D000540210925302EDE1F2E086E0DF011D92FB
+:1043E0008A95E9F7EACF2C960FB6F894DEBF0FBE98
+:1043F000CDBFDF91CF911F910895DF92EF92FF9291
+:104400000F931F93CF93DF93EC01009709F46CC0D7
+:10441000D12CEE24E394F12C8E010F5F1F4FFE018F
+:104420008491843748F4843008F04AC0813071F0B8
+:10443000823009F059C01EC0853709F43DC070F1C3
+:10444000982F9458903708F04FC03DC02296F8013D
+:104450008491982F905E983050F48770FE2D01C0A3
+:10446000FF0F8A95EAF78F2F0E94FF2330C00E942A
+:104470009D192DC02296F8018491982F905E983056
+:1044800050F48770FE2D01C0FF0F8A95EAF78F2F39
+:104490000E9405241CC00E94651A19C02296F801CA
+:1044A000049107C08FE99FE00197F1F700C0000079
+:1044B00001500111F7CF0BC02296F801D49007C02C
+:1044C0000E949D1903C08F770E94651AE8018D2D07
+:1044D00007C08150EFE9FFE03197F1F700C000001D
+:1044E000882309F499CFF5CFDF91CF911F910F91D8
+:1044F000FF90EF90DF9008956093590270935A02F5
+:1045000080935B0290935C020C947A1E6093550238
+:104510007093560280935702909358020C947A1E1F
+:1045200008950C947C220F931F93009159021091CF
+:104530005A0220915B0230915C02602B712B822B1E
+:10454000932B1F910F910C947C220F931F9300913A
+:10455000590210915A0220915B0230915C02602353
+:104560007123822393231F910F910C947C220F932C
+:104570001F930091590210915A0220915B023091D1
+:104580005C0260277127822793271F910F910C945B
+:104590007C2260E070E0CB010C94862241E050E088
+:1045A00060E070E004C0440F551F661F771F8A95B6
+:1045B000D2F7CB01BA010C94862241E050E060E0D2
+:1045C00070E004C0440F551F661F771F8A95D2F70D
+:1045D0008091550290915602A0915702B0915802D5
+:1045E000482B592B6A2B7B2BCB01BA010C948622CA
+:1045F00041E050E060E070E004C0440F551F661FCA
+:10460000771F8A95D2F74095509560957095809167
+:10461000550290915602A0915702B091580248233A
+:1046200059236A237B23CB01BA010C94862241E0F3
+:1046300050E060E070E004C0440F551F661F771F14
+:104640008A95D2F78091550290915602A091570217
+:10465000B0915802482759276A277B27CB01BA0116
+:104660000C9486220F931F930091550210915602CD
+:104670002091570230915802602B712B822B932B83
+:104680001F910F910C9486220F931F930091550256
+:1046900010915602209157023091580260237123E5
+:1046A000822393231F910F910C9486220F931F93C3
+:1046B00000915502109156022091570230915802F4
+:1046C00060277127822793271F910F910C948622D0
+:1046D0000895CF92DF92EF92FF920F931F93CF93A3
+:1046E000DF93EC01C0905902D0905A02E0905B0237
+:1046F000F0905C028091550290915602A091570271
+:10470000B0915802C82AD92AEA2AFB2A0FE110E000
+:10471000B701A601002E04C0769567955795479579
+:104720000A94D2F740FF08C0BE01802F0E94E00328
+:104730008130910509F007C00150110948F7BE0109
+:1047400080E00E94E003DF91CF911F910F91FF90D5
+:10475000EF90DF90CF90089540911B0150911C0184
+:1047600020E030E09FEFFA01E20FF31F628168174B
+:10477000A1F09F3F19F4611101C0922F2F5F3F4FAD
+:104780002630310581F707C0FA01E90FF11D97FDC9
+:10479000FA95828308959F3FB9F7089540911B01D0
+:1047A00050911C0120E030E0FA01E20FF31F9281EA
+:1047B000981301C012822F5F3F4F26303105A1F7B9
+:1047C000089581E090E0E0911B01F0911C01E80F59
+:1047D000F91F1082019688309105A9F708959091EC
+:1047E0005D02982B90935D020895809590915D02F3
+:1047F000982390935D02089510925D020895909120
+:104800005E02982B90935E020895809590915E02CF
+:10481000982390935E02089510925E02089580930B
+:104820005F02089510925F02089540911B0150911C
+:104830001C0120E030E080E0FA01E20FF31F9181DB
+:1048400091118F5F2F5F3F4F27303105A9F70895F2
+:10485000E0911B01F0911C0180915D028083E09149
+:104860001B01F0911C01808190915E02892B808355
+:1048700090915F02992361F0E0911B01F0911C017E
+:104880008081892B80830E94152481110E9412242B
+:1048900080911B0190911C010C946A1880916E0309
+:1048A000843009F11092690220E488E190E00FB6AB
+:1048B000F894A895809360000FBE2093600083B7A2
+:1048C000817F846083BF83B7816083BF789488953C
+:1048D00083B78E7F83BF88E10FB6F8948093600022
+:1048E000109260000FBE0895CF930E94E3020E94D1
+:1048F0007E060E94E402C0E08C2F0E94C407892B30
+:1049000029F4CF5FC430C1F780E001C081E0CF91CE
+:1049100008950E948C1E0C945F2B1F920F920FB66D
+:104920000F9211248F939F93AF93BF93809169024D
+:10493000811113C080916A0290916B02A0916C0268
+:10494000B0916D024196A11DB11D80936A029093B2
+:104950006B02A0936C02B0936D02BF91AF919F91D7
+:104960008F910F900FBE0F901F90189582E084BD1D
+:1049700093E095BD9AEF97BD80936E0008958FB731
+:10498000F89440916A0250916B0260916C027091B0
+:104990006D028FBFCA010895CF92DF92EF92FF920E
+:1049A0000F931F932FB7F89440916A0250916B02B6
+:1049B00060916C0270916D022FBF6A017B01EE2441
+:1049C000FF248C0120E030E0C016D106E206F30699
+:1049D00020F09A01281B390B05C09C0120953095C9
+:1049E000240F351FC9011F910F91FF90EF90DF90A9
+:1049F000CF9008951F920F920FB60F9211248F93AC
+:104A00009F93AF93BF9380916A0290916B02A091A4
+:104A10006C02B0916D020196A11DB11D80936A02D6
+:104A200090936B02A0936C02B0936D02BF91AF9113
+:104A30009F918F910F900FBE0F901F9018950E941D
+:104A4000A111F8942FEF87EA91E621508040904021
+:104A5000E1F700C0000087E090EBDC018093780371
+:104A600090937903A0937A03B0937B032CE088E1C1
+:104A700090E00FB6F894A895809360000FBE209345
+:104A80006000FFCFCF92DF92EF92FF920F931F93C0
+:104A9000CF93DF93C82ED12C01E010E08D2D0E9422
+:104AA000C4077C01C0E0D0E098010C2E02C0220FA8
+:104AB000331F0A94E2F72E213F21232B29F421965C
+:104AC000CC30D10589F708C06C2F7D2D80E00E9485
+:104AD000BB03C812F4CF06C0D39484E0D812DECF53
+:104AE00080E001C081E0DF91CF911F910F91FF9095
+:104AF000EF90DF90CF900895CF93C82F8CE20E9463
+:104B00004225882321F08C2FCF910C94422580E000
+:104B1000CF910895CF930E94CD26811102C00E94AB
+:104B2000AE26C5E608C00E947E068FE39CE9019789
+:104B3000F1F700C00000C150B1F789E20E947C2566
+:104B400081110AC18AE20E947C2581110E94AE2651
+:104B500085E00E947C2581110E941F250E94D82695
+:104B60008093680287E00E947C25882399F18BE17D
+:104B70000E947C25882351F09091680291FB882740
+:104B800080F921E0822780FB91F922C08EE00E940B
+:104B90007C25882351F09091680292FB882780F948
+:104BA00021E0822780FB92F913C080E10E947C25DE
+:104BB00090916802882341F093FB882780F921E0D7
+:104BC000822780FB93F904C0892F809580FB90F9A0
+:104BD00090936802809168020E94DC260E94EA2677
+:104BE00080937B0280EE0E947C25882341F0809197
+:104BF0007B02982F909590FB80F980937B0289E34C
+:104C00000E947C25882359F090917B0291FB882794
+:104C100080F921E0822780FB91F990937B0282EE5C
+:104C20000E947C25882359F090917B0292FB882773
+:104C300080F921E0822780FB92F990937B0286EE37
+:104C40000E947C25882359F090917B0293FB882752
+:104C500080F921E0822780FB93F990937B0283EE19
+:104C60000E947C25882359F090917B0294FB882731
+:104C700080F921E0822780FB94F990937B0285E301
+:104C80000E947C25882359F090917B0295FB882710
+:104C900080F921E0822780FB95F990937B0281E3E4
+:104CA0000E947C25882359F090917B0296FB8827EF
+:104CB00080F921E0822780FB96F990937B0281E1C5
+:104CC0000E947C25882359F090917B0297FB8827CE
+:104CD00080F921E0822780FB97F990937B028091F5
+:104CE0007B020E94EE2687E20E947C25C82F8EE17F
+:104CF0000E947C258111C2608FE10E947C25811178
+:104D0000C46080E20E947C258111C86081E20E941B
+:104D10007C258111C06182E20E947C258111C062E4
+:104D200083E20E947C258111C06484E20E947C257C
+:104D3000882311F0C06802C0CC2329F08C2F0E9478
+:104D4000E5266C2F03C00E94E126682F70E080E00A
+:104D500090E0CF910C949122CF9108956DEE7EEF6B
+:104D600080E090E00E94BA2F60E082E090E00E9434
+:104D7000AC2F60E083E090E00E94AC2F60E084E024
+:104D800090E00E94AC2F60E085E090E00E94AC2FA4
+:104D900060E086E090E00C94AC2F80E090E00E9410
+:104DA000A62F21E08D3E9E4F09F020E0822F08952E
+:104DB00082E090E00C949E2F682F82E090E00C94AB
+:104DC000AC2F83E090E00C949E2F682F83E090E05E
+:104DD0000C94AC2F84E090E00C949E2F682F84E01C
+:104DE00090E00C94AC2F86E090E00C949E2F682FFE
+:104DF00086E090E00C94AC2F8091760280FF0BC08F
+:104E00006091200185E0689FB00111247595679538
+:104E1000759567952AC081FF09C06091200185E0E2
+:104E2000689FB0011124759567951FC082FF07C068
+:104E30006091200185E0689FB001112416C0409167
+:104E400070024423C9F060911F01461788F7209132
+:104E5000200185E0289F90011124429FC001439FBB
+:104E6000900D112470E00E948A2F6038710540F483
+:104E70006115710539F002C065E070E0862F089574
+:104E80008FE7089581E008958091760280FF08C041
+:104E900060911E0170E0759567957595679521C0C5
+:104EA00081FF06C060911E0170E07595679519C07D
+:104EB00082FF04C060911E0170E010C080917002FA
+:104EC0008823C1F060911D018617A0F790911E0103
+:104ED000989FC001112470E00E948A2F60387105EC
+:104EE00028F46115710521F0862F08958FE7089544
+:104EF00081E0089561E070E0F4CF803F21F40E94EA
+:104F0000FC26819504C0813F29F40E94FC268093F1
+:104F100073020895823F21F40E94FC26819504C00B
+:104F2000833F29F40E94FC26809372020895893FF2
+:104F300019F40E94442705C08A3F31F40E94442797
+:104F400081958093740208958B3F21F40E94442739
+:104F5000819504C08C3F29F40E94442780937502F8
+:104F60000895843F21F480917102816017C0853FCC
+:104F700021F480917102826011C0863F21F48091FA
+:104F8000710284600BC0873F21F4809171028860B8
+:104F900005C0883F31F48091710280618093710275
+:104FA00008958D3F21F48091760281600BC08E3F81
+:104FB00021F480917602826005C08F3F29F48091B0
+:104FC00076028460809376020895803F29F4809170
+:104FD000730287FF6EC007C0813F41F48091730266
+:104FE00018160CF066C01092730263C090917202A2
+:104FF000823F19F497FF5DC005C0833F31F4191655
+:105000000CF057C01092720254C0893F31F4809165
+:10501000740218160CF04DC006C08A3F39F4809116
+:10502000740287FF46C01092740243C08B3F29F47C
+:105030008091750287FF3DC006C08C3F39F4809196
+:1050400075021816B4F51092750233C0843F21F42E
+:10505000809171028E7F05C0853F31F4809171028D
+:105060008D7F8093710225C0863F21F4809171026B
+:105070008B7FF7CF873F21F480917102877FF1CF3B
+:10508000883F21F4809171028F7EEBCF8D3F21F418
+:10509000809176028E7F0BC08E3F21F48091760244
+:1050A0008D7F05C08F3F29F4809176028B7F80939E
+:1050B00076028091720281110EC08091730281117B
+:1050C0000AC080917402811106C08091750281111D
+:1050D00002C010927002089581E792E00E94751854
+:1050E0000E94BF2490936F0280936E020895CF9325
+:1050F00080916E0290916F020E94CC2440917002C8
+:10510000442321F02091210130E006C020912201AA
+:105110005AE0259F900111248217930708F486C056
+:105120008091720281110DC090917302911109C09A
+:1051300090917402911105C090917502992309F420
+:1051400075C04F3F19F04F5F40937002181624F45A
+:105150000E94FC26809372028091720287FF05C034
+:105160000E94FC268195809372028091730218162A
+:1051700024F40E94FC26809373028091730287FFBF
+:1051800005C00E94FC268195809373026091720293
+:10519000662339F1C0917302CC2319F1772767FD9B
+:1051A0007095872F972F0E94FA2C23E333E343E374
+:1051B0005FE30E94AE2D0E94C72C609372026C2F99
+:1051C000772767FD7095872F972F0E94FA2C23E38E
+:1051D00033E343E35FE30E94AE2D0E94C72C60934C
+:1051E000730280917402181624F40E94442780935D
+:1051F00074028091740287FF05C00E944427819544
+:105200008093740280917502181624F40E9444273A
+:10521000809375028091750287FF05C00E94442724
+:10522000819580937502CF910C946C28CF9108954D
+:10523000E1E7F2E085E0DF011D928A95E9F710923F
+:105240007002109276020895833089F130F4813033
+:1052500061F0823009F06EC019C0853009F449C090
+:10526000B8F1863009F066C055C020912201862F22
+:1052700090E0820F911D8F3F910520F4620F6093A3
+:10528000220108958FEF809322010895209121013A
+:10529000862F90E0820F911D8F3F910520F4620FC1
+:1052A0006093210108958FEF80932101089520914B
+:1052B0002001862F90E0820F911D8F3F910520F4F1
+:1052C000620F6093200108958FEF8093200108956D
+:1052D00020911F01862F90E0820F911D8F3F910535
+:1052E00020F4620F60931F0108958FEF80931F01D8
+:1052F000089520911E01862F90E0820F911D8F3F0F
+:10530000910520F4620F60931E0108958FEF809342
+:105310001E01089520911D01862F90E0820F911D9E
+:105320008F3F910520F4620F60931D0108958FEF68
+:1053300080931D010895833021F130F4813059F0BC
+:10534000823009F049C012C0853089F128F18630D9
+:1053500009F042C037C080912201681720F4861BF3
+:1053600080932201089510922201089580912101D5
+:10537000681720F4861B8093210108951092210163
+:10538000089580912001681720F4861B80932001E6
+:10539000089510922001089580911F01681720F44C
+:1053A000861B80931F01089510921F01089580911C
+:1053B0001E01681720F4861B80931E010895109229
+:1053C0001E01089580911D01681720F4861B8093AB
+:1053D0001D01089510921D01089541E050E060E024
+:1053E00070E004C0440F551F661F771F8A95D2F7DF
+:1053F000CB01BA010E9491220C948C1E873208F5D1
+:105400008E3108F0B9C08E3009F47EC060F4873068
+:1054100009F465C018F4863059F549C0883051F157
+:105420008B3031F5AEC0883130F4863108F0A9C038
+:105430008031F1F473C0893109F4A3C08B31C1F418
+:1054400059C08933F1F068F4893209F493C018F433
+:10545000873271F48FC0853309F48CC0883341F4EE
+:1054600090C0863409F46BC008F488C0883449F1D0
+:1054700080E008950E94D8260E94EA260E94F32622
+:1054800080C00E945918892B59F00E945918909396
+:105490007902809378020E948C1E80E090E004C024
+:1054A00080917802909179020E9454186AC080918C
+:1054B0006802817F8E7F8093680281E0809377020B
+:1054C00008950E948C1E2FEF83ED90E321508040C1
+:1054D0009040E1F700C000000E941F2552C080915B
+:1054E000680280FF03C0817F8E7F01C0816080934E
+:1054F000680247C09091680291FB882780F921E0FB
+:10550000822780FB91F913C09091680292FB882753
+:1055100080F921E0822780FB92F909C0909168020E
+:1055200093FB882780F921E0822780FB93F99093F1
+:105530006802882331F191609093680222C081E86B
+:1055400090E00E9480182FEF81EE94E0215080407F
+:105550009040E1F700C0000080E090E00E948018D9
+:105560002FEF89E698E1215080409040E1F700C09C
+:10557000000007C080E003C08D5101C089530E9424
+:10558000ED2981E0089580E0089580E00895CF93AB
+:10559000C82F80917702813071F020F0823009F0BD
+:1055A00083C037C0A0911B01B0911C018C91823245
+:1055B00009F07CC007C0A0911B01B0911C018C9127
+:1055C000823249F48C2F0E94C32A81111EC08C2F75
+:1055D0000E94FE291CC08C2F0E94C52A811115C073
+:1055E000C43169F030F4CB3081F0C03109F062C0D1
+:1055F00009C0C93221F0C83309F05CC006C010925E
+:10560000770258C082E08093770281E090E0817059
+:1056100054C0C932C1F060F4C431A9F020F4C730DD
+:1056200009F046C02EC0CE51CA3008F041C011C0AA
+:10563000CE3409F118F4CB34D9F517C0C13599F03F
+:10564000C235B1F50EC010927A0281E080937702E4
+:1056500034C0EC2FF0E0E455FE4F808180937A0255
+:1056600027C061E003C061E007C06AE080917A0270
+:105670000E9424291DC06AE080917A020E949B2921
+:1056800017C08EE18093220182E3809321018AE09A
+:105690008093200184E180931F0188E080931E01A4
+:1056A00088E280931D0104C01092770280E005C05B
+:1056B00081E003C080E090E0AACFCF9108950E94DE
+:1056C000CD26811102C00E94AE260E94F32680934F
+:1056D000770380FF02C0869501C080E00C94DF074D
+:1056E00080917703982F9695292F30E0233031054C
+:1056F0004CF49F5F990F8170892B816080937703B1
+:105700000E94F7268091770386950C94DF0780919D
+:105710007703982F969591F09158990F8170892B66
+:10572000809377038E7F91E009F490E08091770376
+:1057300090FB80F9809377030E94F726809177038E
+:1057400086950C94DF0780917703982F909590FBB6
+:1057500080F9809377030E94F7268091770380FF7A
+:1057600002C0869501C080E00C94DF07309177037A
+:10577000232F26952F5F2F77822F90E0317004978B
+:105780002CF4220F232B2093770302C0309377034E
+:1057900080917703282F2E7F91E009F490E090FB11
+:1057A00080F9809377030E94F7268091770386958E
+:1057B0000C94DF0720917703922F96959827990FE5
+:1057C000822F8170892B809377038E7F91E009F47B
+:1057D00090E08091770390FB80F9809377030E949B
+:1057E000F7268091770386950C94DF075058BB27E6
+:1057F000AA270ED075C166D130F06BD120F031F4FC
+:105800009F3F11F41EF45BC10EF4E095E7FB51C11C
+:10581000E92F77D180F3BA176207730784079507DA
+:1058200018F071F49EF58FC10EF4E0950B2EBA2F8F
+:10583000A02D0B01B90190010C01CA01A001112496
+:10584000FF27591B99F0593F50F4503E68F11A1642
+:10585000F040A22F232F342F4427585FF3CF4695D3
+:1058600037952795A795F0405395C9F77EF41F16F5
+:10587000BA0B620B730B840BBAF09150A1F0FF0FBF
+:10588000BB1F661F771F881FC2F70EC0BA0F621FAB
+:10589000731F841F48F4879577956795B795F7959B
+:1058A0009E3F08F0B3CF9395880F08F09927EE0F2D
+:1058B000979587950895D9D008F481E008950CD084
+:1058C0000FC107D140F0FED030F021F45F3F19F056
+:1058D000F0C0511139C1F3C014D198F39923C9F321
+:1058E0005523B1F3951B550BBB27AA2762177307E6
+:1058F000840738F09F5F5F4F220F331F441FAA1F9A
+:10590000A9F333D00E2E3AF0E0E830D09150504059
+:10591000E695001CCAF729D0FE2F27D0660F771F07
+:10592000881FBB1F261737074807AB07B0E809F0E9
+:10593000BB0B802DBF01FF2793585F4F2AF09E3F7E
+:10594000510568F0B6C000C15F3FECF3983EDCF350
+:10595000869577956795B795F7959F5FC9F7880FF7
+:10596000911D9695879597F90895E1E0660F771F49
+:10597000881FBB1F621773078407BA0720F0621BDA
+:10598000730B840BBA0BEE1F88F7E095089504D0D3
+:105990006894B111D9C00895BCD088F09F5790F099
+:1059A000B92F9927B751A0F0D1F0660F771F881F44
+:1059B000991F1AF0BA95C9F712C0B13081F0C3D05F
+:1059C000B1E00895C0C0672F782F8827B85F39F0FD
+:1059D000B93FCCF3869577956795B395D9F73EF4A3
+:1059E00090958095709561957F4F8F4F9F4F08954B
+:1059F000E89409C097FB3EF4909580957095619569
+:105A00007F4F8F4F9F4F9923A9F0F92F96E9BB271E
+:105A10009395F695879577956795B795F111F8CF9A
+:105A2000FAF4BB0F11F460FF1BC06F5F7F4F8F4F05
+:105A30009F4F16C0882311F096E911C0772321F0FB
+:105A40009EE8872F762F05C0662371F096E8862F93
+:105A500070E060E02AF09A95660F771F881FDAF7EA
+:105A6000880F9695879597F90895990F0008550F17
+:105A7000AA0BE0E8FEEF16161706E807F907C0F0D4
+:105A800012161306E407F50798F0621B730B840BDC
+:105A9000950B39F40A2661F0232B242B252B21F4B6
+:105AA00008950A2609F4A140A6958FEF811D811D56
+:105AB000089597F99F6780E870E060E008959FEF90
+:105AC00080EC089500240A94161617061806090695
+:105AD000089500240A941216130614060506089564
+:105AE000092E0394000C11F4882352F0BB0F40F4EC
+:105AF000BF2B11F460FF04C06F5F7F4F8F4F9F4F2C
+:105B0000089557FD9058440F551F59F05F3F71F0AD
+:105B10004795880F97FB991F61F09F3F79F0879514
+:105B20000895121613061406551FF2CF4695F1DF9D
+:105B300008C0161617061806991FF1CF869571052D
+:105B4000610508940895E894BB2766277727CB0161
+:105B500097F908958ADF08F48FEF08950BD0C0CF2E
+:105B6000B1DF28F0B6DF18F0952309F0A2CFA7CF58
+:105B70001124EACFC6DFA0F3959FD1F3950F50E033
+:105B8000551F629FF001729FBB27F00DB11D639FEF
+:105B9000AA27F00DB11DAA1F649F6627B00DA11D95
+:105BA000661F829F2227B00DA11D621F739FB00D3B
+:105BB000A11D621F839FA00D611D221F749F3327AB
+:105BC000A00D611D231F849F600D211D822F762F44
+:105BD0006A2F11249F5750408AF0E1F088234AF041
+:105BE000EE0FFF1FBB1F661F771F881F915050408D
+:105BF000A9F79E3F510570F05CCFA6CF5F3FECF355
+:105C0000983EDCF3869577956795B795F795E79578
+:105C10009F5FC1F7FE2B880F911D9695879597F989
+:105C20000895FA01EE0FFF1F30962105310599F115
+:105C30006115710561F48038BFE39B0749F16894F1
+:105C40009038810561F08038BFEF9B0741F09923C0
+:105C500042F5FF3FE1053105210511F1E894089473
+:105C6000E795D901AA2329F4AB2FBE2FF85FD0F313
+:105C700010C0FF5F70F4A695E0F7F73950F019F007
+:105C8000FF3A38F49F779F930CD00F9007FC905801
+:105C900008953EF014CF60E070E080E89FE308953F
+:105CA0004FE79F775F934F933F932F939ED02F9112
+:105CB0003F914F915F9152DF05C019F40EF0F9CE7C
+:105CC00042CFFDCE26DFC8F39638C0F707F80F9213
+:105CD000E8942BE33AEA48EB5FE74EDF0F920F922E
+:105CE0000F924DB75EB70F92C0D0ECEAF0E016D03D
+:105CF0004F915F91EF91FF91E595EE1FFF1F49F0E6
+:105D0000FE57E0684427EE0F441FFA95E1F74195EE
+:105D1000550B32D00F9007FE26C00895DF93CF9326
+:105D20001F930F93FF92EF92DF927B018C01689497
+:105D300005C0DA2EEF011EDFFE01E894A591259142
+:105D4000359145915591AEF3EF0162DDFE0197016A
+:105D5000A801DA9479F7DF90EF90FF900F911F91EF
+:105D6000CF91DF9108959B01AC0160E070E080E885
+:105D70009FE3A5CD9ECEACC0CCDEE8F39923D9F34A
+:105D8000940F511DBBF39150504094F059F088236B
+:105D900032F0660F771F881F91505040C1F79E3F29
+:105DA000510544F7880F911D9695879597F90895A9
+:105DB0005F3FACF0983E9CF0BB2786957795679542
+:105DC000B79508F4B1609395C1F7BB0F58F711F47C
+:105DD00060FFE8CF6F5F7F4F8F4F9F4FE3CFB4CE11
+:105DE0000EF076C06CCE689464CE93DEC8F399232F
+:105DF000D1F3C6F3DF93CF931F930F93FF92C92F75
+:105E0000DD2788232AF02197660F771F881FDAF78E
+:105E100020E030E040E85FEB9FE3883920F0803EEF
+:105E200030F021968F77E3DCE4EDF0E003C0DFDCB7
+:105E3000E1E0F1E073DF8B01BE01EC01FB2E6F5757
+:105E400071097595771F880B990BD4DD28E132E72E
+:105E500041E35FE38FDEAF2D9801AE01FF900F911C
+:105E60001F91CF91DF91D4DC3BCEFA01DC01AA0F68
+:105E7000BB1F9B01AC01BF5728F4222733274427BF
+:105E800050781FC0B75188F4AB2F00244695379542
+:105E90002795011CA395D2F3002069F0220F331F30
+:105EA000441FB395DAF30DD0A1CC61307105A0E8A1
+:105EB0008A07B94630F49B01AC016627772788270B
+:105EC0009078309621F02083318342835383089564
+:105ED0009F3F31F0915020F4879577956795B7955E
+:105EE000880F911D9695879597F90895AA1BBB1B5E
+:105EF00051E107C0AA1FBB1FA617B70710F0A61BCA
+:105F0000B70B881F991F5A95A9F780959095BC01EA
+:105F1000CD01089597FB072E16F4009407D077FD66
+:105F200009D00E94762F07FC05D03EF4909581950C
+:105F30009F4F0895709561957F4F0895F999FECF11
+:105F400092BD81BDF89A992780B50895A8E1B0E087
+:105F500042E050E00C94C12F262FF999FECF1FBAD2
+:105F600092BD81BD20BD0FB6F894FA9AF99A0FBE82
+:105F7000019608950E94AC2F272F0C94AD2FDC01C1
+:105F8000CB01FC01F999FECF06C0F2BDE1BDF89A44
+:105F9000319600B40D9241505040B8F70895F894EE
+:025FA000FFCF31
+:105FA2000507000C058540000001064000000100C5
+:105FB200D80B680C440C0F0CDB0B01600228081490
+:105FC2000A321E40004500250026006100600020C4
+:105FD2000037006400650066006700440046002444
+:105FE2000047000000020004000500070009000B42
+:105FF200000C000E0010001100130015001700180D
+:10600200001A001C001D001F00210023002400268E
+:1060120000280029002B002D002F00300032003410
+:10602200003500370039003B008803A103BA03D3CF
+:1060320003FB04AE04780458043F4D3620020302E9
+:10604200000001000101010101000101010203043C
+:0660520005060708090025
+:00000001FF
diff --git a/keyboard/preonic/Makefile b/keyboard/preonic/Makefile
new file mode 100644
index 0000000000..0145e44bc6
--- /dev/null
+++ b/keyboard/preonic/Makefile
@@ -0,0 +1,143 @@
+#----------------------------------------------------------------------------
+# On command line:
+#
+# make all = Make software.
+#
+# make clean = Clean out built project files.
+#
+# make coff = Convert ELF to AVR COFF.
+#
+# make extcoff = Convert ELF to AVR Extended COFF.
+#
+# make program = Download the hex file to the device.
+# Please customize your programmer settings(PROGRAM_CMD)
+#
+# make teensy = Download the hex file to the device, using teensy_loader_cli.
+# (must have teensy_loader_cli installed).
+#
+# make dfu = Download the hex file to the device, using dfu-programmer (must
+# have dfu-programmer installed).
+#
+# make flip = Download the hex file to the device, using Atmel FLIP (must
+# have Atmel FLIP installed).
+#
+# make dfu-ee = Download the eeprom file to the device, using dfu-programmer
+# (must have dfu-programmer installed).
+#
+# make flip-ee = Download the eeprom file to the device, using Atmel FLIP
+# (must have Atmel FLIP installed).
+#
+# make debug = Start either simulavr or avarice as specified for debugging,
+# with avr-gdb or avr-insight as the front end for debugging.
+#
+# make filename.s = Just compile filename.c into the assembler code only.
+#
+# make filename.i = Create a preprocessed source file for use in submitting
+# bug reports to the GCC project.
+#
+# To rebuild project do "make clean" then "make all".
+#----------------------------------------------------------------------------
+
+# Target file name (without extension).
+TARGET = preonic_lufa
+
+# Directory common source filess exist
+TOP_DIR = ../..
+
+# Directory keyboard dependent files exist
+TARGET_DIR = .
+
+# # project specific files
+SRC = extended_keymap_common.c \
+ matrix.c \
+ led.c \
+ backlight.c
+
+ifdef KEYMAP
+ SRC := extended_keymaps/extended_keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := extended_keymaps/extended_keymap_default.c $(SRC)
+endif
+
+CONFIG_H = config.h
+
+# MCU name
+#MCU = at90usb1287
+MCU = atmega32u4
+
+# Processor frequency.
+# This will define a symbol, F_CPU, in all source code files equal to the
+# processor frequency in Hz. You can then use this symbol in your source code to
+# calculate timings. Do NOT tack on a 'UL' at the end, this will be done
+# automatically to create a 32-bit value in your source code.
+#
+# This will be an integer division of F_USB below, as it is sourced by
+# F_USB after it has run through any CPU prescalers. Note that this value
+# does not *change* the processor frequency - it should merely be updated to
+# reflect the processor speed set externally so that the code can use accurate
+# software delays.
+F_CPU = 16000000
+
+
+#
+# LUFA specific
+#
+# Target architecture (see library "Board Types" documentation).
+ARCH = AVR8
+
+# Input clock frequency.
+# This will define a symbol, F_USB, in all source code files equal to the
+# input clock frequency (before any prescaling is performed) in Hz. This value may
+# differ from F_CPU if prescaling is used on the latter, and is required as the
+# raw input clock is fed directly to the PLL sections of the AVR for high speed
+# clock generation for the USB and other AVR subsections. Do NOT tack on a 'UL'
+# at the end, this will be done automatically to create a 32-bit value in your
+# source code.
+#
+# If no clock division is performed on the input clock inside the AVR (via the
+# CPU clock adjust registers or the clock division fuses), this will be equal to F_CPU.
+F_USB = $(F_CPU)
+
+# Interrupt driven control endpoint task(+60)
+OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT
+
+
+# Boot Section Size in *bytes*
+# Teensy halfKay 512
+# Teensy++ halfKay 1024
+# Atmel DFU loader 4096
+# LUFA bootloader 4096
+# USBaspLoader 2048
+OPT_DEFS += -DBOOTLOADER_SIZE=4096
+
+
+# Build Options
+# comment out to disable the options.
+#
+BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration(+1000)
+MOUSEKEY_ENABLE = yes # Mouse keys(+4700)
+EXTRAKEY_ENABLE = yes # Audio control and System control(+450)
+CONSOLE_ENABLE = yes # Console for debug(+400)
+COMMAND_ENABLE = yes # Commands for debug and configuration
+# Do not enable SLEEP_LED_ENABLE. it uses the same timer as BACKLIGHT_ENABLE
+#SLEEP_LED_ENABLE = yes # Breathing sleep LED during USB suspend
+NKRO_ENABLE = yes # USB Nkey Rollover - not yet supported in LUFA
+BACKLIGHT_ENABLE = yes # Enable keyboard backlight functionality
+MIDI_ENABLE = yes # MIDI controls
+BACKLIGHT_ENABLE = yes
+
+ifdef MIDI_ENABLE
+ SRC += keymap_midi.c \
+ beeps.c
+endif
+
+# Optimize size but this may cause error "relocation truncated to fit"
+#EXTRALDFLAGS = -Wl,--relax
+
+# Search Path
+VPATH += $(TARGET_DIR)
+VPATH += $(TOP_DIR)
+
+include $(TOP_DIR)/protocol/lufa.mk
+include $(TOP_DIR)/common.mk
+include $(TOP_DIR)/rules.mk
diff --git a/keyboard/preonic/Makefile.pjrc b/keyboard/preonic/Makefile.pjrc
new file mode 100644
index 0000000000..be83ba18b1
--- /dev/null
+++ b/keyboard/preonic/Makefile.pjrc
@@ -0,0 +1,116 @@
+#----------------------------------------------------------------------------
+# On command line:
+#
+# make all = Make software.
+#
+# make clean = Clean out built project files.
+#
+# make coff = Convert ELF to AVR COFF.
+#
+# make extcoff = Convert ELF to AVR Extended COFF.
+#
+# make program = Download the hex file to the device.
+# Please customize your programmer settings(PROGRAM_CMD)
+#
+# make teensy = Download the hex file to the device, using teensy_loader_cli.
+# (must have teensy_loader_cli installed).
+#
+# make dfu = Download the hex file to the device, using dfu-programmer (must
+# have dfu-programmer installed).
+#
+# make flip = Download the hex file to the device, using Atmel FLIP (must
+# have Atmel FLIP installed).
+#
+# make dfu-ee = Download the eeprom file to the device, using dfu-programmer
+# (must have dfu-programmer installed).
+#
+# make flip-ee = Download the eeprom file to the device, using Atmel FLIP
+# (must have Atmel FLIP installed).
+#
+# make debug = Start either simulavr or avarice as specified for debugging,
+# with avr-gdb or avr-insight as the front end for debugging.
+#
+# make filename.s = Just compile filename.c into the assembler code only.
+#
+# make filename.i = Create a preprocessed source file for use in submitting
+# bug reports to the GCC project.
+#
+# To rebuild project do "make clean" then "make all".
+#----------------------------------------------------------------------------
+
+# Target file name (without extension).
+TARGET = gh60_pjrc
+
+# Directory common source filess exist
+TOP_DIR = ../..
+
+# Directory keyboard dependent files exist
+TARGET_DIR = .
+
+# project specific files
+SRC = keymap_common.c \
+ matrix.c \
+ led.c
+
+ifdef KEYMAP
+ SRC := keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := keymap_jack.c $(SRC)
+endif
+
+CONFIG_H = config.h
+
+
+# MCU name, you MUST set this to match the board you are using
+# type "make clean" after changing this, so all files will be rebuilt
+MCU = atmega32u4
+#MCU = at90usb1286
+
+
+# Processor frequency.
+# Normally the first thing your program should do is set the clock prescaler,
+# so your program will run at the correct speed. You should also set this
+# variable to same clock speed. The _delay_ms() macro uses this, and many
+# examples use this variable to calculate timings. Do not add a "UL" here.
+F_CPU = 16000000
+
+
+# Boot Section Size in *bytes*
+# Teensy halfKay 512
+# Atmel DFU loader 4096
+# LUFA bootloader 4096
+OPT_DEFS += -DBOOTLOADER_SIZE=4096
+
+
+# Build Options
+# comment out to disable the options.
+#
+BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration(+1000)
+MOUSEKEY_ENABLE = yes # Mouse keys(+5000)
+EXTRAKEY_ENABLE = yes # Audio control and System control(+600)
+CONSOLE_ENABLE = yes # Console for debug
+COMMAND_ENABLE = yes # Commands for debug and configuration
+SLEEP_LED_ENABLE = yes # Breathing sleep LED during USB suspend
+NKRO_ENABLE = yes # USB Nkey Rollover(+500)
+#PS2_MOUSE_ENABLE = yes # PS/2 mouse(TrackPoint) support
+
+
+# Search Path
+VPATH += $(TARGET_DIR)
+VPATH += $(TOP_DIR)
+
+include $(TOP_DIR)/protocol/pjrc.mk
+include $(TOP_DIR)/common.mk
+include $(TOP_DIR)/rules.mk
+
+plain: OPT_DEFS += -DKEYMAP_PLAIN
+plain: all
+
+poker: OPT_DEFS += -DKEYMAP_POKER
+poker: all
+
+poker_set: OPT_DEFS += -DKEYMAP_POKER_SET
+poker_set: all
+
+poker_bit: OPT_DEFS += -DKEYMAP_POKER_BIT
+poker_bit: all
diff --git a/keyboard/preonic/PCB_GUIDE.md b/keyboard/preonic/PCB_GUIDE.md
new file mode 100644
index 0000000000..c3004c75a4
--- /dev/null
+++ b/keyboard/preonic/PCB_GUIDE.md
@@ -0,0 +1,116 @@
+# Planck Firmware Guide
+
+## Setting up the environment
+
+### Windows
+1. Install [WinAVR Tools](http://sourceforge.net/projects/winavr/) for AVR GCC compiler.
+2. Install [DFU-Programmer][dfu-prog] (the -win one).
+3. Start DFU bootloader on the chip first time you will see 'Found New Hardware Wizard' to install driver. If you install device driver properly you can find chip name like 'ATmega32U4' under 'LibUSB-Win32 Devices' tree on 'Device Manager'. If not you will need to update its driver on 'Device Manager' to the `dfu-programmer` driver.
+
+### Mac
+1. Install [CrossPack](http://www.obdev.at/products/crosspack/index.html) or install Xcode from the App Store and install the Command Line Tools from `Xcode->Preferences->Downloads`.
+2. Install [DFU-Programmer][dfu-prog].
+
+### Linux
+1. Install AVR GCC with your favorite package manager.
+2. Install [DFU-Programmer][dfu-prog].
+
+##Verify Your Installation
+1. Clone the following repository: https://github.com/jackhumbert/tmk_keyboard
+2. Open a Terminal and `cd` into `tmk_keyboard/keyboard/planck`
+3. Run `make`. This should output a lot of information about the build process.
+
+## Using the built-in functions
+
+Here is a list of some of the functions available from the command line:
+
+* `make clean`: clean the environment - may be required in-between builds
+* `make`: compile the code
+* `make COMMON=true`: compile with the common (non-extended) keymap
+* `make MATRIX=<matrix_file>`: compile with the referenced matrix file. Default if unspecified is `matrix_pcb.c`. For handwired boards, use `matrix_handwired.c`.
+* `make KEYMAP=<keymap>`: compile with the extended keymap file `extended_keymaps/extended_keymap_<keymap>.c`
+* `make COMMON=true KEYMAP=<keymap>`: compile with the common keymap file `common_keymaps/keymap_<keymap>.c`
+* `make dfu`: build and flash the layout to the PCB
+* `make dfu-force`: build and force-flash the layout to the PCB (may be require for first flash)
+
+Generally, the instructions to flash the PCB are as follows:
+
+1. Make changes to the appropriate keymap file
+2. Save the file
+3. `make clean`
+4. Press the reset button on the PCB/press the key with the `RESET` keycode
+5. `make <arguments> dfu` - use the necessary `KEYMAP=<keymap>` and/or `COMMON=true` arguments here.
+
+## Extended keymap
+
+### Keymap
+
+Unlike the common keymap, prefixing the keycodes with `KC_` is required. A full list of the keycodes is available [here](https://github.com/jackhumbert/tmk_keyboard/blob/master/doc/keycode.txt). For the keycodes available only in the extended keymap, see this [header file](https://github.com/jackhumbert/tmk_keyboard/blob/master/keyboard/planck/extended_keymap_common.h).
+
+You can use modifiers with keycodes like this:
+
+ LCTL(KC_C)
+
+Which will generate Ctrl+c. These are daisy-chainable, meaning you can do things like:
+
+ LCTL(LALT(KC_C))
+
+That will generate Ctrl+Alt+c. The entire list of these functions is here:
+
+* `LCTL()`: Left control
+* `LSFT()` / `S()`: Left shift
+* `LALT()`: Left alt/opt
+* `LGUI()`: Left win/cmd
+* `RCTL()`: Right control
+* `RSFT()`: Right shift
+* `RALT()`: Right alt/opt
+* `RGUI()`: Right win/cmd
+
+`S(KC_1)`-like entries are useful in writing keymaps for the Planck.
+
+### Other keycodes
+
+A number of other keycodes have been added that you may find useful:
+
+* `CM_<key>`: the Colemak equivalent of a key (in place of `KC_<key>`), when using Colemak in software (`CM_O` generates `KC_SCLN`)
+* `RESET`: jump to bootloader for flashing (same as press the reset button)
+* `BL_STEP`: step through the backlight brightnesses
+* `BL_<0-15>`: set backlight brightness to 0-15
+* `BL_DEC`: lower the backlight brightness
+* `BL_INC`: raise the backlight brightness
+* `BL_TOGG`: toggle the backlight on/off
+
+### Function layers
+
+The extended keymap extends the number of function layers from 32 to the near-infinite value of 256. Rather than using `FN<num>` notation (still available, but limited to `FN0`-`FN31`), you can use the `FUNC(<num>)` notation. `F(<num>)` is a shortcut for this.
+
+The function actions are unchanged, and you can see the full list of them [here](https://github.com/jackhumbert/tmk_keyboard/blob/master/common/action_code.h). They are explained in detail [here](https://github.com/jackhumbert/tmk_keyboard/blob/master/doc/keymap.md#2-action).
+
+### Macros
+
+Macros have been setup in the `extended_keymaps/extended_keymaps_default.c` file so that you can use `M(<num>)` to access a macro in the `action_get_macro` section on your keymap. The switch/case structure you see here is required, and is setup for `M(0)` - you'll need to copy and paste the code to look like this (e.g. to support `M(3)`):
+
+ switch(id) {
+ case 0:
+ return MACRODOWN(TYPE(KC_A), END);
+ break;
+ case 1:
+ return MACRODOWN(TYPE(KC_B), END);
+ break;
+ case 2:
+ return MACRODOWN(TYPE(KC_C), END);
+ break;
+ case 3:
+ return MACRODOWN(TYPE(KC_D), END);
+ break;
+ }
+ return MACRO_NONE;
+
+`MACRODOWN()` is a shortcut for `(record->event.pressed ? MACRO(__VA_ARGS__) : MACRO_NONE)` which tells the macro to execute when the key is pressed. Without this, the macro will be executed on both the down and up stroke.
+
+[cygwin]: https://www.cygwin.com/
+[mingw]: http://www.mingw.org/
+[mhv]: https://infernoembedded.com/products/avr-tools
+[winavr]: http://winavr.sourceforge.net/
+[crosspack]: http://www.obdev.at/products/crosspack/index.html
+[dfu-prog]: http://dfu-programmer.sourceforge.net/
diff --git a/keyboard/preonic/README.md b/keyboard/preonic/README.md
new file mode 100644
index 0000000000..ee824d26e0
--- /dev/null
+++ b/keyboard/preonic/README.md
@@ -0,0 +1,56 @@
+Planck keyboard firmware
+======================
+DIY/Assembled compact ortholinear 40% keyboard by [Ortholinear Keyboards](http://ortholinearkeyboards.com).
+
+## Extended Keymap
+If you include extended_keymap_common.h instead of keymap_common.h at the top of your file, you'll have access to a bunch of goodies:
+
+- Use `LSFT()`, `LCTL()`, et. al. (listed in extended_keymap_common.h) as modifiers for keys (daisy-chain-able)
+- Use `FUNC(1)` instead of `FN1` (etc.) to access the function layers beyond the 32 function layer limit
+- Use `CM_F` instead of `KC_F` to get the ColeMak equivilent for shortcuts (maps backwards)
+- Use `MACRODOWN()` instead of `MACRO()` to easily make a keydown macro (`CM_*` works here too)
+
+### Some notes on usage:
+
+- The `KEYMAP()` macro is unable to be used due to the bitwise modifications that take place - refer to extended_keymap_jack.c to see how to set things up with the `KC_` prefix
+- Keep an eye on the Makefile - this needs to include the correct files to work
+- Don't forget to use `const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {` instead of the 8bit equivilent
+
+## Build
+
+Follow [this guide](http://deskthority.net/workshop-f7/how-to-build-your-very-own-keyboard-firmware-t7177.html) to setup your development environment before anything else. Abbreviated instructions are provide at the [bottom of this document](https://github.com/rswiernik/tmk_keyboard/tree/rswiernik_dev/keyboard/planck#environment-setup)
+
+Download the whole firmware [here](https://github.com/jackhumbert/tmk_keyboard/archive/master.zip) and navigate to the keyboard/planck folder. Once your dev env is setup, you'll be able to type `make` to generate your .hex that you can load with the Teensy app onto your Planck (once you've hit reset/shorted GND & RST).
+
+Depending on which keymap you would like to use, you will have to compile slightly differently.
+
+####Default
+To build with the default keymap, simply move to the tmk\_keyboard/keyboard/planck/ and run `make` as follows:
+```
+$ make
+```
+
+## Keymap
+Several version of keymap are available in advance but you are recommended to define your favorite layout yourself. To define your own keymap create file named `keymap_<name>.c` and see keymap document (you can find in top README.md) and existent keymap files.
+
+####**Extended Keymaps**
+
+To build the firmware binary hex file with an extended keymap just do `make` with `KEYMAP` option like:
+```
+$ make KEYMAP=[common|jack|<name>]
+```
+_The only applicable keymaps will work with this option._ Extended keymaps follow the format **__extended\_keymap\_\<name\>.c__**
+
+####**Common Keymaps**
+
+Building with a common keymap is as simple as adding the COMMON option. Note that only
+```
+$ make KEYMAP=[common|jack|<name>] COMMON=true
+```
+_The only applicable keymaps will work with this option._ Common keymaps follow the format **__keymap\_\<name\>.c__**
+
+## Notable TMK forks (which some of the keymap files are from)
+- [Shane's Fork](https://github.com/shanecelis/tmk_keyboard/tree/master/keyboard/planck)
+- [Pierre's Fork](https://github.com/pcarrier/tmk_keyboard/blob/pcarrier/planck/keyboard/gh60/keymap_planck.c)
+- [Nathan's Fork](https://github.com/nathanrosspowell/tmk_keyboard/tree/planck-jack/keyboard/planck)
+- [Matthew's Fork](https://github.com/pepers/tmk_keyboard/tree/master/keyboard/planck_grid)
diff --git a/keyboard/preonic/__avr_gdbinit b/keyboard/preonic/__avr_gdbinit
new file mode 100644
index 0000000000..afc51e6d19
--- /dev/null
+++ b/keyboard/preonic/__avr_gdbinit
@@ -0,0 +1,6 @@
+define reset
+SIGNAL SIGHUP
+end
+file planck_lufa.elf
+target remote localhost:4242
+break main
diff --git a/keyboard/preonic/analog.c b/keyboard/preonic/analog.c
new file mode 100644
index 0000000000..49b84ee0e8
--- /dev/null
+++ b/keyboard/preonic/analog.c
@@ -0,0 +1,53 @@
+// Simple analog to digitial conversion
+
+#include <avr/io.h>
+#include <avr/pgmspace.h>
+#include <stdint.h>
+#include "analog.h"
+
+
+static uint8_t aref = (1<<REFS0); // default to AREF = Vcc
+
+
+void analogReference(uint8_t mode)
+{
+ aref = mode & 0xC0;
+}
+
+
+// Arduino compatible pin input
+int16_t analogRead(uint8_t pin)
+{
+#if defined(__AVR_ATmega32U4__)
+ static const uint8_t PROGMEM pin_to_mux[] = {
+ 0x00, 0x01, 0x04, 0x05, 0x06, 0x07,
+ 0x25, 0x24, 0x23, 0x22, 0x21, 0x20};
+ if (pin >= 12) return 0;
+ return adc_read(pgm_read_byte(pin_to_mux + pin));
+#elif defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__)
+ if (pin >= 8) return 0;
+ return adc_read(pin);
+#else
+ return 0;
+#endif
+}
+
+// Mux input
+int16_t adc_read(uint8_t mux)
+{
+#if defined(__AVR_AT90USB162__)
+ return 0;
+#else
+ uint8_t low;
+
+ ADCSRA = (1<<ADEN) | ADC_PRESCALER; // enable ADC
+ ADCSRB = (1<<ADHSM) | (mux & 0x20); // high speed mode
+ ADMUX = aref | (mux & 0x1F); // configure mux input
+ ADCSRA = (1<<ADEN) | ADC_PRESCALER | (1<<ADSC); // start the conversion
+ while (ADCSRA & (1<<ADSC)) ; // wait for result
+ low = ADCL; // must read LSB first
+ return (ADCH << 8) | low; // must read MSB only once!
+#endif
+}
+
+
diff --git a/keyboard/preonic/analog.h b/keyboard/preonic/analog.h
new file mode 100644
index 0000000000..9b95a93bef
--- /dev/null
+++ b/keyboard/preonic/analog.h
@@ -0,0 +1,36 @@
+#ifndef _analog_h_included__
+#define _analog_h_included__
+
+#include <stdint.h>
+
+void analogReference(uint8_t mode);
+int16_t analogRead(uint8_t pin);
+int16_t adc_read(uint8_t mux);
+
+#define ADC_REF_POWER (1<<REFS0)
+#define ADC_REF_INTERNAL ((1<<REFS1) | (1<<REFS0))
+#define ADC_REF_EXTERNAL (0)
+
+// These prescaler values are for high speed mode, ADHSM = 1
+#if F_CPU == 16000000L
+#define ADC_PRESCALER ((1<<ADPS2) | (1<<ADPS1))
+#elif F_CPU == 8000000L
+#define ADC_PRESCALER ((1<<ADPS2) | (1<<ADPS0))
+#elif F_CPU == 4000000L
+#define ADC_PRESCALER ((1<<ADPS2))
+#elif F_CPU == 2000000L
+#define ADC_PRESCALER ((1<<ADPS1) | (1<<ADPS0))
+#elif F_CPU == 1000000L
+#define ADC_PRESCALER ((1<<ADPS1))
+#else
+#define ADC_PRESCALER ((1<<ADPS0))
+#endif
+
+// some avr-libc versions do not properly define ADHSM
+#if defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__)
+#if !defined(ADHSM)
+#define ADHSM (7)
+#endif
+#endif
+
+#endif
diff --git a/keyboard/preonic/backlight.c b/keyboard/preonic/backlight.c
new file mode 100644
index 0000000000..f69364b2af
--- /dev/null
+++ b/keyboard/preonic/backlight.c
@@ -0,0 +1,61 @@
+
+#include <avr/io.h>
+#include "backlight.h"
+
+#define CHANNEL OCR1C
+
+void backlight_init_ports()
+{
+
+ // Setup PB7 as output and output low.
+ DDRB |= (1<<7);
+ PORTB &= ~(1<<7);
+
+ // Use full 16-bit resolution.
+ ICR1 = 0xFFFF;
+
+ // I could write a wall of text here to explain... but TL;DW
+ // Go read the ATmega32u4 datasheet.
+ // And this: http://blog.saikoled.com/post/43165849837/secret-konami-cheat-code-to-high-resolution-pwm-on
+
+ // Pin PB7 = OCR1C (Timer 1, Channel C)
+ // Compare Output Mode = Clear on compare match, Channel C = COM1C1=1 COM1C0=0
+ // (i.e. start high, go low when counter matches.)
+ // WGM Mode 14 (Fast PWM) = WGM13=1 WGM12=1 WGM11=1 WGM10=0
+ // Clock Select = clk/1 (no prescaling) = CS12=0 CS11=0 CS10=1
+
+ TCCR1A = _BV(COM1C1) | _BV(WGM11); // = 0b00001010;
+ TCCR1B = _BV(WGM13) | _BV(WGM12) | _BV(CS10); // = 0b00011001;
+
+ backlight_init();
+}
+
+void backlight_set(uint8_t level)
+{
+ if ( level == 0 )
+ {
+ // Turn off PWM control on PB7, revert to output low.
+ TCCR1A &= ~(_BV(COM1C1));
+ CHANNEL = 0x0;
+ // Prevent backlight blink on lowest level
+ PORTB &= ~(_BV(PORTB7));
+ }
+ else if ( level == BACKLIGHT_LEVELS )
+ {
+ // Prevent backlight blink on lowest level
+ PORTB &= ~(_BV(PORTB7));
+ // Turn on PWM control of PB7
+ TCCR1A |= _BV(COM1C1);
+ // Set the brightness
+ CHANNEL = 0xFFFF;
+ }
+ else
+ {
+ // Prevent backlight blink on lowest level
+ PORTB &= ~(_BV(PORTB7));
+ // Turn on PWM control of PB7
+ TCCR1A |= _BV(COM1C1);
+ // Set the brightness
+ CHANNEL = 0xFFFF >> ((BACKLIGHT_LEVELS - level) * ((BACKLIGHT_LEVELS + 1) / 2));
+ }
+} \ No newline at end of file
diff --git a/keyboard/preonic/beeps.c b/keyboard/preonic/beeps.c
new file mode 100644
index 0000000000..8ffd70f417
--- /dev/null
+++ b/keyboard/preonic/beeps.c
@@ -0,0 +1,246 @@
+#include "beeps.h"
+#include <math.h>
+#include <avr/pgmspace.h>
+#include <avr/interrupt.h>
+#include <avr/io.h>
+
+#define PI 3.14159265
+
+void delay_us(int count) {
+ while(count--) {
+ _delay_us(1);
+ }
+}
+
+int voices = 0;
+double frequency = 0;
+int volume = 0;
+int position = 0;
+
+double frequencies[8] = {0, 0, 0, 0, 0, 0, 0, 0};
+int volumes[8] = {0, 0, 0, 0, 0, 0, 0, 0};
+bool sliding = false;
+#define RANGE 1000
+volatile int i=0; //elements of the wave
+
+
+void beeps() {
+ play_notes();
+}
+
+void send_freq(double freq, int vol) {
+ int duty = (((double)F_CPU) / freq);
+ ICR3 = duty; // Set max to the period
+ OCR3A = duty >> (0x10 - vol); // Set compare to half the period
+}
+
+void stop_all_notes() {
+ voices = 0;
+ TCCR3A = 0;
+ TCCR3B = 0;
+ frequency = 0;
+ volume = 0;
+
+ for (int i = 0; i < 8; i++) {
+ frequencies[i] = 0;
+ volumes[i] = 0;
+ }
+}
+
+void stop_note(double freq) {
+ for (int i = 7; i >= 0; i--) {
+ if (frequencies[i] == freq) {
+ frequencies[i] = 0;
+ volumes[i] = 0;
+ for (int j = i; (j < 7); j++) {
+ frequencies[j] = frequencies[j+1];
+ frequencies[j+1] = 0;
+ volumes[j] = volumes[j+1];
+ volumes[j+1] = 0;
+ }
+ }
+ }
+ voices--;
+ if (voices < 0)
+ voices = 0;
+ if (voices == 0) {
+ TCCR3A = 0;
+ TCCR3B = 0;
+ frequency = 0;
+ volume = 0;
+ } else {
+ double freq = frequencies[voices - 1];
+ int vol = volumes[voices - 1];
+ if (frequency < freq) {
+ sliding = true;
+ for (double f = frequency; f <= freq; f += ((freq - frequency) / 500.0)) {
+ send_freq(f, vol);
+ }
+ sliding = false;
+ } else if (frequency > freq) {
+ sliding = true;
+ for (double f = frequency; f >= freq; f -= ((frequency - freq) / 500.0)) {
+ send_freq(f, vol);
+ }
+ sliding = false;
+ }
+ send_freq(freq, vol);
+ frequency = freq;
+ volume = vol;
+ }
+}
+
+void init_notes() {
+ // TCCR1A = (1 << COM1A1) | (0 << COM1A0) | (1 << WGM11) | (1 << WGM10);
+ // TCCR1B = (1 << COM1B1) | (0 << COM1A0) | (1 << WGM13) | (1 << WGM12) | (0 << CS12) | (0 << CS11) | (1 << CS10);
+
+ // DDRC |= (1<<6);
+
+ // TCCR3A = (1 << COM3A1) | (0 << COM3A0) | (1 << WGM31) | (0 << WGM30);
+ // TCCR3B = (1 << WGM33) | (1 << WGM32) | (0 << CS32) | (0 << CS31) | (1 << CS30);
+
+ // ICR3 = 0xFFFF;
+ // OCR3A = (int)((float)wave[i]*ICR3/RANGE); //go to next array element
+
+
+ // cli();
+
+ // /* Enable interrupt on timer2 == 127, with clk/8 prescaler. At 16MHz,
+ // this gives a timer interrupt at 15625Hz. */
+ // TIMSK3 = (1 << OCIE3A);
+
+ // /* clear/reset timer on match */
+ // // TCCR3A = 1<<WGM31 | 0<<WGM30; CTC mode, reset on match
+ // // TCCR3B = 0<<CS32 | 1<<CS31 | 0<<CS30; /* clk, /8 prescaler */
+
+ // TCCR3A = (1 << COM3A1) | (0 << COM3A0) | (1 << WGM31) | (0 << WGM30);
+ // TCCR3B = (0 << WGM33) | (0 << WGM32) | (0 << CS32) | (0 << CS31) | (1 << CS30);
+
+
+ // TCCR1A = (1 << COM1A1) | (0 << COM1A0) | (1 << WGM11) | (0 << WGM10);
+ // TCCR1B = (1 << WGM12) | (0 << CS12) | (0 << CS11) | (1 << CS10);
+ // // SPCR = 0x50;
+ // // SPSR = 0x01;
+ // DDRC |= (1<<6);
+ // // ICR3 = 0xFFFF;
+ // // OCR3A=80;
+ // PORTC |= (1<<6);
+
+ // sei();
+}
+
+// #define highByte(c) ((c >> 8) & 0x00FF)
+// #define lowByte(c) (c & 0x00FF)
+
+ISR(TIMER3_COMPA_vect) {
+
+ if (ICR3 > 0 && !sliding) {
+ switch (position) {
+ case 0: {
+ int duty = (((double)F_CPU) / (frequency));
+ ICR3 = duty; // Set max to the period
+ OCR3A = duty >> 1; // Set compare to half the period
+ break;
+ }
+ case 1: {
+ int duty = (((double)F_CPU) / (frequency*2));
+ ICR3 = duty; // Set max to the period
+ OCR3A = duty >> 1; // Set compare to half the period
+ break;
+ }
+ case 2: {
+ int duty = (((double)F_CPU) / (frequency*3));
+ ICR3 = duty; // Set max to the period
+ OCR3A = duty >> 1; // Set compare to half the period
+ break;
+ }
+ }
+ position = (position + 1) % 3;
+ }
+// /* OCR2A has been cleared, per TCCR2A above */
+// // OCR3A = 127;
+
+// // pos1 += incr1;
+// // pos2 += incr2;
+// // pos3 += incr3;
+
+// // sample = sinewave[highByte(pos1)] + sinewave[highByte(pos2)] + sinewave[highByte(pos3)];
+
+// // OCR3A = sample;
+
+
+// OCR3A=pgm_read_byte(&sinewave[pos1]);
+// pos1++;
+// // PORTC &= ~(1<<6);
+
+// /* buffered, 1x gain, active mode */
+// // SPDR = highByte(sample) | 0x70;
+// // while (!(SPSR & (1<<SPIF)));
+
+// // SPDR = lowByte(sample);
+// // while (!(SPSR & (1<<SPIF)));
+
+// // PORTC |= (1<<6);
+}
+
+void play_note(double freq, int vol) {
+
+ if (freq > 0) {
+ DDRC |= (1<<6);
+
+ TCCR3A = (1 << COM3A1) | (0 << COM3A0) | (1 << WGM31) | (0 << WGM30);
+ TCCR3B = (1 << WGM33) | (1 << WGM32) | (0 << CS32) | (1 << CS31) | (0 << CS30);
+
+ if (frequency != 0) {
+ if (frequency < freq) {
+ for (double f = frequency; f <= freq; f += ((freq - frequency) / 500.0)) {
+ send_freq(f, vol);
+ }
+ } else if (frequency > freq) {
+ for (double f = frequency; f >= freq; f -= ((frequency - freq) / 500.0)) {
+ send_freq(f, vol);
+ }
+ }
+ }
+ send_freq(freq, vol);
+ frequency = freq;
+ volume = vol;
+
+ frequencies[voices] = frequency;
+ volumes[voices] = volume;
+ voices++;
+ }
+ // ICR3 = 0xFFFF;
+ // for (int i = 0; i < 10000; i++) {
+ // OCR3A = round((sin(i*freq)*.5)+.5)*0xFFFF;
+ // // _delay_us(50);
+ // }
+
+ // TCCR3A = 0;
+ // TCCR3B = 0;
+}
+
+// void note(int x, float length) {
+// DDRC |= (1<<6);
+// int t = (int)(440*pow(2,-x/12.0)); // starting note
+// for (int y = 0; y < length*1000/t; y++) { // note length
+// PORTC |= (1<<6);
+// delay_us(t);
+// PORTC &= ~(1<<6);
+// delay_us(t);
+// }
+// PORTC &= ~(1<<6);
+// }
+
+// void true_note(float x, float y, float length) {
+// for (uint32_t i = 0; i < length * 50; i++) {
+// uint32_t v = (uint32_t) (round(sin(PI*2*i*640000*pow(2, x/12.0))*.5+1 + sin(PI*2*i*640000*pow(2, y/12.0))*.5+1) / 2 * pow(2, 8));
+// for (int u = 0; u < 8; u++) {
+// if (v & (1 << u) && !(PORTC&(1<<6)))
+// PORTC |= (1<<6);
+// else if (PORTC&(1<<6))
+// PORTC &= ~(1<<6);
+// }
+// }
+// PORTC &= ~(1<<6);
+// } \ No newline at end of file
diff --git a/keyboard/preonic/beeps.h b/keyboard/preonic/beeps.h
new file mode 100644
index 0000000000..378983c605
--- /dev/null
+++ b/keyboard/preonic/beeps.h
@@ -0,0 +1,12 @@
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/io.h>
+#include <util/delay.h>
+
+void note(int x, float length);
+void beeps();
+void true_note(float x, float y, float length);
+void play_note(double freq, int vol);
+void stop_note(double freq);
+void stop_all_notes();
+void init_notes(); \ No newline at end of file
diff --git a/keyboard/preonic/config.h b/keyboard/preonic/config.h
new file mode 100644
index 0000000000..cad269c9d4
--- /dev/null
+++ b/keyboard/preonic/config.h
@@ -0,0 +1,76 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef CONFIG_H
+#define CONFIG_H
+
+#include "config_definitions.h"
+
+/* USB Device descriptor parameter */
+#define VENDOR_ID 0xFEED
+#define PRODUCT_ID 0x6062
+#define DEVICE_VER 0x0001
+#define MANUFACTURER Ortholinear Keyboards
+#define PRODUCT The Preonic Keyboard
+#define DESCRIPTION A compact ortholinear keyboard
+
+/* key matrix size */
+#define MATRIX_ROWS 5
+#define MATRIX_COLS 12
+
+/* Planck PCB default pin-out */
+#define COLS (int []){ F1, F0, B0, C7, F4, F5, F6, F7, D4, D6, B4, D7 }
+#define ROWS (int []){ D1, D0, D5, B5, B6 }
+
+/* define if matrix has ghost */
+//#define MATRIX_HAS_GHOST
+
+/* number of backlight levels */
+#define BACKLIGHT_LEVELS 3
+
+/* Set 0 if debouncing isn't needed */
+#define DEBOUNCE 5
+
+/* Mechanical locking support. Use KC_LCAP, KC_LNUM or KC_LSCR instead in keymap */
+#define LOCKING_SUPPORT_ENABLE
+/* Locking resynchronize hack */
+#define LOCKING_RESYNC_ENABLE
+
+/* key combination for command */
+#define IS_COMMAND() ( \
+ keyboard_report->mods == (MOD_BIT(KC_LSHIFT) | MOD_BIT(KC_RSHIFT)) \
+)
+
+/*
+ * Feature disable options
+ * These options are also useful to firmware size reduction.
+ */
+
+/* disable debug print */
+#define NO_DEBUG
+
+/* disable print */
+#define NO_PRINT
+
+/* disable action features */
+//#define NO_ACTION_LAYER
+//#define NO_ACTION_TAPPING
+//#define NO_ACTION_ONESHOT
+//#define NO_ACTION_MACRO
+//#define NO_ACTION_FUNCTION
+
+#endif
diff --git a/keyboard/preonic/config_definitions.h b/keyboard/preonic/config_definitions.h
new file mode 100644
index 0000000000..fd138b8841
--- /dev/null
+++ b/keyboard/preonic/config_definitions.h
@@ -0,0 +1,50 @@
+#ifndef CONFIG_DEFINITIONS_H
+#define CONFIG_DEFINITIONS_H
+
+#define B0 0x20
+#define B1 0x21
+#define B2 0x22
+#define B3 0x23
+#define B4 0x24
+#define B5 0x25
+#define B6 0x26
+#define B7 0x27
+#define C0 0x30
+#define C1 0x31
+#define C2 0x32
+#define C3 0x33
+#define C4 0x34
+#define C5 0x35
+#define C6 0x36
+#define C7 0x37
+#define D0 0x40
+#define D1 0x41
+#define D2 0x42
+#define D3 0x43
+#define D4 0x44
+#define D5 0x45
+#define D6 0x46
+#define D7 0x47
+#define E0 0x50
+#define E1 0x51
+#define E2 0x52
+#define E3 0x53
+#define E4 0x54
+#define E5 0x55
+#define E6 0x56
+#define E7 0x57
+#define F0 0x60
+#define F1 0x61
+#define F2 0x62
+#define F3 0x63
+#define F4 0x64
+#define F5 0x65
+#define F6 0x66
+#define F7 0x67
+
+
+
+
+
+#endif
+
diff --git a/keyboard/preonic/extended_keymap_common.c b/keyboard/preonic/extended_keymap_common.c
new file mode 100644
index 0000000000..4fa80de7cf
--- /dev/null
+++ b/keyboard/preonic/extended_keymap_common.c
@@ -0,0 +1,216 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "extended_keymap_common.h"
+#include "report.h"
+#include "keycode.h"
+#include "action_layer.h"
+#include "action.h"
+#include "action_macro.h"
+#include "debug.h"
+#include "backlight.h"
+#include "keymap_midi.h"
+#include <lufa.h>
+
+static action_t keycode_to_action(uint16_t keycode);
+
+/* converts key to action */
+action_t action_for_key(uint8_t layer, keypos_t key)
+{
+ // 16bit keycodes - important
+ uint16_t keycode = keymap_key_to_keycode(layer, key);
+
+ if (keycode >= 0x0100 && keycode < 0x2000) {
+ // Has a modifier
+ action_t action;
+ // Split it up
+ action.code = ACTION_MODS_KEY(keycode >> 8, keycode & 0xFF);
+ return action;
+ } else if (keycode >= 0x2000 && keycode < 0x3000) {
+ // Is a shortcut for function layer, pull last 12bits
+ return keymap_func_to_action(keycode & 0xFFF);
+ } else if (keycode >= 0x3000 && keycode < 0x4000) {
+ action_t action;
+ action.code = ACTION_MACRO(keycode & 0xFF);
+ return action;
+ } else if (keycode >= BL_0 & keycode <= BL_15) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_LEVEL(keycode & 0x000F);
+ return action;
+ } else if (keycode == BL_DEC) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_DECREASE();
+ return action;
+ } else if (keycode == BL_INC) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_INCREASE();
+ return action;
+ } else if (keycode == BL_TOGG) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_TOGGLE();
+ return action;
+ } else if (keycode == BL_STEP) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_STEP();
+ return action;
+ } else if (keycode == RESET) {
+ bootloader_jump();
+ return;
+ } else if (keycode == DEBUG) {
+ print("\nDEBUG: enabled.\n");
+ debug_enable = true;
+ return;
+ } else if (keycode >= 0x6000 && keycode < 0x7000) {
+ action_t action;
+ action.code = ACTION_FUNCTION_OPT(keycode & 0xFF, (keycode & 0x0F00) >> 8);
+ return action;
+ }
+
+ switch (keycode) {
+ case KC_FN0 ... KC_FN31:
+ return keymap_fn_to_action(keycode);
+#ifdef BOOTMAGIC_ENABLE
+ case KC_CAPSLOCK:
+ case KC_LOCKING_CAPS:
+ if (keymap_config.swap_control_capslock || keymap_config.capslock_to_control) {
+ return keycode_to_action(KC_LCTL);
+ }
+ return keycode_to_action(keycode);
+ case KC_LCTL:
+ if (keymap_config.swap_control_capslock) {
+ return keycode_to_action(KC_CAPSLOCK);
+ }
+ return keycode_to_action(KC_LCTL);
+ case KC_LALT:
+ if (keymap_config.swap_lalt_lgui) {
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_LGUI);
+ }
+ return keycode_to_action(KC_LALT);
+ case KC_LGUI:
+ if (keymap_config.swap_lalt_lgui) {
+ return keycode_to_action(KC_LALT);
+ }
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_LGUI);
+ case KC_RALT:
+ if (keymap_config.swap_ralt_rgui) {
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_RGUI);
+ }
+ return keycode_to_action(KC_RALT);
+ case KC_RGUI:
+ if (keymap_config.swap_ralt_rgui) {
+ return keycode_to_action(KC_RALT);
+ }
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_RGUI);
+ case KC_GRAVE:
+ if (keymap_config.swap_grave_esc) {
+ return keycode_to_action(KC_ESC);
+ }
+ return keycode_to_action(KC_GRAVE);
+ case KC_ESC:
+ if (keymap_config.swap_grave_esc) {
+ return keycode_to_action(KC_GRAVE);
+ }
+ return keycode_to_action(KC_ESC);
+ case KC_BSLASH:
+ if (keymap_config.swap_backslash_backspace) {
+ return keycode_to_action(KC_BSPACE);
+ }
+ return keycode_to_action(KC_BSLASH);
+ case KC_BSPACE:
+ if (keymap_config.swap_backslash_backspace) {
+ return keycode_to_action(KC_BSLASH);
+ }
+ return keycode_to_action(KC_BSPACE);
+#endif
+ default:
+ return keycode_to_action(keycode);
+ }
+}
+
+
+/* Macro */
+__attribute__ ((weak))
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ return MACRO_NONE;
+}
+
+/* Function */
+__attribute__ ((weak))
+void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+}
+
+/* translates keycode to action */
+static action_t keycode_to_action(uint16_t keycode)
+{
+ action_t action;
+ switch (keycode) {
+ case KC_A ... KC_EXSEL:
+ case KC_LCTRL ... KC_RGUI:
+ action.code = ACTION_KEY(keycode);
+ break;
+ case KC_SYSTEM_POWER ... KC_SYSTEM_WAKE:
+ action.code = ACTION_USAGE_SYSTEM(KEYCODE2SYSTEM(keycode));
+ break;
+ case KC_AUDIO_MUTE ... KC_WWW_FAVORITES:
+ action.code = ACTION_USAGE_CONSUMER(KEYCODE2CONSUMER(keycode));
+ break;
+ case KC_MS_UP ... KC_MS_ACCEL2:
+ action.code = ACTION_MOUSEKEY(keycode);
+ break;
+ case KC_TRNS:
+ action.code = ACTION_TRANSPARENT;
+ break;
+ default:
+ action.code = ACTION_NO;
+ break;
+ }
+ return action;
+}
+
+
+/* translates key to keycode */
+uint16_t keymap_key_to_keycode(uint8_t layer, keypos_t key)
+{
+ // Read entire word (16bits)
+ return pgm_read_word(&keymaps[(layer)][(key.row)][(key.col)]);
+}
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint16_t keycode)
+{
+ return (action_t){ .code = pgm_read_word(&fn_actions[FN_INDEX(keycode)]) };
+}
+
+action_t keymap_func_to_action(uint16_t keycode)
+{
+ // For FUNC without 8bit limit
+ return (action_t){ .code = pgm_read_word(&fn_actions[(int)keycode]) };
+}
diff --git a/keyboard/preonic/extended_keymap_common.h b/keyboard/preonic/extended_keymap_common.h
new file mode 100644
index 0000000000..7ccfa1b039
--- /dev/null
+++ b/keyboard/preonic/extended_keymap_common.h
@@ -0,0 +1,181 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef KEYMAP_H
+#define KEYMAP_H
+
+#include <stdint.h>
+#include <stdbool.h>
+#include "action.h"
+#include <avr/pgmspace.h>
+#include "keycode.h"
+#include "keymap.h"
+#include "action_macro.h"
+#include "report.h"
+#include "host.h"
+// #include "print.h"
+#include "debug.h"
+
+#ifdef BOOTMAGIC_ENABLE
+/* NOTE: Not portable. Bit field order depends on implementation */
+typedef union {
+ uint16_t raw;
+ struct {
+ bool swap_control_capslock:1;
+ bool capslock_to_control:1;
+ bool swap_lalt_lgui:1;
+ bool swap_ralt_rgui:1;
+ bool no_gui:1;
+ bool swap_grave_esc:1;
+ bool swap_backslash_backspace:1;
+ bool nkro:1;
+ };
+} keymap_config_t;
+keymap_config_t keymap_config;
+#endif
+
+
+/* translates key to keycode */
+uint16_t keymap_key_to_keycode(uint8_t layer, keypos_t key);
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint16_t keycode);
+
+/* translates Fn keycode to action */
+action_t keymap_func_to_action(uint16_t keycode);
+
+extern const uint16_t keymaps[][MATRIX_ROWS][MATRIX_COLS];
+extern const uint16_t fn_actions[];
+
+// Ability to use mods in layouts
+#define LCTL(kc) kc | 0x0100
+#define LSFT(kc) kc | 0x0200
+#define LALT(kc) kc | 0x0400
+#define LGUI(kc) kc | 0x0800
+#define RCTL(kc) kc | 0x1100
+#define RSFT(kc) kc | 0x1200
+#define RALT(kc) kc | 0x1400
+#define RGUI(kc) kc | 0x1800
+
+// Alias for function layers than expand past FN31
+#define FUNC(kc) kc | 0x2000
+
+// Aliases
+#define S(kc) LSFT(kc)
+#define F(kc) FUNC(kc)
+
+// For software implementation of colemak
+#define CM_Q KC_Q
+#define CM_W KC_W
+#define CM_F KC_E
+#define CM_P KC_R
+#define CM_G KC_T
+#define CM_J KC_Y
+#define CM_L KC_U
+#define CM_U KC_I
+#define CM_Y KC_O
+#define CM_SCLN KC_P
+
+#define CM_A KC_A
+#define CM_R KC_S
+#define CM_S KC_D
+#define CM_T KC_F
+#define CM_D KC_G
+#define CM_H KC_H
+#define CM_N KC_J
+#define CM_E KC_K
+#define CM_I KC_L
+#define CM_O KC_SCLN
+
+#define CM_Z KC_Z
+#define CM_X KC_X
+#define CM_C KC_C
+#define CM_V KC_V
+#define CM_B KC_B
+#define CM_K KC_N
+#define CM_M KC_M
+#define CM_COMM KC_COMM
+#define CM_DOT KC_DOT
+#define CM_SLSH KC_SLSH
+
+// Make it easy to support these in macros
+#define KC_CM_Q CM_Q
+#define KC_CM_W CM_W
+#define KC_CM_F CM_F
+#define KC_CM_P CM_P
+#define KC_CM_G CM_G
+#define KC_CM_J CM_J
+#define KC_CM_L CM_L
+#define KC_CM_U CM_U
+#define KC_CM_Y CM_Y
+#define KC_CM_SCLN CM_SCLN
+
+#define KC_CM_A CM_A
+#define KC_CM_R CM_R
+#define KC_CM_S CM_S
+#define KC_CM_T CM_T
+#define KC_CM_D CM_D
+#define KC_CM_H CM_H
+#define KC_CM_N CM_N
+#define KC_CM_E CM_E
+#define KC_CM_I CM_I
+#define KC_CM_O CM_O
+
+#define KC_CM_Z CM_Z
+#define KC_CM_X CM_X
+#define KC_CM_C CM_C
+#define KC_CM_V CM_V
+#define KC_CM_B CM_B
+#define KC_CM_K CM_K
+#define KC_CM_M CM_M
+#define KC_CM_COMM CM_COMM
+#define KC_CM_DOT CM_DOT
+#define KC_CM_SLSH CM_SLSH
+
+#define M(kc) kc | 0x3000
+
+#define MACRODOWN(...) (record->event.pressed ? MACRO(__VA_ARGS__) : MACRO_NONE)
+
+#define BL_ON 0x4009
+#define BL_OFF 0x4000
+#define BL_0 0x4000
+#define BL_1 0x4001
+#define BL_2 0x4002
+#define BL_3 0x4003
+#define BL_4 0x4004
+#define BL_5 0x4005
+#define BL_6 0x4006
+#define BL_7 0x4007
+#define BL_8 0x4008
+#define BL_9 0x4009
+#define BL_10 0x400A
+#define BL_11 0x400B
+#define BL_12 0x400C
+#define BL_13 0x400D
+#define BL_14 0x400E
+#define BL_15 0x400F
+#define BL_DEC 0x4010
+#define BL_INC 0x4011
+#define BL_TOGG 0x4012
+#define BL_STEP 0x4013
+
+#define RESET 0x5000
+#define DEBUG 0x5001
+
+#define MIDI(n) n | 0x6000
+
+#endif
diff --git a/keyboard/preonic/extended_keymaps/extended_keymap_default.c b/keyboard/preonic/extended_keymaps/extended_keymap_default.c
new file mode 100644
index 0000000000..b52f60fd08
--- /dev/null
+++ b/keyboard/preonic/extended_keymaps/extended_keymap_default.c
@@ -0,0 +1,70 @@
+#include "extended_keymap_common.h"
+#include "backlight.h"
+#include "lufa.h"
+#include "debug.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_DEL},
+ {KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {M(0), KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Colemak */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_DEL},
+ {KC_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN3, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_DEL},
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), RESET, KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F11, KC_F12, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* LOWER */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_DEL},
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), RESET, KC_TRNS, KC_TRNS, KC_TRNS, S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), S(KC_BSLS)},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[4] = { /* TENKEY */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_DEL},
+ {KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_KP_7, KC_KP_8, KC_KP_9, KC_P, KC_BSPC},
+ {KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_KP_4, KC_KP_5, KC_KP_6, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_KP_1, KC_KP_2, KC_KP_3, KC_SLSH, KC_ENT},
+ {KC_TRNS, KC_LCTL, KC_LALT, KC_LGUI, KC_TRNS, KC_SPC, KC_SPC, KC_KP_0, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+}
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ if (record->event.pressed) {
+ register_code(KC_RSFT);
+ midi_send_noteon(&midi_device, 1, 64, 127);
+ backlight_step();
+ } else {
+ unregister_code(KC_RSFT);
+ midi_send_noteoff(&midi_device, 1, 64, 127);
+ }
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/preonic/extended_keymaps/extended_keymap_lock.c b/keyboard/preonic/extended_keymaps/extended_keymap_lock.c
new file mode 100644
index 0000000000..ec7bc776ac
--- /dev/null
+++ b/keyboard/preonic/extended_keymaps/extended_keymap_lock.c
@@ -0,0 +1,81 @@
+#include "extended_keymap_common.h"
+#include "backlight.h"
+#include "action_layer.h"
+#include "keymap_midi.h"
+#include "beeps.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = { /* Qwerty */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ {KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {M(0), KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+ // Space is repeated to accommadate for both spacebar wiring positions
+},
+[1] = { /* Colemak */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TAB, KC_Q, KC_W, KC_F, KC_P, KC_G, KC_J, KC_L, KC_U, KC_Y, KC_SCLN, KC_BSPC},
+ {KC_ESC, KC_A, KC_R, KC_S, KC_T, KC_D, KC_H, KC_N, KC_E, KC_I, KC_O, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_K, KC_M, KC_COMM, KC_DOT, KC_SLSH, KC_ENT},
+ {KC_FN3, KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[2] = { /* RAISE */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), RESET, KC_TRNS, KC_TRNS, KC_TRNS, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_BSLS},
+ {KC_TRNS, KC_F11, KC_F12, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(1), KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[3] = { /* LOWER */
+ {KC_GRV, S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ {S(KC_GRV), S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ {KC_TRNS, FUNC(3), FUNC(4), RESET, KC_TRNS, KC_TRNS, KC_TRNS, S(KC_MINS), S(KC_EQL), S(KC_LBRC), S(KC_RBRC), S(KC_BSLS)},
+ {KC_TRNS, KC_F1, KC_F2, KC_F3, KC_F4, KC_F5, KC_F6, KC_F7, KC_F8, KC_F9, KC_F10, KC_TRNS},
+ {KC_TRNS, KC_TRNS, KC_TRNS, KC_TRNS, FUNC(2), KC_TRNS, KC_TRNS, KC_TRNS, KC_MNXT, KC_VOLD, KC_VOLU, KC_MPLY}
+},
+[4] = { /* TENKEY */
+ {KC_GRV, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_BSPC},
+ {KC_TAB, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_KP_7, KC_KP_8, KC_KP_9, KC_P, KC_BSPC},
+ {KC_ESC, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_KP_4, KC_KP_5, KC_KP_6, KC_SCLN, KC_QUOT},
+ {KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_KP_1, KC_KP_2, KC_KP_3, KC_SLSH, KC_ENT},
+ {KC_TRNS, KC_LCTL, KC_LALT, KC_LGUI, KC_TRNS, KC_SPC, KC_SPC, KC_KP_0, KC_LEFT, KC_DOWN, KC_UP, KC_RGHT}
+},
+[5] = {
+ { MIDI12 },
+ { MIDI12 },
+ { MIDI12 },
+ { MIDI12 },
+ {M(0), KC_LCTL, KC_LALT, KC_LGUI, FUNC(2), KC_SPC, KC_SPC, FUNC(1), MIDI, MIDI, MIDI, MIDI}
+}
+
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ switch(id) {
+ case 0:
+ if (record->event.pressed) {
+ // register_code(KC_RSFT);
+ backlight_set(BACKLIGHT_LEVELS);
+ default_layer_and(0);
+ default_layer_or((1<<5));
+ } else {
+ // unregister_code(KC_RSFT);
+ backlight_set(0);
+ default_layer_and(0);
+ default_layer_or(0);
+ }
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/preonic/keymap_midi.c b/keyboard/preonic/keymap_midi.c
new file mode 100644
index 0000000000..a0fa59990c
--- /dev/null
+++ b/keyboard/preonic/keymap_midi.c
@@ -0,0 +1,110 @@
+/*
+Copyright 2015 Jack Humbert <jack.humb@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "extended_keymap_common.h"
+#include "keymap_midi.h"
+#include <lufa.h>
+
+uint8_t starting_note = 0x0C;
+int offset = 7;
+
+void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ if (id != 0) {
+ if (record->event.pressed) {
+ midi_send_noteon(&midi_device, opt, (id & 0xFF), 127);
+ } else {
+ midi_send_noteoff(&midi_device, opt, (id & 0xFF), 127);
+ }
+ }
+
+ if (record->event.key.col == (MATRIX_COLS - 1) && record->event.key.row == (MATRIX_ROWS - 1)) {
+ if (record->event.pressed) {
+ starting_note++;
+ play_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[0 + offset])/12.0+(MATRIX_ROWS - 1)), 0xC);
+ midi_send_cc(&midi_device, 0, 0x7B, 0);
+ midi_send_cc(&midi_device, 1, 0x7B, 0);
+ midi_send_cc(&midi_device, 2, 0x7B, 0);
+ midi_send_cc(&midi_device, 3, 0x7B, 0);
+ midi_send_cc(&midi_device, 4, 0x7B, 0);
+ return;
+ } else {
+ stop_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[0 + offset])/12.0+(MATRIX_ROWS - 1)));
+ stop_all_notes();
+ return;
+ }
+ }
+ if (record->event.key.col == (MATRIX_COLS - 2) && record->event.key.row == (MATRIX_ROWS - 1)) {
+ if (record->event.pressed) {
+ starting_note--;
+ play_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[0 + offset])/12.0+(MATRIX_ROWS - 1)), 0xC);
+ midi_send_cc(&midi_device, 0, 0x7B, 0);
+ midi_send_cc(&midi_device, 1, 0x7B, 0);
+ midi_send_cc(&midi_device, 2, 0x7B, 0);
+ midi_send_cc(&midi_device, 3, 0x7B, 0);
+ midi_send_cc(&midi_device, 4, 0x7B, 0);
+ return;
+ } else {
+ stop_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[0 + offset])/12.0+(MATRIX_ROWS - 1)));
+ stop_all_notes();
+ return;
+ }
+ }
+
+ if (record->event.key.col == (MATRIX_COLS - 3) && record->event.key.row == (MATRIX_ROWS - 1) && record->event.pressed) {
+ offset++;
+ midi_send_cc(&midi_device, 0, 0x7B, 0);
+ midi_send_cc(&midi_device, 1, 0x7B, 0);
+ midi_send_cc(&midi_device, 2, 0x7B, 0);
+ midi_send_cc(&midi_device, 3, 0x7B, 0);
+ midi_send_cc(&midi_device, 4, 0x7B, 0);
+ stop_all_notes();
+ for (int i = 0; i <= 7; i++) {
+ play_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[i + offset])/12.0+(MATRIX_ROWS - 1)), 0xC);
+ _delay_us(80000);
+ stop_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[i + offset])/12.0+(MATRIX_ROWS - 1)));
+ _delay_us(8000);
+ }
+ return;
+ }
+ if (record->event.key.col == (MATRIX_COLS - 4) && record->event.key.row == (MATRIX_ROWS - 1) && record->event.pressed) {
+ offset--;
+ midi_send_cc(&midi_device, 0, 0x7B, 0);
+ midi_send_cc(&midi_device, 1, 0x7B, 0);
+ midi_send_cc(&midi_device, 2, 0x7B, 0);
+ midi_send_cc(&midi_device, 3, 0x7B, 0);
+ midi_send_cc(&midi_device, 4, 0x7B, 0);
+ stop_all_notes();
+ for (int i = 0; i <= 7; i++) {
+ play_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[i + offset])/12.0+(MATRIX_ROWS - 1)), 0xC);
+ _delay_us(80000);
+ stop_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[i + offset])/12.0+(MATRIX_ROWS - 1)));
+ _delay_us(8000);
+ }
+ return;
+ }
+
+ if (record->event.pressed) {
+ // midi_send_noteon(&midi_device, record->event.key.row, starting_note + SCALE[record->event.key.col], 127);
+ midi_send_noteon(&midi_device, 0, (starting_note + SCALE[record->event.key.col + offset])+12*(MATRIX_ROWS - record->event.key.row), 127);
+ play_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[record->event.key.col + offset])/12.0+(MATRIX_ROWS - record->event.key.row)), 0xF);
+ } else {
+ // midi_send_noteoff(&midi_device, record->event.key.row, starting_note + SCALE[record->event.key.col], 127);
+ midi_send_noteoff(&midi_device, 0, (starting_note + SCALE[record->event.key.col + offset])+12*(MATRIX_ROWS - record->event.key.row), 127);
+ stop_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[record->event.key.col + offset])/12.0+(MATRIX_ROWS - record->event.key.row)));
+ }
+} \ No newline at end of file
diff --git a/keyboard/preonic/keymap_midi.h b/keyboard/preonic/keymap_midi.h
new file mode 100644
index 0000000000..c5917f884e
--- /dev/null
+++ b/keyboard/preonic/keymap_midi.h
@@ -0,0 +1,220 @@
+/*
+Copyright 2015 Jack Humbert <jack.humb@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef KEYMAP_MIDI_H
+#define KEYMAP_MIDI_H
+
+#define MIDI 0x6000
+#define MIDI12 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000
+
+#define CHNL(note, channel) (note + (channel << 8))
+
+#define SCALE (int []){ 0 + (12*0), 2 + (12*0), 4 + (12*0), 5 + (12*0), 7 + (12*0), 9 + (12*0), 11 + (12*0), \
+ 0 + (12*1), 2 + (12*1), 4 + (12*1), 5 + (12*1), 7 + (12*1), 9 + (12*1), 11 + (12*1), \
+ 0 + (12*2), 2 + (12*2), 4 + (12*2), 5 + (12*2), 7 + (12*2), 9 + (12*2), 11 + (12*2), \
+ 0 + (12*3), 2 + (12*3), 4 + (12*3), 5 + (12*3), 7 + (12*3), 9 + (12*3), 11 + (12*3), \
+ 0 + (12*4), 2 + (12*4), 4 + (12*4), 5 + (12*4), 7 + (12*4), 9 + (12*4), 11 + (12*4), }
+
+#define N_CN1 (0x600C + (12 * -1) + 0 )
+#define N_CN1S (0x600C + (12 * -1) + 1 )
+#define N_DN1F (0x600C + (12 * -1) + 1 )
+#define N_DN1 (0x600C + (12 * -1) + 2 )
+#define N_DN1S (0x600C + (12 * -1) + 3 )
+#define N_EN1F (0x600C + (12 * -1) + 3 )
+#define N_EN1 (0x600C + (12 * -1) + 4 )
+#define N_FN1 (0x600C + (12 * -1) + 5 )
+#define N_FN1S (0x600C + (12 * -1) + 6 )
+#define N_GN1F (0x600C + (12 * -1) + 6 )
+#define N_GN1 (0x600C + (12 * -1) + 7 )
+#define N_GN1S (0x600C + (12 * -1) + 8 )
+#define N_AN1F (0x600C + (12 * -1) + 8 )
+#define N_AN1 (0x600C + (12 * -1) + 9 )
+#define N_AN1S (0x600C + (12 * -1) + 10)
+#define N_BN1F (0x600C + (12 * -1) + 10)
+#define N_BN1 (0x600C + (12 * -1) + 11)
+#define N_C0 (0x600C + (12 * 0) + 0 )
+#define N_C0S (0x600C + (12 * 0) + 1 )
+#define N_D0F (0x600C + (12 * 0) + 1 )
+#define N_D0 (0x600C + (12 * 0) + 2 )
+#define N_D0S (0x600C + (12 * 0) + 3 )
+#define N_E0F (0x600C + (12 * 0) + 3 )
+#define N_E0 (0x600C + (12 * 0) + 4 )
+#define N_F0 (0x600C + (12 * 0) + 5 )
+#define N_F0S (0x600C + (12 * 0) + 6 )
+#define N_G0F (0x600C + (12 * 0) + 6 )
+#define N_G0 (0x600C + (12 * 0) + 7 )
+#define N_G0S (0x600C + (12 * 0) + 8 )
+#define N_A0F (0x600C + (12 * 0) + 8 )
+#define N_A0 (0x600C + (12 * 0) + 9 )
+#define N_A0S (0x600C + (12 * 0) + 10)
+#define N_B0F (0x600C + (12 * 0) + 10)
+#define N_B0 (0x600C + (12 * 0) + 11)
+#define N_C1 (0x600C + (12 * 1) + 0 )
+#define N_C1S (0x600C + (12 * 1) + 1 )
+#define N_D1F (0x600C + (12 * 1) + 1 )
+#define N_D1 (0x600C + (12 * 1) + 2 )
+#define N_D1S (0x600C + (12 * 1) + 3 )
+#define N_E1F (0x600C + (12 * 1) + 3 )
+#define N_E1 (0x600C + (12 * 1) + 4 )
+#define N_F1 (0x600C + (12 * 1) + 5 )
+#define N_F1S (0x600C + (12 * 1) + 6 )
+#define N_G1F (0x600C + (12 * 1) + 6 )
+#define N_G1 (0x600C + (12 * 1) + 7 )
+#define N_G1S (0x600C + (12 * 1) + 8 )
+#define N_A1F (0x600C + (12 * 1) + 8 )
+#define N_A1 (0x600C + (12 * 1) + 9 )
+#define N_A1S (0x600C + (12 * 1) + 10)
+#define N_B1F (0x600C + (12 * 1) + 10)
+#define N_B1 (0x600C + (12 * 1) + 11)
+#define N_C2 (0x600C + (12 * 2) + 0 )
+#define N_C2S (0x600C + (12 * 2) + 1 )
+#define N_D2F (0x600C + (12 * 2) + 1 )
+#define N_D2 (0x600C + (12 * 2) + 2 )
+#define N_D2S (0x600C + (12 * 2) + 3 )
+#define N_E2F (0x600C + (12 * 2) + 3 )
+#define N_E2 (0x600C + (12 * 2) + 4 )
+#define N_F2 (0x600C + (12 * 2) + 5 )
+#define N_F2S (0x600C + (12 * 2) + 6 )
+#define N_G2F (0x600C + (12 * 2) + 6 )
+#define N_G2 (0x600C + (12 * 2) + 7 )
+#define N_G2S (0x600C + (12 * 2) + 8 )
+#define N_A2F (0x600C + (12 * 2) + 8 )
+#define N_A2 (0x600C + (12 * 2) + 9 )
+#define N_A2S (0x600C + (12 * 2) + 10)
+#define N_B2F (0x600C + (12 * 2) + 10)
+#define N_B2 (0x600C + (12 * 2) + 11)
+#define N_C3 (0x600C + (12 * 3) + 0 )
+#define N_C3S (0x600C + (12 * 3) + 1 )
+#define N_D3F (0x600C + (12 * 3) + 1 )
+#define N_D3 (0x600C + (12 * 3) + 2 )
+#define N_D3S (0x600C + (12 * 3) + 3 )
+#define N_E3F (0x600C + (12 * 3) + 3 )
+#define N_E3 (0x600C + (12 * 3) + 4 )
+#define N_F3 (0x600C + (12 * 3) + 5 )
+#define N_F3S (0x600C + (12 * 3) + 6 )
+#define N_G3F (0x600C + (12 * 3) + 6 )
+#define N_G3 (0x600C + (12 * 3) + 7 )
+#define N_G3S (0x600C + (12 * 3) + 8 )
+#define N_A3F (0x600C + (12 * 3) + 8 )
+#define N_A3 (0x600C + (12 * 3) + 9 )
+#define N_A3S (0x600C + (12 * 3) + 10)
+#define N_B3F (0x600C + (12 * 3) + 10)
+#define N_B3 (0x600C + (12 * 3) + 11)
+#define N_C4 (0x600C + (12 * 4) + 0 )
+#define N_C4S (0x600C + (12 * 4) + 1 )
+#define N_D4F (0x600C + (12 * 4) + 1 )
+#define N_D4 (0x600C + (12 * 4) + 2 )
+#define N_D4S (0x600C + (12 * 4) + 3 )
+#define N_E4F (0x600C + (12 * 4) + 3 )
+#define N_E4 (0x600C + (12 * 4) + 4 )
+#define N_F4 (0x600C + (12 * 4) + 5 )
+#define N_F4S (0x600C + (12 * 4) + 6 )
+#define N_G4F (0x600C + (12 * 4) + 6 )
+#define N_G4 (0x600C + (12 * 4) + 7 )
+#define N_G4S (0x600C + (12 * 4) + 8 )
+#define N_A4F (0x600C + (12 * 4) + 8 )
+#define N_A4 (0x600C + (12 * 4) + 9 )
+#define N_A4S (0x600C + (12 * 4) + 10)
+#define N_B4F (0x600C + (12 * 4) + 10)
+#define N_B4 (0x600C + (12 * 4) + 11)
+#define N_C5 (0x600C + (12 * 5) + 0 )
+#define N_C5S (0x600C + (12 * 5) + 1 )
+#define N_D5F (0x600C + (12 * 5) + 1 )
+#define N_D5 (0x600C + (12 * 5) + 2 )
+#define N_D5S (0x600C + (12 * 5) + 3 )
+#define N_E5F (0x600C + (12 * 5) + 3 )
+#define N_E5 (0x600C + (12 * 5) + 4 )
+#define N_F5 (0x600C + (12 * 5) + 5 )
+#define N_F5S (0x600C + (12 * 5) + 6 )
+#define N_G5F (0x600C + (12 * 5) + 6 )
+#define N_G5 (0x600C + (12 * 5) + 7 )
+#define N_G5S (0x600C + (12 * 5) + 8 )
+#define N_A5F (0x600C + (12 * 5) + 8 )
+#define N_A5 (0x600C + (12 * 5) + 9 )
+#define N_A5S (0x600C + (12 * 5) + 10)
+#define N_B5F (0x600C + (12 * 5) + 10)
+#define N_B5 (0x600C + (12 * 5) + 11)
+#define N_C6 (0x600C + (12 * 6) + 0 )
+#define N_C6S (0x600C + (12 * 6) + 1 )
+#define N_D6F (0x600C + (12 * 6) + 1 )
+#define N_D6 (0x600C + (12 * 6) + 2 )
+#define N_D6S (0x600C + (12 * 6) + 3 )
+#define N_E6F (0x600C + (12 * 6) + 3 )
+#define N_E6 (0x600C + (12 * 6) + 4 )
+#define N_F6 (0x600C + (12 * 6) + 5 )
+#define N_F6S (0x600C + (12 * 6) + 6 )
+#define N_G6F (0x600C + (12 * 6) + 6 )
+#define N_G6 (0x600C + (12 * 6) + 7 )
+#define N_G6S (0x600C + (12 * 6) + 8 )
+#define N_A6F (0x600C + (12 * 6) + 8 )
+#define N_A6 (0x600C + (12 * 6) + 9 )
+#define N_A6S (0x600C + (12 * 6) + 10)
+#define N_B6F (0x600C + (12 * 6) + 10)
+#define N_B6 (0x600C + (12 * 6) + 11)
+#define N_C7 (0x600C + (12 * 7) + 0 )
+#define N_C7S (0x600C + (12 * 7) + 1 )
+#define N_D7F (0x600C + (12 * 7) + 1 )
+#define N_D7 (0x600C + (12 * 7) + 2 )
+#define N_D7S (0x600C + (12 * 7) + 3 )
+#define N_E7F (0x600C + (12 * 7) + 3 )
+#define N_E7 (0x600C + (12 * 7) + 4 )
+#define N_F7 (0x600C + (12 * 7) + 5 )
+#define N_F7S (0x600C + (12 * 7) + 6 )
+#define N_G7F (0x600C + (12 * 7) + 6 )
+#define N_G7 (0x600C + (12 * 7) + 7 )
+#define N_G7S (0x600C + (12 * 7) + 8 )
+#define N_A7F (0x600C + (12 * 7) + 8 )
+#define N_A7 (0x600C + (12 * 7) + 9 )
+#define N_A7S (0x600C + (12 * 7) + 10)
+#define N_B7F (0x600C + (12 * 7) + 10)
+#define N_B7 (0x600C + (12 * 7) + 11)
+#define N_C8 (0x600C + (12 * 8) + 0 )
+#define N_C8S (0x600C + (12 * 8) + 1 )
+#define N_D8F (0x600C + (12 * 8) + 1 )
+#define N_D8 (0x600C + (12 * 8) + 2 )
+#define N_D8S (0x600C + (12 * 8) + 3 )
+#define N_E8F (0x600C + (12 * 8) + 3 )
+#define N_E8 (0x600C + (12 * 8) + 4 )
+#define N_F8 (0x600C + (12 * 8) + 5 )
+#define N_F8S (0x600C + (12 * 8) + 6 )
+#define N_G8F (0x600C + (12 * 8) + 6 )
+#define N_G8 (0x600C + (12 * 8) + 7 )
+#define N_G8S (0x600C + (12 * 8) + 8 )
+#define N_A8F (0x600C + (12 * 8) + 8 )
+#define N_A8 (0x600C + (12 * 8) + 9 )
+#define N_A8S (0x600C + (12 * 8) + 10)
+#define N_B8F (0x600C + (12 * 8) + 10)
+#define N_B8 (0x600C + (12 * 8) + 11)
+#define N_C8 (0x600C + (12 * 8) + 0 )
+#define N_C8S (0x600C + (12 * 8) + 1 )
+#define N_D8F (0x600C + (12 * 8) + 1 )
+#define N_D8 (0x600C + (12 * 8) + 2 )
+#define N_D8S (0x600C + (12 * 8) + 3 )
+#define N_E8F (0x600C + (12 * 8) + 3 )
+#define N_E8 (0x600C + (12 * 8) + 4 )
+#define N_F8 (0x600C + (12 * 8) + 5 )
+#define N_F8S (0x600C + (12 * 8) + 6 )
+#define N_G8F (0x600C + (12 * 8) + 6 )
+#define N_G8 (0x600C + (12 * 8) + 7 )
+#define N_G8S (0x600C + (12 * 8) + 8 )
+#define N_A8F (0x600C + (12 * 8) + 8 )
+#define N_A8 (0x600C + (12 * 8) + 9 )
+#define N_A8S (0x600C + (12 * 8) + 10)
+#define N_B8F (0x600C + (12 * 8) + 10)
+#define N_B8 (0x600C + (12 * 8) + 11)
+
+#endif \ No newline at end of file
diff --git a/keyboard/preonic/led.c b/keyboard/preonic/led.c
new file mode 100644
index 0000000000..2c05746607
--- /dev/null
+++ b/keyboard/preonic/led.c
@@ -0,0 +1,38 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include <avr/io.h>
+#include "stdint.h"
+#include "led.h"
+
+
+void led_set(uint8_t usb_led)
+{
+ // // Using PE6 Caps Lock LED
+ // if (usb_led & (1<<USB_LED_CAPS_LOCK))
+ // {
+ // // Output high.
+ // DDRE |= (1<<6);
+ // PORTE |= (1<<6);
+ // }
+ // else
+ // {
+ // // Output low.
+ // DDRE &= ~(1<<6);
+ // PORTE &= ~(1<<6);
+ // }
+}
diff --git a/keyboard/preonic/matrix.c b/keyboard/preonic/matrix.c
new file mode 100644
index 0000000000..98ef55ed68
--- /dev/null
+++ b/keyboard/preonic/matrix.c
@@ -0,0 +1,234 @@
+/*
+Copyright 2012 Jun Wako
+Generated by planckkeyboard.com (2014 Jack Humbert)
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+/*
+ * scan matrix
+ */
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/io.h>
+#include <util/delay.h>
+#include "print.h"
+#include "debug.h"
+#include "util.h"
+#include "matrix.h"
+
+#ifndef DEBOUNCE
+# define DEBOUNCE 10
+#endif
+static uint8_t debouncing = DEBOUNCE;
+
+/* matrix state(1:on, 0:off) */
+static matrix_row_t matrix[MATRIX_ROWS];
+static matrix_row_t matrix_debouncing[MATRIX_ROWS];
+
+static matrix_row_t read_cols(void);
+static void init_cols(void);
+static void unselect_rows(void);
+static void select_row(uint8_t row);
+
+inline
+uint8_t matrix_rows(void)
+{
+ return MATRIX_ROWS;
+}
+
+inline
+uint8_t matrix_cols(void)
+{
+ return MATRIX_COLS;
+}
+
+void matrix_init(void)
+{
+ // To use PORTF disable JTAG with writing JTD bit twice within four cycles.
+ MCUCR |= (1<<JTD);
+ MCUCR |= (1<<JTD);
+
+ backlight_init_ports();
+
+ // Turn status LED on
+ DDRE |= (1<<6);
+ PORTE |= (1<<6);
+
+ // initialize row and col
+ unselect_rows();
+ init_cols();
+
+ // initialize matrix state: all keys off
+ for (uint8_t i=0; i < MATRIX_ROWS; i++) {
+ matrix[i] = 0;
+ matrix_debouncing[i] = 0;
+ }
+}
+
+
+uint8_t matrix_scan(void)
+{
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ select_row(i);
+ _delay_us(30); // without this wait read unstable value.
+ matrix_row_t cols = read_cols();
+ if (matrix_debouncing[i] != cols) {
+ matrix_debouncing[i] = cols;
+ if (debouncing) {
+ debug("bounce!: "); debug_hex(debouncing); debug("\n");
+ }
+ debouncing = DEBOUNCE;
+ }
+ unselect_rows();
+ }
+
+ if (debouncing) {
+ if (--debouncing) {
+ _delay_ms(1);
+ } else {
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ matrix[i] = matrix_debouncing[i];
+ }
+ }
+ }
+
+ return 1;
+}
+
+bool matrix_is_modified(void)
+{
+ if (debouncing) return false;
+ return true;
+}
+
+inline
+bool matrix_is_on(uint8_t row, uint8_t col)
+{
+ return (matrix[row] & ((matrix_row_t)1<col));
+}
+
+inline
+matrix_row_t matrix_get_row(uint8_t row)
+{
+ return matrix[row];
+}
+
+void matrix_print(void)
+{
+ print("\nr/c 0123456789ABCDEF\n");
+ for (uint8_t row = 0; row < MATRIX_ROWS; row++) {
+ phex(row); print(": ");
+ pbin_reverse16(matrix_get_row(row));
+ print("\n");
+ }
+}
+
+uint8_t matrix_key_count(void)
+{
+ uint8_t count = 0;
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ count += bitpop16(matrix[i]);
+ }
+ return count;
+}
+
+static void init_cols(void)
+{
+ int B = 0, C = 0, D = 0, E = 0, F = 0;
+ for(int x = 0; x < MATRIX_COLS; x++) {
+ int col = COLS[x];
+ if ((col & 0xF0) == 0x20) {
+ B |= (1<<(col & 0x0F));
+ } else if ((col & 0xF0) == 0x30) {
+ C |= (1<<(col & 0x0F));
+ } else if ((col & 0xF0) == 0x40) {
+ D |= (1<<(col & 0x0F));
+ } else if ((col & 0xF0) == 0x50) {
+ E |= (1<<(col & 0x0F));
+ } else if ((col & 0xF0) == 0x60) {
+ F |= (1<<(col & 0x0F));
+ }
+ }
+ DDRB &= ~(B); PORTB |= (B);
+ DDRC &= ~(C); PORTC |= (C);
+ DDRD &= ~(D); PORTD |= (D);
+ DDRE &= ~(E); PORTE |= (E);
+ DDRF &= ~(F); PORTF |= (F);
+}
+
+static matrix_row_t read_cols(void)
+{
+ matrix_row_t result = 0;
+ for(int x = 0; x < MATRIX_COLS; x++) {
+ int col = COLS[x];
+ if ((col & 0xF0) == 0x20) {
+ result |= (PINB&(1<<(col & 0x0F)) ? 0 : (1<<x));
+ } else if ((col & 0xF0) == 0x30) {
+ result |= (PINC&(1<<(col & 0x0F)) ? 0 : (1<<x));
+ } else if ((col & 0xF0) == 0x40) {
+ result |= (PIND&(1<<(col & 0x0F)) ? 0 : (1<<x));
+ } else if ((col & 0xF0) == 0x50) {
+ result |= (PINE&(1<<(col & 0x0F)) ? 0 : (1<<x));
+ } else if ((col & 0xF0) == 0x60) {
+ result |= (PINF&(1<<(col & 0x0F)) ? 0 : (1<<x));
+ }
+ }
+ return result;
+}
+
+static void unselect_rows(void)
+{
+ int B = 0, C = 0, D = 0, E = 0, F = 0;
+ for(int x = 0; x < MATRIX_ROWS; x++) {
+ int row = ROWS[x];
+ if ((row & 0xF0) == 0x20) {
+ B |= (1<<(row & 0x0F));
+ } else if ((row & 0xF0) == 0x30) {
+ C |= (1<<(row & 0x0F));
+ } else if ((row & 0xF0) == 0x40) {
+ D |= (1<<(row & 0x0F));
+ } else if ((row & 0xF0) == 0x50) {
+ E |= (1<<(row & 0x0F));
+ } else if ((row & 0xF0) == 0x60) {
+ F |= (1<<(row & 0x0F));
+ }
+ }
+ DDRB &= ~(B); PORTB |= (B);
+ DDRC &= ~(C); PORTC |= (C);
+ DDRD &= ~(D); PORTD |= (D);
+ DDRE &= ~(E); PORTE |= (E);
+ DDRF &= ~(F); PORTF |= (F);
+}
+
+static void select_row(uint8_t row)
+{
+ int row_pin = ROWS[row];
+ if ((row_pin & 0xF0) == 0x20) {
+ DDRB |= (1<<(row_pin & 0x0F));
+ PORTB &= ~(1<<(row_pin & 0x0F));
+ } else if ((row_pin & 0xF0) == 0x30) {
+ DDRC |= (1<<(row_pin & 0x0F));
+ PORTC &= ~(1<<(row_pin & 0x0F));
+ } else if ((row_pin & 0xF0) == 0x40) {
+ DDRD |= (1<<(row_pin & 0x0F));
+ PORTD &= ~(1<<(row_pin & 0x0F));
+ } else if ((row_pin & 0xF0) == 0x50) {
+ DDRE |= (1<<(row_pin & 0x0F));
+ PORTE &= ~(1<<(row_pin & 0x0F));
+ } else if ((row_pin & 0xF0) == 0x60) {
+ DDRF |= (1<<(row_pin & 0x0F));
+ PORTF &= ~(1<<(row_pin & 0x0F));
+ }
+} \ No newline at end of file
diff --git a/keyboard/quark/Makefile b/keyboard/quark/Makefile
new file mode 100644
index 0000000000..f79445e23b
--- /dev/null
+++ b/keyboard/quark/Makefile
@@ -0,0 +1,155 @@
+#----------------------------------------------------------------------------
+# On command line:
+#
+# make all = Make software.
+#
+# make clean = Clean out built project files.
+#
+# make coff = Convert ELF to AVR COFF.
+#
+# make extcoff = Convert ELF to AVR Extended COFF.
+#
+# make program = Download the hex file to the device.
+# Please customize your programmer settings(PROGRAM_CMD)
+#
+# make teensy = Download the hex file to the device, using teensy_loader_cli.
+# (must have teensy_loader_cli installed).
+#
+# make dfu = Download the hex file to the device, using dfu-programmer (must
+# have dfu-programmer installed).
+#
+# make flip = Download the hex file to the device, using Atmel FLIP (must
+# have Atmel FLIP installed).
+#
+# make dfu-ee = Download the eeprom file to the device, using dfu-programmer
+# (must have dfu-programmer installed).
+#
+# make flip-ee = Download the eeprom file to the device, using Atmel FLIP
+# (must have Atmel FLIP installed).
+#
+# make debug = Start either simulavr or avarice as specified for debugging,
+# with avr-gdb or avr-insight as the front end for debugging.
+#
+# make filename.s = Just compile filename.c into the assembler code only.
+#
+# make filename.i = Create a preprocessed source file for use in submitting
+# bug reports to the GCC project.
+#
+# To rebuild project do "make clean" then "make all".
+#----------------------------------------------------------------------------
+
+# Target file name (without extension).
+TARGET = quark_lufa
+
+# Directory common source filess exist
+TOP_DIR = ../..
+
+# Directory keyboard dependent files exist
+TARGET_DIR = .
+
+
+
+# # project specific files
+ifdef COMMON
+
+ SRC = keymap_common.c \
+ matrix.c \
+ led.c \
+ backlight.c
+
+ifdef KEYMAP
+ SRC := common_keymaps/keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := common_keymaps/keymap_jack.c $(SRC)
+endif
+
+else
+
+SRC = extended_keymap_common.c \
+ matrix.c \
+ led.c \
+ backlight.c
+
+ifdef KEYMAP
+ SRC := extended_keymaps/extended_keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := extended_keymaps/extended_keymap_default.c $(SRC)
+endif
+
+endif
+
+CONFIG_H = config.h
+
+# MCU name
+#MCU = at90usb1287
+MCU = atmega32u4
+
+# Processor frequency.
+# This will define a symbol, F_CPU, in all source code files equal to the
+# processor frequency in Hz. You can then use this symbol in your source code to
+# calculate timings. Do NOT tack on a 'UL' at the end, this will be done
+# automatically to create a 32-bit value in your source code.
+#
+# This will be an integer division of F_USB below, as it is sourced by
+# F_USB after it has run through any CPU prescalers. Note that this value
+# does not *change* the processor frequency - it should merely be updated to
+# reflect the processor speed set externally so that the code can use accurate
+# software delays.
+F_CPU = 16000000
+
+
+#
+# LUFA specific
+#
+# Target architecture (see library "Board Types" documentation).
+ARCH = AVR8
+
+# Input clock frequency.
+# This will define a symbol, F_USB, in all source code files equal to the
+# input clock frequency (before any prescaling is performed) in Hz. This value may
+# differ from F_CPU if prescaling is used on the latter, and is required as the
+# raw input clock is fed directly to the PLL sections of the AVR for high speed
+# clock generation for the USB and other AVR subsections. Do NOT tack on a 'UL'
+# at the end, this will be done automatically to create a 32-bit value in your
+# source code.
+#
+# If no clock division is performed on the input clock inside the AVR (via the
+# CPU clock adjust registers or the clock division fuses), this will be equal to F_CPU.
+F_USB = $(F_CPU)
+
+# Interrupt driven control endpoint task(+60)
+OPT_DEFS += -DINTERRUPT_CONTROL_ENDPOINT
+
+
+# Boot Section Size in *bytes*
+# Teensy halfKay 512
+# Teensy++ halfKay 1024
+# Atmel DFU loader 4096
+# LUFA bootloader 4096
+# USBaspLoader 2048
+OPT_DEFS += -DBOOTLOADER_SIZE=4096
+
+
+# Build Options
+# comment out to disable the options.
+#
+BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration(+1000)
+MOUSEKEY_ENABLE = yes # Mouse keys(+4700)
+EXTRAKEY_ENABLE = yes # Audio control and System control(+450)
+CONSOLE_ENABLE = yes # Console for debug(+400)
+COMMAND_ENABLE = yes # Commands for debug and configuration
+# Do not enable SLEEP_LED_ENABLE. it uses the same timer as BACKLIGHT_ENABLE
+#SLEEP_LED_ENABLE = yes # Breathing sleep LED during USB suspend
+NKRO_ENABLE = yes # USB Nkey Rollover - not yet supported in LUFA
+BACKLIGHT_ENABLE = yes # Enable keyboard backlight functionality
+
+# Optimize size but this may cause error "relocation truncated to fit"
+#EXTRALDFLAGS = -Wl,--relax
+
+# Search Path
+VPATH += $(TARGET_DIR)
+VPATH += $(TOP_DIR)
+
+include $(TOP_DIR)/protocol/lufa.mk
+include $(TOP_DIR)/common.mk
+include $(TOP_DIR)/rules.mk
diff --git a/keyboard/quark/Makefile.pjrc b/keyboard/quark/Makefile.pjrc
new file mode 100644
index 0000000000..be83ba18b1
--- /dev/null
+++ b/keyboard/quark/Makefile.pjrc
@@ -0,0 +1,116 @@
+#----------------------------------------------------------------------------
+# On command line:
+#
+# make all = Make software.
+#
+# make clean = Clean out built project files.
+#
+# make coff = Convert ELF to AVR COFF.
+#
+# make extcoff = Convert ELF to AVR Extended COFF.
+#
+# make program = Download the hex file to the device.
+# Please customize your programmer settings(PROGRAM_CMD)
+#
+# make teensy = Download the hex file to the device, using teensy_loader_cli.
+# (must have teensy_loader_cli installed).
+#
+# make dfu = Download the hex file to the device, using dfu-programmer (must
+# have dfu-programmer installed).
+#
+# make flip = Download the hex file to the device, using Atmel FLIP (must
+# have Atmel FLIP installed).
+#
+# make dfu-ee = Download the eeprom file to the device, using dfu-programmer
+# (must have dfu-programmer installed).
+#
+# make flip-ee = Download the eeprom file to the device, using Atmel FLIP
+# (must have Atmel FLIP installed).
+#
+# make debug = Start either simulavr or avarice as specified for debugging,
+# with avr-gdb or avr-insight as the front end for debugging.
+#
+# make filename.s = Just compile filename.c into the assembler code only.
+#
+# make filename.i = Create a preprocessed source file for use in submitting
+# bug reports to the GCC project.
+#
+# To rebuild project do "make clean" then "make all".
+#----------------------------------------------------------------------------
+
+# Target file name (without extension).
+TARGET = gh60_pjrc
+
+# Directory common source filess exist
+TOP_DIR = ../..
+
+# Directory keyboard dependent files exist
+TARGET_DIR = .
+
+# project specific files
+SRC = keymap_common.c \
+ matrix.c \
+ led.c
+
+ifdef KEYMAP
+ SRC := keymap_$(KEYMAP).c $(SRC)
+else
+ SRC := keymap_jack.c $(SRC)
+endif
+
+CONFIG_H = config.h
+
+
+# MCU name, you MUST set this to match the board you are using
+# type "make clean" after changing this, so all files will be rebuilt
+MCU = atmega32u4
+#MCU = at90usb1286
+
+
+# Processor frequency.
+# Normally the first thing your program should do is set the clock prescaler,
+# so your program will run at the correct speed. You should also set this
+# variable to same clock speed. The _delay_ms() macro uses this, and many
+# examples use this variable to calculate timings. Do not add a "UL" here.
+F_CPU = 16000000
+
+
+# Boot Section Size in *bytes*
+# Teensy halfKay 512
+# Atmel DFU loader 4096
+# LUFA bootloader 4096
+OPT_DEFS += -DBOOTLOADER_SIZE=4096
+
+
+# Build Options
+# comment out to disable the options.
+#
+BOOTMAGIC_ENABLE = yes # Virtual DIP switch configuration(+1000)
+MOUSEKEY_ENABLE = yes # Mouse keys(+5000)
+EXTRAKEY_ENABLE = yes # Audio control and System control(+600)
+CONSOLE_ENABLE = yes # Console for debug
+COMMAND_ENABLE = yes # Commands for debug and configuration
+SLEEP_LED_ENABLE = yes # Breathing sleep LED during USB suspend
+NKRO_ENABLE = yes # USB Nkey Rollover(+500)
+#PS2_MOUSE_ENABLE = yes # PS/2 mouse(TrackPoint) support
+
+
+# Search Path
+VPATH += $(TARGET_DIR)
+VPATH += $(TOP_DIR)
+
+include $(TOP_DIR)/protocol/pjrc.mk
+include $(TOP_DIR)/common.mk
+include $(TOP_DIR)/rules.mk
+
+plain: OPT_DEFS += -DKEYMAP_PLAIN
+plain: all
+
+poker: OPT_DEFS += -DKEYMAP_POKER
+poker: all
+
+poker_set: OPT_DEFS += -DKEYMAP_POKER_SET
+poker_set: all
+
+poker_bit: OPT_DEFS += -DKEYMAP_POKER_BIT
+poker_bit: all
diff --git a/keyboard/quark/README.md b/keyboard/quark/README.md
new file mode 100644
index 0000000000..59afbab1ae
--- /dev/null
+++ b/keyboard/quark/README.md
@@ -0,0 +1,53 @@
+Quark keyboard firmware
+======================
+DIY/Assembled compact 40% keyboard by [Ortholinear Keyboards](http://ortholinearkeyboards.com).
+
+## Extended Keymap
+If you include extended_keymap_common.h instead of keymap_common.h at the top of your file, you'll have access to a bunch of goodies:
+
+- Use `LSFT()`, `LCTL()`, et. al. (listed in extended_keymap_common.h) as modifiers for keys (daisy-chain-able)
+- Use `FUNC(1)` instead of `FN1` (etc.) to access the function layers beyond the 32 function layer limit
+- Use `CM_F` instead of `KC_F` to get the ColeMak equivilent for shortcuts (maps backwards)
+- Use `MACRODOWN()` instead of `MACRO()` to easily make a keydown macro (`CM_*` works here too)
+
+### Some notes on usage:
+
+- The `KEYMAP()` macro is unable to be used due to the bitwise modifications that take place - refer to extended_keymap_jack.c to see how to set things up with the `KC_` prefix
+- Keep an eye on the Makefile - this needs to include the correct files to work
+- Don't forget to use `const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {` instead of the 8bit equivilent
+
+## Build
+
+Follow [this guide](http://deskthority.net/workshop-f7/how-to-build-your-very-own-keyboard-firmware-t7177.html) to setup your development environment before anything else. Abbreviated instructions are provide at the [bottom of this document](https://github.com/rswiernik/tmk_keyboard/tree/rswiernik_dev/keyboard/quark#environment-setup)
+
+Download the whole firmware [here](https://github.com/jackhumbert/tmk_keyboard/archive/master.zip) and navigate to the keyboard/quark folder. Once your dev env is setup, you'll be able to type `make` to generate your .hex that you can load with the Teensy app onto your Planck (once you've hit reset/shorted GND & RST).
+
+Depending on which keymap you would like to use, you will have to compile slightly differently.
+
+####Default
+To build with the default keymap, simply move to the tmk\_keyboard/keyboard/quark/ and run `make` as follows:
+```
+$ make
+```
+
+## Keymap
+Several version of keymap are available in advance but you are recommended to define your favorite layout yourself. To define your own keymap create file named `keymap_<name>.c` and see keymap document (you can find in top README.md) and existent keymap files.
+
+####**Extended Keymaps**
+
+To build the firmware binary hex file with an extended keymap just do `make` with `KEYMAP` option like:
+```
+$ make KEYMAP=[common|jack|<name>]
+```
+_The only applicable keymaps will work with this option._ Extended keymaps follow the format **__extended\_keymap\_\<name\>.c__**
+
+####**Common Keymaps**
+
+Building with a common keymap is as simple as adding the COMMON option. Note that only
+```
+$ make KEYMAP=[common|jack|<name>] COMMON=true
+```
+_The only applicable keymaps will work with this option._ Common keymaps follow the format **__keymap\_\<name\>.c__**
+
+## Notable TMK forks (which some of the keymap files are from)
+- (add yours)
diff --git a/keyboard/quark/backlight.c b/keyboard/quark/backlight.c
new file mode 100644
index 0000000000..ee7e31ee9c
--- /dev/null
+++ b/keyboard/quark/backlight.c
@@ -0,0 +1,46 @@
+
+#include <avr/io.h>
+#include "backlight.h"
+
+
+void backlight_init_ports()
+{
+ // Setup PB7 as output and output low.
+ DDRB |= (1<<7);
+ PORTB &= ~(1<<7);
+
+ // Use full 16-bit resolution.
+ ICR1 = 0xFFFF;
+
+ // I could write a wall of text here to explain... but TL;DW
+ // Go read the ATmega32u4 datasheet.
+ // And this: http://blog.saikoled.com/post/43165849837/secret-konami-cheat-code-to-high-resolution-pwm-on
+
+ // Pin PB7 = OCR1C (Timer 1, Channel C)
+ // Compare Output Mode = Clear on compare match, Channel C = COM1C1=1 COM1C0=0
+ // (i.e. start high, go low when counter matches.)
+ // WGM Mode 14 (Fast PWM) = WGM13=1 WGM12=1 WGM11=1 WGM10=0
+ // Clock Select = clk/1 (no prescaling) = CS12=0 CS11=0 CS10=1
+
+ TCCR1A = _BV(COM1C1) | _BV(WGM11); // = 0b00001010;
+ TCCR1B = _BV(WGM13) | _BV(WGM12) | _BV(CS10); // = 0b00011001;
+
+ // Default to zero duty cycle.
+ OCR1C = 0x0000;
+}
+
+void backlight_set(uint8_t level)
+{
+ if ( level == 0 )
+ {
+ // Turn off PWM control on PB7, revert to output low.
+ TCCR1A &= ~(_BV(COM1C1));
+ }
+ else
+ {
+ // Turn on PWM control of PB7
+ TCCR1A |= _BV(COM1C1);
+ OCR1C = level << 12 | 0x0FFF;
+ }
+}
+
diff --git a/keyboard/quark/backlight.h b/keyboard/quark/backlight.h
new file mode 100644
index 0000000000..0fe1f4a72b
--- /dev/null
+++ b/keyboard/quark/backlight.h
@@ -0,0 +1,2 @@
+
+void backlight_init_ports(void);
diff --git a/keyboard/quark/common_keymaps/keymap_brett.c b/keyboard/quark/common_keymaps/keymap_brett.c
new file mode 100644
index 0000000000..97d832b47a
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_brett.c
@@ -0,0 +1,42 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP(
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ LCTL, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, RSFT,
+ TAB, LGUI, RSFT, LALT, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* RAISE */
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, DEL,
+ TRNS, F1, F2, F3, F4, F5, F6, 4, 5, 6, QUOT, TRNS,
+ TRNS, F7, F8, F9, F10, F11, F12, 1, 2, 3, TRNS, PGUP,
+ MPRV, MNXT, TRNS, MUTE, TRNS, TRNS, FN1, 0, 0, TRNS, PGDN),
+[2] = KEYMAP( /* LOWER */
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MINS,
+ TRNS, TRNS, TRNS, PAUSE, TRNS, TRNS, TRNS, TRNS, LBRC, RBRC, BSLS, EQL,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ MPLY, MSTP, VOLU, VOLD, FN2, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/quark/common_keymaps/keymap_dotcom.c b/keyboard/quark/common_keymaps/keymap_dotcom.c
new file mode 100644
index 0000000000..347f6dea91
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_dotcom.c
@@ -0,0 +1,34 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP(
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ FN1, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, LBRC,
+ LCTL, BSLS, QUOT, LALT, FN22, SPC, LEFT, UP, DOWN, RGHT, RBRC),
+[1] = KEYMAP(
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, DEL,
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, TRNS, TRNS, TRNS,
+ TRNS, FN18, FN19, FN22, EQL, MINS, FN20, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, TRNS, VOLD, VOLU, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to Fn overlay
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+};
diff --git a/keyboard/quark/common_keymaps/keymap_jack.c b/keyboard/quark/common_keymaps/keymap_jack.c
new file mode 100644
index 0000000000..c74812121f
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_jack.c
@@ -0,0 +1,50 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Jack */
+ TAB, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ ESC, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ RSFT, LCTL, LALT, LGUI, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* Jack colemak */
+ TAB, Q, W, F, P, G, J, L, U, Y, SCLN, BSPC,
+ ESC, A, R, S, T, D, H, N, E, I, O, QUOT,
+ LSFT, Z, X, C, V, B, K, M, COMM, DOT, SLSH, ENT,
+ FN3, LCTL, LALT, LGUI, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[2] = KEYMAP( /* Jack RAISE */
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, BSPC,
+ TRNS, FN3, FN4, PAUSE, TRNS, TRNS, TRNS, MINS, EQL, LBRC, RBRC, BSLS,
+ TRNS, F11, F12, F13, F14, F15, F16, F17, F18, F19, F20, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, MNXT, VOLD, VOLU, MPLY),
+[3] = KEYMAP( /* Jack LOWER */
+ FN22, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, BSPC,
+ TRNS, FN3, FN4, PAUSE, TRNS, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, MNXT, VOLD, VOLU, MPLY),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/quark/common_keymaps/keymap_joe.c b/keyboard/quark/common_keymaps/keymap_joe.c
new file mode 100644
index 0000000000..07122b702c
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_joe.c
@@ -0,0 +1,107 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Joe colemak */
+ ESC, Q, W, F, P, G, J, L, U, Y, SCLN, MINS,
+ BSPC, A, R, S, T, D, H, N, E, I, O, ENT,
+ TAB, Z, X, C, V, B, K, M, COMM, DOT, SLSH, QUOT,
+ LCTL, LGUI, LALT, LSFT, FN1, SPC, FN0, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* Joe qwerty */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, MINS,
+ BSPC, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ TAB, Z, X, C, V, B, N, M, COMM, DOT, SLSH, QUOT,
+ LCTL, LGUI, LALT, LSFT, FN1, SPC, FN0, LEFT, DOWN, UP, RGHT),
+[2] = KEYMAP( /* Joe RAISE */
+ F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12,
+ DEL, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, TRNS,
+ BSLS, FN5, FN6, TRNS, TRNS, MENU, CAPS, INS, PSCR, LBRC, RBRC, FN21,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, FN0, FN26, FN27, FN28, FN29),
+[3] = KEYMAP( /* Joe LOWER */
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN7, FN8, FN9, FN30, FN31,
+ DEL, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, TRNS,
+ FN25, FN3, FN4, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN23, FN24, EQL,
+ TRNS, TRNS, TRNS, TRNS, FN1, TRNS, FN2, HOME, PGDN, PGUP, END),
+[4] = KEYMAP( /* Joe LOWER + RAISE */
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MNXT, VOLD, VOLU, MPLY),
+};
+
+enum macro_id {
+ M_Q0,
+ M_Q1,
+ M_Q2,
+ M_Q3,
+ M_Q4
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [0] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [1] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(4), // to Fn overlay
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [5] = ACTION_MODS_KEY(MOD_LCTL, KC_PGDN),
+ [6] = ACTION_MODS_KEY(MOD_LCTL, KC_PGUP),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [25] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [7] = ACTION_MACRO(M_Q0),
+ [8] = ACTION_MACRO(M_Q1),
+ [9] = ACTION_MACRO(M_Q2),
+ [30] = ACTION_MACRO(M_Q3),
+ [31] = ACTION_MACRO(M_Q4),
+
+ [26] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_LEFT),
+ [27] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_DOWN),
+ [28] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_UP),
+ [29] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT, KC_RGHT),
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ keyevent_t event = record->event;
+ switch (id) {
+ case M_Q0:
+ return event.pressed ?
+ MACRO( D(LSFT), T(SCLN), U(LSFT), T(SLSH), END ) :
+ MACRO_NONE;
+ case M_Q1:
+ return event.pressed ?
+ MACRO( D(LSFT), T(SCLN), T(9), U(LSFT), END ) :
+ MACRO_NONE;
+ case M_Q2:
+ return event.pressed ?
+ MACRO( D(LSFT), T(0), T(SCLN), U(LSFT), END ) :
+ MACRO_NONE;
+ case M_Q3:
+ return event.pressed ?
+ MACRO( D(LSFT), T(9), T(SCLN), U(LSFT), END ) :
+ MACRO_NONE;
+ case M_Q4:
+ return event.pressed ?
+ MACRO( D(LSFT), T(SCLN), T(0), U(LSFT), END ) :
+ MACRO_NONE;
+
+ }
+ return MACRO_NONE;
+} \ No newline at end of file
diff --git a/keyboard/quark/common_keymaps/keymap_matthew.c b/keyboard/quark/common_keymaps/keymap_matthew.c
new file mode 100644
index 0000000000..56e7003a97
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_matthew.c
@@ -0,0 +1,70 @@
+// by Matthew Pepers - https://github.com/pepers
+
+/* grid planck layout - modified programmer dvorak
+,-----------------------------------------------------------------------------------------------.
+| pause | @ | | | ^ | | | | | * | # | $ | del |
+| esc | ; : | , < | . > | P | Y | F | G | G | C | R | bkspc |
+| F1 | F2 | F3 | F4 | F5 | F6 | F7 | F8 | F9 | F10 | F11 | F12 |
+|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|
+| & | / | { | ( | [ | = | ! | ] | ) | } | \ | + |
+| ` ~ | A | O | E | U | I | D | H | T | N | S | - _ |
+| % | 7 | 5 | 3 | 1 | 9 | 0 | 2 | 4 | 6 | 8 | ? |
+|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|
+| | | | | | | | | | | | prtsc |
+| tab | ' " | Q | J | K | X | B | M | W | V | Z | retrn |
+| | | | | | | | | | | | insrt |
+|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|-------|
+| | | | | | | | | | | | |
+| lctrl | lgui | lalt | ralt | lower | shift | space | raise | left | down | up | right |
+| | | | | | | | | home | pgdn | pgup | end |
+`-----------------------------------------------------------------------------------------------'
+*/
+
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ /* 0: dvorak */
+ [0] = KEYMAP_GRID( ESC, SCLN, COMM, DOT, P, Y, F, G, C, R, L, BSPC, \
+ GRV, A, O, E, U, I, D, H, T, N, S, MINS, \
+ TAB, QUOT, Q, J, K, X, B, M, W, V, Z, ENT, \
+ LCTL, LGUI, LALT, RALT, FN1, LSFT, SPC, FN2, LEFT, DOWN, UP, RGHT),
+
+ /* 1: lower (FN1) */
+ [1] = KEYMAP_GRID( F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12, \
+ FN17, 7, 5, 3, 1, 9, 0, 2, 4, 6, 8, FN18, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, INS, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, HOME, PGDN, PGUP, END),
+
+ /* 2: raise (FN2) */
+ [2] = KEYMAP_GRID(PAUS, FN19, FN20, FN21, TRNS, TRNS, TRNS, TRNS, FN22, FN23, FN24, DEL, \
+ FN10, SLSH, FN11, FN12, LBRC, EQL, FN13, RBRC, FN14, FN15, BSLS, FN16, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, PSCR, \
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // lower Fn layer
+ [2] = ACTION_LAYER_MOMENTARY(2), // raise Fn layer
+
+ // lower row1
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_5), // %
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_SLASH), // ?
+
+ // raise row0
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_2), // @
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLASH), // |
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_6), // ^
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_8), // *
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_3), // #
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_4), // $
+
+ // raise row1
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_7), // &
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRACKET), // {
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_9), // (
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_1), // !
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_0), // )
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRACKET), // }
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_EQUAL), // +
+};
diff --git a/keyboard/quark/common_keymaps/keymap_nathan.c b/keyboard/quark/common_keymaps/keymap_nathan.c
new file mode 100644
index 0000000000..5a0900b66d
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_nathan.c
@@ -0,0 +1,153 @@
+// Author: Nathan Ross Powell <nathanrospowell@gmail.com>
+// https://github.com/nathanrosspowell/tmk_keyboard/blob/planck-jack/keyboard/planck/keymap_nathan.c
+
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ /* 0: main layer
+ * ,-----------------------------------------------------------------------.
+ * |Tab | q | w | e | r | t | y | u | i | o | p | BS |
+ * |-----------------------------------------------------------------------|
+ * |Ctrl | a | s | d | f | g | h | j | k | l | ; | Ret |
+ * |-----------------------------------------------------------------------|
+ * |Shift| z | x | c | v | b | n | m | [ | ( | { | < |
+ * |-----------------------------------------------------------------------|
+ * |Meta | \ | / | Alt |Lower|Space|Space|Upper|Left |Down | Up |Right|
+ * `-----------------------------------------------------------------------'
+ */
+ [0] = KEYMAP_GRID(
+ TAB, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ LCTL, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ RSFT, Z, X, C, V, B, N, M, LBRC, FN10, FN11, FN12,
+ LGUI, BSLS, SLSH, LALT, FN0, SPC, SPC, FN1, LEFT, DOWN, UP, RGHT),
+
+ /* 1: fn left/lower layer
+ * The top row are Visual Studio combos:
+ * 'Run', 'Breakpoint', 'Step over', 'Step into', 'Set cursor to line'
+ * 2nd row are key combos:
+ * 'ctrl-alt-delete', 'ctrl-shift-escape'
+ * 3rd row are macros keys:
+ * 'P0' - 'P5' execute a script on Windows machines
+ * ,-----------------------------------------------------------------------.
+ * | ESC | F5 | F9 | F10 | F11 |S+F11|CSF10|NLock|Num7 |Num8 |Num9 | Del |
+ * |-----------------------------------------------------------------------|
+ * | |C/A/D|C/S/E| Ins |Print|Pause|SLock|Num0 |Num4 |Num5 |Num6 |Num= |
+ * |-----------------------------------------------------------------------|
+ * | | P0 | P1 | P2 | P3 | P4 | P5 |Num. |Num1 |Num2 |Num3 |Num/ |
+ * |-----------------------------------------------------------------------|
+ * | |User | | | | | | |Home |PgDn |PgUp | End |
+ * `-----------------------------------------------------------------------'
+ */
+ [1] = KEYMAP_GRID(
+ ESC, F5, F9, F10, F11, FN30, FN31, NLCK, P7, P8, P9, DEL,
+ TRNS, FN16, FN17, INS, PSCR, PAUS, SLCK, P0, P4, P5, P6, PEQL,
+ TRNS, FN2, FN3, FN4, FN5, FN6, FN7, PDOT, P1, P2, P3, PSLS,
+ TRNS, FN8, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, HOME, PGDN, PGUP, END ),
+
+ /* 2: fn right/raise layer
+ * ,-----------------------------------------------------------------------.
+ * | F1 | F2 | F3 | F4 |F5 | F6 | F7 | F8 | F9 | F10 | F11 | F12 |
+ * |-----------------------------------------------------------------------|
+ * | | ! | @ | # | $ | % | ^ | & | * | - | + | = |
+ * |-----------------------------------------------------------------------|
+ * | | _ | ' | " | ` | ~ | , | . | ] | ) | } | > |
+ * |-----------------------------------------------------------------------|
+ * | |NextT|PrevT| | | | Esc | |Mute |Vol- |Vol+ | P/P |
+ * `-----------------------------------------------------------------------'
+ */
+ [2] = KEYMAP_GRID(
+ F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, F11, F12,
+ TRNS, FN18, FN19, FN20, FN21, FN22, FN23, FN24, FN25, MINS, FN26, PAST,
+ TRNS, FN27, QUOT, FN28, GRV, FN29, COMM, DOT, RBRC, FN13, FN14, FN15,
+ TRNS, MNXT, MPRV, TRNS, TRNS, TRNS, ESC, TRNS, MUTE, VOLD, VOLU, MPLY ),
+};
+
+enum macro_id {
+ M_P0,
+ M_P1,
+ M_P2,
+ M_P3,
+ M_P4,
+ M_P5,
+ M_USERNAME
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [0] = ACTION_LAYER_MOMENTARY(1), // left/lower layer
+ [1] = ACTION_LAYER_MOMENTARY(2), // right/raise layer
+ // Program macros
+ [2] = ACTION_MACRO(M_P0),
+ [3] = ACTION_MACRO(M_P1),
+ [4] = ACTION_MACRO(M_P2),
+ [5] = ACTION_MACRO(M_P3),
+ [6] = ACTION_MACRO(M_P4),
+ [7] = ACTION_MACRO(M_P5),
+ [8] = ACTION_MACRO(M_USERNAME),
+ // Braces
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_9), // (
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC), // {
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_COMMA), // <
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_0), // )
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC), // }
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_DOT), // >
+ // Combo
+ [16] = ACTION_MODS_KEY(MOD_LALT | MOD_LCTL, KC_DEL), // Ctrl+Alt+Delete
+ [17] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_ESC), // Ctrl+Shft+Escape
+ // Symbols
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_1), // !
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_2), // @
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_3), // #
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_4), // $
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_5), // %
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_6), // ^
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_7), // &
+ [25] = ACTION_MODS_KEY(MOD_LSFT, KC_8), // *
+ [26] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // +
+ [27] = ACTION_MODS_KEY(MOD_LSFT, KC_MINUS), // _
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_QUOTE), // "
+ [29] = ACTION_MODS_KEY(MOD_LSFT, KC_GRAVE), // ~
+ // Debugging
+ [30] = ACTION_MODS_KEY(MOD_LSFT, KC_F11), // Step into
+ [31] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_F10), // Set cursor to line
+ };
+
+// Run a script and pass a key number to it. This is Windows specific and the script needs to be on your path.
+// *open run dialog* keypress.py [PRG_NUM]
+#define ADD_PYTHON_PROGRAM_ON_WIN( PRG_NUM ) MACRO( D(LGUI), T(R), U(LGUI), W(100), T(K), T(E), T(Y), T(P), T(R), T(E), T(S), T(S), T(DOT), T(P), T(Y), T(SPC), T(PRG_NUM), END )
+// *return*
+#define RUN_PYTHON_PROGRAM_ON_WIN MACRO( T(ENT), END )
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt) {
+ keyevent_t event = record->event;
+ switch (id) {
+ case M_P0:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 0 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P1:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 1 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P2:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 2 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P3:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 3 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P4:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 4 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_P5:
+ return event.pressed ?
+ ADD_PYTHON_PROGRAM_ON_WIN( 5 ) :
+ RUN_PYTHON_PROGRAM_ON_WIN;
+ case M_USERNAME:
+ return event.pressed ?
+ MACRO( T(N), T(A), T(T), T(H), T(A), T(N), T(R), T(O), T(S), T(S), T(P), T(O), T(W), T(E), T(L), T(L), END ) :
+ MACRO_NONE;
+ }
+ return MACRO_NONE;
+}
diff --git a/keyboard/quark/common_keymaps/keymap_peasant.c b/keyboard/quark/common_keymaps/keymap_peasant.c
new file mode 100644
index 0000000000..ddacb614e6
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_peasant.c
@@ -0,0 +1,51 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = KEYMAP( /* Native */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, FN2,
+ BSPC, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ TAB, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ DEL, LCTL, NO, LSFT, LALT, SPC, NO, LEFT, DOWN, UP, RGHT),
+ [1] = KEYMAP( /* QWERTY->PHOTOSHOP */
+ DELETE, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, FN1,
+ O, G, S, U, T, FN27, F21, F10, F11, F7, F8, F9,
+ TAB, FN4, FN5, FN6, F1, FN7, F18, F19, F23, F20, F22, FN9,
+ COMM, DOT, FN10, FN11, FN3, SPC, FN12, F2, FN8, F3, F14),
+ [2] = KEYMAP( /* 2: FN3 PHOTOSHOP */
+ ESC, FN25, FN26, NO, NO, NO, NO, NO, NO, NO, NO, NO,
+ NO, NO, NO, NO, NO, NO, NO, NO, NO, FN19, FN20, FN21,
+ C, NO, FN22, FN5, NO, FN23, NO, NO, NO, NO, FN13, NO,
+ FN14, FN15, FN16, FN17, FN3, SPC, FN18, NO, NO, F24, NO),
+};
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_DEFAULT_LAYER_SET(0), // set Qwerty layout
+ [2] = ACTION_DEFAULT_LAYER_SET(1), // set Photoshop presets
+ [3] = ACTION_LAYER_ON_OFF(2), // Photoshop function layer
+
+ [4] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F9), // photo folder AHK
+ [5] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_I), // select inverse
+ [6] = ACTION_MODS_KEY(MOD_LSFT, KC_M), // marquee select
+ [7] = ACTION_MODS_KEY(MOD_LALT, KC_BSPC), // fill
+ [8] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_X), // warp
+ [9] = ACTION_MODS_KEY(MOD_LCTL | MOD_LALT | MOD_LSFT, KC_F12), // merge all new layer
+ [10] = ACTION_MODS_KEY(MOD_LCTL, KC_MINS), // zoom out
+ [11] = ACTION_MODS_KEY(MOD_LCTL, KC_H), // RBG sliders
+ [12] = ACTION_MODS_KEY(MOD_LCTL, KC_S), // save
+ [13] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_F5), // layer mask from transparancy
+ [14] = ACTION_MODS_KEY(MOD_LALT, KC_LBRC), // prev layer
+ [15] = ACTION_MODS_KEY(MOD_LALT, KC_RBRC), // next layer
+ [16] = ACTION_MODS_KEY(MOD_LCTL, KC_EQL), // zoom in
+ [17] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_H), // HSV sliders
+ [18] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F11), // save as PNG
+ [19] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F7), // gaussian blur
+ [20] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL | MOD_LALT, KC_F8), // motion blur
+ [21] = ACTION_MODS_KEY(MOD_LSFT | MOD_LCTL, KC_X), // liquify filter
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS), // prev layer blending
+ [23] = ACTION_MODS_KEY(MOD_LSFT | MOD_LALT, KC_N), // normal layer blending
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // next layer blending
+ [25] = ACTION_MODS_KEY(MOD_LCTL, KC_Z), // step back
+ [26] = ACTION_MODS_KEY(MOD_LCTL, KC_Y), // step forward
+ [27] = ACTION_MODS_KEY(MOD_LCTL, KC_R), // rasterize
+
+};
diff --git a/keyboard/quark/common_keymaps/keymap_reed.c b/keyboard/quark/common_keymaps/keymap_reed.c
new file mode 100644
index 0000000000..1aa24e10de
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_reed.c
@@ -0,0 +1,74 @@
+#include "keymap_common.h"
+
+/*
+ * BUILD:
+ * Simply run the command below in the keyboard/planck directory
+ * to build against this keymap
+ *
+ * make KEYMAP=reed COMMON_KEYMAP=true
+ *
+ *
+ * DETAILS:
+ *
+ * This layout works off of Jack's layout, making some changes that I
+ * feel significantly improve the function of the keyboard. Major changes
+ * include adding a "gaming mode" that will allow users to still access
+ * the number keys 1 through 4 easily for games that require it. Also
+ * included is the ability to use the tap/hold function for easy use of
+ * right shift and thumb shift with their tapped companions.
+ *
+ */
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP_GRID( /* Reed */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, FN5,
+ LCTL, CAPS, LALT, LGUI, FN2, FN7, SPC, FN1, LEFT, DOWN, UP, RGHT),
+
+[1] = KEYMAP_GRID( /* Reed EXTREME GAMING */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, FN5,
+ LCTL, 1, 2, 3, 4, SPC, FN2, FN1, LEFT, DOWN, UP, RGHT),
+
+[2] = KEYMAP_GRID( /* Reed RAISE */
+ GRV, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, BSPC,
+ TRNS, FN3, FN4, PAUSE, TRNS, TRNS, TRNS, MINS, EQL, LBRC, RBRC, BSLS,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, MNXT, VOLD, VOLU, MPLY),
+
+[3] = KEYMAP_GRID( /* Reed LOWER */
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, DEL,
+ TRNS, TRNS, INS, HOME, PGUP, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, TRNS, DEL, END, PGDN, F11, F12, F13, TRNS, VOLD, VOLU, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, TRNS, MPRV, MUTE, MPLY, MNXT),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay - RAISE
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay - LOWER
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+ // Actions for the tap/hold modifiers listed above
+ [5] = ACTION_MODS_TAP_KEY(MOD_RSFT, KC_ENT),
+ [7] = ACTION_MODS_TAP_KEY(MOD_LSFT, KC_BSPC),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/quark/common_keymaps/keymap_sean.c b/keyboard/quark/common_keymaps/keymap_sean.c
new file mode 100644
index 0000000000..4fe07f701a
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_sean.c
@@ -0,0 +1,57 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = KEYMAP( /* Matrix Dvorak */
+ QUOT, COMM, DOT, P, Y, SLSH, EQL, F, G, C, R, L,
+ A, O, E, U, I, ESC, BSPC, D, H, T, N, S,
+ SCLN, Q, J, K, X, TAB, ENT, B, M, W, V, Z,
+ LSFT, LCTL, LALT, LGUI, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+
+ [1] = KEYMAP( /* Matrix Qwerty */
+ Q, W, E, R, T, QUOT, EQL, Y, U, I, O, P,
+ A, S, D, F, G, ESC, BSPC, H, J, K, L, SCLN,
+ Z, X, C, V, B, TAB, ENT, N, M, COMM, DOT, SLSH,
+ LSFT, LCTL, LALT, LGUI, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+
+ [2] = KEYMAP( /* fn1 lower */
+ F1, F2, F3, F4, F5, TRNS, TRNS, F6, F7, F8, F9, F10,
+ 1, 2, 3, 4, 5, F18, DEL, 6, 7, 8, 9, 0,
+ FN3, FN4, TRNS, GRV, MINS, TRNS, TRNS, BSLS, LBRC, RBRC, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN5, HOME, PGDN, PGUP, END),
+
+ [3] = KEYMAP( /* fn2 raise */
+ F1, F2, F3, F4, F5, TRNS, TRNS, F6, F7, F8, F9, F10,
+ F11, F12, F13, F14, F15, F18, DEL, F16, F17, F18, F19, F20,
+ FN3, FN4, TRNS, TRNS, TRNS, TRNS, TRNS, EJCT, PWR, LSFT,PAUSE, RSFT,
+ LEFT, DOWN, UP, RGHT, FN5, TRNS, TRNS, MNXT, VOLD, VOLU, MUTE),
+
+ [4] = KEYMAP( /* lower + raise */
+ LEFT, DOWN, UP, RGHT, TRNS, TRNS, TRNS, TRNS, LEFT, DOWN, UP, RGHT,
+ HOME, PGDN, PGUP, END, TRNS, F18, DEL, TRNS, HOME, PGDN, PGUP, END,
+ FN3, FN4, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, EJCT, PWR, MPLY, RSFT,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MNXT, VOLD, VOLU, MUTE),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay LOWER
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay RAISE
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+ [5] = ACTION_LAYER_MOMENTARY(4), // to Fn overlay LOWER + RAISE
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+};
diff --git a/keyboard/quark/common_keymaps/keymap_shane.c b/keyboard/quark/common_keymaps/keymap_shane.c
new file mode 100644
index 0000000000..d4e40fe63a
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_shane.c
@@ -0,0 +1,100 @@
+// https://github.com/shanecelis/tmk_keyboard/blob/master/keyboard/planck/keymap_shane.c
+
+#include "keymap_common.h"
+#include "action_layer.h"
+#include "action.h"
+#include "action_util.h"
+
+/*
+ Shane's Planck Layout
+ http://www.keyboard-layout-editor.com/#/layouts/015d9011102619d7695c86ffe57cf441
+*/
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+ [0] = KEYMAP_AND_SWAP( /* Base */
+ TAB, Q, W, E, R, T, Y, U, I, O, P, MINS,
+ LCTL, A, S, D, F, G, H, J, K, L, SCLN, BSPC,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, FN5,
+ /*ALPHA*/FN3, /*HYPER*/ /*SUPER*/LGUI, /*META*/LALT, LCTL, FN2, FN6, FN1, LEFT, DOWN, UP, RGHT),
+ [2] = KEYMAP_AND_SWAP( /* More modifiers */
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, RCTL, RALT, RGUI, TRNS),
+ [4] = KEYMAP_AND_SWAP( /* WASD */
+ TRNS, TRNS, UP, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, LEFT, DOWN, RIGHT, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+ [6] = KEYMAP_AND_SWAP( /* Raise/FN1 */
+ FN23, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, EQL,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, ENT,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, BSLS, TRNS,
+ PAUS, TRNS, TRNS, TRNS, TRNS, BSPC, TRNS, MUTE, PGUP, PGDN, MNXT),
+ [8] = KEYMAP_AND_SWAP( /* Lower/FN2 */
+ ESC, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN19, FN20, TRNS,
+ TRNS, TRNS, TRNS, TRNS, CAPS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, QUOT,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN24, FN25, LBRC, RBRC, TRNS, TRNS,
+ FN4, TRNS, TRNS, TRNS, TRNS, ENT, TRNS, MPLY, VOLD, VOLU, MPRV),
+};
+
+enum function_id {
+ SPACE_FN,
+};
+
+void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ switch (id) {
+ case SPACE_FN:
+ if (record->event.pressed) {
+ // Change the keyboard maps.
+ // Whatever even layer's are on, turn on the odd one's too.
+ for (uint8_t i = 0; i < 9; i += 2) {
+ if (layer_state & (1UL << i))
+ layer_on(i + 1);
+ }
+ layer_on(1);
+ } else {
+ // turn off all the even layers.
+ for (uint8_t i = 0; i < 9; i += 2)
+ layer_off(i + 1);
+
+ if (record->tap.count != 0) {
+ // Space was tapped rather than used like a modifier.
+ // So send a space up and down event.
+ add_key(KC_SPC);
+ send_keyboard_report();
+ del_key(KC_SPC);
+ send_keyboard_report();
+ }
+ }
+ break;
+ }
+}
+
+
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(6), // to fist Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(8), // to second Fn overlay
+ [3] = ACTION_LAYER_TOGGLE(2), // toggle more modifiers
+ [4] = ACTION_LAYER_TOGGLE(4), // toggle wasd
+ [5] = ACTION_MODS_TAP_KEY(MOD_RSFT, KC_ENT),
+ [6] = ACTION_FUNCTION_TAP(SPACE_FN),
+
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [25] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [26] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+};
diff --git a/keyboard/quark/common_keymaps/keymap_simon.c b/keyboard/quark/common_keymaps/keymap_simon.c
new file mode 100644
index 0000000000..37951364be
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_simon.c
@@ -0,0 +1,44 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Jack */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, DOT, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SCLN, DEL,
+ LCTL, ENT, LALT, CAPS, FN2, SPC, FN1, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* Jack RAISE */
+ TRNS, F1, F2, F3, F4, NO, FN11, FN9, FN12, NO, FN14, TRNS,
+ TRNS, F5, F6, F7, F8, FN16, SLSH, MINS, EQL, LBRC, FN8, TRNS,
+ TRNS, F9, F10, F11, F12, F15, F16, FN22, SCLN, MINS, QUOT, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+[2] = KEYMAP( /* Jack LOWER */
+ FN22, 1, 2, 3, FN13, FN14, FN15, FN16, FN17, FN18, FN19, BSPC,
+ TRNS, 4, 5, 6, TRNS, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, 7, 8, 9, 0, FN28, FN15, F7, F8, F9, F10, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+
+ [8] = ACTION_MODS_KEY(MOD_LSFT, KC_SLSH),
+ [9] = ACTION_MODS_KEY(MOD_LSFT, KC_QUOT),
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+
+ [29] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+};
diff --git a/keyboard/quark/common_keymaps/keymap_tim.c b/keyboard/quark/common_keymaps/keymap_tim.c
new file mode 100644
index 0000000000..7444f3877b
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_tim.c
@@ -0,0 +1,44 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP(
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, ENT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, RSFT,
+ LCTL, LALT, DEL, LGUI, FN2, SPC, FN1, F2, F5, F9, F12),
+[2] = KEYMAP( /* RAISE */
+ TRNS, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, BSPC,
+ GRV, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, MINS, EQL, LBRC, RBRC, BSLS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, QUOT, FN29, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN1, TRNS, TRNS, TRNS, TRNS),
+[3] = KEYMAP( /* LOWER */
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, BSPC,
+ FN22, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN20, FN21, FN23, FN24, FN28,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, QUOT, FN29, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(3), // to Fn overlay
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1),
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2),
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3),
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4),
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5),
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6),
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7),
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8),
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9),
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0),
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS),
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL),
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV),
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC),
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC),
+ [28] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS),
+ [29] = ACTION_MODS_KEY(MOD_LSFT, KC_QUOT),
+};
diff --git a/keyboard/quark/common_keymaps/keymap_wilba.c b/keyboard/quark/common_keymaps/keymap_wilba.c
new file mode 100644
index 0000000000..9781f8fcd8
--- /dev/null
+++ b/keyboard/quark/common_keymaps/keymap_wilba.c
@@ -0,0 +1,56 @@
+#include "keymap_common.h"
+
+const uint8_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = KEYMAP( /* Wilba */
+ FN27, FN28, FN29, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ LCTL, LGUI, LALT, RSFT, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+[1] = KEYMAP( /* Wilba Alternate */
+ ESC, Q, W, E, R, T, Y, U, I, O, P, BSPC,
+ TAB, A, S, D, F, G, H, J, K, L, SCLN, QUOT,
+ LSFT, Z, X, C, V, B, N, M, COMM, DOT, SLSH, ENT,
+ LCTL, LGUI, LALT, RSFT, FN1, SPC, FN2, LEFT, DOWN, UP, RGHT),
+[2] = KEYMAP( /* Wilba LOWER */
+ TRNS, 1, 2, 3, 4, 5, 6, 7, 8, 9, 0, TRNS,
+ TRNS, F11, F12, LBRC, RBRC, FN20, EQL, FN23, FN24, MINS, FN21, TRNS,
+ TRNS, BSLS, GRV, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, FN1, TRNS, TRNS, MNXT, VOLD, VOLU, MPLY),
+[3] = KEYMAP( /* Wilba RAISE */
+ TRNS, FN10, FN11, FN12, FN13, FN14, FN15, FN16, FN17, FN18, FN19, TRNS,
+ TRNS, F1, F2, F3, F4, F5, F6, F7, F8, F9, F10, TRNS,
+ TRNS, FN25, FN22, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, TRNS,
+ TRNS, TRNS, TRNS, TRNS, TRNS, TRNS, FN2, TRNS, TRNS, TRNS, TRNS),
+};
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(2), // LOWER
+ [2] = ACTION_LAYER_MOMENTARY(3), // RAISE
+
+ [3] = ACTION_DEFAULT_LAYER_SET(0),
+ [4] = ACTION_DEFAULT_LAYER_SET(1),
+
+ [10] = ACTION_MODS_KEY(MOD_LSFT, KC_1), // !
+ [11] = ACTION_MODS_KEY(MOD_LSFT, KC_2), // @
+ [12] = ACTION_MODS_KEY(MOD_LSFT, KC_3), // #
+ [13] = ACTION_MODS_KEY(MOD_LSFT, KC_4), // $
+ [14] = ACTION_MODS_KEY(MOD_LSFT, KC_5), // %
+ [15] = ACTION_MODS_KEY(MOD_LSFT, KC_6), // ^
+ [16] = ACTION_MODS_KEY(MOD_LSFT, KC_7), // &
+ [17] = ACTION_MODS_KEY(MOD_LSFT, KC_8), // *
+ [18] = ACTION_MODS_KEY(MOD_LSFT, KC_9), // (
+ [19] = ACTION_MODS_KEY(MOD_LSFT, KC_0), // )
+
+ [20] = ACTION_MODS_KEY(MOD_LSFT, KC_MINS), // _
+ [21] = ACTION_MODS_KEY(MOD_LSFT, KC_EQL), // +
+ [22] = ACTION_MODS_KEY(MOD_LSFT, KC_GRV), // ~
+ [23] = ACTION_MODS_KEY(MOD_LSFT, KC_LBRC), // {
+ [24] = ACTION_MODS_KEY(MOD_LSFT, KC_RBRC), // }
+ [25] = ACTION_MODS_KEY(MOD_LSFT, KC_BSLS), // |
+
+ [26] = ACTION_MODS_KEY(MOD_LSFT | MOD_RSFT, KC_PAUSE),
+
+ [27] = ACTION_BACKLIGHT_TOGGLE(),
+ [28] = ACTION_BACKLIGHT_INCREASE(),
+ [29] = ACTION_BACKLIGHT_DECREASE()
+
+};
diff --git a/keyboard/quark/config.h b/keyboard/quark/config.h
new file mode 100644
index 0000000000..7f9a48ce4d
--- /dev/null
+++ b/keyboard/quark/config.h
@@ -0,0 +1,74 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef CONFIG_H
+#define CONFIG_H
+
+
+/* USB Device descriptor parameter */
+#define VENDOR_ID 0xFEED
+#define PRODUCT_ID 0x6060
+#define DEVICE_VER 0x0001
+#define MANUFACTURER jackhumbert
+#define PRODUCT Quark
+#define DESCRIPTION t.m.k. keyboard firmware for the Quark
+
+/* key matrix size */
+#define MATRIX_ROWS 4
+#define MATRIX_COLS 12
+
+/* define if matrix has ghost */
+//#define MATRIX_HAS_GHOST
+
+/* number of backlight levels */
+/* NOTE: this is the max value of 0..BACKLIGHT_LEVELS so really 16 levels. */
+#define BACKLIGHT_LEVELS 15
+
+/* Set 0 if debouncing isn't needed */
+#define DEBOUNCE 5
+
+/* Mechanical locking support. Use KC_LCAP, KC_LNUM or KC_LSCR instead in keymap */
+#define LOCKING_SUPPORT_ENABLE
+/* Locking resynchronize hack */
+#define LOCKING_RESYNC_ENABLE
+
+/* key combination for command */
+#define IS_COMMAND() ( \
+ keyboard_report->mods == (MOD_BIT(KC_LSHIFT) | MOD_BIT(KC_RSHIFT)) \
+)
+
+
+
+/*
+ * Feature disable options
+ * These options are also useful to firmware size reduction.
+ */
+
+/* disable debug print */
+//#define NO_DEBUG
+
+/* disable print */
+//#define NO_PRINT
+
+/* disable action features */
+//#define NO_ACTION_LAYER
+//#define NO_ACTION_TAPPING
+//#define NO_ACTION_ONESHOT
+//#define NO_ACTION_MACRO
+//#define NO_ACTION_FUNCTION
+
+#endif
diff --git a/keyboard/quark/extended_keymap_common.c b/keyboard/quark/extended_keymap_common.c
new file mode 100644
index 0000000000..f8fc3209fb
--- /dev/null
+++ b/keyboard/quark/extended_keymap_common.c
@@ -0,0 +1,184 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "extended_keymap_common.h"
+#include "report.h"
+#include "keycode.h"
+#include "action_layer.h"
+#include "action.h"
+#include "action_macro.h"
+#include "debug.h"
+
+
+static action_t keycode_to_action(uint16_t keycode);
+
+
+/* converts key to action */
+action_t action_for_key(uint8_t layer, keypos_t key)
+{
+ // 16bit keycodes - important
+ uint16_t keycode = keymap_key_to_keycode(layer, key);
+
+ if (keycode >= 0x0100 && keycode < 0x2000) {
+ // Has a modifier
+ action_t action;
+ // Split it up
+ action.code = ACTION_MODS_KEY(keycode >> 8, keycode & 0xFF);
+ return action;
+ } else if (keycode >= 0x2000 && keycode < 0x3000) {
+ // Is a shortcut for function layer, pull last 12bits
+ return keymap_func_to_action(keycode & 0xFFF);
+ } else if (keycode >= 0x3000 && keycode < 0x4000) {
+ action_t action;
+ action.code = ACTION_MACRO(keycode & 0xFF);
+ return action;
+ }
+
+ switch (keycode) {
+ case KC_FN0 ... KC_FN31:
+ return keymap_fn_to_action(keycode);
+#ifdef BOOTMAGIC_ENABLE
+ case KC_CAPSLOCK:
+ case KC_LOCKING_CAPS:
+ if (keymap_config.swap_control_capslock || keymap_config.capslock_to_control) {
+ return keycode_to_action(KC_LCTL);
+ }
+ return keycode_to_action(keycode);
+ case KC_LCTL:
+ if (keymap_config.swap_control_capslock) {
+ return keycode_to_action(KC_CAPSLOCK);
+ }
+ return keycode_to_action(KC_LCTL);
+ case KC_LALT:
+ if (keymap_config.swap_lalt_lgui) {
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_LGUI);
+ }
+ return keycode_to_action(KC_LALT);
+ case KC_LGUI:
+ if (keymap_config.swap_lalt_lgui) {
+ return keycode_to_action(KC_LALT);
+ }
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_LGUI);
+ case KC_RALT:
+ if (keymap_config.swap_ralt_rgui) {
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_RGUI);
+ }
+ return keycode_to_action(KC_RALT);
+ case KC_RGUI:
+ if (keymap_config.swap_ralt_rgui) {
+ return keycode_to_action(KC_RALT);
+ }
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_RGUI);
+ case KC_GRAVE:
+ if (keymap_config.swap_grave_esc) {
+ return keycode_to_action(KC_ESC);
+ }
+ return keycode_to_action(KC_GRAVE);
+ case KC_ESC:
+ if (keymap_config.swap_grave_esc) {
+ return keycode_to_action(KC_GRAVE);
+ }
+ return keycode_to_action(KC_ESC);
+ case KC_BSLASH:
+ if (keymap_config.swap_backslash_backspace) {
+ return keycode_to_action(KC_BSPACE);
+ }
+ return keycode_to_action(KC_BSLASH);
+ case KC_BSPACE:
+ if (keymap_config.swap_backslash_backspace) {
+ return keycode_to_action(KC_BSLASH);
+ }
+ return keycode_to_action(KC_BSPACE);
+#endif
+ default:
+ return keycode_to_action(keycode);
+ }
+}
+
+
+/* Macro */
+__attribute__ ((weak))
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ return MACRO_NONE;
+}
+
+/* Function */
+__attribute__ ((weak))
+void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+}
+
+/* translates keycode to action */
+static action_t keycode_to_action(uint16_t keycode)
+{
+ action_t action;
+ switch (keycode) {
+ case KC_A ... KC_EXSEL:
+ case KC_LCTRL ... KC_RGUI:
+ action.code = ACTION_KEY(keycode);
+ break;
+ case KC_SYSTEM_POWER ... KC_SYSTEM_WAKE:
+ action.code = ACTION_USAGE_SYSTEM(KEYCODE2SYSTEM(keycode));
+ break;
+ case KC_AUDIO_MUTE ... KC_WWW_FAVORITES:
+ action.code = ACTION_USAGE_CONSUMER(KEYCODE2CONSUMER(keycode));
+ break;
+ case KC_MS_UP ... KC_MS_ACCEL2:
+ action.code = ACTION_MOUSEKEY(keycode);
+ break;
+ case KC_TRNS:
+ action.code = ACTION_TRANSPARENT;
+ break;
+ default:
+ action.code = ACTION_NO;
+ break;
+ }
+ return action;
+}
+
+
+/* translates key to keycode */
+uint16_t keymap_key_to_keycode(uint8_t layer, keypos_t key)
+{
+ // Read entire word (16bits)
+ return pgm_read_word(&keymaps[(layer)][(key.row)][(key.col)]);
+}
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint16_t keycode)
+{
+ return (action_t){ .code = pgm_read_word(&fn_actions[FN_INDEX(keycode)]) };
+}
+
+action_t keymap_func_to_action(uint16_t keycode)
+{
+ // For FUNC without 8bit limit
+ return (action_t){ .code = pgm_read_word(&fn_actions[(int)keycode]) };
+}
diff --git a/keyboard/quark/extended_keymap_common.h b/keyboard/quark/extended_keymap_common.h
new file mode 100644
index 0000000000..66712459c6
--- /dev/null
+++ b/keyboard/quark/extended_keymap_common.h
@@ -0,0 +1,152 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef KEYMAP_H
+#define KEYMAP_H
+
+#include <stdint.h>
+#include <stdbool.h>
+#include "action.h"
+#include <avr/pgmspace.h>
+#include "keycode.h"
+#include "keymap.h"
+#include "action_macro.h"
+#include "report.h"
+#include "host.h"
+#include "print.h"
+#include "debug.h"
+
+#ifdef BOOTMAGIC_ENABLE
+/* NOTE: Not portable. Bit field order depends on implementation */
+typedef union {
+ uint16_t raw;
+ struct {
+ bool swap_control_capslock:1;
+ bool capslock_to_control:1;
+ bool swap_lalt_lgui:1;
+ bool swap_ralt_rgui:1;
+ bool no_gui:1;
+ bool swap_grave_esc:1;
+ bool swap_backslash_backspace:1;
+ bool nkro:1;
+ };
+} keymap_config_t;
+keymap_config_t keymap_config;
+#endif
+
+/* translates key to keycode */
+uint16_t keymap_key_to_keycode(uint8_t layer, keypos_t key);
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint16_t keycode);
+
+/* translates Fn keycode to action */
+action_t keymap_func_to_action(uint16_t keycode);
+
+extern const uint16_t keymaps[][MATRIX_ROWS][MATRIX_COLS];
+extern const uint16_t fn_actions[];
+
+// Ability to use mods in layouts
+#define LCTL(kc) kc | 0x0100
+#define LSFT(kc) kc | 0x0200
+#define LALT(kc) kc | 0x0400
+#define LGUI(kc) kc | 0x0800
+#define RCTL(kc) kc | 0x1100
+#define RSFT(kc) kc | 0x1200
+#define RALT(kc) kc | 0x1400
+#define RGUI(kc) kc | 0x1800
+
+// Alias for function layers than expand past FN31
+#define FUNC(kc) kc | 0x2000
+
+// Aliases
+#define S(kc) LSFT(kc)
+#define F(kc) FUNC(kc)
+
+// For software implementation of colemak
+#define CM_Q KC_Q
+#define CM_W KC_W
+#define CM_F KC_E
+#define CM_P KC_R
+#define CM_G KC_T
+#define CM_J KC_Y
+#define CM_L KC_U
+#define CM_U KC_I
+#define CM_Y KC_O
+#define CM_SCLN KC_P
+
+#define CM_A KC_A
+#define CM_R KC_S
+#define CM_S KC_D
+#define CM_T KC_F
+#define CM_D KC_G
+#define CM_H KC_H
+#define CM_N KC_J
+#define CM_E KC_K
+#define CM_I KC_L
+#define CM_O KC_SCLN
+
+#define CM_Z KC_Z
+#define CM_X KC_X
+#define CM_C KC_C
+#define CM_V KC_V
+#define CM_B KC_B
+#define CM_K KC_N
+#define CM_M KC_M
+#define CM_COMM KC_COMM
+#define CM_DOT KC_DOT
+#define CM_SLSH KC_SLSH
+
+// Make it easy to support these in macros
+#define KC_CM_Q CM_Q
+#define KC_CM_W CM_W
+#define KC_CM_F CM_F
+#define KC_CM_P CM_P
+#define KC_CM_G CM_G
+#define KC_CM_J CM_J
+#define KC_CM_L CM_L
+#define KC_CM_U CM_U
+#define KC_CM_Y CM_Y
+#define KC_CM_SCLN CM_SCLN
+
+#define KC_CM_A CM_A
+#define KC_CM_R CM_R
+#define KC_CM_S CM_S
+#define KC_CM_T CM_T
+#define KC_CM_D CM_D
+#define KC_CM_H CM_H
+#define KC_CM_N CM_N
+#define KC_CM_E CM_E
+#define KC_CM_I CM_I
+#define KC_CM_O CM_O
+
+#define KC_CM_Z CM_Z
+#define KC_CM_X CM_X
+#define KC_CM_C CM_C
+#define KC_CM_V CM_V
+#define KC_CM_B CM_B
+#define KC_CM_K CM_K
+#define KC_CM_M CM_M
+#define KC_CM_COMM CM_COMM
+#define KC_CM_DOT CM_DOT
+#define KC_CM_SLSH CM_SLSH
+
+#define M(kc) kc | 0x3000
+
+#define MACRODOWN(...) (record->event.pressed ? MACRO(__VA_ARGS__) : MACRO_NONE)
+
+#endif
diff --git a/keyboard/quark/extended_keymaps/extended_keymap_default.c b/keyboard/quark/extended_keymaps/extended_keymap_default.c
new file mode 100644
index 0000000000..7ddc1aad96
--- /dev/null
+++ b/keyboard/quark/extended_keymaps/extended_keymap_default.c
@@ -0,0 +1,40 @@
+#include "extended_keymap_common.h"
+
+const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
+[0] = {
+ {KC_ESC, KC_Q, KC_W, KC_E, KC_R, KC_T, KC_Y, KC_U, KC_I, KC_O, KC_P, KC_BSPC},
+ { KC_TAB, KC_A, KC_S, KC_D, KC_F, KC_G, KC_H, KC_J, KC_K, KC_L, KC_NO, KC_ENT},
+ {KC_CAPS, KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_N, KC_M, KC_COMM, KC_DOT, KC_RSFT},
+ { KC_LCTL, KC_LALT, KC_LGUI, KC_NO, FUNC(2), KC_SPC, KC_NO, KC_NO, FUNC(1), KC_LEFT, KC_DOWN, KC_RGHT}
+},
+[1] = {
+ {KC_ESC, KC_1, KC_2, KC_3, KC_4, KC_5, KC_6, KC_7, KC_8, KC_9, KC_0, KC_DEL},
+ { KC_TAB, KC_A, KC_S,S(KC_BSLS), S(KC_COMM),S(KC_DOT),S(KC_MINS),S(KC_GRV),S(KC_LBRC), S(KC_RBRC), KC_NO, KC_ENT},
+ {KC_CAPS, KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, KC_SCLN, S(KC_SCLN), KC_HOME, KC_PGUP, KC_RSFT},
+ { KC_LCTL, KC_LALT, KC_LGUI, KC_NO, FUNC(2), KC_SPC, KC_NO, KC_NO, FUNC(1), KC_SCLN, KC_QUOT, KC_SLSH}
+},
+[2] = {
+ {KC_ESC, S(KC_1), S(KC_2), S(KC_3), S(KC_4), S(KC_5), S(KC_6), S(KC_7), S(KC_8), S(KC_9), S(KC_0), KC_BSPC},
+ { KC_TAB, KC_A, KC_S, KC_D, KC_BSLS, KC_SLSH, KC_MINS, KC_EQL, KC_LBRC, KC_RBRC, KC_NO, KC_ENT},
+ {KC_CAPS, KC_LSFT, KC_Z, KC_X, KC_C, KC_V, KC_B, S(KC_7), S(KC_EQL), KC_COMM, KC_UP, KC_RSFT},
+ { KC_LCTL, KC_LALT, KC_LGUI, KC_NO, FUNC(2), KC_SPC, KC_NO, KC_NO, FUNC(1), KC_LEFT, KC_DOWN, KC_RGHT}
+}
+};
+
+
+const uint16_t PROGMEM fn_actions[] = {
+ [1] = ACTION_LAYER_MOMENTARY(1), // to Fn overlay
+ [2] = ACTION_LAYER_MOMENTARY(2), // to Fn overlay
+
+};
+
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ // MACRODOWN only works in this function
+ switch(id) {
+ case 0:
+ return MACRO_NONE;
+ break;
+ }
+ return MACRO_NONE;
+};
diff --git a/keyboard/quark/keymap_common.c b/keyboard/quark/keymap_common.c
new file mode 100644
index 0000000000..fdb1769e1c
--- /dev/null
+++ b/keyboard/quark/keymap_common.c
@@ -0,0 +1,30 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+#include "keymap_common.h"
+
+
+/* translates key to keycode */
+uint8_t keymap_key_to_keycode(uint8_t layer, keypos_t key)
+{
+ return pgm_read_byte(&keymaps[(layer)][(key.row)][(key.col)]);
+}
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint8_t keycode)
+{
+ return (action_t){ .code = pgm_read_word(&fn_actions[FN_INDEX(keycode)]) };
+}
diff --git a/keyboard/quark/keymap_common.h b/keyboard/quark/keymap_common.h
new file mode 100644
index 0000000000..c74c7e9a28
--- /dev/null
+++ b/keyboard/quark/keymap_common.h
@@ -0,0 +1,86 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+#ifndef KEYMAP_COMMON_H
+#define KEYMAP_COMMON_H
+
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/pgmspace.h>
+#include "keycode.h"
+#include "action.h"
+#include "action_macro.h"
+#include "report.h"
+#include "host.h"
+#include "print.h"
+#include "debug.h"
+#include "keymap.h"
+
+
+extern const uint8_t keymaps[][MATRIX_ROWS][MATRIX_COLS];
+extern const uint16_t fn_actions[];
+
+
+// MIT Layout
+/*
+ * ,-----------------------------------------------------------------------.
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | |
+ * `-----------------------------------------------------------------------'
+ */
+#define KEYMAP( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K35, K37, K38, K39, K3A, K3B \
+) { \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_NO, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B } \
+}
+
+// Grid Layout
+/*
+ * ,-----------------------------------------------------------------------.
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * |-----------------------------------------------------------------------|
+ * | | | | | | | | | | | | |
+ * `-----------------------------------------------------------------------'
+ */
+#define KEYMAP_GRID( \
+ K00, K01, K02, K03, K04, K05, K06, K07, K08, K09, K0A, K0B, \
+ K10, K11, K12, K13, K14, K15, K16, K17, K18, K19, K1A, K1B, \
+ K20, K21, K22, K23, K24, K25, K26, K27, K28, K29, K2A, K2B, \
+ K30, K31, K32, K33, K34, K35, K36, K37, K38, K39, K3A, K3B \
+) { \
+ { KC_##K00, KC_##K01, KC_##K02, KC_##K03, KC_##K04, KC_##K05, KC_##K06, KC_##K07, KC_##K08, KC_##K09, KC_##K0A, KC_##K0B }, \
+ { KC_##K10, KC_##K11, KC_##K12, KC_##K13, KC_##K14, KC_##K15, KC_##K16, KC_##K17, KC_##K18, KC_##K19, KC_##K1A, KC_##K1B }, \
+ { KC_##K20, KC_##K21, KC_##K22, KC_##K23, KC_##K24, KC_##K25, KC_##K26, KC_##K27, KC_##K28, KC_##K29, KC_##K2A, KC_##K2B }, \
+ { KC_##K30, KC_##K31, KC_##K32, KC_##K33, KC_##K34, KC_##K35, KC_##K36, KC_##K37, KC_##K38, KC_##K39, KC_##K3A, KC_##K3B } \
+}
+
+
+#endif
diff --git a/keyboard/quark/led.c b/keyboard/quark/led.c
new file mode 100644
index 0000000000..1f36434883
--- /dev/null
+++ b/keyboard/quark/led.c
@@ -0,0 +1,38 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include <avr/io.h>
+#include "stdint.h"
+#include "led.h"
+
+
+void led_set(uint8_t usb_led)
+{
+ // Using PE6 Caps Lock LED
+ if (usb_led & (1<<USB_LED_CAPS_LOCK))
+ {
+ // Output high.
+ DDRE |= (1<<6);
+ PORTE |= (1<<6);
+ }
+ else
+ {
+ // Output low.
+ DDRE &= ~(1<<6);
+ PORTE &= ~(1<<6);
+ }
+}
diff --git a/keyboard/quark/matrix.c b/keyboard/quark/matrix.c
new file mode 100644
index 0000000000..2f2dbdb108
--- /dev/null
+++ b/keyboard/quark/matrix.c
@@ -0,0 +1,193 @@
+/*
+Copyright 2012 Jun Wako
+Generated by planckkeyboard.com (2014 Jack Humbert)
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+/*
+ * scan matrix
+ */
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/io.h>
+#include <util/delay.h>
+#include "print.h"
+#include "debug.h"
+#include "util.h"
+#include "matrix.h"
+
+
+#ifndef DEBOUNCE
+# define DEBOUNCE 10
+#endif
+static uint8_t debouncing = DEBOUNCE;
+
+/* matrix state(1:on, 0:off) */
+static matrix_row_t matrix[MATRIX_ROWS];
+static matrix_row_t matrix_debouncing[MATRIX_ROWS];
+
+static matrix_row_t read_cols(void);
+static void init_cols(void);
+static void unselect_rows(void);
+static void select_row(uint8_t row);
+
+inline
+uint8_t matrix_rows(void)
+{
+ return MATRIX_ROWS;
+}
+
+inline
+uint8_t matrix_cols(void)
+{
+ return MATRIX_COLS;
+}
+
+void matrix_init(void)
+{
+ // initialize row and col
+ unselect_rows();
+ init_cols();
+
+ // initialize matrix state: all keys off
+ for (uint8_t i=0; i < MATRIX_ROWS; i++) {
+ matrix[i] = 0;
+ matrix_debouncing[i] = 0;
+ }
+}
+
+uint8_t matrix_scan(void)
+{
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ select_row(i);
+ _delay_us(30); // without this wait read unstable value.
+ matrix_row_t cols = read_cols();
+ if (matrix_debouncing[i] != cols) {
+ matrix_debouncing[i] = cols;
+ if (debouncing) {
+ debug("bounce!: "); debug_hex(debouncing); debug("\n");
+ }
+ debouncing = DEBOUNCE;
+ }
+ unselect_rows();
+ }
+
+ if (debouncing) {
+ if (--debouncing) {
+ _delay_ms(1);
+ } else {
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ matrix[i] = matrix_debouncing[i];
+ }
+ }
+ }
+
+ return 1;
+}
+
+bool matrix_is_modified(void)
+{
+ if (debouncing) return false;
+ return true;
+}
+
+inline
+bool matrix_is_on(uint8_t row, uint8_t col)
+{
+ return (matrix[row] & ((matrix_row_t)1<col));
+}
+
+inline
+matrix_row_t matrix_get_row(uint8_t row)
+{
+ return matrix[row];
+}
+
+void matrix_print(void)
+{
+ print("\nr/c 0123456789ABCDEF\n");
+ for (uint8_t row = 0; row < MATRIX_ROWS; row++) {
+ phex(row); print(": ");
+ pbin_reverse16(matrix_get_row(row));
+ print("\n");
+ }
+}
+
+uint8_t matrix_key_count(void)
+{
+ uint8_t count = 0;
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ count += bitpop16(matrix[i]);
+ }
+ return count;
+}
+
+static void init_cols(void)
+{
+ DDRB &= ~(1<<6 | 1<<5 | 1<<4);
+ PORTB |= (1<<6 | 1<<5 | 1<<4);
+ DDRD &= ~(1<<7 | 1<<6 | 1<<4);
+ PORTD |= (1<<7 | 1<<6 | 1<<4);
+ DDRF &= ~(1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+ PORTF |= (1<<0 | 1<<1 | 1<<4 | 1<<5 | 1<<6 | 1<<7);
+
+}
+
+static matrix_row_t read_cols(void)
+{
+ return (PIND&(1<<4) ? 0 : (1<<0)) |
+ (PIND&(1<<6) ? 0 : (1<<1)) |
+ (PIND&(1<<7) ? 0 : (1<<2)) |
+ (PINB&(1<<4) ? 0 : (1<<3)) |
+ (PINB&(1<<5) ? 0 : (1<<4)) |
+ (PINB&(1<<6) ? 0 : (1<<5)) |
+ (PINF&(1<<7) ? 0 : (1<<6)) |
+ (PINF&(1<<6) ? 0 : (1<<7)) |
+ (PINF&(1<<5) ? 0 : (1<<8)) |
+ (PINF&(1<<4) ? 0 : (1<<9)) |
+ (PINF&(1<<1) ? 0 : (1<<10)) |
+ (PINF&(1<<0) ? 0 : (1<<11));
+
+}
+
+static void unselect_rows(void)
+{
+ DDRB &= ~(1<<0 | 1<<1 | 1<<2 | 1<<3);
+ PORTB |= (1<<0 | 1<<1 | 1<<2 | 1<<3);
+
+}
+
+static void select_row(uint8_t row)
+{
+ switch (row) {
+ case 0:
+ DDRB |= (1<<0);
+ PORTB &= ~(1<<0);
+ break;
+ case 1:
+ DDRB |= (1<<1);
+ PORTB &= ~(1<<1);
+ break;
+ case 2:
+ DDRB |= (1<<2);
+ PORTB &= ~(1<<2);
+ break;
+ case 3:
+ DDRB |= (1<<3);
+ PORTB &= ~(1<<3);
+ break;
+
+ }
+}
diff --git a/quantum.mk b/quantum.mk
new file mode 100644
index 0000000000..c82e478725
--- /dev/null
+++ b/quantum.mk
@@ -0,0 +1,30 @@
+QUANTUM_DIR = quantum
+
+# # project specific files
+SRC += $(QUANTUM_DIR)/keymap_common.c \
+ $(QUANTUM_DIR)/led.c
+
+ifndef CUSTOM_MATRIX
+ SRC += $(QUANTUM_DIR)/matrix.c
+endif
+
+ifdef MIDI_ENABLE
+ SRC += $(QUANTUM_DIR)/keymap_midi.c \
+ $(QUANTUM_DIR)/beeps.c
+endif
+
+ifdef UNICODE_ENABLE
+ SRC += $(QUANTUM_DIR)/keymap_unicode.c
+endif
+
+# Optimize size but this may cause error "relocation truncated to fit"
+#EXTRALDFLAGS = -Wl,--relax
+
+# Search Path
+VPATH += $(TOP_DIR)/$(QUANTUM_DIR)
+
+include $(TMK_DIR)/protocol/lufa.mk
+
+include $(TMK_DIR)/common.mk
+include $(TMK_DIR)/rules.mk
+
diff --git a/quantum/analog.c b/quantum/analog.c
new file mode 100644
index 0000000000..49b84ee0e8
--- /dev/null
+++ b/quantum/analog.c
@@ -0,0 +1,53 @@
+// Simple analog to digitial conversion
+
+#include <avr/io.h>
+#include <avr/pgmspace.h>
+#include <stdint.h>
+#include "analog.h"
+
+
+static uint8_t aref = (1<<REFS0); // default to AREF = Vcc
+
+
+void analogReference(uint8_t mode)
+{
+ aref = mode & 0xC0;
+}
+
+
+// Arduino compatible pin input
+int16_t analogRead(uint8_t pin)
+{
+#if defined(__AVR_ATmega32U4__)
+ static const uint8_t PROGMEM pin_to_mux[] = {
+ 0x00, 0x01, 0x04, 0x05, 0x06, 0x07,
+ 0x25, 0x24, 0x23, 0x22, 0x21, 0x20};
+ if (pin >= 12) return 0;
+ return adc_read(pgm_read_byte(pin_to_mux + pin));
+#elif defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__)
+ if (pin >= 8) return 0;
+ return adc_read(pin);
+#else
+ return 0;
+#endif
+}
+
+// Mux input
+int16_t adc_read(uint8_t mux)
+{
+#if defined(__AVR_AT90USB162__)
+ return 0;
+#else
+ uint8_t low;
+
+ ADCSRA = (1<<ADEN) | ADC_PRESCALER; // enable ADC
+ ADCSRB = (1<<ADHSM) | (mux & 0x20); // high speed mode
+ ADMUX = aref | (mux & 0x1F); // configure mux input
+ ADCSRA = (1<<ADEN) | ADC_PRESCALER | (1<<ADSC); // start the conversion
+ while (ADCSRA & (1<<ADSC)) ; // wait for result
+ low = ADCL; // must read LSB first
+ return (ADCH << 8) | low; // must read MSB only once!
+#endif
+}
+
+
diff --git a/quantum/analog.h b/quantum/analog.h
new file mode 100644
index 0000000000..9b95a93bef
--- /dev/null
+++ b/quantum/analog.h
@@ -0,0 +1,36 @@
+#ifndef _analog_h_included__
+#define _analog_h_included__
+
+#include <stdint.h>
+
+void analogReference(uint8_t mode);
+int16_t analogRead(uint8_t pin);
+int16_t adc_read(uint8_t mux);
+
+#define ADC_REF_POWER (1<<REFS0)
+#define ADC_REF_INTERNAL ((1<<REFS1) | (1<<REFS0))
+#define ADC_REF_EXTERNAL (0)
+
+// These prescaler values are for high speed mode, ADHSM = 1
+#if F_CPU == 16000000L
+#define ADC_PRESCALER ((1<<ADPS2) | (1<<ADPS1))
+#elif F_CPU == 8000000L
+#define ADC_PRESCALER ((1<<ADPS2) | (1<<ADPS0))
+#elif F_CPU == 4000000L
+#define ADC_PRESCALER ((1<<ADPS2))
+#elif F_CPU == 2000000L
+#define ADC_PRESCALER ((1<<ADPS1) | (1<<ADPS0))
+#elif F_CPU == 1000000L
+#define ADC_PRESCALER ((1<<ADPS1))
+#else
+#define ADC_PRESCALER ((1<<ADPS0))
+#endif
+
+// some avr-libc versions do not properly define ADHSM
+#if defined(__AVR_AT90USB646__) || defined(__AVR_AT90USB1286__)
+#if !defined(ADHSM)
+#define ADHSM (7)
+#endif
+#endif
+
+#endif
diff --git a/quantum/beeps.c b/quantum/beeps.c
new file mode 100644
index 0000000000..8d1f81f210
--- /dev/null
+++ b/quantum/beeps.c
@@ -0,0 +1,246 @@
+#include "beeps.h"
+#include <math.h>
+#include <avr/pgmspace.h>
+#include <avr/interrupt.h>
+#include <avr/io.h>
+
+#define PI 3.14159265
+
+void delay_us(int count) {
+ while(count--) {
+ _delay_us(1);
+ }
+}
+
+int voices = 0;
+double frequency = 0;
+int volume = 0;
+int position = 0;
+
+double frequencies[8] = {0, 0, 0, 0, 0, 0, 0, 0};
+int volumes[8] = {0, 0, 0, 0, 0, 0, 0, 0};
+bool sliding = false;
+#define RANGE 1000
+volatile int i=0; //elements of the wave
+
+
+void beeps() {
+ play_notes();
+}
+
+void send_freq(double freq, int vol) {
+ int duty = (((double)F_CPU) / freq);
+ ICR3 = duty; // Set max to the period
+ OCR3A = duty >> (0x10 - vol); // Set compare to half the period
+}
+
+void stop_all_notes() {
+ voices = 0;
+ TCCR3A = 0;
+ TCCR3B = 0;
+ frequency = 0;
+ volume = 0;
+
+ for (int i = 0; i < 8; i++) {
+ frequencies[i] = 0;
+ volumes[i] = 0;
+ }
+}
+
+void stop_note(double freq) {
+ for (int i = 7; i >= 0; i--) {
+ if (frequencies[i] == freq) {
+ frequencies[i] = 0;
+ volumes[i] = 0;
+ for (int j = i; (j < 7); j++) {
+ frequencies[j] = frequencies[j+1];
+ frequencies[j+1] = 0;
+ volumes[j] = volumes[j+1];
+ volumes[j+1] = 0;
+ }
+ }
+ }
+ voices--;
+ if (voices < 0)
+ voices = 0;
+ if (voices == 0) {
+ TCCR3A = 0;
+ TCCR3B = 0;
+ frequency = 0;
+ volume = 0;
+ } else {
+ double freq = frequencies[voices - 1];
+ int vol = volumes[voices - 1];
+ if (frequency < freq) {
+ sliding = true;
+ for (double f = frequency; f <= freq; f += ((freq - frequency) / 500.0)) {
+ send_freq(f, vol);
+ }
+ sliding = false;
+ } else if (frequency > freq) {
+ sliding = true;
+ for (double f = frequency; f >= freq; f -= ((frequency - freq) / 500.0)) {
+ send_freq(f, vol);
+ }
+ sliding = false;
+ }
+ send_freq(freq, vol);
+ frequency = freq;
+ volume = vol;
+ }
+}
+
+void init_notes() {
+ // TCCR1A = (1 << COM1A1) | (0 << COM1A0) | (1 << WGM11) | (1 << WGM10);
+ // TCCR1B = (1 << COM1B1) | (0 << COM1A0) | (1 << WGM13) | (1 << WGM12) | (0 << CS12) | (0 << CS11) | (1 << CS10);
+
+ // DDRC |= (1<<6);
+
+ // TCCR3A = (1 << COM3A1) | (0 << COM3A0) | (1 << WGM31) | (0 << WGM30);
+ // TCCR3B = (1 << WGM33) | (1 << WGM32) | (0 << CS32) | (0 << CS31) | (1 << CS30);
+
+ // ICR3 = 0xFFFF;
+ // OCR3A = (int)((float)wave[i]*ICR3/RANGE); //go to next array element
+
+
+ // cli();
+
+ // /* Enable interrupt on timer2 == 127, with clk/8 prescaler. At 16MHz,
+ // this gives a timer interrupt at 15625Hz. */
+ // TIMSK3 = (1 << OCIE3A);
+
+ // /* clear/reset timer on match */
+ // // TCCR3A = 1<<WGM31 | 0<<WGM30; CTC mode, reset on match
+ // // TCCR3B = 0<<CS32 | 1<<CS31 | 0<<CS30; /* clk, /8 prescaler */
+
+ // TCCR3A = (1 << COM3A1) | (0 << COM3A0) | (1 << WGM31) | (0 << WGM30);
+ // TCCR3B = (0 << WGM33) | (0 << WGM32) | (0 << CS32) | (0 << CS31) | (1 << CS30);
+
+
+ // TCCR1A = (1 << COM1A1) | (0 << COM1A0) | (1 << WGM11) | (0 << WGM10);
+ // TCCR1B = (1 << WGM12) | (0 << CS12) | (0 << CS11) | (1 << CS10);
+ // // SPCR = 0x50;
+ // // SPSR = 0x01;
+ // DDRC |= (1<<6);
+ // // ICR3 = 0xFFFF;
+ // // OCR3A=80;
+ // PORTC |= (1<<6);
+
+ // sei();
+}
+
+// #define highByte(c) ((c >> 8) & 0x00FF)
+// #define lowByte(c) (c & 0x00FF)
+
+ISR(TIMER3_COMPA_vect) {
+
+ if (ICR3 > 0 && !sliding) {
+ switch (position) {
+ case 0: {
+ int duty = (((double)F_CPU) / (frequency));
+ ICR3 = duty; // Set max to the period
+ OCR3A = duty >> 1; // Set compare to half the period
+ break;
+ }
+ case 1: {
+ int duty = (((double)F_CPU) / (frequency*2));
+ ICR3 = duty; // Set max to the period
+ OCR3A = duty >> 1; // Set compare to half the period
+ break;
+ }
+ case 2: {
+ int duty = (((double)F_CPU) / (frequency*3));
+ ICR3 = duty; // Set max to the period
+ OCR3A = duty >> 1; // Set compare to half the period
+ break;
+ }
+ }
+ position = (position + 1) % 3;
+ }
+// /* OCR2A has been cleared, per TCCR2A above */
+// // OCR3A = 127;
+
+// // pos1 += incr1;
+// // pos2 += incr2;
+// // pos3 += incr3;
+
+// // sample = sinewave[highByte(pos1)] + sinewave[highByte(pos2)] + sinewave[highByte(pos3)];
+
+// // OCR3A = sample;
+
+
+// OCR3A=pgm_read_byte(&sinewave[pos1]);
+// pos1++;
+// // PORTC &= ~(1<<6);
+
+// /* buffered, 1x gain, active mode */
+// // SPDR = highByte(sample) | 0x70;
+// // while (!(SPSR & (1<<SPIF)));
+
+// // SPDR = lowByte(sample);
+// // while (!(SPSR & (1<<SPIF)));
+
+// // PORTC |= (1<<6);
+}
+
+void play_note(double freq, int vol) {
+
+ if (freq > 0) {
+ DDRC |= (1<<6);
+
+ TCCR3A = (1 << COM3A1) | (0 << COM3A0) | (1 << WGM31) | (0 << WGM30);
+ TCCR3B = (1 << WGM33) | (1 << WGM32) | (0 << CS32) | (1 << CS31) | (0 << CS30);
+
+ if (frequency != 0) {
+ if (frequency < freq) {
+ for (double f = frequency; f <= freq; f += ((freq - frequency) / 500.0)) {
+ send_freq(f, vol);
+ }
+ } else if (frequency > freq) {
+ for (double f = frequency; f >= freq; f -= ((frequency - freq) / 500.0)) {
+ send_freq(f, vol);
+ }
+ }
+ }
+ send_freq(freq, vol);
+ frequency = freq;
+ volume = vol;
+
+ frequencies[voices] = frequency;
+ volumes[voices] = volume;
+ voices++;
+ }
+ // ICR3 = 0xFFFF;
+ // for (int i = 0; i < 10000; i++) {
+ // OCR3A = round((sin(i*freq)*.5)+.5)*0xFFFF;
+ // // _delay_us(50);
+ // }
+
+ // TCCR3A = 0;
+ // TCCR3B = 0;
+}
+
+// void note(int x, float length) {
+// DDRC |= (1<<6);
+// int t = (int)(440*pow(2,-x/12.0)); // starting note
+// for (int y = 0; y < length*1000/t; y++) { // note length
+// PORTC |= (1<<6);
+// delay_us(t);
+// PORTC &= ~(1<<6);
+// delay_us(t);
+// }
+// PORTC &= ~(1<<6);
+// }
+
+// void true_note(float x, float y, float length) {
+// for (uint32_t i = 0; i < length * 50; i++) {
+// uint32_t v = (uint32_t) (round(sin(PI*2*i*640000*pow(2, x/12.0))*.5+1 + sin(PI*2*i*640000*pow(2, y/12.0))*.5+1) / 2 * pow(2, 8));
+// for (int u = 0; u < 8; u++) {
+// if (v & (1 << u) && !(PORTC&(1<<6)))
+// PORTC |= (1<<6);
+// else if (PORTC&(1<<6))
+// PORTC &= ~(1<<6);
+// }
+// }
+// PORTC &= ~(1<<6);
+// } \ No newline at end of file
diff --git a/quantum/beeps.h b/quantum/beeps.h
new file mode 100644
index 0000000000..378983c605
--- /dev/null
+++ b/quantum/beeps.h
@@ -0,0 +1,12 @@
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/io.h>
+#include <util/delay.h>
+
+void note(int x, float length);
+void beeps();
+void true_note(float x, float y, float length);
+void play_note(double freq, int vol);
+void stop_note(double freq);
+void stop_all_notes();
+void init_notes(); \ No newline at end of file
diff --git a/quantum/config_common.h b/quantum/config_common.h
new file mode 100644
index 0000000000..da53fce89b
--- /dev/null
+++ b/quantum/config_common.h
@@ -0,0 +1,116 @@
+#ifndef CONFIG_DEFINITIONS_H
+#define CONFIG_DEFINITIONS_H
+
+#define B0 0x20
+#define B1 0x21
+#define B2 0x22
+#define B3 0x23
+#define B4 0x24
+#define B5 0x25
+#define B6 0x26
+#define B7 0x27
+#define C0 0x30
+#define C1 0x31
+#define C2 0x32
+#define C3 0x33
+#define C4 0x34
+#define C5 0x35
+#define C6 0x36
+#define C7 0x37
+#define D0 0x40
+#define D1 0x41
+#define D2 0x42
+#define D3 0x43
+#define D4 0x44
+#define D5 0x45
+#define D6 0x46
+#define D7 0x47
+#define E0 0x50
+#define E1 0x51
+#define E2 0x52
+#define E3 0x53
+#define E4 0x54
+#define E5 0x55
+#define E6 0x56
+#define E7 0x57
+#define F0 0x60
+#define F1 0x61
+#define F2 0x62
+#define F3 0x63
+#define F4 0x64
+#define F5 0x65
+#define F6 0x66
+#define F7 0x67
+
+#define COL2ROW 0x0
+#define ROW2COL 0x1
+
+#ifdef BLUETOOTH_ENABLE
+#ifdef __AVR_ATmega32U4__
+ #define SERIAL_UART_BAUD 9600
+ #define SERIAL_UART_DATA UDR1
+ #define SERIAL_UART_UBRR ((F_CPU/(16UL*SERIAL_UART_BAUD))-1)
+ #define SERIAL_UART_RXD_VECT USART1_RX_vect
+ #define SERIAL_UART_TXD_READY (UCSR1A&(1<<UDRE1))
+ #define SERIAL_UART_INIT() do { \
+ UBRR1L = (uint8_t) SERIAL_UART_UBRR; /* baud rate */ \
+ UBRR1H = (uint8_t) (SERIAL_UART_UBRR>>8); /* baud rate */ \
+ UCSR1B = (1<<TXEN1); /* TX: enable */ \
+ UCSR1C = (0<<UPM11) | (0<<UPM10) | /* parity: none(00), even(01), odd(11) */ \
+ (0<<UCSZ12) | (1<<UCSZ11) | (1<<UCSZ10); /* data-8bit(011) */ \
+ sei(); \
+ } while(0)
+#else
+# error "USART configuration is needed."
+#endif
+
+
+// I'm fairly sure these aren't needed, but oh well - Jack
+
+/*
+ * PS/2 Interrupt configuration
+ */
+#ifdef PS2_USE_INT
+/* uses INT1 for clock line(ATMega32U4) */
+#define PS2_CLOCK_PORT PORTD
+#define PS2_CLOCK_PIN PIND
+#define PS2_CLOCK_DDR DDRD
+#define PS2_CLOCK_BIT 1
+
+#define PS2_DATA_PORT PORTD
+#define PS2_DATA_PIN PIND
+#define PS2_DATA_DDR DDRD
+#define PS2_DATA_BIT 0
+
+#define PS2_INT_INIT() do { \
+ EICRA |= ((1<<ISC11) | \
+ (0<<ISC10)); \
+} while (0)
+#define PS2_INT_ON() do { \
+ EIMSK |= (1<<INT1); \
+} while (0)
+#define PS2_INT_OFF() do { \
+ EIMSK &= ~(1<<INT1); \
+} while (0)
+#define PS2_INT_VECT INT1_vect
+#endif
+
+/*
+ * PS/2 Busywait configuration
+ */
+#ifdef PS2_USE_BUSYWAIT
+#define PS2_CLOCK_PORT PORTD
+#define PS2_CLOCK_PIN PIND
+#define PS2_CLOCK_DDR DDRD
+#define PS2_CLOCK_BIT 1
+
+#define PS2_DATA_PORT PORTD
+#define PS2_DATA_PIN PIND
+#define PS2_DATA_DDR DDRD
+#define PS2_DATA_BIT 0
+#endif
+
+#endif
+
+#endif
+
diff --git a/quantum/keymap_common.c b/quantum/keymap_common.c
new file mode 100644
index 0000000000..5c00c0afa2
--- /dev/null
+++ b/quantum/keymap_common.c
@@ -0,0 +1,255 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "keymap_common.h"
+#include "report.h"
+#include "keycode.h"
+#include "action_layer.h"
+#include "action.h"
+#include "action_macro.h"
+#include "debug.h"
+#include "backlight.h"
+#include "keymap_midi.h"
+
+static action_t keycode_to_action(uint16_t keycode);
+
+/* converts key to action */
+action_t action_for_key(uint8_t layer, keypos_t key)
+{
+ // 16bit keycodes - important
+ uint16_t keycode = keymap_key_to_keycode(layer, key);
+
+ if (keycode >= 0x0100 && keycode < 0x2000) {
+ // Has a modifier
+ action_t action;
+ // Split it up
+ action.code = ACTION_MODS_KEY(keycode >> 8, keycode & 0xFF); // adds modifier to key
+ return action;
+ } else if (keycode >= 0x2000 && keycode < 0x3000) {
+ // Is a shortcut for function layer, pull last 12bits
+ // This means we have 4,096 FN macros at our disposal
+ return keymap_func_to_action(keycode & 0xFFF);
+ } else if (keycode >= 0x3000 && keycode < 0x4000) {
+ // When the code starts with 3, it's an action macro.
+ action_t action;
+ action.code = ACTION_MACRO(keycode & 0xFF);
+ return action;
+#ifdef BACKLIGHT_ENABLE
+ } else if (keycode >= BL_0 & keycode <= BL_15) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_LEVEL(keycode & 0x000F);
+ return action;
+ } else if (keycode == BL_DEC) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_DECREASE();
+ return action;
+ } else if (keycode == BL_INC) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_INCREASE();
+ return action;
+ } else if (keycode == BL_TOGG) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_TOGGLE();
+ return action;
+ } else if (keycode == BL_STEP) {
+ action_t action;
+ action.code = ACTION_BACKLIGHT_STEP();
+ return action;
+#endif
+ } else if (keycode == RESET) { // RESET is 0x5000, which is why this is here
+ bootloader_jump();
+ return;
+ } else if (keycode == DEBUG) { // DEBUG is 0x5001
+ // TODO: Does this actually work?
+ print("\nDEBUG: enabled.\n");
+ debug_enable = true;
+ return;
+ } else if (keycode >= 0x5000 && keycode < 0x6000) {
+ // Layer movement shortcuts
+ // See .h to see constraints/usage
+ int type = (keycode >> 0x8) & 0xF;
+ if (type == 0x1) {
+ // Layer set "GOTO"
+ int when = (keycode >> 0x4) & 0x3;
+ int layer = keycode & 0xF;
+ action_t action;
+ action.code = ACTION_LAYER_SET(layer, when);
+ return action;
+ } else if (type == 0x2) {
+ // Momentary layer
+ int layer = keycode & 0xFF;
+ action_t action;
+ action.code = ACTION_LAYER_MOMENTARY(layer);
+ return action;
+ } else if (type == 0x3) {
+ // Set default layer
+ int layer = keycode & 0xFF;
+ action_t action;
+ action.code = ACTION_DEFAULT_LAYER_SET(layer);
+ return action;
+ }
+#ifdef MIDI_ENABLE
+ } else if (keycode >= 0x6000 && keycode < 0x7000) {
+ action_t action;
+ action.code = ACTION_FUNCTION_OPT(keycode & 0xFF, (keycode & 0x0F00) >> 8);
+ return action;
+#endif
+#ifdef UNICODE_ENABLE
+ } else if (keycode >= 0x8000) {
+ action_t action;
+ uint16_t unicode = keycode & ~(0x8000);
+ action.code = ACTION_FUNCTION_OPT(unicode & 0xFF, (unicode & 0xFF00) >> 8);
+ return action;
+#endif
+ } else {
+
+ }
+
+ switch (keycode) {
+ case KC_FN0 ... KC_FN31:
+ return keymap_fn_to_action(keycode);
+#ifdef BOOTMAGIC_ENABLE
+ case KC_CAPSLOCK:
+ case KC_LOCKING_CAPS:
+ if (keymap_config.swap_control_capslock || keymap_config.capslock_to_control) {
+ return keycode_to_action(KC_LCTL);
+ }
+ return keycode_to_action(keycode);
+ case KC_LCTL:
+ if (keymap_config.swap_control_capslock) {
+ return keycode_to_action(KC_CAPSLOCK);
+ }
+ return keycode_to_action(KC_LCTL);
+ case KC_LALT:
+ if (keymap_config.swap_lalt_lgui) {
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_LGUI);
+ }
+ return keycode_to_action(KC_LALT);
+ case KC_LGUI:
+ if (keymap_config.swap_lalt_lgui) {
+ return keycode_to_action(KC_LALT);
+ }
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_LGUI);
+ case KC_RALT:
+ if (keymap_config.swap_ralt_rgui) {
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_RGUI);
+ }
+ return keycode_to_action(KC_RALT);
+ case KC_RGUI:
+ if (keymap_config.swap_ralt_rgui) {
+ return keycode_to_action(KC_RALT);
+ }
+ if (keymap_config.no_gui) {
+ return keycode_to_action(ACTION_NO);
+ }
+ return keycode_to_action(KC_RGUI);
+ case KC_GRAVE:
+ if (keymap_config.swap_grave_esc) {
+ return keycode_to_action(KC_ESC);
+ }
+ return keycode_to_action(KC_GRAVE);
+ case KC_ESC:
+ if (keymap_config.swap_grave_esc) {
+ return keycode_to_action(KC_GRAVE);
+ }
+ return keycode_to_action(KC_ESC);
+ case KC_BSLASH:
+ if (keymap_config.swap_backslash_backspace) {
+ return keycode_to_action(KC_BSPACE);
+ }
+ return keycode_to_action(KC_BSLASH);
+ case KC_BSPACE:
+ if (keymap_config.swap_backslash_backspace) {
+ return keycode_to_action(KC_BSLASH);
+ }
+ return keycode_to_action(KC_BSPACE);
+#endif
+ default:
+ return keycode_to_action(keycode);
+ }
+}
+
+
+/* Macro */
+__attribute__ ((weak))
+const macro_t *action_get_macro(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ return MACRO_NONE;
+}
+
+/* Function */
+__attribute__ ((weak))
+void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+}
+
+/* translates keycode to action */
+static action_t keycode_to_action(uint16_t keycode)
+{
+ action_t action;
+ switch (keycode) {
+ case KC_A ... KC_EXSEL:
+ case KC_LCTRL ... KC_RGUI:
+ action.code = ACTION_KEY(keycode);
+ break;
+ case KC_SYSTEM_POWER ... KC_SYSTEM_WAKE:
+ action.code = ACTION_USAGE_SYSTEM(KEYCODE2SYSTEM(keycode));
+ break;
+ case KC_AUDIO_MUTE ... KC_WWW_FAVORITES:
+ action.code = ACTION_USAGE_CONSUMER(KEYCODE2CONSUMER(keycode));
+ break;
+ case KC_MS_UP ... KC_MS_ACCEL2:
+ action.code = ACTION_MOUSEKEY(keycode);
+ break;
+ case KC_TRNS:
+ action.code = ACTION_TRANSPARENT;
+ break;
+ default:
+ action.code = ACTION_NO;
+ break;
+ }
+ return action;
+}
+
+
+/* translates key to keycode */
+uint16_t keymap_key_to_keycode(uint8_t layer, keypos_t key)
+{
+ // Read entire word (16bits)
+ return pgm_read_word(&keymaps[(layer)][(key.row)][(key.col)]);
+}
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint16_t keycode)
+{
+ return (action_t){ .code = pgm_read_word(&fn_actions[FN_INDEX(keycode)]) };
+}
+
+action_t keymap_func_to_action(uint16_t keycode)
+{
+ // For FUNC without 8bit limit
+ return (action_t){ .code = pgm_read_word(&fn_actions[(int)keycode]) };
+}
diff --git a/quantum/keymap_common.h b/quantum/keymap_common.h
new file mode 100644
index 0000000000..b1df4eb0f6
--- /dev/null
+++ b/quantum/keymap_common.h
@@ -0,0 +1,184 @@
+/*
+Copyright 2012,2013 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef KEYMAP_H
+#define KEYMAP_H
+
+#include <stdint.h>
+#include <stdbool.h>
+#include "action.h"
+#include <avr/pgmspace.h>
+#include "keycode.h"
+#include "keymap.h"
+#include "action_macro.h"
+#include "report.h"
+#include "host.h"
+// #include "print.h"
+#include "debug.h"
+
+#ifdef BOOTMAGIC_ENABLE
+/* NOTE: Not portable. Bit field order depends on implementation */
+typedef union {
+ uint16_t raw;
+ struct {
+ bool swap_control_capslock:1;
+ bool capslock_to_control:1;
+ bool swap_lalt_lgui:1;
+ bool swap_ralt_rgui:1;
+ bool no_gui:1;
+ bool swap_grave_esc:1;
+ bool swap_backslash_backspace:1;
+ bool nkro:1;
+ };
+} keymap_config_t;
+keymap_config_t keymap_config;
+#endif
+
+
+/* translates key to keycode */
+uint16_t keymap_key_to_keycode(uint8_t layer, keypos_t key);
+
+/* translates Fn keycode to action */
+action_t keymap_fn_to_action(uint16_t keycode);
+
+/* translates Fn keycode to action */
+action_t keymap_func_to_action(uint16_t keycode);
+
+extern const uint16_t keymaps[][MATRIX_ROWS][MATRIX_COLS];
+extern const uint16_t fn_actions[];
+
+// Ability to use mods in layouts
+#define LCTL(kc) kc | 0x0100
+#define LSFT(kc) kc | 0x0200
+#define LALT(kc) kc | 0x0400
+#define LGUI(kc) kc | 0x0800
+#define RCTL(kc) kc | 0x1100
+#define RSFT(kc) kc | 0x1200
+#define RALT(kc) kc | 0x1400
+#define RGUI(kc) kc | 0x1800
+
+// Aliases for shifted symbols
+// Each key has a 4-letter code, and some have longer aliases too.
+// While the long aliases are descriptive, the 4-letter codes
+// make for nicer grid layouts (everything lines up), and are
+// the preferred style for Quantum.
+#define KC_TILD LSFT(KC_GRV) // ~
+#define KC_TILDE KC_TILD
+
+#define KC_EXLM LSFT(KC_1) // !
+#define KC_EXCLAIM KC_EXLM
+
+#define KC_AT LSFT(KC_2) // @
+#define KC_HASH LSFT(KC_3) // #
+
+#define KC_DLR LSFT(KC_4) // $
+#define KC_DOLLAR KC_DLR
+
+#define KC_PERC LSFT(KC_5) // %
+#define KC_PERCENT KC_PERC
+
+#define KC_CIRC LSFT(KC_6) // ^
+#define KC_CIRCUMFLEX KC_CIRC
+
+#define KC_AMPR LSFT(KC_7) // &
+#define KC_AMPERSAND KC_AMPR
+
+#define KC_ASTR LSFT(KC_8) // *
+#define KC_ASTERISK KC_ASTR
+
+#define KC_LPRN LSFT(KC_9) // (
+#define KC_LEFT_PAREN KC_LPRN
+
+#define KC_RPRN LSFT(KC_0) // )
+#define KC_RIGHT_PAREN KC_RPRN
+
+#define KC_UNDS LSFT(KC_MINS) // _
+#define KC_UNDERSCORE KC_UNDS
+
+#define KC_PLUS LSFT(KC_EQL) // +
+
+#define KC_LCBR LSFT(KC_LBRC) // {
+#define KC_LEFT_CURLY_BRACE KC_LCBR
+
+#define KC_RCBR LSFT(KC_RBRC) // }
+#define KC_RIGHT_CURLY_BRACE KC_RCBR
+
+#define KC_PIPE LSFT(KC_SLSH) // |
+
+// Alias for function layers than expand past FN31
+#define FUNC(kc) kc | 0x2000
+
+// Aliases
+#define S(kc) LSFT(kc)
+#define F(kc) FUNC(kc)
+
+#define M(kc) kc | 0x3000
+
+#define MACRODOWN(...) (record->event.pressed ? MACRO(__VA_ARGS__) : MACRO_NONE)
+
+// These affect the backlight (if your keyboard has one).
+// We don't need to comment them out if your keyboard doesn't have a backlight,
+// since they don't take up any space.
+#define BL_ON 0x4009
+#define BL_OFF 0x4000
+#define BL_0 0x4000
+#define BL_1 0x4001
+#define BL_2 0x4002
+#define BL_3 0x4003
+#define BL_4 0x4004
+#define BL_5 0x4005
+#define BL_6 0x4006
+#define BL_7 0x4007
+#define BL_8 0x4008
+#define BL_9 0x4009
+#define BL_10 0x400A
+#define BL_11 0x400B
+#define BL_12 0x400C
+#define BL_13 0x400D
+#define BL_14 0x400E
+#define BL_15 0x400F
+#define BL_DEC 0x4010
+#define BL_INC 0x4011
+#define BL_TOGG 0x4012
+#define BL_STEP 0x4013
+
+#define RESET 0x5000
+#define DEBUG 0x5001
+
+// GOTO layer - 16 layers max
+// when:
+// ON_PRESS = 1
+// ON_RELEASE = 2
+// Unless you have a good reason not to do so, prefer ON_PRESS (1) as your default.
+#define TO(layer, when) (layer | 0x5100 | (when << 0x4))
+
+// Momentary switch layer - 256 layer max
+#define MO(layer) (layer | 0x5200)
+
+// Set default layer - 256 layer max
+#define DF(layer) (layer | 0x5300)
+
+#define MIDI(n) (n | 0x6000)
+
+// For sending unicode codes.
+// You may not send codes over 1FFF -- this supports most of UTF8.
+// To have a key that sends out Œ, go UC(0x0152)
+#define UNICODE(n) (n | 0x8000)
+#define UC(n) UNICODE(n)
+
+
+#endif
diff --git a/quantum/keymap_extras/keymap_colemak.h b/quantum/keymap_extras/keymap_colemak.h
new file mode 100644
index 0000000000..c8066ea666
--- /dev/null
+++ b/quantum/keymap_extras/keymap_colemak.h
@@ -0,0 +1,74 @@
+#ifndef KEYMAP_COLEMAK_H
+#define KEYMAP_COLEMAK_H
+
+#include "keymap_common.h"
+// For software implementation of colemak
+#define CM_Q KC_Q
+#define CM_W KC_W
+#define CM_F KC_E
+#define CM_P KC_R
+#define CM_G KC_T
+#define CM_J KC_Y
+#define CM_L KC_U
+#define CM_U KC_I
+#define CM_Y KC_O
+#define CM_SCLN KC_P
+
+#define CM_A KC_A
+#define CM_R KC_S
+#define CM_S KC_D
+#define CM_T KC_F
+#define CM_D KC_G
+#define CM_H KC_H
+#define CM_N KC_J
+#define CM_E KC_K
+#define CM_I KC_L
+#define CM_O KC_SCLN
+
+#define CM_Z KC_Z
+#define CM_X KC_X
+#define CM_C KC_C
+#define CM_V KC_V
+#define CM_B KC_B
+#define CM_K KC_N
+#define CM_M KC_M
+#define CM_COMM KC_COMM
+#define CM_DOT KC_DOT
+#define CM_SLSH KC_SLSH
+
+// Make it easy to support these in macros
+// TODO: change macro implementation so these aren't needed
+#define KC_CM_Q CM_Q
+#define KC_CM_W CM_W
+#define KC_CM_F CM_F
+#define KC_CM_P CM_P
+#define KC_CM_G CM_G
+#define KC_CM_J CM_J
+#define KC_CM_L CM_L
+#define KC_CM_U CM_U
+#define KC_CM_Y CM_Y
+#define KC_CM_SCLN CM_SCLN
+
+#define KC_CM_A CM_A
+#define KC_CM_R CM_R
+#define KC_CM_S CM_S
+#define KC_CM_T CM_T
+#define KC_CM_D CM_D
+#define KC_CM_H CM_H
+#define KC_CM_N CM_N
+#define KC_CM_E CM_E
+#define KC_CM_I CM_I
+#define KC_CM_O CM_O
+
+#define KC_CM_Z CM_Z
+#define KC_CM_X CM_X
+#define KC_CM_C CM_C
+#define KC_CM_V CM_V
+#define KC_CM_B CM_B
+#define KC_CM_K CM_K
+#define KC_CM_M CM_M
+#define KC_CM_COMM CM_COMM
+#define KC_CM_DOT CM_DOT
+#define KC_CM_SLSH CM_SLSH
+
+#endif
diff --git a/quantum/keymap_extras/keymap_dvorak.h b/quantum/keymap_extras/keymap_dvorak.h
new file mode 100644
index 0000000000..d172e0019b
--- /dev/null
+++ b/quantum/keymap_extras/keymap_dvorak.h
@@ -0,0 +1,72 @@
+#ifndef KEYMAP_DVORAK_H
+#define KEYMAP_DVORAK_H
+
+#include "keymap_common.h"
+
+// Normal characters
+#define DV_GRV KC_GRV
+#define DV_1 KC_1
+#define DV_2 KC_2
+#define DV_3 KC_3
+#define DV_4 KC_4
+#define DV_5 KC_5
+#define DV_6 KC_6
+#define DV_7 KC_7
+#define DV_8 KC_8
+#define DV_9 KC_9
+#define DV_0 KC_0
+#define DV_LBRC KC_MINS
+#define DV_RBRC KC_EQL
+
+#define DV_QUOT KC_Q
+#define DV_COMM KC_W
+#define DV_DOT KC_E
+#define DV_P KC_R
+#define DV_Y KC_T
+#define DV_F KC_Y
+#define DV_G KC_U
+#define DV_C KC_I
+#define DV_R KC_O
+#define DV_L KC_P
+#define DV_SLSH KC_LBRC
+#define DV_EQL KC_RBRC
+
+#define DV_A KC_A
+#define DV_O KC_S
+#define DV_E KC_D
+#define DV_U KC_F
+#define DV_I KC_G
+#define DV_D KC_H
+#define DV_H KC_J
+#define DV_T KC_K
+#define DV_N KC_L
+#define DV_S KC_SCLN
+#define DV_MINS KC_QUOT
+
+#define DV_SCLN KC_Z
+#define DV_Q KC_X
+#define DV_J KC_C
+#define DV_K KC_V
+#define DV_X KC_B
+#define DV_B KC_N
+#define DV_M KC_M
+#define DV_W KC_COMM
+#define DV_V KC_DOT
+#define DV_Z KC_SLSH
+
+// Shifted characters
+#define DV_TILD LSFT(DV_GRV)
+#define DV_EXLM LSFT(DV_1)
+#define DV_AT LSFT(DV_2)
+#define DV_HASH LSFT(DV_3)
+#define DV_DLR LSFT(DV_4)
+#define DV_PERC LSFT(DV_5)
+#define DV_CIRC LSFT(DV_6)
+#define DV_AMPR LSFT(DV_7)
+#define DV_ASTR LSFT(DV_8)
+#define DV_LPRN LSFT(DV_9)
+#define DV_RPRN LSFT(DV_0)
+#define DV_LCBR LSFT(DV_LBRC)
+#define DV_RCBR LSFT(DV_RBRC)
+
+#endif \ No newline at end of file
diff --git a/quantum/keymap_extras/keymap_french.h b/quantum/keymap_extras/keymap_french.h
new file mode 100644
index 0000000000..ccfaed8f07
--- /dev/null
+++ b/quantum/keymap_extras/keymap_french.h
@@ -0,0 +1,83 @@
+#ifndef KEYMAP_FRENCH_H
+#define KEYMAP_FRENCH_H
+
+#include "keymap_common.h"
+
+// Alt gr
+#define ALGR(kc) kc | 0x1400
+#define NO_ALGR KC_RALT
+
+// Normal characters
+#define FR_SUP2 KC_GRV
+#define FR_AMP KC_1
+#define FR_EACU KC_2
+#define FR_QUOT KC_3
+#define FR_APOS KC_4
+#define FR_LPRN KC_5
+#define FR_MINS KC_6
+#define FR_EGRV KC_7
+#define FR_UNDS KC_8
+#define FR_CCED KC_9
+#define FR_AGRV KC_0
+#define FR_RPRN KC_MINS
+#define FR_EQL KC_EQL
+
+#define FR_A KC_Q
+#define FR_Z KC_W
+#define FR_CIRC KC_LBRC
+#define FR_DLR KC_RBRC
+
+#define FR_Q KC_A
+#define FR_M KC_SCLN
+#define FR_UGRV KC_QUOT
+#define FR_ASTR KC_NUHS
+
+#define FR_LESS KC_NUBS
+#define FR_W KC_Z
+#define FR_COMM KC_M
+#define FR_SCLN KC_COMM
+#define FR_COLN KC_DOT
+#define FR_EXLM KC_SLSH
+
+// Shifted characters
+#define FR_1 LSFT(KC_1)
+#define FR_2 LSFT(KC_2)
+#define FR_3 LSFT(KC_3)
+#define FR_4 LSFT(KC_4)
+#define FR_5 LSFT(KC_5)
+#define FR_6 LSFT(KC_6)
+#define FR_7 LSFT(KC_7)
+#define FR_8 LSFT(KC_8)
+#define FR_9 LSFT(KC_9)
+#define FR_0 LSFT(KC_0)
+#define FR_OVRR LSFT(FR_RPRN)
+#define FR_PLUS LSFT(FR_EQL)
+
+#define FR_UMLT LSFT(FR_CIRC)
+#define FR_PND LSFT(FR_DLR)
+#define FR_PERC LSFT(FR_UGRV)
+#define FR_MU LSFT(FR_ASTR)
+
+#define FR_GRTR LSFT(FR_LESS)
+#define FR_QUES LSFT(FR_COMM)
+#define FR_DOT LSFT(FR_SCLN)
+#define FR_SLSH LSFT(FR_COLN)
+#define FR_SECT LSFT(FR_EXLM)
+
+// Alt Gr-ed characters
+#define FR_TILD ALGR(KC_2)
+#define FR_HASH ALGR(KC_3)
+#define FR_LCBR ALGR(KC_4)
+#define FR_LBRC ALGR(KC_5)
+#define FR_PIPE ALGR(KC_6)
+#define FR_GRV ALGR(KC_7)
+#define FR_BSLS ALGR(KC_8)
+#define FR_CIRC ALGR(KC_9)
+#define FR_AT ALGR(KC_0)
+#define FR_RBRC ALGR(FR_RPRN)
+#define FR_LCBR ALGR(FR_EQL)
+
+#define FR_EURO ALGR(KC_E)
+#define FR_BULT ALGR(FR_DLR)
+
+#endif \ No newline at end of file
diff --git a/quantum/keymap_extras/keymap_nordic.h b/quantum/keymap_extras/keymap_nordic.h
new file mode 100644
index 0000000000..02a704216a
--- /dev/null
+++ b/quantum/keymap_extras/keymap_nordic.h
@@ -0,0 +1,59 @@
+#ifndef KEYMAP_NORDIC_H
+#define KEYMAP_NORDIC_H
+
+#include "keymap_common.h"
+
+// Alt gr
+#define ALGR(kc) kc | 0x1400
+#define NO_ALGR KC_RALT
+
+// Normal characters
+#define NO_HALF KC_GRV
+#define NO_PLUS KC_MINS
+#define NO_ACUT KC_EQL
+
+#define NO_AM KC_LBRC
+#define NO_QUOT KC_RBRC
+#define NO_AE KC_SCLN
+#define NO_OSLH KC_QUOT
+#define NO_APOS KC_NUHS
+
+#define NO_LESS KC_NUBS
+#define NO_MINS KC_SLSH
+
+// Shifted characters
+#define NO_SECT LSFT(NO_HALF)
+#define NO_QUO2 LSFT(KC_2)
+#define NO_BULT LSFT(KC_4)
+#define NO_AMP LSFT(KC_6)
+#define NO_SLSH LSFT(KC_7)
+#define NO_LPRN LSFT(KC_8)
+#define NO_RPRN LSFT(KC_9)
+#define NO_EQL LSFT(KC_0)
+#define NO_QUES LSFT(NO_PLUS)
+#define NO_GRV LSFT(NO_ACUT)
+
+#define NO_CIRC LSFT(NO_QUOT)
+
+#define NO_GRTR LSFT(NO_LESS)
+#define NO_SCLN LSFT(KC_COMM)
+#define NO_COLN LSFT(KC_DOT)
+#define NO_UNDS LSFT(NO_MINS)
+
+// Alt Gr-ed characters
+#define NO_AT ALGR(KC_2)
+#define NO_PND ALGR(KC_3)
+#define NO_DLR ALGR(KC_4)
+#define NO_LCBR ALGR(KC_7)
+#define NO_LBRC ALGR(KC_8)
+#define NO_RBRC ALGR(KC_9)
+#define NO_RCBR ALGR(KC_0)
+#define NO_PIPE ALGR(NO_ACUT)
+
+#define NO_EURO ALGR(KC_E)
+#define NO_TILD ALGR(NO_QUOT)
+
+#define NO_BSLS ALGR(NO_LESS)
+#define NO_MU ALGR(KC_M)
+
+#endif \ No newline at end of file
diff --git a/quantum/keymap_extras/keymap_spanish.h b/quantum/keymap_extras/keymap_spanish.h
new file mode 100644
index 0000000000..7f980afbcf
--- /dev/null
+++ b/quantum/keymap_extras/keymap_spanish.h
@@ -0,0 +1,62 @@
+#ifndef KEYMAP_SPANISH_H
+#define KEYMAP_SPANISH_H
+
+#include "keymap_common.h"
+
+// Alt gr
+#define ALGR(kc) kc | 0x1400
+#define NO_ALGR KC_RALT
+
+// Normal characters
+#define ES_OVRR KC_GRV
+#define ES_APOS KC_MINS
+#define ES_IEXL KC_EQL
+
+#define ES_GRV KC_LBRC
+#define ES_PLUS KC_RBRC
+
+#define ES_NTIL KC_SCLN
+#define ES_ACUT KC_QUOT
+#define ES_CCED KC_NUHS
+
+#define ES_LESS KC_NUBS
+#define ES_MINS KC_SLSH
+
+// Shifted characters
+#define ES_ASML LSFT(ES_OVRR)
+#define ES_QUOT LSFT(KC_2)
+#define ES_OVDT LSFT(KC_3)
+#define ES_AMPR LSFT(KC_6)
+#define ES_SLSH LSFT(KC_7)
+#define ES_LPRN LSFT(KC_8)
+#define ES_RPRN LSFT(KC_9)
+#define ES_EQL LSFT(KC_0)
+#define ES_QUES LSFT(ES_APOS)
+#define ES_IQUE LSFT(ES_IEXL)
+
+#define ES_CIRC LSFT(ES_GRV)
+#define ES_ASTR LSFT(ES_PLUS)
+
+#define ES_UMLT LSFT(ES_GRV)
+
+#define ES_GRTR LSFT(ES_LESS)
+#define ES_SCLN LSFT(ES_COMM)
+#define ES_COLN LSFT(ES_DOT)
+#define ES_UNDS LSFT(ES_MINS)
+
+// Alt Gr-ed characters
+#define ES_BSLS ALGR(ES_OVRR)
+#define ES_PIPE ALGR(KC_1)
+#define ES_AT ALGR(KC_2)
+#define ES_HASH ALGR(KC_3)
+#define ES_TILD ALGR(KC_4)
+#define ES_EURO ALGR(KC_5)
+#define ES_NOT ALGR(KC_6)
+
+#define ES_LBRC ALGR(ES_GRV)
+#define ES_RBRC ALGR(ES_PLUS)
+
+#define ES_LCBR ALGR(ES_ACUT)
+#define ES_RCRB ALGR(ES_CCED)
+
+#endif \ No newline at end of file
diff --git a/quantum/keymap_extras/keymap_uk.h b/quantum/keymap_extras/keymap_uk.h
new file mode 100644
index 0000000000..5b4bd3c0d4
--- /dev/null
+++ b/quantum/keymap_extras/keymap_uk.h
@@ -0,0 +1,36 @@
+#ifndef KEYMAP_UK_H
+#define KEYMAP_UK_H
+
+#include "keymap_common.h"
+
+// Alt gr
+#define ALGR(kc) kc | 0x1400
+#define NO_ALGR KC_RALT
+
+// Normal characters
+#define UK_HASH KC_NUHS
+
+#define UK_BSLS KC_NUBS
+
+// Shifted characters
+#define UK_NOT LSFT(KC_GRV)
+#define UK_QUOT LSFT(KC_2)
+#define UK_PND LSFT(KC_3)
+
+#define UK_AT LSFT(KC_QUOT)
+#define UK_TILD LSFT(KC_NUHS)
+
+#define UK_PIPE LSFT(KC_NUBS)
+
+// Alt Gr-ed characters
+#define UK_BRKP ALGR(KC_GRV)
+#define UK_EURO ALGR(KC_4)
+
+#define UK_EACT ALGR(KC_E)
+#define UK_UACT ALGR(KC_U)
+#define UK_IACT ALGR(KC_I)
+#define UK_OACT ALGR(KC_O)
+
+#define UK_AACT ALGR(KC_A)
+
+#endif \ No newline at end of file
diff --git a/quantum/keymap_midi.c b/quantum/keymap_midi.c
new file mode 100644
index 0000000000..b7eba3ab76
--- /dev/null
+++ b/quantum/keymap_midi.c
@@ -0,0 +1,110 @@
+/*
+Copyright 2015 Jack Humbert <jack.humb@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "keymap_common.h"
+#include "keymap_midi.h"
+#include <lufa.h>
+
+uint8_t starting_note = 0x0C;
+int offset = 7;
+
+void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+ if (id != 0) {
+ if (record->event.pressed) {
+ midi_send_noteon(&midi_device, opt, (id & 0xFF), 127);
+ } else {
+ midi_send_noteoff(&midi_device, opt, (id & 0xFF), 127);
+ }
+ }
+
+ if (record->event.key.col == (MATRIX_COLS - 1) && record->event.key.row == (MATRIX_ROWS - 1)) {
+ if (record->event.pressed) {
+ starting_note++;
+ play_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[0 + offset])/12.0+(MATRIX_ROWS - 1)), 0xC);
+ midi_send_cc(&midi_device, 0, 0x7B, 0);
+ midi_send_cc(&midi_device, 1, 0x7B, 0);
+ midi_send_cc(&midi_device, 2, 0x7B, 0);
+ midi_send_cc(&midi_device, 3, 0x7B, 0);
+ midi_send_cc(&midi_device, 4, 0x7B, 0);
+ return;
+ } else {
+ stop_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[0 + offset])/12.0+(MATRIX_ROWS - 1)));
+ stop_all_notes();
+ return;
+ }
+ }
+ if (record->event.key.col == (MATRIX_COLS - 2) && record->event.key.row == (MATRIX_ROWS - 1)) {
+ if (record->event.pressed) {
+ starting_note--;
+ play_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[0 + offset])/12.0+(MATRIX_ROWS - 1)), 0xC);
+ midi_send_cc(&midi_device, 0, 0x7B, 0);
+ midi_send_cc(&midi_device, 1, 0x7B, 0);
+ midi_send_cc(&midi_device, 2, 0x7B, 0);
+ midi_send_cc(&midi_device, 3, 0x7B, 0);
+ midi_send_cc(&midi_device, 4, 0x7B, 0);
+ return;
+ } else {
+ stop_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[0 + offset])/12.0+(MATRIX_ROWS - 1)));
+ stop_all_notes();
+ return;
+ }
+ }
+
+ if (record->event.key.col == (MATRIX_COLS - 3) && record->event.key.row == (MATRIX_ROWS - 1) && record->event.pressed) {
+ offset++;
+ midi_send_cc(&midi_device, 0, 0x7B, 0);
+ midi_send_cc(&midi_device, 1, 0x7B, 0);
+ midi_send_cc(&midi_device, 2, 0x7B, 0);
+ midi_send_cc(&midi_device, 3, 0x7B, 0);
+ midi_send_cc(&midi_device, 4, 0x7B, 0);
+ stop_all_notes();
+ for (int i = 0; i <= 7; i++) {
+ play_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[i + offset])/12.0+(MATRIX_ROWS - 1)), 0xC);
+ _delay_us(80000);
+ stop_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[i + offset])/12.0+(MATRIX_ROWS - 1)));
+ _delay_us(8000);
+ }
+ return;
+ }
+ if (record->event.key.col == (MATRIX_COLS - 4) && record->event.key.row == (MATRIX_ROWS - 1) && record->event.pressed) {
+ offset--;
+ midi_send_cc(&midi_device, 0, 0x7B, 0);
+ midi_send_cc(&midi_device, 1, 0x7B, 0);
+ midi_send_cc(&midi_device, 2, 0x7B, 0);
+ midi_send_cc(&midi_device, 3, 0x7B, 0);
+ midi_send_cc(&midi_device, 4, 0x7B, 0);
+ stop_all_notes();
+ for (int i = 0; i <= 7; i++) {
+ play_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[i + offset])/12.0+(MATRIX_ROWS - 1)), 0xC);
+ _delay_us(80000);
+ stop_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[i + offset])/12.0+(MATRIX_ROWS - 1)));
+ _delay_us(8000);
+ }
+ return;
+ }
+
+ if (record->event.pressed) {
+ // midi_send_noteon(&midi_device, record->event.key.row, starting_note + SCALE[record->event.key.col], 127);
+ midi_send_noteon(&midi_device, 0, (starting_note + SCALE[record->event.key.col + offset])+12*(MATRIX_ROWS - record->event.key.row), 127);
+ play_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[record->event.key.col + offset])/12.0+(MATRIX_ROWS - record->event.key.row)), 0xF);
+ } else {
+ // midi_send_noteoff(&midi_device, record->event.key.row, starting_note + SCALE[record->event.key.col], 127);
+ midi_send_noteoff(&midi_device, 0, (starting_note + SCALE[record->event.key.col + offset])+12*(MATRIX_ROWS - record->event.key.row), 127);
+ stop_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(starting_note + SCALE[record->event.key.col + offset])/12.0+(MATRIX_ROWS - record->event.key.row)));
+ }
+} \ No newline at end of file
diff --git a/quantum/keymap_midi.h b/quantum/keymap_midi.h
new file mode 100644
index 0000000000..c5917f884e
--- /dev/null
+++ b/quantum/keymap_midi.h
@@ -0,0 +1,220 @@
+/*
+Copyright 2015 Jack Humbert <jack.humb@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef KEYMAP_MIDI_H
+#define KEYMAP_MIDI_H
+
+#define MIDI 0x6000
+#define MIDI12 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000, 0x6000
+
+#define CHNL(note, channel) (note + (channel << 8))
+
+#define SCALE (int []){ 0 + (12*0), 2 + (12*0), 4 + (12*0), 5 + (12*0), 7 + (12*0), 9 + (12*0), 11 + (12*0), \
+ 0 + (12*1), 2 + (12*1), 4 + (12*1), 5 + (12*1), 7 + (12*1), 9 + (12*1), 11 + (12*1), \
+ 0 + (12*2), 2 + (12*2), 4 + (12*2), 5 + (12*2), 7 + (12*2), 9 + (12*2), 11 + (12*2), \
+ 0 + (12*3), 2 + (12*3), 4 + (12*3), 5 + (12*3), 7 + (12*3), 9 + (12*3), 11 + (12*3), \
+ 0 + (12*4), 2 + (12*4), 4 + (12*4), 5 + (12*4), 7 + (12*4), 9 + (12*4), 11 + (12*4), }
+
+#define N_CN1 (0x600C + (12 * -1) + 0 )
+#define N_CN1S (0x600C + (12 * -1) + 1 )
+#define N_DN1F (0x600C + (12 * -1) + 1 )
+#define N_DN1 (0x600C + (12 * -1) + 2 )
+#define N_DN1S (0x600C + (12 * -1) + 3 )
+#define N_EN1F (0x600C + (12 * -1) + 3 )
+#define N_EN1 (0x600C + (12 * -1) + 4 )
+#define N_FN1 (0x600C + (12 * -1) + 5 )
+#define N_FN1S (0x600C + (12 * -1) + 6 )
+#define N_GN1F (0x600C + (12 * -1) + 6 )
+#define N_GN1 (0x600C + (12 * -1) + 7 )
+#define N_GN1S (0x600C + (12 * -1) + 8 )
+#define N_AN1F (0x600C + (12 * -1) + 8 )
+#define N_AN1 (0x600C + (12 * -1) + 9 )
+#define N_AN1S (0x600C + (12 * -1) + 10)
+#define N_BN1F (0x600C + (12 * -1) + 10)
+#define N_BN1 (0x600C + (12 * -1) + 11)
+#define N_C0 (0x600C + (12 * 0) + 0 )
+#define N_C0S (0x600C + (12 * 0) + 1 )
+#define N_D0F (0x600C + (12 * 0) + 1 )
+#define N_D0 (0x600C + (12 * 0) + 2 )
+#define N_D0S (0x600C + (12 * 0) + 3 )
+#define N_E0F (0x600C + (12 * 0) + 3 )
+#define N_E0 (0x600C + (12 * 0) + 4 )
+#define N_F0 (0x600C + (12 * 0) + 5 )
+#define N_F0S (0x600C + (12 * 0) + 6 )
+#define N_G0F (0x600C + (12 * 0) + 6 )
+#define N_G0 (0x600C + (12 * 0) + 7 )
+#define N_G0S (0x600C + (12 * 0) + 8 )
+#define N_A0F (0x600C + (12 * 0) + 8 )
+#define N_A0 (0x600C + (12 * 0) + 9 )
+#define N_A0S (0x600C + (12 * 0) + 10)
+#define N_B0F (0x600C + (12 * 0) + 10)
+#define N_B0 (0x600C + (12 * 0) + 11)
+#define N_C1 (0x600C + (12 * 1) + 0 )
+#define N_C1S (0x600C + (12 * 1) + 1 )
+#define N_D1F (0x600C + (12 * 1) + 1 )
+#define N_D1 (0x600C + (12 * 1) + 2 )
+#define N_D1S (0x600C + (12 * 1) + 3 )
+#define N_E1F (0x600C + (12 * 1) + 3 )
+#define N_E1 (0x600C + (12 * 1) + 4 )
+#define N_F1 (0x600C + (12 * 1) + 5 )
+#define N_F1S (0x600C + (12 * 1) + 6 )
+#define N_G1F (0x600C + (12 * 1) + 6 )
+#define N_G1 (0x600C + (12 * 1) + 7 )
+#define N_G1S (0x600C + (12 * 1) + 8 )
+#define N_A1F (0x600C + (12 * 1) + 8 )
+#define N_A1 (0x600C + (12 * 1) + 9 )
+#define N_A1S (0x600C + (12 * 1) + 10)
+#define N_B1F (0x600C + (12 * 1) + 10)
+#define N_B1 (0x600C + (12 * 1) + 11)
+#define N_C2 (0x600C + (12 * 2) + 0 )
+#define N_C2S (0x600C + (12 * 2) + 1 )
+#define N_D2F (0x600C + (12 * 2) + 1 )
+#define N_D2 (0x600C + (12 * 2) + 2 )
+#define N_D2S (0x600C + (12 * 2) + 3 )
+#define N_E2F (0x600C + (12 * 2) + 3 )
+#define N_E2 (0x600C + (12 * 2) + 4 )
+#define N_F2 (0x600C + (12 * 2) + 5 )
+#define N_F2S (0x600C + (12 * 2) + 6 )
+#define N_G2F (0x600C + (12 * 2) + 6 )
+#define N_G2 (0x600C + (12 * 2) + 7 )
+#define N_G2S (0x600C + (12 * 2) + 8 )
+#define N_A2F (0x600C + (12 * 2) + 8 )
+#define N_A2 (0x600C + (12 * 2) + 9 )
+#define N_A2S (0x600C + (12 * 2) + 10)
+#define N_B2F (0x600C + (12 * 2) + 10)
+#define N_B2 (0x600C + (12 * 2) + 11)
+#define N_C3 (0x600C + (12 * 3) + 0 )
+#define N_C3S (0x600C + (12 * 3) + 1 )
+#define N_D3F (0x600C + (12 * 3) + 1 )
+#define N_D3 (0x600C + (12 * 3) + 2 )
+#define N_D3S (0x600C + (12 * 3) + 3 )
+#define N_E3F (0x600C + (12 * 3) + 3 )
+#define N_E3 (0x600C + (12 * 3) + 4 )
+#define N_F3 (0x600C + (12 * 3) + 5 )
+#define N_F3S (0x600C + (12 * 3) + 6 )
+#define N_G3F (0x600C + (12 * 3) + 6 )
+#define N_G3 (0x600C + (12 * 3) + 7 )
+#define N_G3S (0x600C + (12 * 3) + 8 )
+#define N_A3F (0x600C + (12 * 3) + 8 )
+#define N_A3 (0x600C + (12 * 3) + 9 )
+#define N_A3S (0x600C + (12 * 3) + 10)
+#define N_B3F (0x600C + (12 * 3) + 10)
+#define N_B3 (0x600C + (12 * 3) + 11)
+#define N_C4 (0x600C + (12 * 4) + 0 )
+#define N_C4S (0x600C + (12 * 4) + 1 )
+#define N_D4F (0x600C + (12 * 4) + 1 )
+#define N_D4 (0x600C + (12 * 4) + 2 )
+#define N_D4S (0x600C + (12 * 4) + 3 )
+#define N_E4F (0x600C + (12 * 4) + 3 )
+#define N_E4 (0x600C + (12 * 4) + 4 )
+#define N_F4 (0x600C + (12 * 4) + 5 )
+#define N_F4S (0x600C + (12 * 4) + 6 )
+#define N_G4F (0x600C + (12 * 4) + 6 )
+#define N_G4 (0x600C + (12 * 4) + 7 )
+#define N_G4S (0x600C + (12 * 4) + 8 )
+#define N_A4F (0x600C + (12 * 4) + 8 )
+#define N_A4 (0x600C + (12 * 4) + 9 )
+#define N_A4S (0x600C + (12 * 4) + 10)
+#define N_B4F (0x600C + (12 * 4) + 10)
+#define N_B4 (0x600C + (12 * 4) + 11)
+#define N_C5 (0x600C + (12 * 5) + 0 )
+#define N_C5S (0x600C + (12 * 5) + 1 )
+#define N_D5F (0x600C + (12 * 5) + 1 )
+#define N_D5 (0x600C + (12 * 5) + 2 )
+#define N_D5S (0x600C + (12 * 5) + 3 )
+#define N_E5F (0x600C + (12 * 5) + 3 )
+#define N_E5 (0x600C + (12 * 5) + 4 )
+#define N_F5 (0x600C + (12 * 5) + 5 )
+#define N_F5S (0x600C + (12 * 5) + 6 )
+#define N_G5F (0x600C + (12 * 5) + 6 )
+#define N_G5 (0x600C + (12 * 5) + 7 )
+#define N_G5S (0x600C + (12 * 5) + 8 )
+#define N_A5F (0x600C + (12 * 5) + 8 )
+#define N_A5 (0x600C + (12 * 5) + 9 )
+#define N_A5S (0x600C + (12 * 5) + 10)
+#define N_B5F (0x600C + (12 * 5) + 10)
+#define N_B5 (0x600C + (12 * 5) + 11)
+#define N_C6 (0x600C + (12 * 6) + 0 )
+#define N_C6S (0x600C + (12 * 6) + 1 )
+#define N_D6F (0x600C + (12 * 6) + 1 )
+#define N_D6 (0x600C + (12 * 6) + 2 )
+#define N_D6S (0x600C + (12 * 6) + 3 )
+#define N_E6F (0x600C + (12 * 6) + 3 )
+#define N_E6 (0x600C + (12 * 6) + 4 )
+#define N_F6 (0x600C + (12 * 6) + 5 )
+#define N_F6S (0x600C + (12 * 6) + 6 )
+#define N_G6F (0x600C + (12 * 6) + 6 )
+#define N_G6 (0x600C + (12 * 6) + 7 )
+#define N_G6S (0x600C + (12 * 6) + 8 )
+#define N_A6F (0x600C + (12 * 6) + 8 )
+#define N_A6 (0x600C + (12 * 6) + 9 )
+#define N_A6S (0x600C + (12 * 6) + 10)
+#define N_B6F (0x600C + (12 * 6) + 10)
+#define N_B6 (0x600C + (12 * 6) + 11)
+#define N_C7 (0x600C + (12 * 7) + 0 )
+#define N_C7S (0x600C + (12 * 7) + 1 )
+#define N_D7F (0x600C + (12 * 7) + 1 )
+#define N_D7 (0x600C + (12 * 7) + 2 )
+#define N_D7S (0x600C + (12 * 7) + 3 )
+#define N_E7F (0x600C + (12 * 7) + 3 )
+#define N_E7 (0x600C + (12 * 7) + 4 )
+#define N_F7 (0x600C + (12 * 7) + 5 )
+#define N_F7S (0x600C + (12 * 7) + 6 )
+#define N_G7F (0x600C + (12 * 7) + 6 )
+#define N_G7 (0x600C + (12 * 7) + 7 )
+#define N_G7S (0x600C + (12 * 7) + 8 )
+#define N_A7F (0x600C + (12 * 7) + 8 )
+#define N_A7 (0x600C + (12 * 7) + 9 )
+#define N_A7S (0x600C + (12 * 7) + 10)
+#define N_B7F (0x600C + (12 * 7) + 10)
+#define N_B7 (0x600C + (12 * 7) + 11)
+#define N_C8 (0x600C + (12 * 8) + 0 )
+#define N_C8S (0x600C + (12 * 8) + 1 )
+#define N_D8F (0x600C + (12 * 8) + 1 )
+#define N_D8 (0x600C + (12 * 8) + 2 )
+#define N_D8S (0x600C + (12 * 8) + 3 )
+#define N_E8F (0x600C + (12 * 8) + 3 )
+#define N_E8 (0x600C + (12 * 8) + 4 )
+#define N_F8 (0x600C + (12 * 8) + 5 )
+#define N_F8S (0x600C + (12 * 8) + 6 )
+#define N_G8F (0x600C + (12 * 8) + 6 )
+#define N_G8 (0x600C + (12 * 8) + 7 )
+#define N_G8S (0x600C + (12 * 8) + 8 )
+#define N_A8F (0x600C + (12 * 8) + 8 )
+#define N_A8 (0x600C + (12 * 8) + 9 )
+#define N_A8S (0x600C + (12 * 8) + 10)
+#define N_B8F (0x600C + (12 * 8) + 10)
+#define N_B8 (0x600C + (12 * 8) + 11)
+#define N_C8 (0x600C + (12 * 8) + 0 )
+#define N_C8S (0x600C + (12 * 8) + 1 )
+#define N_D8F (0x600C + (12 * 8) + 1 )
+#define N_D8 (0x600C + (12 * 8) + 2 )
+#define N_D8S (0x600C + (12 * 8) + 3 )
+#define N_E8F (0x600C + (12 * 8) + 3 )
+#define N_E8 (0x600C + (12 * 8) + 4 )
+#define N_F8 (0x600C + (12 * 8) + 5 )
+#define N_F8S (0x600C + (12 * 8) + 6 )
+#define N_G8F (0x600C + (12 * 8) + 6 )
+#define N_G8 (0x600C + (12 * 8) + 7 )
+#define N_G8S (0x600C + (12 * 8) + 8 )
+#define N_A8F (0x600C + (12 * 8) + 8 )
+#define N_A8 (0x600C + (12 * 8) + 9 )
+#define N_A8S (0x600C + (12 * 8) + 10)
+#define N_B8F (0x600C + (12 * 8) + 10)
+#define N_B8 (0x600C + (12 * 8) + 11)
+
+#endif \ No newline at end of file
diff --git a/quantum/keymap_unicode.c b/quantum/keymap_unicode.c
new file mode 100644
index 0000000000..a9357edec7
--- /dev/null
+++ b/quantum/keymap_unicode.c
@@ -0,0 +1,59 @@
+/*
+Copyright 2015 Jack Humbert <jack.humb@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include "keymap_common.h"
+
+uint16_t hextokeycode(int hex) {
+ if (hex == 0x0) {
+ return KC_0;
+ } else if (hex < 0xA) {
+ return KC_1 + (hex - 0x1);
+ } else {
+ return KC_A + (hex - 0xA);
+ }
+}
+
+void action_function(keyrecord_t *record, uint8_t id, uint8_t opt)
+{
+
+ if (record->event.pressed) {
+ uint16_t unicode = (opt << 8) | id;
+ register_code(KC_LALT);
+
+ register_code(hextokeycode((unicode & 0xF000) >> 12));
+ unregister_code(hextokeycode((unicode & 0xF000) >> 12));
+ register_code(hextokeycode((unicode & 0x0F00) >> 8));
+ unregister_code(hextokeycode((unicode & 0x0F00) >> 8));
+ register_code(hextokeycode((unicode & 0x00F0) >> 4));
+ unregister_code(hextokeycode((unicode & 0x00F0) >> 4));
+ register_code(hextokeycode((unicode & 0x000F)));
+ unregister_code(hextokeycode((unicode & 0x000F)));
+
+ /* Test 'a' */
+ // register_code(hextokeycode(0x0));
+ // unregister_code(hextokeycode(0x0));
+ // register_code(hextokeycode(0x0));
+ // unregister_code(hextokeycode(0x0));
+ // register_code(hextokeycode(0x6));
+ // unregister_code(hextokeycode(0x6));
+ // register_code(hextokeycode(0x1));
+ // unregister_code(hextokeycode(0x1));
+
+ unregister_code(KC_LALT);
+ }
+ return;
+} \ No newline at end of file
diff --git a/quantum/led.c b/quantum/led.c
new file mode 100644
index 0000000000..2c05746607
--- /dev/null
+++ b/quantum/led.c
@@ -0,0 +1,38 @@
+/*
+Copyright 2012 Jun Wako <wakojun@gmail.com>
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include <avr/io.h>
+#include "stdint.h"
+#include "led.h"
+
+
+void led_set(uint8_t usb_led)
+{
+ // // Using PE6 Caps Lock LED
+ // if (usb_led & (1<<USB_LED_CAPS_LOCK))
+ // {
+ // // Output high.
+ // DDRE |= (1<<6);
+ // PORTE |= (1<<6);
+ // }
+ // else
+ // {
+ // // Output low.
+ // DDRE &= ~(1<<6);
+ // PORTE &= ~(1<<6);
+ // }
+}
diff --git a/quantum/matrix.c b/quantum/matrix.c
new file mode 100644
index 0000000000..95bf4c0973
--- /dev/null
+++ b/quantum/matrix.c
@@ -0,0 +1,311 @@
+/*
+Copyright 2012 Jun Wako
+Generated by planckkeyboard.com (2014 Jack Humbert)
+
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+/*
+ * scan matrix
+ */
+#include <stdint.h>
+#include <stdbool.h>
+#include <avr/io.h>
+#include <util/delay.h>
+#include "print.h"
+#include "debug.h"
+#include "util.h"
+#include "matrix.h"
+
+#ifndef DEBOUNCE
+# define DEBOUNCE 10
+#endif
+static uint8_t debouncing = DEBOUNCE;
+
+/* matrix state(1:on, 0:off) */
+static matrix_row_t matrix[MATRIX_ROWS];
+static matrix_row_t matrix_debouncing[MATRIX_ROWS];
+
+#if DIODE_DIRECTION == ROW2COL
+ static matrix_row_t matrix_reversed[MATRIX_COLS];
+ static matrix_row_t matrix_reversed_debouncing[MATRIX_COLS];
+#endif
+
+static matrix_row_t read_cols(void);
+static void init_cols(void);
+static void unselect_rows(void);
+static void select_row(uint8_t row);
+
+__attribute__ ((weak))
+void * matrix_init_kb(void) {
+
+};
+
+__attribute__ ((weak))
+void * matrix_scan_kb(void) {
+
+};
+
+inline
+uint8_t matrix_rows(void)
+{
+ return MATRIX_ROWS;
+}
+
+inline
+uint8_t matrix_cols(void)
+{
+ return MATRIX_COLS;
+}
+
+void matrix_init(void)
+{
+ // To use PORTF disable JTAG with writing JTD bit twice within four cycles.
+ MCUCR |= (1<<JTD);
+ MCUCR |= (1<<JTD);
+
+
+ // initialize row and col
+ unselect_rows();
+ init_cols();
+
+ // initialize matrix state: all keys off
+ for (uint8_t i=0; i < MATRIX_ROWS; i++) {
+ matrix[i] = 0;
+ matrix_debouncing[i] = 0;
+ }
+
+ if (matrix_init_kb) {
+ (*matrix_init_kb)();
+ }
+}
+
+
+uint8_t matrix_scan(void)
+{
+
+#if DIODE_DIRECTION == COL2ROW
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ select_row(i);
+ _delay_us(30); // without this wait read unstable value.
+ matrix_row_t cols = read_cols();
+ if (matrix_debouncing[i] != cols) {
+ matrix_debouncing[i] = cols;
+ if (debouncing) {
+ debug("bounce!: "); debug_hex(debouncing); debug("\n");
+ }
+ debouncing = DEBOUNCE;
+ }
+ unselect_rows();
+ }
+
+ if (debouncing) {
+ if (--debouncing) {
+ _delay_ms(1);
+ } else {
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ matrix[i] = matrix_debouncing[i];
+ }
+ }
+ }
+#else
+ for (uint8_t i = 0; i < MATRIX_COLS; i++) {
+ select_row(i);
+ _delay_us(30); // without this wait read unstable value.
+ matrix_row_t rows = read_cols();
+ if (matrix_reversed_debouncing[i] != rows) {
+ matrix_reversed_debouncing[i] = rows;
+ if (debouncing) {
+ debug("bounce!: "); debug_hex(debouncing); debug("\n");
+ }
+ debouncing = DEBOUNCE;
+ }
+ unselect_rows();
+ }
+
+ if (debouncing) {
+ if (--debouncing) {
+ _delay_ms(1);
+ } else {
+ for (uint8_t i = 0; i < MATRIX_COLS; i++) {
+ matrix_reversed[i] = matrix_reversed_debouncing[i];
+ }
+ }
+ }
+ for (uint8_t y = 0; y < MATRIX_ROWS; y++) {
+ matrix_row_t row = 0;
+ for (uint8_t x = 0; x < MATRIX_COLS; x++) {
+ row |= ((matrix_reversed[x] & (1<<y)) >> y) << x;
+ }
+ matrix[y] = row;
+ }
+#endif
+
+ if (matrix_scan_kb) {
+ (*matrix_scan_kb)();
+ }
+
+ return 1;
+}
+
+bool matrix_is_modified(void)
+{
+ if (debouncing) return false;
+ return true;
+}
+
+inline
+bool matrix_is_on(uint8_t row, uint8_t col)
+{
+ return (matrix[row] & ((matrix_row_t)1<col));
+}
+
+inline
+matrix_row_t matrix_get_row(uint8_t row)
+{
+ return matrix[row];
+}
+
+void matrix_print(void)
+{
+ print("\nr/c 0123456789ABCDEF\n");
+ for (uint8_t row = 0; row < MATRIX_ROWS; row++) {
+ phex(row); print(": ");
+ pbin_reverse16(matrix_get_row(row));
+ print("\n");
+ }
+}
+
+uint8_t matrix_key_count(void)
+{
+ uint8_t count = 0;
+ for (uint8_t i = 0; i < MATRIX_ROWS; i++) {
+ count += bitpop16(matrix[i]);
+ }
+ return count;
+}
+
+static void init_cols(void)
+{
+ int B = 0, C = 0, D = 0, E = 0, F = 0;
+
+#if DIODE_DIRECTION == COL2ROW
+ for(int x = 0; x < MATRIX_COLS; x++) {
+ int col = COLS[x];
+#else
+ for(int x = 0; x < MATRIX_ROWS; x++) {
+ int col = ROWS[x];
+#endif
+ if ((col & 0xF0) == 0x20) {
+ B |= (1<<(col & 0x0F));
+ } else if ((col & 0xF0) == 0x30) {
+ C |= (1<<(col & 0x0F));
+ } else if ((col & 0xF0) == 0x40) {
+ D |= (1<<(col & 0x0F));
+ } else if ((col & 0xF0) == 0x50) {
+ E |= (1<<(col & 0x0F));
+ } else if ((col & 0xF0) == 0x60) {
+ F |= (1<<(col & 0x0F));
+ }
+ }
+ DDRB &= ~(B); PORTB |= (B);
+ DDRC &= ~(C); PORTC |= (C);
+ DDRD &= ~(D); PORTD |= (D);
+ DDRE &= ~(E); PORTE |= (E);
+ DDRF &= ~(F); PORTF |= (F);
+}
+
+static matrix_row_t read_cols(void)
+{
+ matrix_row_t result = 0;
+
+#if DIODE_DIRECTION == COL2ROW
+ for(int x = 0; x < MATRIX_COLS; x++) {
+ int col = COLS[x];
+#else
+ for(int x = 0; x < MATRIX_ROWS; x++) {
+ int col = ROWS[x];
+#endif
+
+ if ((col & 0xF0) == 0x20) {
+ result |= (PINB&(1<<(col & 0x0F)) ? 0 : (1<<x));
+ } else if ((col & 0xF0) == 0x30) {
+ result |= (PINC&(1<<(col & 0x0F)) ? 0 : (1<<x));
+ } else if ((col & 0xF0) == 0x40) {
+ result |= (PIND&(1<<(col & 0x0F)) ? 0 : (1<<x));
+ } else if ((col & 0xF0) == 0x50) {
+ result |= (PINE&(1<<(col & 0x0F)) ? 0 : (1<<x));
+ } else if ((col & 0xF0) == 0x60) {
+ result |= (PINF&(1<<(col & 0x0F)) ? 0 : (1<<x));
+ }
+ }
+ return result;
+}
+
+static void unselect_rows(void)
+{
+ int B = 0, C = 0, D = 0, E = 0, F = 0;
+
+#if DIODE_DIRECTION == COL2ROW
+ for(int x = 0; x < MATRIX_ROWS; x++) {
+ int row = ROWS[x];
+#else
+ for(int x = 0; x < MATRIX_COLS; x++) {
+ int row = COLS[x];
+#endif
+ if ((row & 0xF0) == 0x20) {
+ B |= (1<<(row & 0x0F));
+ } else if ((row & 0xF0) == 0x30) {
+ C |= (1<<(row & 0x0F));
+ } else if ((row & 0xF0) == 0x40) {
+ D |= (1<<(row & 0x0F));
+ } else if ((row & 0xF0) == 0x50) {
+ E |= (1<<(row & 0x0F));
+ } else if ((row & 0xF0) == 0x60) {
+ F |= (1<<(row & 0x0F));
+ }
+ }
+ DDRB &= ~(B); PORTB |= (B);
+ DDRC &= ~(C); PORTC |= (C);
+ DDRD &= ~(D); PORTD |= (D);
+ DDRE &= ~(E); PORTE |= (E);
+ DDRF &= ~(F); PORTF |= (F);
+}
+
+static void select_row(uint8_t row)
+{
+
+#if DIODE_DIRECTION == COL2ROW
+ int row_pin = ROWS[row];
+#else
+ int row_pin = COLS[row];
+#endif
+
+ if ((row_pin & 0xF0) == 0x20) {
+ DDRB |= (1<<(row_pin & 0x0F));
+ PORTB &= ~(1<<(row_pin & 0x0F));
+ } else if ((row_pin & 0xF0) == 0x30) {
+ DDRC |= (1<<(row_pin & 0x0F));
+ PORTC &= ~(1<<(row_pin & 0x0F));
+ } else if ((row_pin & 0xF0) == 0x40) {
+ DDRD |= (1<<(row_pin & 0x0F));
+ PORTD &= ~(1<<(row_pin & 0x0F));
+ } else if ((row_pin & 0xF0) == 0x50) {
+ DDRE |= (1<<(row_pin & 0x0F));
+ PORTE &= ~(1<<(row_pin & 0x0F));
+ } else if ((row_pin & 0xF0) == 0x60) {
+ DDRF |= (1<<(row_pin & 0x0F));
+ PORTF &= ~(1<<(row_pin & 0x0F));
+ }
+} \ No newline at end of file
diff --git a/teensy-sdk b/teensy-sdk
new file mode 160000
+Subproject 19892c196894e6676fa69c732e05a03a68d5cb0
diff --git a/tmk_core/common.mk b/tmk_core/common.mk
index cb030b3313..edbcc282a5 100644
--- a/tmk_core/common.mk
+++ b/tmk_core/common.mk
@@ -49,6 +49,11 @@ ifdef NKRO_ENABLE
OPT_DEFS += -DNKRO_ENABLE
endif
+ifdef MIDI_ENABLE
+ OPT_DEFS += -DMIDI_ENABLE
+endif
+
+
ifdef USB_6KRO_ENABLE
OPT_DEFS += -DUSB_6KRO_ENABLE
endif
@@ -64,6 +69,10 @@ ifdef BACKLIGHT_ENABLE
OPT_DEFS += -DBACKLIGHT_ENABLE
endif
+ifdef BLUETOOTH_ENABLE
+ OPT_DEFS += -DBLUETOOTH_ENABLE
+endif
+
ifdef KEYMAP_SECTION_ENABLE
OPT_DEFS += -DKEYMAP_SECTION_ENABLE
diff --git a/tmk_core/common/keymap.c b/tmk_core/common/keymap.c
index d489238085..11f4aa8aaa 100644
--- a/tmk_core/common/keymap.c
+++ b/tmk_core/common/keymap.c
@@ -28,6 +28,7 @@ static action_t keycode_to_action(uint8_t keycode);
/* converts key to action */
+__attribute__ ((weak))
action_t action_for_key(uint8_t layer, keypos_t key)
{
uint8_t keycode = keymap_key_to_keycode(layer, key);
diff --git a/tmk_core/common/matrix.h b/tmk_core/common/matrix.h
index ec6f8cd431..85415df719 100644
--- a/tmk_core/common/matrix.h
+++ b/tmk_core/common/matrix.h
@@ -63,6 +63,10 @@ void matrix_print(void);
void matrix_power_up(void);
void matrix_power_down(void);
+/* keyboard-specific setup/loop functionality */
+void * matrix_init_kb(void);
+void * matrix_scan_kb(void);
+
#ifdef __cplusplus
}
#endif
diff --git a/tmk_core/protocol/bluefruit/bluefruit.c b/tmk_core/protocol/bluefruit/bluefruit.c
index cf26b83dff..47c63555cd 100644
--- a/tmk_core/protocol/bluefruit/bluefruit.c
+++ b/tmk_core/protocol/bluefruit/bluefruit.c
@@ -2,20 +2,16 @@
Bluefruit Protocol for TMK firmware
Author: Benjamin Gould, 2013
Based on code Copyright 2011 Jun Wako <wakojun@gmail.com>
-
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 2 of the License, or
(at your option) any later version.
-
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
-
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
-
*/
#include <stdint.h>
@@ -76,6 +72,13 @@ static void send_mouse(report_mouse_t *report);
static void send_system(uint16_t data);
static void send_consumer(uint16_t data);
+
+void sendString(char string[], int length) {
+ for(int i = 0; i < length; i++) {
+ serial_send(string[i]);
+ }
+}
+
static host_driver_t driver = {
keyboard_leds,
send_keyboard,
@@ -100,6 +103,7 @@ static void send_keyboard(report_keyboard_t *report)
#endif
bluefruit_serial_send(0xFD);
for (uint8_t i = 0; i < KEYBOARD_REPORT_SIZE; i++) {
+
bluefruit_serial_send(report->raw[i]);
}
#ifdef BLUEFRUIT_TRACE_SERIAL
@@ -198,5 +202,4 @@ static void send_consumer(uint16_t data)
#ifdef BLUEFRUIT_TRACE_SERIAL
bluefruit_trace_footer();
#endif
-}
-
+} \ No newline at end of file
diff --git a/tmk_core/protocol/bluefruit/bluefruit.h b/tmk_core/protocol/bluefruit/bluefruit.h
index 4f9b58836d..ceacc4a367 100644
--- a/tmk_core/protocol/bluefruit/bluefruit.h
+++ b/tmk_core/protocol/bluefruit/bluefruit.h
@@ -2,17 +2,14 @@
Bluefruit Protocol for TMK firmware
Author: Benjamin Gould, 2013
Based on code Copyright 2011 Jun Wako <wakojun@gmail.com>
-
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 2 of the License, or
(at your option) any later version.
-
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
-
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
@@ -25,4 +22,4 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
host_driver_t *bluefruit_driver(void);
-#endif
+#endif \ No newline at end of file
diff --git a/tmk_core/protocol/bluefruit/main.c b/tmk_core/protocol/bluefruit/main.c
index 871062ab11..0dbb637e2c 100644
--- a/tmk_core/protocol/bluefruit/main.c
+++ b/tmk_core/protocol/bluefruit/main.c
@@ -22,7 +22,7 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
#include <avr/wdt.h>
#include <avr/sleep.h>
#include <util/delay.h>
-#include "serial.h"
+#include "../serial.h"
#include "keyboard.h"
#include "usb.h"
#include "host.h"
@@ -40,23 +40,26 @@ along with this program. If not, see <http://www.gnu.org/licenses/>.
#define BLUEFRUIT_HOST_DRIVER 1
#define PJRC_HOST_DRIVER 2
+
int main(void)
{
CPU_PRESCALE(0);
- DDRD = _BV(PD5);
- DDRB = _BV(PB0);
+ // DDRD = _BV(PD5);
+ // DDRB = _BV(PB0);
- PORTD = _BV(PD5);
- PORTB = _BV(PB0);
+ // PORTD = _BV(PD5);
+ // PORTB = _BV(PB0);
print_set_sendchar(sendchar);
- usb_init();
- _delay_ms(2000);
+ // usb_init();
+ // _delay_ms(2000);
// while (!usb_configured()) /* wait */
+
+
dprintf("Initializing keyboard...\n");
keyboard_init();
@@ -64,53 +67,72 @@ int main(void)
// is not configured, choose the Bluefruit, otherwise use USB
// Definitely would prefer to have this driven by an input pin and make
// it switch dynamically - BCG
- if (!usb_configured()) {
+ // if (!usb_configured()) {
- // Send power to Bluefruit... Adafruit says it takes 27 mA, I think
- // the pins should provide 40 mA, but just in case I switch the
- // Bluefruit using a transistor - BCG
- DDRB = _BV(PB6);
- PORTB |= _BV(PB6);
+ // // Send power to Bluefruit... Adafruit says it takes 27 mA, I think
+ // // the pins should provide 40 mA, but just in case I switch the
+ // // Bluefruit using a transistor - BCG
+ // DDRB = _BV(PB6);
+ // PORTB |= _BV(PB6);
dprintf("Setting host driver to bluefruit...\n");
host_set_driver(bluefruit_driver());
dprintf("Initializing serial...\n");
serial_init();
-
- // wait an extra second for the PC's operating system
- // to load drivers and do whatever it does to actually
- // be ready for input
- _delay_ms(1000);
- PORTD = ~_BV(PD5);
- dprintf("Starting main loop");
- while (1) {
- keyboard_task();
- }
- } else {
+ // char swpa[] = "+++\r\n";
+ // for (int i = 0; i < 5; i++) {
+ // serial_send(swpa[i]);
+ // }
+
+ // char ble_enable[] = "AT+BLEKEYBOARDEN=1\r\n";
+ // for (int i = 0; i < 20; i++) {
+ // serial_send(ble_enable[i]);
+ // }
+
+ // char reset[] = "ATZ\r\n";
+ // for (int i = 0; i < 5; i++) {
+ // serial_send(reset[i]);
+ // }
+
+ // for (int i = 0; i < 5; i++) {
+ // serial_send(swpa[i]);
+ // }
- // I'm not smart enough to get this done with LUFA - BCG
- dprintf("Setting host driver to PJRC...\n");
- host_set_driver(pjrc_driver());
-#ifdef SLEEP_LED_ENABLE
- sleep_led_init();
-#endif
// wait an extra second for the PC's operating system
// to load drivers and do whatever it does to actually
// be ready for input
_delay_ms(1000);
- PORTB = ~_BV(PB0);
+ // PORTD = ~_BV(PD5);
dprintf("Starting main loop");
while (1) {
- while (suspend) {
- suspend_power_down();
- if (remote_wakeup && suspend_wakeup_condition()) {
- usb_remote_wakeup();
- }
- }
- keyboard_task();
+ keyboard_task();
}
- }
+
+// } else {
+
+// // I'm not smart enough to get this done with LUFA - BCG
+// dprintf("Setting host driver to PJRC...\n");
+// host_set_driver(pjrc_driver());
+// #ifdef SLEEP_LED_ENABLE
+// sleep_led_init();
+// #endif
+// // wait an extra second for the PC's operating system
+// // to load drivers and do whatever it does to actually
+// // be ready for input
+// _delay_ms(1000);
+// PORTB = ~_BV(PB0);
+// dprintf("Starting main loop");
+// while (1) {
+// while (suspend) {
+// suspend_power_down();
+// if (remote_wakeup && suspend_wakeup_condition()) {
+// usb_remote_wakeup();
+// }
+// }
+// keyboard_task();
+// }
+// }
}
diff --git a/tmk_core/protocol/lufa.mk b/tmk_core/protocol/lufa.mk
index 87386be998..4905760bb4 100644
--- a/tmk_core/protocol/lufa.mk
+++ b/tmk_core/protocol/lufa.mk
@@ -17,6 +17,19 @@ LUFA_SRC = $(LUFA_DIR)/lufa.c \
$(LUFA_DIR)/descriptor.c \
$(LUFA_SRC_USB)
+ifdef MIDI_ENABLE
+ LUFA_SRC += $(LUFA_DIR)/midi/midi.c \
+ $(LUFA_DIR)/midi/midi_device.c \
+ $(LUFA_DIR)/midi/bytequeue/bytequeue.c \
+ $(LUFA_DIR)/midi/bytequeue/interrupt_setting.c \
+ $(LUFA_SRC_USBCLASS)
+endif
+
+ifdef BLUETOOTH_ENABLE
+ LUFA_SRC += $(LUFA_DIR)/bluetooth.c \
+ $(TMK_DIR)/protocol/serial_uart.c
+endif
+
SRC += $(LUFA_SRC)
# Search Path
diff --git a/tmk_core/protocol/lufa/bluetooth.c b/tmk_core/protocol/lufa/bluetooth.c
new file mode 100644
index 0000000000..ed66e52c1f
--- /dev/null
+++ b/tmk_core/protocol/lufa/bluetooth.c
@@ -0,0 +1,37 @@
+/*
+Bluefruit Protocol for TMK firmware
+Author: Benjamin Gould, 2013
+ Jack Humbert, 2015
+Based on code Copyright 2011 Jun Wako <wakojun@gmail.com>
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#include <stdint.h>
+#include "report.h"
+#include "print.h"
+#include "debug.h"
+#include "../serial.h"
+#include "bluetooth.h"
+
+void bluefruit_keyboard_print_report(report_keyboard_t *report)
+{
+ if (!debug_keyboard) return;
+ dprintf("keys: "); for (int i = 0; i < KEYBOARD_REPORT_KEYS; i++) { debug_hex8(report->keys[i]); dprintf(" "); }
+ dprintf(" mods: "); debug_hex8(report->mods);
+ dprintf(" reserved: "); debug_hex8(report->reserved);
+ dprintf("\n");
+}
+
+void bluefruit_serial_send(uint8_t data)
+{
+ serial_send(data);
+} \ No newline at end of file
diff --git a/tmk_core/protocol/lufa/bluetooth.h b/tmk_core/protocol/lufa/bluetooth.h
new file mode 100644
index 0000000000..01f07e8e67
--- /dev/null
+++ b/tmk_core/protocol/lufa/bluetooth.h
@@ -0,0 +1,63 @@
+/*
+Bluefruit Protocol for TMK firmware
+Author: Benjamin Gould, 2013
+ Jack Humbert, 2015
+Based on code Copyright 2011 Jun Wako <wakojun@gmail.com>
+This program is free software: you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation, either version 2 of the License, or
+(at your option) any later version.
+This program is distributed in the hope that it will be useful,
+but WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+GNU General Public License for more details.
+You should have received a copy of the GNU General Public License
+along with this program. If not, see <http://www.gnu.org/licenses/>.
+*/
+
+#ifndef BLUETOOTH_H
+#define BLUETOOTH_H
+
+void bluefruit_serial_send(uint8_t data);
+
+/*
++-----------------+-------------------+-------+
+| Consumer Key | Bit Map | Hex |
++-----------------+-------------------+-------+
+| Home | 00000001 00000000 | 01 00 |
+| KeyboardLayout | 00000010 00000000 | 02 00 |
+| Search | 00000100 00000000 | 04 00 |
+| Snapshot | 00001000 00000000 | 08 00 |
+| VolumeUp | 00010000 00000000 | 10 00 |
+| VolumeDown | 00100000 00000000 | 20 00 |
+| Play/Pause | 01000000 00000000 | 40 00 |
+| Fast Forward | 10000000 00000000 | 80 00 |
+| Rewind | 00000000 00000001 | 00 01 |
+| Scan Next Track | 00000000 00000010 | 00 02 |
+| Scan Prev Track | 00000000 00000100 | 00 04 |
+| Random Play | 00000000 00001000 | 00 08 |
+| Stop | 00000000 00010000 | 00 10 |
++-------------------------------------+-------+
+*/
+#define CONSUMER2BLUEFRUIT(usage) \
+ (usage == AUDIO_MUTE ? 0x0000 : \
+ (usage == AUDIO_VOL_UP ? 0x1000 : \
+ (usage == AUDIO_VOL_DOWN ? 0x2000 : \
+ (usage == TRANSPORT_NEXT_TRACK ? 0x0002 : \
+ (usage == TRANSPORT_PREV_TRACK ? 0x0004 : \
+ (usage == TRANSPORT_STOP ? 0x0010 : \
+ (usage == TRANSPORT_STOP_EJECT ? 0x0000 : \
+ (usage == TRANSPORT_PLAY_PAUSE ? 0x4000 : \
+ (usage == AL_CC_CONFIG ? 0x0000 : \
+ (usage == AL_EMAIL ? 0x0000 : \
+ (usage == AL_CALCULATOR ? 0x0000 : \
+ (usage == AL_LOCAL_BROWSER ? 0x0000 : \
+ (usage == AC_SEARCH ? 0x0400 : \
+ (usage == AC_HOME ? 0x0100 : \
+ (usage == AC_BACK ? 0x0000 : \
+ (usage == AC_FORWARD ? 0x0000 : \
+ (usage == AC_STOP ? 0x0000 : \
+ (usage == AC_REFRESH ? 0x0000 : \
+ (usage == AC_BOOKMARKS ? 0x0000 : 0)))))))))))))))))))
+
+#endif \ No newline at end of file
diff --git a/tmk_core/protocol/lufa/descriptor.c b/tmk_core/protocol/lufa/descriptor.c
index c13a81bda8..b345da27b4 100644
--- a/tmk_core/protocol/lufa/descriptor.c
+++ b/tmk_core/protocol/lufa/descriptor.c
@@ -266,7 +266,7 @@ const USB_Descriptor_Configuration_t PROGMEM ConfigurationDescriptor =
.ConfigAttributes = (USB_CONFIG_ATTR_RESERVED | USB_CONFIG_ATTR_REMOTEWAKEUP),
- .MaxPowerConsumption = USB_CONFIG_POWER_MA(100)
+ .MaxPowerConsumption = USB_CONFIG_POWER_MA(500)
},
/*
@@ -486,6 +486,165 @@ const USB_Descriptor_Configuration_t PROGMEM ConfigurationDescriptor =
.PollingIntervalMS = 0x01
},
#endif
+
+#ifdef MIDI_ENABLE
+ .Audio_ControlInterface =
+ {
+ .Header = {.Size = sizeof(USB_Descriptor_Interface_t), .Type = DTYPE_Interface},
+
+ .InterfaceNumber = AC_INTERFACE,
+ .AlternateSetting = 0,
+
+ .TotalEndpoints = 0,
+
+ .Class = AUDIO_CSCP_AudioClass,
+ .SubClass = AUDIO_CSCP_ControlSubclass,
+ .Protocol = AUDIO_CSCP_ControlProtocol,
+
+ .InterfaceStrIndex = NO_DESCRIPTOR
+ },
+
+ .Audio_ControlInterface_SPC =
+ {
+ .Header = {.Size = sizeof(USB_Audio_Descriptor_Interface_AC_t), .Type = DTYPE_CSInterface},
+ .Subtype = AUDIO_DSUBTYPE_CSInterface_Header,
+
+ .ACSpecification = VERSION_BCD(1,0,0),
+ .TotalLength = sizeof(USB_Audio_Descriptor_Interface_AC_t),
+
+ .InCollection = 1,
+ .InterfaceNumber = AS_INTERFACE,
+ },
+
+ .Audio_StreamInterface =
+ {
+ .Header = {.Size = sizeof(USB_Descriptor_Interface_t), .Type = DTYPE_Interface},
+
+ .InterfaceNumber = AS_INTERFACE,
+ .AlternateSetting = 0,
+
+ .TotalEndpoints = 2,
+
+ .Class = AUDIO_CSCP_AudioClass,
+ .SubClass = AUDIO_CSCP_MIDIStreamingSubclass,
+ .Protocol = AUDIO_CSCP_StreamingProtocol,
+
+ .InterfaceStrIndex = NO_DESCRIPTOR
+ },
+
+ .Audio_StreamInterface_SPC =
+ {
+ .Header = {.Size = sizeof(USB_MIDI_Descriptor_AudioInterface_AS_t), .Type = DTYPE_CSInterface},
+ .Subtype = AUDIO_DSUBTYPE_CSInterface_General,
+
+ .AudioSpecification = VERSION_BCD(1,0,0),
+
+ .TotalLength = (sizeof(USB_Descriptor_Configuration_t) -
+ offsetof(USB_Descriptor_Configuration_t, Audio_StreamInterface_SPC))
+ },
+
+ .MIDI_In_Jack_Emb =
+ {
+ .Header = {.Size = sizeof(USB_MIDI_Descriptor_InputJack_t), .Type = DTYPE_CSInterface},
+ .Subtype = AUDIO_DSUBTYPE_CSInterface_InputTerminal,
+
+ .JackType = MIDI_JACKTYPE_Embedded,
+ .JackID = 0x01,
+
+ .JackStrIndex = NO_DESCRIPTOR
+ },
+
+ .MIDI_In_Jack_Ext =
+ {
+ .Header = {.Size = sizeof(USB_MIDI_Descriptor_InputJack_t), .Type = DTYPE_CSInterface},
+ .Subtype = AUDIO_DSUBTYPE_CSInterface_InputTerminal,
+
+ .JackType = MIDI_JACKTYPE_External,
+ .JackID = 0x02,
+
+ .JackStrIndex = NO_DESCRIPTOR
+ },
+
+ .MIDI_Out_Jack_Emb =
+ {
+ .Header = {.Size = sizeof(USB_MIDI_Descriptor_OutputJack_t), .Type = DTYPE_CSInterface},
+ .Subtype = AUDIO_DSUBTYPE_CSInterface_OutputTerminal,
+
+ .JackType = MIDI_JACKTYPE_Embedded,
+ .JackID = 0x03,
+
+ .NumberOfPins = 1,
+ .SourceJackID = {0x02},
+ .SourcePinID = {0x01},
+
+ .JackStrIndex = NO_DESCRIPTOR
+ },
+
+ .MIDI_Out_Jack_Ext =
+ {
+ .Header = {.Size = sizeof(USB_MIDI_Descriptor_OutputJack_t), .Type = DTYPE_CSInterface},
+ .Subtype = AUDIO_DSUBTYPE_CSInterface_OutputTerminal,
+
+ .JackType = MIDI_JACKTYPE_External,
+ .JackID = 0x04,
+
+ .NumberOfPins = 1,
+ .SourceJackID = {0x01},
+ .SourcePinID = {0x01},
+
+ .JackStrIndex = NO_DESCRIPTOR
+ },
+
+ .MIDI_In_Jack_Endpoint =
+ {
+ .Endpoint =
+ {
+ .Header = {.Size = sizeof(USB_Audio_Descriptor_StreamEndpoint_Std_t), .Type = DTYPE_Endpoint},
+
+ .EndpointAddress = MIDI_STREAM_OUT_EPADDR,
+ .Attributes = (EP_TYPE_BULK | ENDPOINT_ATTR_NO_SYNC | ENDPOINT_USAGE_DATA),
+ .EndpointSize = MIDI_STREAM_EPSIZE,
+ .PollingIntervalMS = 0x05
+ },
+
+ .Refresh = 0,
+ .SyncEndpointNumber = 0
+ },
+
+ .MIDI_In_Jack_Endpoint_SPC =
+ {
+ .Header = {.Size = sizeof(USB_MIDI_Descriptor_Jack_Endpoint_t), .Type = DTYPE_CSEndpoint},
+ .Subtype = AUDIO_DSUBTYPE_CSEndpoint_General,
+
+ .TotalEmbeddedJacks = 0x01,
+ .AssociatedJackID = {0x01}
+ },
+
+ .MIDI_Out_Jack_Endpoint =
+ {
+ .Endpoint =
+ {
+ .Header = {.Size = sizeof(USB_Audio_Descriptor_StreamEndpoint_Std_t), .Type = DTYPE_Endpoint},
+
+ .EndpointAddress = MIDI_STREAM_IN_EPADDR,
+ .Attributes = (EP_TYPE_BULK | ENDPOINT_ATTR_NO_SYNC | ENDPOINT_USAGE_DATA),
+ .EndpointSize = MIDI_STREAM_EPSIZE,
+ .PollingIntervalMS = 0x05
+ },
+
+ .Refresh = 0,
+ .SyncEndpointNumber = 0
+ },
+
+ .MIDI_Out_Jack_Endpoint_SPC =
+ {
+ .Header = {.Size = sizeof(USB_MIDI_Descriptor_Jack_Endpoint_t), .Type = DTYPE_CSEndpoint},
+ .Subtype = AUDIO_DSUBTYPE_CSEndpoint_General,
+
+ .TotalEmbeddedJacks = 0x01,
+ .AssociatedJackID = {0x03}
+ }
+#endif
};
diff --git a/tmk_core/protocol/lufa/descriptor.h b/tmk_core/protocol/lufa/descriptor.h
index 42af07917c..4fd81a0e87 100644
--- a/tmk_core/protocol/lufa/descriptor.h
+++ b/tmk_core/protocol/lufa/descriptor.h
@@ -85,6 +85,25 @@ typedef struct
USB_HID_Descriptor_HID_t NKRO_HID;
USB_Descriptor_Endpoint_t NKRO_INEndpoint;
#endif
+
+#ifdef MIDI_ENABLE
+ // MIDI Audio Control Interface
+ USB_Descriptor_Interface_t Audio_ControlInterface;
+ USB_Audio_Descriptor_Interface_AC_t Audio_ControlInterface_SPC;
+
+ // MIDI Audio Streaming Interface
+ USB_Descriptor_Interface_t Audio_StreamInterface;
+ USB_MIDI_Descriptor_AudioInterface_AS_t Audio_StreamInterface_SPC;
+ USB_MIDI_Descriptor_InputJack_t MIDI_In_Jack_Emb;
+ USB_MIDI_Descriptor_InputJack_t MIDI_In_Jack_Ext;
+ USB_MIDI_Descriptor_OutputJack_t MIDI_Out_Jack_Emb;
+ USB_MIDI_Descriptor_OutputJack_t MIDI_Out_Jack_Ext;
+ USB_Audio_Descriptor_StreamEndpoint_Std_t MIDI_In_Jack_Endpoint;
+ USB_MIDI_Descriptor_Jack_Endpoint_t MIDI_In_Jack_Endpoint_SPC;
+ USB_Audio_Descriptor_StreamEndpoint_Std_t MIDI_Out_Jack_Endpoint;
+ USB_MIDI_Descriptor_Jack_Endpoint_t MIDI_Out_Jack_Endpoint_SPC;
+#endif
+
} USB_Descriptor_Configuration_t;
@@ -115,9 +134,15 @@ typedef struct
# define NKRO_INTERFACE CONSOLE_INTERFACE
#endif
+#ifdef MIDI_ENABLE
+# define AC_INTERFACE (NKRO_INTERFACE + 1)
+# define AS_INTERFACE (NKRO_INTERFACE + 2)
+#else
+# define AS_INTERFACE NKRO_INTERFACE
+#endif
/* nubmer of interfaces */
-#define TOTAL_INTERFACES (NKRO_INTERFACE + 1)
+#define TOTAL_INTERFACES AS_INTERFACE + 1
// Endopoint number and size
@@ -145,17 +170,29 @@ typedef struct
#ifdef NKRO_ENABLE
# define NKRO_IN_EPNUM (CONSOLE_OUT_EPNUM + 1)
-# if defined(__AVR_ATmega32U2__) && NKRO_IN_EPNUM > 4
-# error "Endpoints are not available enough to support all functions. Remove some in Makefile.(MOUSEKEY, EXTRAKEY, CONSOLE, NKRO)"
-# endif
+#else
+# define NKRO_IN_EPNUM CONSOLE_OUT_EPNUM
+#endif
+
+#ifdef MIDI_ENABLE
+# define MIDI_STREAM_IN_EPNUM (NKRO_IN_EPNUM + 1)
+// # define MIDI_STREAM_OUT_EPNUM (NKRO_IN_EPNUM + 1)
+# define MIDI_STREAM_OUT_EPNUM (NKRO_IN_EPNUM + 2)
+# define MIDI_STREAM_IN_EPADDR (ENDPOINT_DIR_IN | MIDI_STREAM_IN_EPNUM)
+# define MIDI_STREAM_OUT_EPADDR (ENDPOINT_DIR_OUT | MIDI_STREAM_OUT_EPNUM)
#endif
+#if defined(__AVR_ATmega32U2__) && MIDI_STREAM_OUT_EPADDR > 4
+# error "Endpoints are not available enough to support all functions. Remove some in Makefile.(MOUSEKEY, EXTRAKEY, CONSOLE, NKRO, MIDI)"
+#endif
+
#define KEYBOARD_EPSIZE 8
#define MOUSE_EPSIZE 8
#define EXTRAKEY_EPSIZE 8
#define CONSOLE_EPSIZE 32
#define NKRO_EPSIZE 16
+#define MIDI_STREAM_EPSIZE 64
uint16_t CALLBACK_USB_GetDescriptor(const uint16_t wValue,
diff --git a/tmk_core/protocol/lufa/lufa.c b/tmk_core/protocol/lufa/lufa.c
index 345630aa90..f04790f4e8 100644
--- a/tmk_core/protocol/lufa/lufa.c
+++ b/tmk_core/protocol/lufa/lufa.c
@@ -52,6 +52,14 @@
#include "descriptor.h"
#include "lufa.h"
+#ifdef MIDI_ENABLE
+ #include <beeps.h>
+#endif
+
+#ifdef BLUETOOTH_ENABLE
+ #include "bluetooth.h"
+#endif
+
uint8_t keyboard_idle = 0;
/* 0: Boot Protocol, 1: Report Protocol(default) */
uint8_t keyboard_protocol = 1;
@@ -59,6 +67,11 @@ static uint8_t keyboard_led_stats = 0;
static report_keyboard_t keyboard_report_sent;
+#ifdef MIDI_ENABLE
+void usb_send_func(MidiDevice * device, uint16_t cnt, uint8_t byte0, uint8_t byte1, uint8_t byte2);
+void usb_get_midi(MidiDevice * device);
+void midi_usb_init(MidiDevice * device);
+#endif
/* Host driver */
static uint8_t keyboard_leds(void);
@@ -71,9 +84,49 @@ host_driver_t lufa_driver = {
send_keyboard,
send_mouse,
send_system,
- send_consumer
+ send_consumer,
+#ifdef MIDI_ENABLE
+ usb_send_func,
+ usb_get_midi,
+ midi_usb_init
+#endif
+};
+
+/*******************************************************************************
+ * MIDI
+ ******************************************************************************/
+
+#ifdef MIDI_ENABLE
+USB_ClassInfo_MIDI_Device_t USB_MIDI_Interface =
+{
+ .Config =
+ {
+ .StreamingInterfaceNumber = AS_INTERFACE,
+ .DataINEndpoint =
+ {
+ .Address = MIDI_STREAM_IN_EPADDR,
+ .Size = MIDI_STREAM_EPSIZE,
+ .Banks = 1,
+ },
+ .DataOUTEndpoint =
+ {
+ .Address = MIDI_STREAM_OUT_EPADDR,
+ .Size = MIDI_STREAM_EPSIZE,
+ .Banks = 1,
+ },
+ },
};
+#define SYSEX_START_OR_CONT 0x40
+#define SYSEX_ENDS_IN_1 0x50
+#define SYSEX_ENDS_IN_2 0x60
+#define SYSEX_ENDS_IN_3 0x70
+
+#define SYS_COMMON_1 0x50
+#define SYS_COMMON_2 0x20
+#define SYS_COMMON_3 0x30
+#endif
+
/*******************************************************************************
* Console
@@ -257,6 +310,11 @@ void EVENT_USB_Device_ConfigurationChanged(void)
ConfigSuccess &= ENDPOINT_CONFIG(NKRO_IN_EPNUM, EP_TYPE_INTERRUPT, ENDPOINT_DIR_IN,
NKRO_EPSIZE, ENDPOINT_BANK_SINGLE);
#endif
+
+#ifdef MIDI_ENABLE
+ ConfigSuccess &= Endpoint_ConfigureEndpoint(MIDI_STREAM_IN_EPADDR, EP_TYPE_BULK, MIDI_STREAM_EPSIZE, ENDPOINT_BANK_SINGLE);
+ ConfigSuccess &= Endpoint_ConfigureEndpoint(MIDI_STREAM_OUT_EPADDR, EP_TYPE_BULK, MIDI_STREAM_EPSIZE, ENDPOINT_BANK_SINGLE);
+#endif
}
/*
@@ -390,6 +448,14 @@ static uint8_t keyboard_leds(void)
static void send_keyboard(report_keyboard_t *report)
{
+
+#ifdef BLUETOOTH_ENABLE
+ bluefruit_serial_send(0xFD);
+ for (uint8_t i = 0; i < KEYBOARD_EPSIZE; i++) {
+ bluefruit_serial_send(report->raw[i]);
+ }
+#endif
+
uint8_t timeout = 255;
if (USB_DeviceState != DEVICE_STATE_Configured)
@@ -431,6 +497,19 @@ static void send_keyboard(report_keyboard_t *report)
static void send_mouse(report_mouse_t *report)
{
#ifdef MOUSE_ENABLE
+
+#ifdef BLUETOOTH_ENABLE
+ bluefruit_serial_send(0xFD);
+ bluefruit_serial_send(0x00);
+ bluefruit_serial_send(0x03);
+ bluefruit_serial_send(report->buttons);
+ bluefruit_serial_send(report->x);
+ bluefruit_serial_send(report->y);
+ bluefruit_serial_send(report->v); // should try sending the wheel v here
+ bluefruit_serial_send(report->h); // should try sending the wheel h here
+ bluefruit_serial_send(0x00);
+#endif
+
uint8_t timeout = 255;
if (USB_DeviceState != DEVICE_STATE_Configured)
@@ -474,6 +553,23 @@ static void send_system(uint16_t data)
static void send_consumer(uint16_t data)
{
+
+#ifdef BLUETOOTH_ENABLE
+ static uint16_t last_data = 0;
+ if (data == last_data) return;
+ last_data = data;
+ uint16_t bitmap = CONSUMER2BLUEFRUIT(data);
+ bluefruit_serial_send(0xFD);
+ bluefruit_serial_send(0x00);
+ bluefruit_serial_send(0x02);
+ bluefruit_serial_send((bitmap>>8)&0xFF);
+ bluefruit_serial_send(bitmap&0xFF);
+ bluefruit_serial_send(0x00);
+ bluefruit_serial_send(0x00);
+ bluefruit_serial_send(0x00);
+ bluefruit_serial_send(0x00);
+#endif
+
uint8_t timeout = 255;
if (USB_DeviceState != DEVICE_STATE_Configured)
@@ -562,6 +658,179 @@ int8_t sendchar(uint8_t c)
}
#endif
+/*******************************************************************************
+ * MIDI
+ ******************************************************************************/
+
+#ifdef MIDI_ENABLE
+void usb_send_func(MidiDevice * device, uint16_t cnt, uint8_t byte0, uint8_t byte1, uint8_t byte2) {
+ MIDI_EventPacket_t event;
+ event.Data1 = byte0;
+ event.Data2 = byte1;
+ event.Data3 = byte2;
+
+ uint8_t cable = 0;
+
+// Endpoint_SelectEndpoint(MIDI_STREAM_IN_EPNUM);
+
+ //if the length is undefined we assume it is a SYSEX message
+ if (midi_packet_length(byte0) == UNDEFINED) {
+ switch(cnt) {
+ case 3:
+ if (byte2 == SYSEX_END)
+ event.Event = MIDI_EVENT(cable, SYSEX_ENDS_IN_3);
+ else
+ event.Event = MIDI_EVENT(cable, SYSEX_START_OR_CONT);
+ break;
+ case 2:
+ if (byte1 == SYSEX_END)
+ event.Event = MIDI_EVENT(cable, SYSEX_ENDS_IN_2);
+ else
+ event.Event = MIDI_EVENT(cable, SYSEX_START_OR_CONT);
+ break;
+ case 1:
+ if (byte0 == SYSEX_END)
+ event.Event = MIDI_EVENT(cable, SYSEX_ENDS_IN_1);
+ else
+ event.Event = MIDI_EVENT(cable, SYSEX_START_OR_CONT);
+ break;
+ default:
+ return; //invalid cnt
+ }
+ } else {
+ //deal with 'system common' messages
+ //TODO are there any more?
+ switch(byte0 & 0xF0){
+ case MIDI_SONGPOSITION:
+ event.Event = MIDI_EVENT(cable, SYS_COMMON_3);
+ break;
+ case MIDI_SONGSELECT:
+ case MIDI_TC_QUARTERFRAME:
+ event.Event = MIDI_EVENT(cable, SYS_COMMON_2);
+ break;
+ default:
+ event.Event = MIDI_EVENT(cable, byte0);
+ break;
+ }
+ }
+
+// Endpoint_Write_Stream_LE(&event, sizeof(event), NULL);
+// Endpoint_ClearIN();
+
+ MIDI_Device_SendEventPacket(&USB_MIDI_Interface, &event);
+ MIDI_Device_Flush(&USB_MIDI_Interface);
+ MIDI_Device_USBTask(&USB_MIDI_Interface);
+ USB_USBTask();
+}
+
+void usb_get_midi(MidiDevice * device) {
+ MIDI_EventPacket_t event;
+ while (MIDI_Device_ReceiveEventPacket(&USB_MIDI_Interface, &event)) {
+
+ midi_packet_length_t length = midi_packet_length(event.Data1);
+ uint8_t input[3];
+ input[0] = event.Data1;
+ input[1] = event.Data2;
+ input[2] = event.Data3;
+ if (length == UNDEFINED) {
+ //sysex
+ if (event.Event == MIDI_EVENT(0, SYSEX_START_OR_CONT) || event.Event == MIDI_EVENT(0, SYSEX_ENDS_IN_3)) {
+ length = 3;
+ } else if (event.Event == MIDI_EVENT(0, SYSEX_ENDS_IN_2)) {
+ length = 2;
+ } else if(event.Event == MIDI_EVENT(0, SYSEX_ENDS_IN_1)) {
+ length = 1;
+ } else {
+ //XXX what to do?
+ }
+ }
+
+ //pass the data to the device input function
+ if (length != UNDEFINED)
+ midi_device_input(device, length, input);
+ }
+ MIDI_Device_USBTask(&USB_MIDI_Interface);
+ USB_USBTask();
+}
+
+void midi_usb_init(MidiDevice * device){
+ midi_device_init(device);
+ midi_device_set_send_func(device, usb_send_func);
+ midi_device_set_pre_input_process_func(device, usb_get_midi);
+
+ SetupHardware();
+ sei();
+}
+
+void MIDI_Task(void)
+{
+
+ /* Device must be connected and configured for the task to run */
+ dprint("in MIDI_TASK\n");
+ if (USB_DeviceState != DEVICE_STATE_Configured)
+ return;
+ dprint("continuing in MIDI_TASK\n");
+
+ Endpoint_SelectEndpoint(MIDI_STREAM_IN_EPADDR);
+
+ if (Endpoint_IsINReady())
+ {
+
+ dprint("Endpoint is ready\n");
+
+ uint8_t MIDICommand = 0;
+ uint8_t MIDIPitch;
+
+ /* Get board button status - if pressed use channel 10 (percussion), otherwise use channel 1 */
+ uint8_t Channel = MIDI_CHANNEL(1);
+
+ MIDICommand = MIDI_COMMAND_NOTE_ON;
+ MIDIPitch = 0x3E;
+
+ /* Check if a MIDI command is to be sent */
+ if (MIDICommand)
+ {
+ dprint("Command exists\n");
+ MIDI_EventPacket_t MIDIEvent = (MIDI_EventPacket_t)
+ {
+ .Event = MIDI_EVENT(0, MIDICommand),
+
+ .Data1 = MIDICommand | Channel,
+ .Data2 = MIDIPitch,
+ .Data3 = MIDI_STANDARD_VELOCITY,
+ };
+
+ /* Write the MIDI event packet to the endpoint */
+ Endpoint_Write_Stream_LE(&MIDIEvent, sizeof(MIDIEvent), NULL);
+
+ /* Send the data in the endpoint to the host */
+ Endpoint_ClearIN();
+ }
+ }
+
+
+ /* Select the MIDI OUT stream */
+ Endpoint_SelectEndpoint(MIDI_STREAM_OUT_EPADDR);
+
+ /* Check if a MIDI command has been received */
+ if (Endpoint_IsOUTReceived())
+ {
+ MIDI_EventPacket_t MIDIEvent;
+
+ /* Read the MIDI event packet from the endpoint */
+ Endpoint_Read_Stream_LE(&MIDIEvent, sizeof(MIDIEvent), NULL);
+
+ /* If the endpoint is now empty, clear the bank */
+ if (!(Endpoint_BytesInEndpoint()))
+ {
+ /* Clear the endpoint ready for new packet */
+ Endpoint_ClearOUT();
+ }
+ }
+}
+
+#endif
+
/*******************************************************************************
* main
@@ -588,24 +857,61 @@ static void setup_usb(void)
print_set_sendchar(sendchar);
}
+
+#ifdef MIDI_ENABLE
+void fallthrough_callback(MidiDevice * device,
+ uint16_t cnt, uint8_t byte0, uint8_t byte1, uint8_t byte2);
+void cc_callback(MidiDevice * device,
+ uint8_t chan, uint8_t num, uint8_t val);
+void sysex_callback(MidiDevice * device,
+ uint16_t start, uint8_t length, uint8_t * data);
+#endif
+
int main(void) __attribute__ ((weak));
int main(void)
{
+
+#ifdef MIDI_ENABLE
+ midi_device_init(&midi_device);
+ midi_device_set_send_func(&midi_device, usb_send_func);
+ midi_device_set_pre_input_process_func(&midi_device, usb_get_midi);
+#endif
+
setup_mcu();
keyboard_setup();
setup_usb();
sei();
+#ifdef MIDI_ENABLE
+ midi_register_fallthrough_callback(&midi_device, fallthrough_callback);
+ midi_register_cc_callback(&midi_device, cc_callback);
+ midi_register_sysex_callback(&midi_device, sysex_callback);
+
+ init_notes();
+ // midi_send_cc(&midi_device, 0, 1, 2);
+ // midi_send_cc(&midi_device, 15, 1, 0);
+ // midi_send_noteon(&midi_device, 0, 64, 127);
+ // midi_send_noteoff(&midi_device, 0, 64, 127);
+#endif
+
+#ifdef BLUETOOTH_ENABLE
+ serial_init();
+#endif
+
/* wait for USB startup & debug output */
+
+#ifdef WAIT_FOR_USB
while (USB_DeviceState != DEVICE_STATE_Configured) {
-#if defined(INTERRUPT_CONTROL_ENDPOINT)
- ;
-#else
- USB_USBTask();
-#endif
+ #if defined(INTERRUPT_CONTROL_ENDPOINT)
+ ;
+ #else
+ USB_USBTask();
+ #endif
}
print("USB configured.\n");
-
+#else
+ USB_USBTask();
+#endif
/* init modules */
keyboard_init();
host_set_driver(&lufa_driver);
@@ -615,6 +921,7 @@ int main(void)
print("Keyboard start.\n");
while (1) {
+ #ifndef BLUETOOTH_ENABLE
while (USB_DeviceState == DEVICE_STATE_Suspended) {
print("[s]");
suspend_power_down();
@@ -622,7 +929,12 @@ int main(void)
USB_Device_SendRemoteWakeup();
}
}
+ #endif
+#ifdef MIDI_ENABLE
+ midi_device_process(&midi_device);
+ // MIDI_Task();
+#endif
keyboard_task();
#if !defined(INTERRUPT_CONTROL_ENDPOINT)
@@ -630,3 +942,34 @@ int main(void)
#endif
}
}
+
+#ifdef MIDI_ENABLE
+void fallthrough_callback(MidiDevice * device,
+ uint16_t cnt, uint8_t byte0, uint8_t byte1, uint8_t byte2){
+ if (cnt == 3) {
+ switch (byte0 & 0xF0) {
+ case MIDI_NOTEON:
+ play_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(byte1 & 0x7F)/12.0), (byte2 & 0x7F) / 8);
+ break;
+ case MIDI_NOTEOFF:
+ stop_note(((double)261.6)*pow(2.0, -1.0)*pow(2.0,(byte1 & 0x7F)/12.0));
+ break;
+ }
+ }
+ if (byte0 == MIDI_STOP) {
+ stop_all_notes();
+ }
+}
+
+void cc_callback(MidiDevice * device,
+ uint8_t chan, uint8_t num, uint8_t val) {
+ //sending it back on the next channel
+ midi_send_cc(device, (chan + 1) % 16, num, val);
+}
+
+void sysex_callback(MidiDevice * device,
+ uint16_t start, uint8_t length, uint8_t * data) {
+ for (int i = 0; i < length; i++)
+ midi_send_cc(device, 15, 0x7F & data[i], 0x7F & (start + i));
+}
+#endif
diff --git a/tmk_core/protocol/lufa/lufa.h b/tmk_core/protocol/lufa/lufa.h
index 195123c0f9..af01bf6b9d 100644
--- a/tmk_core/protocol/lufa/lufa.h
+++ b/tmk_core/protocol/lufa/lufa.h
@@ -48,8 +48,9 @@
#include <LUFA/Version.h>
#include <LUFA/Drivers/USB/USB.h>
#include "host.h"
-
-
+#ifdef MIDI_ENABLE
+ #include "midi/midi.h"
+#endif
#ifdef __cplusplus
extern "C" {
#endif
@@ -66,15 +67,19 @@ typedef struct {
uint16_t usage;
} __attribute__ ((packed)) report_extra_t;
+#ifdef MIDI_ENABLE
+void MIDI_Task(void);
+MidiDevice midi_device;
+#endif
-#if LUFA_VERSION_INTEGER < 0x120730
- /* old API 120219 */
- #define ENDPOINT_CONFIG(epnum, eptype, epdir, epsize, epbank) Endpoint_ConfigureEndpoint(epnum, eptype, epdir, epsize, epbank)
-#else
+// #if LUFA_VERSION_INTEGER < 0x120730
+// /* old API 120219 */
+// #define ENDPOINT_CONFIG(epnum, eptype, epdir, epsize, epbank) Endpoint_ConfigureEndpoint(epnum, eptype, epdir, epsize, epbank)
+// #else
/* new API >= 120730 */
#define ENDPOINT_BANK_SINGLE 1
#define ENDPOINT_BANK_DOUBLE 2
#define ENDPOINT_CONFIG(epnum, eptype, epdir, epsize, epbank) Endpoint_ConfigureEndpoint((epdir) | (epnum) , eptype, epsize, epbank)
-#endif
+// #endif
#endif
diff --git a/tmk_core/protocol/lufa/midi/Config/LUFAConfig.h b/tmk_core/protocol/lufa/midi/Config/LUFAConfig.h
new file mode 100755
index 0000000000..fa9404498f
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/Config/LUFAConfig.h
@@ -0,0 +1,93 @@
+/*
+ LUFA Library
+ Copyright (C) Dean Camera, 2012.
+
+ dean [at] fourwalledcubicle [dot] com
+ www.lufa-lib.org
+*/
+
+/*
+ Copyright 2012 Dean Camera (dean [at] fourwalledcubicle [dot] com)
+
+ Permission to use, copy, modify, distribute, and sell this
+ software and its documentation for any purpose is hereby granted
+ without fee, provided that the above copyright notice appear in
+ all copies and that both that the copyright notice and this
+ permission notice and warranty disclaimer appear in supporting
+ documentation, and that the name of the author not be used in
+ advertising or publicity pertaining to distribution of the
+ software without specific, written prior permission.
+
+ The author disclaim all warranties with regard to this
+ software, including all implied warranties of merchantability
+ and fitness. In no event shall the author be liable for any
+ special, indirect or consequential damages or any damages
+ whatsoever resulting from loss of use, data or profits, whether
+ in an action of contract, negligence or other tortious action,
+ arising out of or in connection with the use or performance of
+ this software.
+*/
+
+/** \file
+ * \brief LUFA Library Configuration Header File
+ *
+ * This header file is used to configure LUFA's compile time options,
+ * as an alternative to the compile time constants supplied through
+ * a makefile.
+ *
+ * For information on what each token does, refer to the LUFA
+ * manual section "Summary of Compile Tokens".
+ */
+
+#ifndef _LUFA_CONFIG_H_
+#define _LUFA_CONFIG_H_
+
+ #if (ARCH == ARCH_AVR8)
+
+ /* Non-USB Related Configuration Tokens: */
+// #define DISABLE_TERMINAL_CODES
+
+ /* USB Class Driver Related Tokens: */
+// #define HID_HOST_BOOT_PROTOCOL_ONLY
+// #define HID_STATETABLE_STACK_DEPTH {Insert Value Here}
+// #define HID_USAGE_STACK_DEPTH {Insert Value Here}
+// #define HID_MAX_COLLECTIONS {Insert Value Here}
+// #define HID_MAX_REPORTITEMS {Insert Value Here}
+// #define HID_MAX_REPORT_IDS {Insert Value Here}
+// #define NO_CLASS_DRIVER_AUTOFLUSH
+
+ /* General USB Driver Related Tokens: */
+// #define ORDERED_EP_CONFIG
+ #define USE_STATIC_OPTIONS (USB_DEVICE_OPT_FULLSPEED | USB_OPT_REG_ENABLED | USB_OPT_AUTO_PLL)
+ #define USB_DEVICE_ONLY
+// #define USB_HOST_ONLY
+// #define USB_STREAM_TIMEOUT_MS {Insert Value Here}
+// #define NO_LIMITED_CONTROLLER_CONNECT
+// #define NO_SOF_EVENTS
+
+ /* USB Device Mode Driver Related Tokens: */
+// #define USE_RAM_DESCRIPTORS
+ #define USE_FLASH_DESCRIPTORS
+// #define USE_EEPROM_DESCRIPTORS
+// #define NO_INTERNAL_SERIAL
+ #define FIXED_CONTROL_ENDPOINT_SIZE 8
+// #define DEVICE_STATE_AS_GPIOR {Insert Value Here}
+ #define FIXED_NUM_CONFIGURATIONS 1
+// #define CONTROL_ONLY_DEVICE
+// #define INTERRUPT_CONTROL_ENDPOINT
+// #define NO_DEVICE_REMOTE_WAKEUP
+// #define NO_DEVICE_SELF_POWER
+
+ /* USB Host Mode Driver Related Tokens: */
+// #define HOST_STATE_AS_GPIOR {Insert Value Here}
+// #define USB_HOST_TIMEOUT_MS {Insert Value Here}
+// #define HOST_DEVICE_SETTLE_DELAY_MS {Insert Value Here}
+// #define NO_AUTO_VBUS_MANAGEMENT
+// #define INVERTED_VBUS_ENABLE_LINE
+
+ #else
+
+ #error Unsupported architecture for this LUFA configuration file.
+
+ #endif
+#endif
diff --git a/doc/COPYING.GPLv3 b/tmk_core/protocol/lufa/midi/bytequeue/COPYING
index 94a9ed024d..94a9ed024d 100644..100755
--- a/doc/COPYING.GPLv3
+++ b/tmk_core/protocol/lufa/midi/bytequeue/COPYING
diff --git a/tmk_core/protocol/lufa/midi/bytequeue/bytequeue.c b/tmk_core/protocol/lufa/midi/bytequeue/bytequeue.c
new file mode 100755
index 0000000000..e434956328
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/bytequeue/bytequeue.c
@@ -0,0 +1,65 @@
+//this is a single reader [maybe multiple writer?] byte queue
+//Copyright 2008 Alex Norman
+//writen by Alex Norman
+//
+//This file is part of avr-bytequeue.
+//
+//avr-bytequeue is free software: you can redistribute it and/or modify
+//it under the terms of the GNU General Public License as published by
+//the Free Software Foundation, either version 3 of the License, or
+//(at your option) any later version.
+//
+//avr-bytequeue is distributed in the hope that it will be useful,
+//but WITHOUT ANY WARRANTY; without even the implied warranty of
+//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+//GNU General Public License for more details.
+//
+//You should have received a copy of the GNU General Public License
+//along with avr-bytequeue. If not, see <http://www.gnu.org/licenses/>.
+
+#include "bytequeue.h"
+#include "interrupt_setting.h"
+
+void bytequeue_init(byteQueue_t * queue, uint8_t * dataArray, byteQueueIndex_t arrayLen){
+ queue->length = arrayLen;
+ queue->data = dataArray;
+ queue->start = queue->end = 0;
+}
+
+bool bytequeue_enqueue(byteQueue_t * queue, uint8_t item){
+ interrupt_setting_t setting = store_and_clear_interrupt();
+ //full
+ if(((queue->end + 1) % queue->length) == queue->start){
+ restore_interrupt_setting(setting);
+ return false;
+ } else {
+ queue->data[queue->end] = item;
+ queue->end = (queue->end + 1) % queue->length;
+ restore_interrupt_setting(setting);
+ return true;
+ }
+}
+
+byteQueueIndex_t bytequeue_length(byteQueue_t * queue){
+ byteQueueIndex_t len;
+ interrupt_setting_t setting = store_and_clear_interrupt();
+ if(queue->end >= queue->start)
+ len = queue->end - queue->start;
+ else
+ len = (queue->length - queue->start) + queue->end;
+ restore_interrupt_setting(setting);
+ return len;
+}
+
+//we don't need to avoid interrupts if there is only one reader
+uint8_t bytequeue_get(byteQueue_t * queue, byteQueueIndex_t index){
+ return queue->data[(queue->start + index) % queue->length];
+}
+
+//we just update the start index to remove elements
+void bytequeue_remove(byteQueue_t * queue, byteQueueIndex_t numToRemove){
+ interrupt_setting_t setting = store_and_clear_interrupt();
+ queue->start = (queue->start + numToRemove) % queue->length;
+ restore_interrupt_setting(setting);
+}
+
diff --git a/tmk_core/protocol/lufa/midi/bytequeue/bytequeue.h b/tmk_core/protocol/lufa/midi/bytequeue/bytequeue.h
new file mode 100755
index 0000000000..e4a286134f
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/bytequeue/bytequeue.h
@@ -0,0 +1,59 @@
+//this is a single reader [maybe multiple writer?] byte queue
+//Copyright 2008 Alex Norman
+//writen by Alex Norman
+//
+//This file is part of avr-bytequeue.
+//
+//avr-bytequeue is free software: you can redistribute it and/or modify
+//it under the terms of the GNU General Public License as published by
+//the Free Software Foundation, either version 3 of the License, or
+//(at your option) any later version.
+//
+//avr-bytequeue is distributed in the hope that it will be useful,
+//but WITHOUT ANY WARRANTY; without even the implied warranty of
+//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+//GNU General Public License for more details.
+//
+//You should have received a copy of the GNU General Public License
+//along with avr-bytequeue. If not, see <http://www.gnu.org/licenses/>.
+
+#ifndef BYTEQUEUE_H
+#define BYTEQUEUE_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <inttypes.h>
+#include <stdbool.h>
+
+typedef uint8_t byteQueueIndex_t;
+
+typedef struct {
+ byteQueueIndex_t start;
+ byteQueueIndex_t end;
+ byteQueueIndex_t length;
+ uint8_t * data;
+} byteQueue_t;
+
+//you must have a queue, an array of data which the queue will use, and the length of that array
+void bytequeue_init(byteQueue_t * queue, uint8_t * dataArray, byteQueueIndex_t arrayLen);
+
+//add an item to the queue, returns false if the queue is full
+bool bytequeue_enqueue(byteQueue_t * queue, uint8_t item);
+
+//get the length of the queue
+byteQueueIndex_t bytequeue_length(byteQueue_t * queue);
+
+//this grabs data at the index given [starting at queue->start]
+uint8_t bytequeue_get(byteQueue_t * queue, byteQueueIndex_t index);
+
+//update the index in the queue to reflect data that has been dealt with
+void bytequeue_remove(byteQueue_t * queue, byteQueueIndex_t numToRemove);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
+
diff --git a/tmk_core/protocol/lufa/midi/bytequeue/interrupt_setting.c b/tmk_core/protocol/lufa/midi/bytequeue/interrupt_setting.c
new file mode 100755
index 0000000000..eafef527c0
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/bytequeue/interrupt_setting.c
@@ -0,0 +1,36 @@
+//Copyright 20010 Alex Norman
+//writen by Alex Norman
+//
+//This file is part of avr-bytequeue.
+//
+//avr-bytequeue is free software: you can redistribute it and/or modify
+//it under the terms of the GNU General Public License as published by
+//the Free Software Foundation, either version 3 of the License, or
+//(at your option) any later version.
+//
+//avr-bytequeue is distributed in the hope that it will be useful,
+//but WITHOUT ANY WARRANTY; without even the implied warranty of
+//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+//GNU General Public License for more details.
+//
+//You should have received a copy of the GNU General Public License
+//along with avr-bytequeue. If not, see <http://www.gnu.org/licenses/>.
+
+
+//AVR specific code
+//should be able to port to other systems by simply providing chip specific
+//implementations of the typedef and these functions
+
+#include "interrupt_setting.h"
+#include <avr/interrupt.h>
+
+interrupt_setting_t store_and_clear_interrupt(void) {
+ uint8_t sreg = SREG;
+ cli();
+ return sreg;
+}
+
+void restore_interrupt_setting(interrupt_setting_t setting) {
+ SREG = setting;
+}
+
diff --git a/tmk_core/protocol/lufa/midi/bytequeue/interrupt_setting.h b/tmk_core/protocol/lufa/midi/bytequeue/interrupt_setting.h
new file mode 100755
index 0000000000..053d02c9d0
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/bytequeue/interrupt_setting.h
@@ -0,0 +1,39 @@
+//Copyright 20010 Alex Norman
+//writen by Alex Norman
+//
+//This file is part of avr-bytequeue.
+//
+//avr-bytequeue is free software: you can redistribute it and/or modify
+//it under the terms of the GNU General Public License as published by
+//the Free Software Foundation, either version 3 of the License, or
+//(at your option) any later version.
+//
+//avr-bytequeue is distributed in the hope that it will be useful,
+//but WITHOUT ANY WARRANTY; without even the implied warranty of
+//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+//GNU General Public License for more details.
+//
+//You should have received a copy of the GNU General Public License
+//along with avr-bytequeue. If not, see <http://www.gnu.org/licenses/>.
+
+#ifndef INTERRUPT_SETTING_H
+#define INTERRUPT_SETTING_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <inttypes.h>
+
+//AVR specific typedef
+typedef uint8_t interrupt_setting_t;
+
+interrupt_setting_t store_and_clear_interrupt(void);
+void restore_interrupt_setting(interrupt_setting_t setting);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
+
diff --git a/tmk_core/protocol/lufa/midi/midi.c b/tmk_core/protocol/lufa/midi/midi.c
new file mode 100755
index 0000000000..11a589078c
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/midi.c
@@ -0,0 +1,277 @@
+//midi for embedded chips,
+//Copyright 2010 Alex Norman
+//
+//This file is part of avr-midi.
+//
+//avr-midi is free software: you can redistribute it and/or modify
+//it under the terms of the GNU General Public License as published by
+//the Free Software Foundation, either version 3 of the License, or
+//(at your option) any later version.
+//
+//avr-midi is distributed in the hope that it will be useful,
+//but WITHOUT ANY WARRANTY; without even the implied warranty of
+//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+//GNU General Public License for more details.
+//
+//You should have received a copy of the GNU General Public License
+//along with avr-midi. If not, see <http://www.gnu.org/licenses/>.
+
+#include "midi.h"
+#include <string.h> //for memcpy
+
+#define MIN(x,y) (((x) < (y)) ? (x) : (y))
+
+#ifndef NULL
+#define NULL 0
+#endif
+
+bool midi_is_statusbyte(uint8_t theByte){
+ return (bool)(theByte & MIDI_STATUSMASK);
+}
+
+bool midi_is_realtime(uint8_t theByte){
+ return (theByte >= MIDI_CLOCK);
+}
+
+midi_packet_length_t midi_packet_length(uint8_t status){
+ switch(status & 0xF0){
+ case MIDI_CC:
+ case MIDI_NOTEON:
+ case MIDI_NOTEOFF:
+ case MIDI_AFTERTOUCH:
+ case MIDI_PITCHBEND:
+ return THREE;
+ case MIDI_PROGCHANGE:
+ case MIDI_CHANPRESSURE:
+ case MIDI_SONGSELECT:
+ return TWO;
+ case 0xF0:
+ switch(status) {
+ case MIDI_CLOCK:
+ case MIDI_TICK:
+ case MIDI_START:
+ case MIDI_CONTINUE:
+ case MIDI_STOP:
+ case MIDI_ACTIVESENSE:
+ case MIDI_RESET:
+ case MIDI_TUNEREQUEST:
+ return ONE;
+ case MIDI_SONGPOSITION:
+ return THREE;
+ case MIDI_TC_QUARTERFRAME:
+ case MIDI_SONGSELECT:
+ return TWO;
+ case SYSEX_END:
+ case SYSEX_BEGIN:
+ default:
+ return UNDEFINED;
+ }
+ default:
+ return UNDEFINED;
+ }
+}
+
+void midi_send_cc(MidiDevice * device, uint8_t chan, uint8_t num, uint8_t val){
+ //CC Status: 0xB0 to 0xBF where the low nibble is the MIDI channel.
+ //CC Data: Controller Num, Controller Val
+ device->send_func(device, 3,
+ MIDI_CC | (chan & MIDI_CHANMASK),
+ num & 0x7F,
+ val & 0x7F);
+}
+
+void midi_send_noteon(MidiDevice * device, uint8_t chan, uint8_t num, uint8_t vel){
+ //Note Data: Note Num, Note Velocity
+ device->send_func(device, 3,
+ MIDI_NOTEON | (chan & MIDI_CHANMASK),
+ num & 0x7F,
+ vel & 0x7F);
+}
+
+void midi_send_noteoff(MidiDevice * device, uint8_t chan, uint8_t num, uint8_t vel){
+ //Note Data: Note Num, Note Velocity
+ device->send_func(device, 3,
+ MIDI_NOTEOFF | (chan & MIDI_CHANMASK),
+ num & 0x7F,
+ vel & 0x7F);
+}
+
+void midi_send_aftertouch(MidiDevice * device, uint8_t chan, uint8_t note_num, uint8_t amt){
+ device->send_func(device, 3,
+ MIDI_AFTERTOUCH | (chan & MIDI_CHANMASK),
+ note_num & 0x7F,
+ amt & 0x7F);
+}
+
+//XXX does this work right?
+//amt in range -0x2000, 0x1fff
+//uAmt should be in range..
+//0x0000 to 0x3FFF
+void midi_send_pitchbend(MidiDevice * device, uint8_t chan, int16_t amt){
+ uint16_t uAmt;
+ //check range
+ if(amt > 0x1fff){
+ uAmt = 0x3FFF;
+ } else if(amt < -0x2000){
+ uAmt = 0;
+ } else {
+ uAmt = amt + 0x2000;
+ }
+ device->send_func(device, 3,
+ MIDI_PITCHBEND | (chan & MIDI_CHANMASK),
+ uAmt & 0x7F,
+ (uAmt >> 7) & 0x7F);
+}
+
+void midi_send_programchange(MidiDevice * device, uint8_t chan, uint8_t num){
+ device->send_func(device, 2,
+ MIDI_PROGCHANGE | (chan & MIDI_CHANMASK),
+ num & 0x7F,
+ 0);
+}
+
+void midi_send_channelpressure(MidiDevice * device, uint8_t chan, uint8_t amt){
+ device->send_func(device, 2,
+ MIDI_CHANPRESSURE | (chan & MIDI_CHANMASK),
+ amt & 0x7F,
+ 0);
+}
+
+void midi_send_clock(MidiDevice * device){
+ device->send_func(device, 1, MIDI_CLOCK, 0, 0);
+}
+
+void midi_send_tick(MidiDevice * device){
+ device->send_func(device, 1, MIDI_TICK, 0, 0);
+}
+
+void midi_send_start(MidiDevice * device){
+ device->send_func(device, 1, MIDI_START, 0, 0);
+}
+
+void midi_send_continue(MidiDevice * device){
+ device->send_func(device, 1, MIDI_CONTINUE, 0, 0);
+}
+
+void midi_send_stop(MidiDevice * device){
+ device->send_func(device, 1, MIDI_STOP, 0, 0);
+}
+
+void midi_send_activesense(MidiDevice * device){
+ device->send_func(device, 1, MIDI_ACTIVESENSE, 0, 0);
+}
+
+void midi_send_reset(MidiDevice * device){
+ device->send_func(device, 1, MIDI_RESET, 0, 0);
+}
+
+void midi_send_tcquarterframe(MidiDevice * device, uint8_t time){
+ device->send_func(device, 2,
+ MIDI_TC_QUARTERFRAME,
+ time & 0x7F,
+ 0);
+}
+
+//XXX is this right?
+void midi_send_songposition(MidiDevice * device, uint16_t pos){
+ device->send_func(device, 3,
+ MIDI_SONGPOSITION,
+ pos & 0x7F,
+ (pos >> 7) & 0x7F);
+}
+
+void midi_send_songselect(MidiDevice * device, uint8_t song){
+ device->send_func(device, 2,
+ MIDI_SONGSELECT,
+ song & 0x7F,
+ 0);
+}
+
+void midi_send_tunerequest(MidiDevice * device){
+ device->send_func(device, 1, MIDI_TUNEREQUEST, 0, 0);
+}
+
+void midi_send_byte(MidiDevice * device, uint8_t b){
+ device->send_func(device, 1, b, 0, 0);
+}
+
+void midi_send_data(MidiDevice * device, uint16_t count, uint8_t byte0, uint8_t byte1, uint8_t byte2){
+ //ensure that the count passed along is always 3 or lower
+ if (count > 3) {
+ //TODO how to do this correctly?
+ }
+ device->send_func(device, count, byte0, byte1, byte2);
+}
+
+void midi_send_array(MidiDevice * device, uint16_t count, uint8_t * array) {
+ uint16_t i;
+ for (i = 0; i < count; i += 3) {
+ uint8_t b[3] = { 0, 0, 0 };
+ uint16_t to_send = count - i;
+ to_send = (to_send > 3) ? 3 : to_send;
+ memcpy(b, array + i, to_send);
+ midi_send_data(device, to_send, b[0], b[1], b[2]);
+ }
+}
+
+
+void midi_register_cc_callback(MidiDevice * device, midi_three_byte_func_t func){
+ device->input_cc_callback = func;
+}
+
+void midi_register_noteon_callback(MidiDevice * device, midi_three_byte_func_t func){
+ device->input_noteon_callback = func;
+}
+
+void midi_register_noteoff_callback(MidiDevice * device, midi_three_byte_func_t func){
+ device->input_noteoff_callback = func;
+}
+
+void midi_register_aftertouch_callback(MidiDevice * device, midi_three_byte_func_t func){
+ device->input_aftertouch_callback = func;
+}
+
+void midi_register_pitchbend_callback(MidiDevice * device, midi_three_byte_func_t func){
+ device->input_pitchbend_callback = func;
+}
+
+void midi_register_songposition_callback(MidiDevice * device, midi_three_byte_func_t func){
+ device->input_songposition_callback = func;
+}
+
+void midi_register_progchange_callback(MidiDevice * device, midi_two_byte_func_t func) {
+ device->input_progchange_callback = func;
+}
+
+void midi_register_chanpressure_callback(MidiDevice * device, midi_two_byte_func_t func) {
+ device->input_chanpressure_callback = func;
+}
+
+void midi_register_songselect_callback(MidiDevice * device, midi_two_byte_func_t func) {
+ device->input_songselect_callback = func;
+}
+
+void midi_register_tc_quarterframe_callback(MidiDevice * device, midi_two_byte_func_t func) {
+ device->input_tc_quarterframe_callback = func;
+}
+
+void midi_register_realtime_callback(MidiDevice * device, midi_one_byte_func_t func){
+ device->input_realtime_callback = func;
+}
+
+void midi_register_tunerequest_callback(MidiDevice * device, midi_one_byte_func_t func){
+ device->input_tunerequest_callback = func;
+}
+
+void midi_register_sysex_callback(MidiDevice * device, midi_sysex_func_t func) {
+ device->input_sysex_callback = func;
+}
+
+void midi_register_fallthrough_callback(MidiDevice * device, midi_var_byte_func_t func){
+ device->input_fallthrough_callback = func;
+}
+
+void midi_register_catchall_callback(MidiDevice * device, midi_var_byte_func_t func){
+ device->input_catchall_callback = func;
+}
+
diff --git a/tmk_core/protocol/lufa/midi/midi.h b/tmk_core/protocol/lufa/midi/midi.h
new file mode 100755
index 0000000000..1a36737df8
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/midi.h
@@ -0,0 +1,498 @@
+//midi for embedded chips,
+//Copyright 2010 Alex Norman
+//
+//This file is part of avr-midi.
+//
+//avr-midi is free software: you can redistribute it and/or modify
+//it under the terms of the GNU General Public License as published by
+//the Free Software Foundation, either version 3 of the License, or
+//(at your option) any later version.
+//
+//avr-midi is distributed in the hope that it will be useful,
+//but WITHOUT ANY WARRANTY; without even the implied warranty of
+//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+//GNU General Public License for more details.
+//
+//You should have received a copy of the GNU General Public License
+//along with avr-midi. If not, see <http://www.gnu.org/licenses/>.
+
+/**
+ * @file
+ * @brief The main midi functions
+ *
+ * This file includes all of the functions you need to set up and process a
+ * midi device, send midi, and register midi callbacks.
+ *
+ */
+
+#ifndef XNOR_MIDI_H
+#define XNOR_MIDI_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include "midi_device.h"
+#include "midi_function_types.h"
+
+/**
+ * @defgroup midi_device_setup_process Device initialization and processing
+ * @brief These are method that you must use to initialize and run a device
+ *
+ * @{
+ */
+
+/**
+ * @brief Initialize a device
+ *
+ * You must call this before using the device in question.
+ *
+ * @param device the device to initialize
+*/
+void midi_device_init(MidiDevice * device); // [implementation in midi_device.c]
+
+/**
+ * @brief Process input data
+ *
+ * This method drives the input processing, you must call this method frequently
+ * if you expect to have your input callbacks called.
+ *
+ * @param device the device to process
+*/
+void midi_device_process(MidiDevice * device); // [implementation in midi_device.c]
+
+/**@}*/
+
+/**
+ * @defgroup send_functions Midi send functions
+ * @brief These are the functions you use to send midi data through a device.
+ * @{
+ */
+
+/**
+ * @brief Send a control change message (cc) via the given device.
+ *
+ * @param device the device to use for sending
+ * @param chan the channel to send on, 0-15
+ * @param num the cc num
+ * @param val the value of that cc num
+*/
+void midi_send_cc(MidiDevice * device, uint8_t chan, uint8_t num, uint8_t val);
+
+/**
+ * @brief Send a note on message via the given device.
+ *
+ * @param device the device to use for sending
+ * @param chan the channel to send on, 0-15
+ * @param num the note number
+ * @param vel the note velocity
+*/
+void midi_send_noteon(MidiDevice * device, uint8_t chan, uint8_t num, uint8_t vel);
+
+/**
+ * @brief Send a note off message via the given device.
+ *
+ * @param device the device to use for sending
+ * @param chan the channel to send on, 0-15
+ * @param num the note number
+ * @param vel the note velocity
+*/
+void midi_send_noteoff(MidiDevice * device, uint8_t chan, uint8_t num, uint8_t vel);
+
+/**
+ * @brief Send an after touch message via the given device.
+ *
+ * @param device the device to use for sending
+ * @param chan the channel to send on, 0-15
+ * @param note_num the note number
+ * @param amt the after touch amount
+*/
+void midi_send_aftertouch(MidiDevice * device, uint8_t chan, uint8_t note_num, uint8_t amt);
+
+/**
+ * @brief Send a pitch bend message via the given device.
+ *
+ * @param device the device to use for sending
+ * @param chan the channel to send on, 0-15
+ * @param amt the bend amount range: -8192..8191, 0 means no bend
+*/
+void midi_send_pitchbend(MidiDevice * device, uint8_t chan, int16_t amt); //range -8192, 8191
+
+/**
+ * @brief Send a program change message via the given device.
+ *
+ * @param device the device to use for sending
+ * @param chan the channel to send on, 0-15
+ * @param num the program to change to
+*/
+void midi_send_programchange(MidiDevice * device, uint8_t chan, uint8_t num);
+
+/**
+ * @brief Send a channel pressure message via the given device.
+ *
+ * @param device the device to use for sending
+ * @param chan the channel to send on, 0-15
+ * @param amt the amount of channel pressure
+*/
+void midi_send_channelpressure(MidiDevice * device, uint8_t chan, uint8_t amt);
+
+/**
+ * @brief Send a clock message via the given device.
+ *
+ * @param device the device to use for sending
+ */
+void midi_send_clock(MidiDevice * device);
+
+/**
+ * @brief Send a tick message via the given device.
+ *
+ * @param device the device to use for sending
+ */
+void midi_send_tick(MidiDevice * device);
+
+/**
+ * @brief Send a start message via the given device.
+ *
+ * @param device the device to use for sending
+ */
+void midi_send_start(MidiDevice * device);
+
+/**
+ * @brief Send a continue message via the given device.
+ *
+ * @param device the device to use for sending
+ */
+void midi_send_continue(MidiDevice * device);
+
+/**
+ * @brief Send a stop message via the given device.
+ *
+ * @param device the device to use for sending
+ */
+void midi_send_stop(MidiDevice * device);
+
+/**
+ * @brief Send an active sense message via the given device.
+ *
+ * @param device the device to use for sending
+ */
+void midi_send_activesense(MidiDevice * device);
+
+/**
+ * @brief Send a reset message via the given device.
+ *
+ * @param device the device to use for sending
+ */
+void midi_send_reset(MidiDevice * device);
+
+
+/**
+ * @brief Send a tc quarter frame message via the given device.
+ *
+ * @param device the device to use for sending
+ * @param time the time of this quarter frame, range 0..16383
+ */
+void midi_send_tcquarterframe(MidiDevice * device, uint8_t time);
+
+/**
+ * @brief Send a song position message via the given device.
+ *
+ * @param device the device to use for sending
+ * @param pos the song position
+ */
+void midi_send_songposition(MidiDevice * device, uint16_t pos);
+
+/**
+ * @brief Send a song select message via the given device.
+ *
+ * @param device the device to use for sending
+ * @param song the song to select
+ */
+void midi_send_songselect(MidiDevice * device, uint8_t song);
+
+/**
+ * @brief Send a tune request message via the given device.
+ *
+ * @param device the device to use for sending
+ */
+void midi_send_tunerequest(MidiDevice * device);
+
+/**
+ * @brief Send a byte via the given device.
+ *
+ * This is a generic method for sending data via the given midi device.
+ * This would be useful for sending sysex data or messages that are not
+ * implemented in this API, if there are any. Please contact the author
+ * if you find some so we can add them.
+ *
+ * @param device the device to use for sending
+ * @param b the byte to send
+ */
+void midi_send_byte(MidiDevice * device, uint8_t b);
+
+/**
+ * @brief Send up to 3 bytes of data
+ *
+ * % 4 is applied to count so that you can use this to pass sysex through
+ *
+ * @param device the device to use for sending
+ * @param count the count of bytes to send, %4 is applied
+ * @param byte0 the first byte
+ * @param byte1 the second byte, ignored if cnt % 4 != 2
+ * @param byte2 the third byte, ignored if cnt % 4 != 3
+ */
+void midi_send_data(MidiDevice * device, uint16_t count, uint8_t byte0, uint8_t byte1, uint8_t byte2);
+
+/**
+ * @brief Send an array of formatted midi data.
+ *
+ * Can be used for sysex.
+ *
+ * @param device the device to use for sending
+ * @param count the count of bytes to send
+ * @param array the array of bytes
+ */
+void midi_send_array(MidiDevice * device, uint16_t count, uint8_t * array);
+
+/**@}*/
+
+
+/**
+ * @defgroup input_callback_reg Input callback registration functions
+ *
+ * @brief These are the functions you use to register your input callbacks.
+ *
+ * The functions are called when the appropriate midi message is matched on the
+ * associated device's input.
+ *
+ * @{
+ */
+
+//three byte funcs
+
+/**
+ * @brief Register a control change message (cc) callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_cc_callback(MidiDevice * device, midi_three_byte_func_t func);
+
+/**
+ * @brief Register a note on callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_noteon_callback(MidiDevice * device, midi_three_byte_func_t func);
+
+/**
+ * @brief Register a note off callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_noteoff_callback(MidiDevice * device, midi_three_byte_func_t func);
+
+/**
+ * @brief Register an after touch callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+
+void midi_register_aftertouch_callback(MidiDevice * device, midi_three_byte_func_t func);
+
+/**
+ * @brief Register a pitch bend callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_pitchbend_callback(MidiDevice * device, midi_three_byte_func_t func);
+
+/**
+ * @brief Register a song position callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_songposition_callback(MidiDevice * device, midi_three_byte_func_t func);
+
+//two byte funcs
+
+/**
+ * @brief Register a program change callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_progchange_callback(MidiDevice * device, midi_two_byte_func_t func);
+
+/**
+ * @brief Register a channel pressure callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_chanpressure_callback(MidiDevice * device, midi_two_byte_func_t func);
+
+/**
+ * @brief Register a song select callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_songselect_callback(MidiDevice * device, midi_two_byte_func_t func);
+
+/**
+ * @brief Register a tc quarter frame callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_tc_quarterframe_callback(MidiDevice * device, midi_two_byte_func_t func);
+
+//one byte funcs
+
+/**
+ * @brief Register a realtime callback.
+ *
+ * The callback will be called for all of the real time message types.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_realtime_callback(MidiDevice * device, midi_one_byte_func_t func);
+
+/**
+ * @brief Register a tune request callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_tunerequest_callback(MidiDevice * device, midi_one_byte_func_t func);
+
+/**
+ * @brief Register a sysex callback.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_sysex_callback(MidiDevice * device, midi_sysex_func_t func);
+
+/**
+ * @brief Register fall through callback.
+ *
+ * This is only called if a more specific callback is not matched and called.
+ * For instance, if you don't register a note on callback but you get a note on message
+ * the fall through callback will be called, if it is registered.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_fallthrough_callback(MidiDevice * device, midi_var_byte_func_t func);
+
+
+/**
+ * @brief Register a catch all callback.
+ *
+ * If registered, the catch all callback is called for every message that is
+ * matched, even if a more specific or the fallthrough callback is registered.
+ *
+ * @param device the device associate with
+ * @param func the callback function to register
+ */
+void midi_register_catchall_callback(MidiDevice * device, midi_var_byte_func_t func);
+
+/**@}*/
+
+/**
+ * @defgroup midi_util Device independent utility functions.
+ * @{
+ */
+
+/**
+ * \enum midi_packet_length_t
+ *
+ * An enumeration of the possible packet length values.
+ */
+typedef enum {
+ UNDEFINED = 0,
+ ONE = 1,
+ TWO = 2,
+ THREE = 3} midi_packet_length_t;
+
+/**
+ * @brief Test to see if the byte given is a status byte
+ * @param theByte the byte to test
+ * @return true if the byte given is a midi status byte
+ */
+bool midi_is_statusbyte(uint8_t theByte);
+
+/**
+ * @brief Test to see if the byte given is a realtime message
+ * @param theByte the byte to test
+ * @return true if it is a realtime message, false otherwise
+ */
+bool midi_is_realtime(uint8_t theByte);
+
+/**
+ * @brief Find the length of the packet associated with the status byte given
+ * @param status the status byte
+ * @return the length of the packet, will return UNDEFINED if the byte is not
+ * a status byte or if it is a sysex status byte
+ */
+midi_packet_length_t midi_packet_length(uint8_t status);
+
+/**@}*/
+
+/**
+ * @defgroup defines Midi status and miscellaneous utility #defines
+ *
+ * @{
+ */
+
+#define SYSEX_BEGIN 0xF0
+#define SYSEX_END 0xF7
+
+//if you and this with a byte and you get anything non-zero
+//it is a status message
+#define MIDI_STATUSMASK 0x80
+//if you and this with a status message that contains channel info,
+//you'll get the channel
+#define MIDI_CHANMASK 0x0F
+
+#define MIDI_CC 0xB0
+#define MIDI_NOTEON 0x90
+#define MIDI_NOTEOFF 0x80
+#define MIDI_AFTERTOUCH 0xA0
+#define MIDI_PITCHBEND 0xE0
+#define MIDI_PROGCHANGE 0xC0
+#define MIDI_CHANPRESSURE 0xD0
+
+//midi realtime
+#define MIDI_CLOCK 0xF8
+#define MIDI_TICK 0xF9
+#define MIDI_START 0xFA
+#define MIDI_CONTINUE 0xFB
+#define MIDI_STOP 0xFC
+#define MIDI_ACTIVESENSE 0xFE
+#define MIDI_RESET 0xFF
+
+#define MIDI_TC_QUARTERFRAME 0xF1
+#define MIDI_SONGPOSITION 0xF2
+#define MIDI_SONGSELECT 0xF3
+#define MIDI_TUNEREQUEST 0xF6
+
+//This ID is for educational or development use only
+#define SYSEX_EDUMANUFID 0x7D
+
+/**@}*/
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
+
diff --git a/tmk_core/protocol/lufa/midi/midi_device.c b/tmk_core/protocol/lufa/midi/midi_device.c
new file mode 100755
index 0000000000..3215a007d5
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/midi_device.c
@@ -0,0 +1,291 @@
+//midi for embedded chips,
+//Copyright 2010 Alex Norman
+//
+//This file is part of avr-midi.
+//
+//avr-midi is free software: you can redistribute it and/or modify
+//it under the terms of the GNU General Public License as published by
+//the Free Software Foundation, either version 3 of the License, or
+//(at your option) any later version.
+//
+//avr-midi is distributed in the hope that it will be useful,
+//but WITHOUT ANY WARRANTY; without even the implied warranty of
+//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+//GNU General Public License for more details.
+//
+//You should have received a copy of the GNU General Public License
+//along with avr-midi. If not, see <http://www.gnu.org/licenses/>.
+
+#include "midi_device.h"
+#include "midi.h"
+
+#ifndef NULL
+#define NULL 0
+#endif
+
+//forward declarations, internally used to call the callbacks
+void midi_input_callbacks(MidiDevice * device, uint16_t cnt, uint8_t byte0, uint8_t byte1, uint8_t byte2);
+void midi_process_byte(MidiDevice * device, uint8_t input);
+
+void midi_device_init(MidiDevice * device){
+ device->input_state = IDLE;
+ device->input_count = 0;
+ bytequeue_init(&device->input_queue, device->input_queue_data, MIDI_INPUT_QUEUE_LENGTH);
+
+ //three byte funcs
+ device->input_cc_callback = NULL;
+ device->input_noteon_callback = NULL;
+ device->input_noteoff_callback = NULL;
+ device->input_aftertouch_callback = NULL;
+ device->input_pitchbend_callback = NULL;
+ device->input_songposition_callback = NULL;
+
+ //two byte funcs
+ device->input_progchange_callback = NULL;
+ device->input_chanpressure_callback = NULL;
+ device->input_songselect_callback = NULL;
+ device->input_tc_quarterframe_callback = NULL;
+
+ //one byte funcs
+ device->input_realtime_callback = NULL;
+ device->input_tunerequest_callback = NULL;
+
+ //var byte functions
+ device->input_sysex_callback = NULL;
+ device->input_fallthrough_callback = NULL;
+ device->input_catchall_callback = NULL;
+
+ device->pre_input_process_callback = NULL;
+}
+
+void midi_device_input(MidiDevice * device, uint8_t cnt, uint8_t * input) {
+ uint8_t i;
+ for (i = 0; i < cnt; i++)
+ bytequeue_enqueue(&device->input_queue, input[i]);
+}
+
+void midi_device_set_send_func(MidiDevice * device, midi_var_byte_func_t send_func){
+ device->send_func = send_func;
+}
+
+void midi_device_set_pre_input_process_func(MidiDevice * device, midi_no_byte_func_t pre_process_func){
+ device->pre_input_process_callback = pre_process_func;
+}
+
+void midi_device_process(MidiDevice * device) {
+ //call the pre_input_process_callback if there is one
+ if(device->pre_input_process_callback)
+ device->pre_input_process_callback(device);
+
+ //pull stuff off the queue and process
+ byteQueueIndex_t len = bytequeue_length(&device->input_queue);
+ uint16_t i;
+ //TODO limit number of bytes processed?
+ for(i = 0; i < len; i++) {
+ uint8_t val = bytequeue_get(&device->input_queue, 0);
+ midi_process_byte(device, val);
+ bytequeue_remove(&device->input_queue, 1);
+ }
+}
+
+void midi_process_byte(MidiDevice * device, uint8_t input) {
+ if (midi_is_realtime(input)) {
+ //call callback, store and restore state
+ input_state_t state = device->input_state;
+ device->input_state = ONE_BYTE_MESSAGE;
+ midi_input_callbacks(device, 1, input, 0, 0);
+ device->input_state = state;
+ } else if (midi_is_statusbyte(input)) {
+ //store the byte
+ if (device->input_state != SYSEX_MESSAGE) {
+ device->input_buffer[0] = input;
+ device->input_count = 1;
+ }
+ switch (midi_packet_length(input)) {
+ case ONE:
+ device->input_state = ONE_BYTE_MESSAGE;;
+ midi_input_callbacks(device, 1, input, 0, 0);
+ device->input_state = IDLE;
+ break;
+ case TWO:
+ device->input_state = TWO_BYTE_MESSAGE;
+ break;
+ case THREE:
+ device->input_state = THREE_BYTE_MESSAGE;
+ break;
+ case UNDEFINED:
+ switch(input) {
+ case SYSEX_BEGIN:
+ device->input_state = SYSEX_MESSAGE;
+ device->input_buffer[0] = input;
+ device->input_count = 1;
+ break;
+ case SYSEX_END:
+ //send what is left in the input buffer, set idle
+ device->input_buffer[device->input_count % 3] = input;
+ device->input_count += 1;
+ //call the callback
+ midi_input_callbacks(device, device->input_count,
+ device->input_buffer[0], device->input_buffer[1], device->input_buffer[2]);
+ device->input_state = IDLE;
+ break;
+ default:
+ device->input_state = IDLE;
+ device->input_count = 0;
+ }
+
+ break;
+ default:
+ device->input_state = IDLE;
+ device->input_count = 0;
+ break;
+ }
+ } else {
+ if (device->input_state != IDLE) {
+ //store the byte
+ device->input_buffer[device->input_count % 3] = input;
+ //increment count
+ uint16_t prev = device->input_count;
+ device->input_count += 1;
+
+ switch(prev % 3) {
+ case 2:
+ //call callback
+ midi_input_callbacks(device, device->input_count,
+ device->input_buffer[0], device->input_buffer[1], device->input_buffer[2]);
+ if (device->input_state != SYSEX_MESSAGE) {
+ //set to 1, keeping status byte, allowing for running status
+ device->input_count = 1;
+ }
+ break;
+ case 1:
+ if (device->input_state == TWO_BYTE_MESSAGE) {
+ //call callback
+ midi_input_callbacks(device, device->input_count,
+ device->input_buffer[0], device->input_buffer[1], 0);
+ if (device->input_state != SYSEX_MESSAGE) {
+ //set to 1, keeping status byte, allowing for running status
+ device->input_count = 1;
+ }
+ }
+ break;
+ case 0:
+ default:
+ //one byte messages are dealt with directly
+ break;
+ }
+ }
+ }
+}
+
+void midi_input_callbacks(MidiDevice * device, uint16_t cnt, uint8_t byte0, uint8_t byte1, uint8_t byte2) {
+ //did we end up calling a callback?
+ bool called = false;
+ if (device->input_state == SYSEX_MESSAGE) {
+ if (device->input_sysex_callback) {
+ const uint16_t start = ((cnt - 1) / 3) * 3;
+ const uint8_t length = (cnt - start);
+ uint8_t data[3];
+ data[0] = byte0;
+ data[1] = byte1;
+ data[2] = byte2;
+ device->input_sysex_callback(device, start, length, data);
+ called = true;
+ }
+ } else {
+ switch (cnt) {
+ case 3:
+ {
+ midi_three_byte_func_t func = NULL;
+ switch (byte0 & 0xF0) {
+ case MIDI_CC:
+ func = device->input_cc_callback;
+ break;
+ case MIDI_NOTEON:
+ func = device->input_noteon_callback;
+ break;
+ case MIDI_NOTEOFF:
+ func = device->input_noteoff_callback;
+ break;
+ case MIDI_AFTERTOUCH:
+ func = device->input_aftertouch_callback;
+ break;
+ case MIDI_PITCHBEND:
+ func = device->input_pitchbend_callback;
+ break;
+ case 0xF0:
+ if (byte0 == MIDI_SONGPOSITION)
+ func = device->input_songposition_callback;
+ break;
+ default:
+ break;
+ }
+ if(func) {
+ //mask off the channel for non song position functions
+ if (byte0 == MIDI_SONGPOSITION)
+ func(device, byte0, byte1, byte2);
+ else
+ func(device, byte0 & 0x0F, byte1, byte2);
+ called = true;
+ }
+ }
+ break;
+ case 2:
+ {
+ midi_two_byte_func_t func = NULL;
+ switch (byte0 & 0xF0) {
+ case MIDI_PROGCHANGE:
+ func = device->input_progchange_callback;
+ break;
+ case MIDI_CHANPRESSURE:
+ func = device->input_chanpressure_callback;
+ break;
+ case 0xF0:
+ if (byte0 == MIDI_SONGSELECT)
+ func = device->input_songselect_callback;
+ else if (byte0 == MIDI_TC_QUARTERFRAME)
+ func = device->input_tc_quarterframe_callback;
+ break;
+ default:
+ break;
+ }
+ if(func) {
+ //mask off the channel
+ if (byte0 == MIDI_SONGSELECT || byte0 == MIDI_TC_QUARTERFRAME)
+ func(device, byte0, byte1);
+ else
+ func(device, byte0 & 0x0F, byte1);
+ called = true;
+ }
+ }
+ break;
+ case 1:
+ {
+ midi_one_byte_func_t func = NULL;
+ if (midi_is_realtime(byte0))
+ func = device->input_realtime_callback;
+ else if (byte0 == MIDI_TUNEREQUEST)
+ func = device->input_tunerequest_callback;
+ if (func) {
+ func(device, byte0);
+ called = true;
+ }
+ }
+ break;
+ default:
+ //just in case
+ if (cnt > 3)
+ cnt = 0;
+ break;
+ }
+ }
+
+ //if there is fallthrough default callback and we haven't called a more specific one,
+ //call the fallthrough
+ if (!called && device->input_fallthrough_callback)
+ device->input_fallthrough_callback(device, cnt, byte0, byte1, byte2);
+ //always call the catch all if it exists
+ if (device->input_catchall_callback)
+ device->input_catchall_callback(device, cnt, byte0, byte1, byte2);
+}
+
diff --git a/tmk_core/protocol/lufa/midi/midi_device.h b/tmk_core/protocol/lufa/midi/midi_device.h
new file mode 100755
index 0000000000..088995286c
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/midi_device.h
@@ -0,0 +1,156 @@
+//midi for embedded chips,
+//Copyright 2010 Alex Norman
+//
+//This file is part of avr-midi.
+//
+//avr-midi is free software: you can redistribute it and/or modify
+//it under the terms of the GNU General Public License as published by
+//the Free Software Foundation, either version 3 of the License, or
+//(at your option) any later version.
+//
+//avr-midi is distributed in the hope that it will be useful,
+//but WITHOUT ANY WARRANTY; without even the implied warranty of
+//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+//GNU General Public License for more details.
+//
+//You should have received a copy of the GNU General Public License
+//along with avr-midi. If not, see <http://www.gnu.org/licenses/>.
+
+/**
+ * @file
+ * @brief Device implementation functions
+ */
+
+#ifndef MIDI_DEVICE_H
+#define MIDI_DEVICE_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+/**
+ * @defgroup midi_device Functions used when implementing your own midi device.
+ *
+ * You use the functions when you are implementing your own midi device.
+ *
+ * You set a send function to actually send bytes via your device, this method
+ * is called when you call a send function with this device, for instance
+ * midi_send_cc
+ *
+ * You use the midi_device_input to process input data from the device and pass
+ * it through the device's associated callbacks.
+ *
+ * You use the midi_device_set_pre_input_process_func if you want to have a
+ * function called at the beginning of the device's process function, generally
+ * to poll for input and pass that into midi_device_input
+ *
+ * @{
+ */
+
+#include "midi_function_types.h"
+#include "bytequeue/bytequeue.h"
+#define MIDI_INPUT_QUEUE_LENGTH 192
+
+typedef enum {
+ IDLE,
+ ONE_BYTE_MESSAGE = 1,
+ TWO_BYTE_MESSAGE = 2,
+ THREE_BYTE_MESSAGE = 3,
+ SYSEX_MESSAGE} input_state_t;
+
+typedef void (* midi_no_byte_func_t)(MidiDevice * device);
+
+/**
+ * \struct _midi_device
+ *
+ * @brief This structure represents the input and output functions and
+ * processing data for a midi device.
+ *
+ * A device can represent an actual physical device [serial port, usb port] or
+ * something virtual.
+ * You should not need to modify this structure directly.
+ */
+struct _midi_device {
+ //output send function
+ midi_var_byte_func_t send_func;
+
+ //********input callbacks
+ //three byte funcs
+ midi_three_byte_func_t input_cc_callback;
+ midi_three_byte_func_t input_noteon_callback;
+ midi_three_byte_func_t input_noteoff_callback;
+ midi_three_byte_func_t input_aftertouch_callback;
+ midi_three_byte_func_t input_pitchbend_callback;
+ midi_three_byte_func_t input_songposition_callback;
+ //two byte funcs
+ midi_two_byte_func_t input_progchange_callback;
+ midi_two_byte_func_t input_chanpressure_callback;
+ midi_two_byte_func_t input_songselect_callback;
+ midi_two_byte_func_t input_tc_quarterframe_callback;
+ //one byte funcs
+ midi_one_byte_func_t input_realtime_callback;
+ midi_one_byte_func_t input_tunerequest_callback;
+
+ //sysex
+ midi_sysex_func_t input_sysex_callback;
+
+ //only called if more specific callback is not matched
+ midi_var_byte_func_t input_fallthrough_callback;
+ //called if registered, independent of other callbacks
+ midi_var_byte_func_t input_catchall_callback;
+
+ //pre input processing function
+ midi_no_byte_func_t pre_input_process_callback;
+
+ //for internal input processing
+ uint8_t input_buffer[3];
+ input_state_t input_state;
+ uint16_t input_count;
+
+ //for queueing data between the input and the processing functions
+ uint8_t input_queue_data[MIDI_INPUT_QUEUE_LENGTH];
+ byteQueue_t input_queue;
+};
+
+/**
+ * @brief Process input bytes. This function parses bytes and calls the
+ * appropriate callbacks associated with the given device. You use this
+ * function if you are creating a custom device and you want to have midi
+ * input.
+ *
+ * @param device the midi device to associate the input with
+ * @param cnt the number of bytes you are processing
+ * @param input the bytes to process
+ */
+void midi_device_input(MidiDevice * device, uint8_t cnt, uint8_t * input);
+
+/**
+ * @brief Set the callback function that will be used for sending output
+ * data bytes. This is only used if you're creating a custom device.
+ * You'll most likely want the callback function to disable interrupts so
+ * that you can call the various midi send functions without worrying about
+ * locking.
+ *
+ * \param device the midi device to associate this callback with
+ * \param send_func the callback function that will do the sending
+ */
+void midi_device_set_send_func(MidiDevice * device, midi_var_byte_func_t send_func);
+
+/**
+ * @brief Set a callback which is called at the beginning of the
+ * midi_device_process call. This can be used to poll for input
+ * data and send the data through the midi_device_input function.
+ * You'll probably only use this if you're creating a custom device.
+ *
+ * \param device the midi device to associate this callback with
+ * \param midi_no_byte_func_t the actual callback function
+ */
+void midi_device_set_pre_input_process_func(MidiDevice * device, midi_no_byte_func_t pre_process_func);
+
+/**@}*/
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/tmk_core/protocol/lufa/midi/midi_function_types.h b/tmk_core/protocol/lufa/midi/midi_function_types.h
new file mode 100755
index 0000000000..35c4601b20
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/midi_function_types.h
@@ -0,0 +1,50 @@
+//midi for embedded chips,
+//Copyright 2010 Alex Norman
+//
+//This file is part of avr-midi.
+//
+//avr-midi is free software: you can redistribute it and/or modify
+//it under the terms of the GNU General Public License as published by
+//the Free Software Foundation, either version 3 of the License, or
+//(at your option) any later version.
+//
+//avr-midi is distributed in the hope that it will be useful,
+//but WITHOUT ANY WARRANTY; without even the implied warranty of
+//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+//GNU General Public License for more details.
+//
+//You should have received a copy of the GNU General Public License
+//along with avr-midi. If not, see <http://www.gnu.org/licenses/>.
+
+/**
+ * @file
+ * @brief Function signature definitions
+ */
+
+#ifndef MIDI_FUNCTION_TYPES_H
+#define MIDI_FUNCTION_TYPES_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <inttypes.h>
+#include <stdbool.h>
+
+//forward declaration
+typedef struct _midi_device MidiDevice;
+
+typedef void (* midi_one_byte_func_t)(MidiDevice * device, uint8_t byte);
+typedef void (* midi_two_byte_func_t)(MidiDevice * device, uint8_t byte0, uint8_t byte1);
+typedef void (* midi_three_byte_func_t)(MidiDevice * device, uint8_t byte0, uint8_t byte1, uint8_t byte2);
+//all bytes after count bytes should be ignored
+typedef void (* midi_var_byte_func_t)(MidiDevice * device, uint16_t count, uint8_t byte0, uint8_t byte1, uint8_t byte2);
+
+//the start byte tells you how far into the sysex message you are, the data_length tells you how many bytes data is
+typedef void (* midi_sysex_func_t)(MidiDevice * device, uint16_t start_byte, uint8_t data_length, uint8_t *data);
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/tmk_core/protocol/lufa/midi/sysex_tools.c b/tmk_core/protocol/lufa/midi/sysex_tools.c
new file mode 100755
index 0000000000..7563a3e2aa
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/sysex_tools.c
@@ -0,0 +1,99 @@
+//midi for embedded chips,
+//Copyright 2010 Alex Norman
+//
+//This file is part of avr-midi.
+//
+//avr-midi is free software: you can redistribute it and/or modify
+//it under the terms of the GNU General Public License as published by
+//the Free Software Foundation, either version 3 of the License, or
+//(at your option) any later version.
+//
+//avr-midi is distributed in the hope that it will be useful,
+//but WITHOUT ANY WARRANTY; without even the implied warranty of
+//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+//GNU General Public License for more details.
+//
+//You should have received a copy of the GNU General Public License
+//along with avr-midi. If not, see <http://www.gnu.org/licenses/>.
+
+#include "sysex_tools.h"
+
+uint16_t sysex_encoded_length(uint16_t decoded_length){
+ uint8_t remainder = decoded_length % 7;
+ if (remainder)
+ return (decoded_length / 7) * 8 + remainder + 1;
+ else
+ return (decoded_length / 7) * 8;
+}
+
+uint16_t sysex_decoded_length(uint16_t encoded_length){
+ uint8_t remainder = encoded_length % 8;
+ if (remainder)
+ return (encoded_length / 8) * 7 + remainder - 1;
+ else
+ return (encoded_length / 8) * 7;
+}
+
+uint16_t sysex_encode(uint8_t *encoded, const uint8_t *source, const uint16_t length){
+ uint16_t encoded_full = length / 7; //number of full 8 byte sections from 7 bytes of input
+ uint16_t i,j;
+
+ //fill out the fully encoded sections
+ for(i = 0; i < encoded_full; i++) {
+ uint16_t encoded_msb_idx = i * 8;
+ uint16_t input_start_idx = i * 7;
+ encoded[encoded_msb_idx] = 0;
+ for(j = 0; j < 7; j++){
+ uint8_t current = source[input_start_idx + j];
+ encoded[encoded_msb_idx] |= (0x80 & current) >> (1 + j);
+ encoded[encoded_msb_idx + 1 + j] = 0x7F & current;
+ }
+ }
+
+ //fill out the rest if there is any more
+ uint8_t remainder = length % 7;
+ if (remainder) {
+ uint16_t encoded_msb_idx = encoded_full * 8;
+ uint16_t input_start_idx = encoded_full * 7;
+ encoded[encoded_msb_idx] = 0;
+ for(j = 0; j < remainder; j++){
+ uint8_t current = source[input_start_idx + j];
+ encoded[encoded_msb_idx] |= (0x80 & current) >> (1 + j);
+ encoded[encoded_msb_idx + 1 + j] = 0x7F & current;
+ }
+ return encoded_msb_idx + remainder + 1;
+ } else {
+ return encoded_full * 8;
+ }
+}
+
+uint16_t sysex_decode(uint8_t *decoded, const uint8_t *source, const uint16_t length){
+ uint16_t decoded_full = length / 8;
+ uint16_t i,j;
+
+ if (length < 2)
+ return 0;
+
+ //fill out the fully encoded sections
+ for(i = 0; i < decoded_full; i++) {
+ uint16_t encoded_msb_idx = i * 8;
+ uint16_t output_start_index = i * 7;
+ for(j = 0; j < 7; j++){
+ decoded[output_start_index + j] = 0x7F & source[encoded_msb_idx + j + 1];
+ decoded[output_start_index + j] |= (0x80 & (source[encoded_msb_idx] << (1 + j)));
+ }
+ }
+ uint8_t remainder = length % 8;
+ if (remainder) {
+ uint16_t encoded_msb_idx = decoded_full * 8;
+ uint16_t output_start_index = decoded_full * 7;
+ for(j = 0; j < (remainder - 1); j++) {
+ decoded[output_start_index + j] = 0x7F & source[encoded_msb_idx + j + 1];
+ decoded[output_start_index + j] |= (0x80 & (source[encoded_msb_idx] << (1 + j)));
+ }
+ return decoded_full * 7 + remainder - 1;
+ } else {
+ return decoded_full * 7;
+ }
+}
+
diff --git a/tmk_core/protocol/lufa/midi/sysex_tools.h b/tmk_core/protocol/lufa/midi/sysex_tools.h
new file mode 100755
index 0000000000..3654d0114f
--- /dev/null
+++ b/tmk_core/protocol/lufa/midi/sysex_tools.h
@@ -0,0 +1,95 @@
+//midi for embedded chips,
+//Copyright 2010 Alex Norman
+//
+//This file is part of avr-midi.
+//
+//avr-midi is free software: you can redistribute it and/or modify
+//it under the terms of the GNU General Public License as published by
+//the Free Software Foundation, either version 3 of the License, or
+//(at your option) any later version.
+//
+//avr-midi is distributed in the hope that it will be useful,
+//but WITHOUT ANY WARRANTY; without even the implied warranty of
+//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+//GNU General Public License for more details.
+//
+//You should have received a copy of the GNU General Public License
+//along with avr-midi. If not, see <http://www.gnu.org/licenses/>.
+
+#ifndef SYSEX_TOOLS_H
+#define SYSEX_TOOLS_H
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#include <inttypes.h>
+
+/**
+ * @file
+ * @brief Sysex utility functions
+ *
+ * These functions are for converting data to and from a "midi-safe" format,
+ * which can be use to send data with sysex messages. Sysex messages may only
+ * contain data where the to bit is not set.
+ *
+ * An "encoded" midi message is one that contains all of the data from its
+ * original state, but does not have any of the top bits set.
+ *
+ * Every 7 bytes of decoded data is converted into 8 bytes of encoded data and
+ * visa-versa. If you'd like to operate on small segments, make sure that you
+ * encode in 7 byte increments and decode in 8 byte increments.
+ *
+ */
+
+/** @defgroup sysex_tools Sysex utility functions
+ * @{
+ */
+
+/**
+ * @brief Compute the length of a message after it is encoded.
+ *
+ * @param decoded_length The length, in bytes, of the message to encode.
+ *
+ * @return The length, in bytes, of the message after encodeing.
+ */
+uint16_t sysex_encoded_length(uint16_t decoded_length);
+
+/**
+ * @brief Compute the length of a message after it is decoded.
+ *
+ * @param encoded_length The length, in bytes, of the encoded message.
+ *
+ * @return The length, in bytes, of the message after it is decoded.
+ */
+uint16_t sysex_decoded_length(uint16_t encoded_length);
+
+/**
+ * @brief Encode data so that it can be transmitted safely in a sysex message.
+ *
+ * @param encoded The output data buffer, must be at least sysex_encoded_length(length) bytes long.
+ * @param source The input buffer of data to be encoded.
+ * @param length The number of bytes from the input buffer to encode.
+ *
+ * @return number of bytes encoded.
+ */
+uint16_t sysex_encode(uint8_t *encoded, const uint8_t *source, uint16_t length);
+
+/**
+ * @brief Decode encoded data.
+ *
+ * @param decoded The output data buffer, must be at least sysex_decoded_length(length) bytes long.
+ * @param source The input buffer of data to be decoded.
+ * @param length The number of bytes from the input buffer to decode.
+ *
+ * @return number of bytes decoded.
+ */
+uint16_t sysex_decode(uint8_t *decoded, const uint8_t *source, uint16_t length);
+
+/**@}*/
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif