@@ -594,6 +594,7 @@ Array string_to_array(const String input, bool crlf)
594
594
void modify_keymap(Buffer buffer, bool is_unmap, String mode, String lhs, String rhs,
595
595
Dict(keymap) *opts, Error *err)
596
596
{
597
+
LuaRef lua_funcref = LUA_NOREF;
597
598
bool global = (buffer == -1);
598
599
if (global) {
599
600
buffer = 0;
@@ -604,6 +605,9 @@ void modify_keymap(Buffer buffer, bool is_unmap, String mode, String lhs, String
604
605
return;
605
606
}
606
607
608
+
if (opts != NULL && opts->callback.type == kObjectTypeLuaRef) {
609
+
lua_funcref = api_new_luaref(opts->callback.data.luaref);
610
+
}
607
611
MapArguments parsed_args = MAP_ARGUMENTS_INIT;
608
612
if (opts) {
609
613
#define KEY_TO_BOOL(name) \
@@ -623,9 +627,13 @@ void modify_keymap(Buffer buffer, bool is_unmap, String mode, String lhs, String
623
627
parsed_args.buffer = !global;
624
628
625
629
set_maparg_lhs_rhs((char_u *)lhs.data, lhs.size,
626
-
(char_u *)rhs.data, rhs.size,
630
+
(char_u *)rhs.data, rhs.size, lua_funcref,
627
631
CPO_TO_CPO_FLAGS, &parsed_args);
628
-
632
+
if (opts != NULL && opts->desc.type == kObjectTypeString) {
633
+
parsed_args.desc = xstrdup(opts->desc.data.string.data);
634
+
} else {
635
+
parsed_args.desc = NULL;
636
+
}
629
637
if (parsed_args.lhs_len > MAXMAPLEN) {
630
638
api_set_error(err, kErrorTypeValidation, "LHS exceeds maximum map length: %s", lhs.data);
631
639
goto fail_and_free;
@@ -658,7 +666,8 @@ void modify_keymap(Buffer buffer, bool is_unmap, String mode, String lhs, String
658
666
bool is_noremap = parsed_args.noremap;
659
667
assert(!(is_unmap && is_noremap));
660
668
661
-
if (!is_unmap && (parsed_args.rhs_len == 0 && !parsed_args.rhs_is_noop)) {
669
+
if (!is_unmap && lua_funcref == LUA_NOREF
670
+
&& (parsed_args.rhs_len == 0 && !parsed_args.rhs_is_noop)) {
662
671
if (rhs.size == 0) { // assume that the user wants RHS to be a <Nop>
663
672
parsed_args.rhs_is_noop = true;
664
673
} else {
@@ -668,9 +677,13 @@ void modify_keymap(Buffer buffer, bool is_unmap, String mode, String lhs, String
668
677
api_set_error(err, kErrorTypeValidation, "Parsing of nonempty RHS failed: %s", rhs.data);
669
678
goto fail_and_free;
670
679
}
671
-
} else if (is_unmap && parsed_args.rhs_len) {
672
-
api_set_error(err, kErrorTypeValidation,
673
-
"Gave nonempty RHS in unmap command: %s", parsed_args.rhs);
680
+
} else if (is_unmap && (parsed_args.rhs_len || parsed_args.rhs_lua != LUA_NOREF)) {
681
+
if (parsed_args.rhs_len) {
682
+
api_set_error(err, kErrorTypeValidation,
683
+
"Gave nonempty RHS in unmap command: %s", parsed_args.rhs);
684
+
} else {
685
+
api_set_error(err, kErrorTypeValidation, "Gave nonempty RHS for unmap");
686
+
}
674
687
goto fail_and_free;
675
688
}
676
689
@@ -700,9 +713,12 @@ void modify_keymap(Buffer buffer, bool is_unmap, String mode, String lhs, String
700
713
goto fail_and_free;
701
714
} // switch
702
715
716
+
parsed_args.rhs_lua = LUA_NOREF; // don't clear ref on success
703
717
fail_and_free:
718
+
NLUA_CLEAR_REF(parsed_args.rhs_lua);
704
719
xfree(parsed_args.rhs);
705
720
xfree(parsed_args.orig_rhs);
721
+
XFREE_CLEAR(parsed_args.desc);
706
722
return;
707
723
}
708
724
@@ -1052,8 +1068,9 @@ void api_set_error(Error *err, ErrorType errType, const char *format, ...)
1052
1068
///
1053
1069
/// @param mode The abbreviation for the mode
1054
1070
/// @param buf The buffer to get the mapping array. NULL for global
1071
+
/// @param from_lua Whether it is called from internal lua api.
1055
1072
/// @returns Array of maparg()-like dictionaries describing mappings
1056
-
ArrayOf(Dictionary) keymap_array(String mode, buf_T *buf)
1073
+
ArrayOf(Dictionary) keymap_array(String mode, buf_T *buf, bool from_lua)
1057
1074
{
1058
1075
Array mappings = ARRAY_DICT_INIT;
1059
1076
dict_T *const dict = tv_dict_alloc();
@@ -1073,8 +1090,19 @@ ArrayOf(Dictionary) keymap_array(String mode, buf_T *buf)
1073
1090
// Check for correct mode
1074
1091
if (int_mode & current_maphash->m_mode) {
1075
1092
mapblock_fill_dict(dict, current_maphash, buffer_value, false);
1076
-
ADD(mappings, vim_to_object((typval_T[]) { { .v_type = VAR_DICT, .vval.v_dict = dict } }));
1077
-
1093
+
Object api_dict = vim_to_object((typval_T[]) { { .v_type = VAR_DICT,
1094
+
.vval.v_dict = dict } });
1095
+
if (from_lua) {
1096
+
Dictionary d = api_dict.data.dictionary;
1097
+
for (size_t j = 0; j < d.size; j++) {
1098
+
if (strequal("callback", d.items[j].key.data)) {
1099
+
d.items[j].value.type = kObjectTypeLuaRef;
1100
+
d.items[j].value.data.luaref = api_new_luaref((LuaRef)d.items[j].value.data.integer);
1101
+
break;
1102
+
}
1103
+
}
1104
+
}
1105
+
ADD(mappings, api_dict);
1078
1106
tv_dict_clear(dict);
1079
1107
}
1080
1108
}
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4