[Keymap] catrielmuller keymap for the dztech/dz65rgb (#7015)
[jackhill/qmk/firmware.git] / quantum / encoder.c
CommitLineData
85688e5b
JH
1/*
2 * Copyright 2018 Jack Humbert <jack.humb@gmail.com>
3 *
4 * This program is free software: you can redistribute it and/or modify
5 * it under the terms of the GNU General Public License as published by
6 * the Free Software Foundation, either version 2 of the License, or
7 * (at your option) any later version.
8 *
9 * This program is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 * GNU General Public License for more details.
13 *
14 * You should have received a copy of the GNU General Public License
15 * along with this program. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18#include "encoder.h"
36dd261d 19#ifdef SPLIT_KEYBOARD
b624f32f 20# include "split_util.h"
36dd261d 21#endif
85688e5b 22
63177760
X
23// for memcpy
24#include <string.h>
25
85688e5b 26#ifndef ENCODER_RESOLUTION
b624f32f 27# define ENCODER_RESOLUTION 4
85688e5b
JH
28#endif
29
85688e5b 30#if !defined(ENCODERS_PAD_A) || !defined(ENCODERS_PAD_B)
b624f32f 31# error "No encoder pads defined by ENCODERS_PAD_A and ENCODERS_PAD_B"
85688e5b
JH
32#endif
33
b624f32f 34#define NUMBER_OF_ENCODERS (sizeof(encoders_pad_a) / sizeof(pin_t))
f6c7e114
DJ
35static pin_t encoders_pad_a[] = ENCODERS_PAD_A;
36static pin_t encoders_pad_b[] = ENCODERS_PAD_B;
85688e5b 37
b624f32f 38static int8_t encoder_LUT[] = {0, -1, 1, 0, 1, 0, 0, -1, -1, 0, 0, 1, 0, 1, -1, 0};
85688e5b
JH
39
40static uint8_t encoder_state[NUMBER_OF_ENCODERS] = {0};
63177760
X
41
42#ifdef SPLIT_KEYBOARD
46c49ae4 43// right half encoders come over as second set of encoders
63177760 44static int8_t encoder_value[NUMBER_OF_ENCODERS * 2] = {0};
46c49ae4
X
45// row offsets for each hand
46static uint8_t thisHand, thatHand;
63177760 47#else
85688e5b 48static int8_t encoder_value[NUMBER_OF_ENCODERS] = {0};
63177760 49#endif
85688e5b 50
b624f32f 51__attribute__((weak)) void encoder_update_user(int8_t index, bool clockwise) {}
85688e5b 52
b624f32f 53__attribute__((weak)) void encoder_update_kb(int8_t index, bool clockwise) { encoder_update_user(index, clockwise); }
85688e5b
JH
54
55void encoder_init(void) {
36dd261d 56#if defined(SPLIT_KEYBOARD) && defined(ENCODERS_PAD_A_RIGHT) && defined(ENCODERS_PAD_B_RIGHT)
b624f32f 57 if (!isLeftHand) {
58 const pin_t encoders_pad_a_right[] = ENCODERS_PAD_A_RIGHT;
59 const pin_t encoders_pad_b_right[] = ENCODERS_PAD_B_RIGHT;
60 for (uint8_t i = 0; i < NUMBER_OF_ENCODERS; i++) {
61 encoders_pad_a[i] = encoders_pad_a_right[i];
62 encoders_pad_b[i] = encoders_pad_b_right[i];
63 }
36dd261d 64 }
36dd261d
D
65#endif
66
b624f32f 67 for (int i = 0; i < NUMBER_OF_ENCODERS; i++) {
68 setPinInputHigh(encoders_pad_a[i]);
69 setPinInputHigh(encoders_pad_b[i]);
85688e5b 70
b624f32f 71 encoder_state[i] = (readPin(encoders_pad_a[i]) << 0) | (readPin(encoders_pad_b[i]) << 1);
72 }
46c49ae4
X
73
74#ifdef SPLIT_KEYBOARD
75 thisHand = isLeftHand ? 0 : NUMBER_OF_ENCODERS;
76 thatHand = NUMBER_OF_ENCODERS - thisHand;
77#endif
78}
79
80static void encoder_update(int8_t index, uint8_t state) {
81 encoder_value[index] += encoder_LUT[state & 0xF];
82 if (encoder_value[index] >= ENCODER_RESOLUTION) {
83 encoder_update_kb(index, false);
84 }
85 if (encoder_value[index] <= -ENCODER_RESOLUTION) { // direction is arbitrary here, but this clockwise
86 encoder_update_kb(index, true);
87 }
88 encoder_value[index] %= ENCODER_RESOLUTION;
85688e5b
JH
89}
90
91void encoder_read(void) {
b624f32f 92 for (int i = 0; i < NUMBER_OF_ENCODERS; i++) {
93 encoder_state[i] <<= 2;
94 encoder_state[i] |= (readPin(encoders_pad_a[i]) << 0) | (readPin(encoders_pad_b[i]) << 1);
46c49ae4
X
95#if SPLIT_KEYBOARD
96 encoder_update(i + thisHand, encoder_state[i]);
97#else
98 encoder_update(i, encoder_state[i]);
99#endif
85688e5b 100 }
85688e5b 101}
63177760
X
102
103#ifdef SPLIT_KEYBOARD
b624f32f 104void encoder_state_raw(uint8_t* slave_state) { memcpy(slave_state, encoder_state, sizeof(encoder_state)); }
63177760
X
105
106void encoder_update_raw(uint8_t* slave_state) {
b624f32f 107 for (int i = 0; i < NUMBER_OF_ENCODERS; i++) {
46c49ae4 108 encoder_update(i + thatHand, slave_state[i]);
63177760 109 }
63177760
X
110}
111#endif