~ruther/qmk_firmware

444fd3b1cc07d7f68aa37cbc9e38f2e4ed4d3ea7 — Nick Brassel 5 years ago e18be69
Add support for delays in send_string. (#8244)

3 files changed, 75 insertions(+), 34 deletions(-)

M docs/feature_macros.md
M quantum/quantum.c
M quantum/send_string_keycodes.h
M docs/feature_macros.md => docs/feature_macros.md +15 -5
@@ 107,6 107,16 @@ Would tap `KC_HOME` - note how the prefix is now `X_`, and not `KC_`. You can al

Which would send "VE" followed by a `KC_HOME` tap, and "LO" (spelling "LOVE" if on a newline).

Delays can be also added to the string:

* `SS_DELAY(msecs)` will delay for the specified number of milliseconds.

For example:

    SEND_STRING("VE" SS_DELAY(1000) SS_TAP(X_HOME) "LO");

Which would send "VE" followed by a 1-second delay, then a `KC_HOME` tap, and "LO" (spelling "LOVE" if on a newline, but delayed in the middle).

There's also a couple of mod shortcuts you can use:

* `SS_LCTL(string)`


@@ 200,11 210,11 @@ This will clear all mods currently pressed.

This will clear all keys besides the mods currently pressed.

## Advanced Example: 
## Advanced Example:

### Super ALT↯TAB

This macro will register `KC_LALT` and tap `KC_TAB`, then wait for 1000ms. If the key is tapped again, it will send another `KC_TAB`; if there is no tap, `KC_LALT` will be unregistered, thus allowing you to cycle through windows. 
This macro will register `KC_LALT` and tap `KC_TAB`, then wait for 1000ms. If the key is tapped again, it will send another `KC_TAB`; if there is no tap, `KC_LALT` will be unregistered, thus allowing you to cycle through windows.

```c
bool is_alt_tab_active = false;    # ADD this near the begining of keymap.c


@@ 221,7 231,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
        if (!is_alt_tab_active) {
          is_alt_tab_active = true;
          register_code(KC_LALT);
        } 
        }
        alt_tab_timer = timer_read();
        register_code(KC_TAB);
      } else {


@@ 232,7 242,7 @@ bool process_record_user(uint16_t keycode, keyrecord_t *record) {
  return true;
}

void matrix_scan_user(void) {     # The very important timer. 
void matrix_scan_user(void) {     # The very important timer.
  if (is_alt_tab_active) {
    if (timer_elapsed(alt_tab_timer) > 1000) {
      unregister_code(KC_LALT);


@@ 321,7 331,7 @@ const uint16_t PROGMEM keymaps[][MATRIX_ROWS][MATRIX_COLS] = {
```


## Advanced Example: 
## Advanced Example:

### Single-Key Copy/Paste


M quantum/quantum.c => quantum/quantum.c +53 -26
@@ 14,6 14,7 @@
 * along with this program.  If not, see <http://www.gnu.org/licenses/>.
 */

#include <ctype.h>
#include "quantum.h"

#ifdef PROTOCOL_LUFA


@@ 374,19 375,32 @@ void send_string_with_delay(const char *str, uint8_t interval) {
    while (1) {
        char ascii_code = *str;
        if (!ascii_code) break;
        if (ascii_code == SS_TAP_CODE) {
            // tap
            uint8_t keycode = *(++str);
            register_code(keycode);
            unregister_code(keycode);
        } else if (ascii_code == SS_DOWN_CODE) {
            // down
            uint8_t keycode = *(++str);
            register_code(keycode);
        } else if (ascii_code == SS_UP_CODE) {
            // up
            uint8_t keycode = *(++str);
            unregister_code(keycode);
        if (ascii_code == SS_QMK_PREFIX) {
            ascii_code = *(++str);
            if (ascii_code == SS_TAP_CODE) {
                // tap
                uint8_t keycode = *(++str);
                register_code(keycode);
                unregister_code(keycode);
            } else if (ascii_code == SS_DOWN_CODE) {
                // down
                uint8_t keycode = *(++str);
                register_code(keycode);
            } else if (ascii_code == SS_UP_CODE) {
                // up
                uint8_t keycode = *(++str);
                unregister_code(keycode);
            } else if (ascii_code == SS_DELAY_CODE) {
                // delay
                int     ms      = 0;
                uint8_t keycode = *(++str);
                while (isdigit(keycode)) {
                    ms *= 10;
                    ms += keycode - '0';
                    keycode = *(++str);
                }
                while (ms--) wait_ms(1);
            }
        } else {
            send_char(ascii_code);
        }


@@ 403,19 417,32 @@ void send_string_with_delay_P(const char *str, uint8_t interval) {
    while (1) {
        char ascii_code = pgm_read_byte(str);
        if (!ascii_code) break;
        if (ascii_code == SS_TAP_CODE) {
            // tap
            uint8_t keycode = pgm_read_byte(++str);
            register_code(keycode);
            unregister_code(keycode);
        } else if (ascii_code == SS_DOWN_CODE) {
            // down
            uint8_t keycode = pgm_read_byte(++str);
            register_code(keycode);
        } else if (ascii_code == SS_UP_CODE) {
            // up
            uint8_t keycode = pgm_read_byte(++str);
            unregister_code(keycode);
        if (ascii_code == SS_QMK_PREFIX) {
            ascii_code = pgm_read_byte(++str);
            if (ascii_code == SS_TAP_CODE) {
                // tap
                uint8_t keycode = pgm_read_byte(++str);
                register_code(keycode);
                unregister_code(keycode);
            } else if (ascii_code == SS_DOWN_CODE) {
                // down
                uint8_t keycode = pgm_read_byte(++str);
                register_code(keycode);
            } else if (ascii_code == SS_UP_CODE) {
                // up
                uint8_t keycode = pgm_read_byte(++str);
                unregister_code(keycode);
            } else if (ascii_code == SS_DELAY_CODE) {
                // delay
                int     ms      = 0;
                uint8_t keycode = pgm_read_byte(++str);
                while (isdigit(keycode)) {
                    ms *= 10;
                    ms += keycode - '0';
                    keycode = pgm_read_byte(++str);
                }
                while (ms--) wait_ms(1);
            }
        } else {
            send_char(ascii_code);
        }

M quantum/send_string_keycodes.h => quantum/send_string_keycodes.h +7 -3
@@ 382,13 382,17 @@
#define ADD_SLASH_X(y) STRINGIZE(\x##y)
#define SYMBOL_STR(x) ADD_SLASH_X(x)

#define SS_QMK_PREFIX 1

#define SS_TAP_CODE 1
#define SS_DOWN_CODE 2
#define SS_UP_CODE 3
#define SS_DELAY_CODE 4

#define SS_TAP(keycode) "\1" SYMBOL_STR(keycode)
#define SS_DOWN(keycode) "\2" SYMBOL_STR(keycode)
#define SS_UP(keycode) "\3" SYMBOL_STR(keycode)
#define SS_TAP(keycode) "\1\1" SYMBOL_STR(keycode)
#define SS_DOWN(keycode) "\1\2" SYMBOL_STR(keycode)
#define SS_UP(keycode) "\1\3" SYMBOL_STR(keycode)
#define SS_DELAY(msecs) "\1\4" STRINGIZE(msecs) "|"

// `string` arguments must not be parenthesized
#define SS_LCTL(string) SS_DOWN(X_LCTL) string SS_UP(X_LCTL)