Skip to content

Commit

Permalink
save as fcitx key string
Browse files Browse the repository at this point in the history
  • Loading branch information
eagleoflqj committed Jun 14, 2024
1 parent e7014b5 commit b34b2e2
Show file tree
Hide file tree
Showing 7 changed files with 80 additions and 30 deletions.
5 changes: 3 additions & 2 deletions macosfrontend/keycode.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -176,8 +176,9 @@ static struct {
{OSX_VK_SHIFT_R, 54},
};

fcitx::KeySym osx_unicode_to_fcitx_keysym(uint32_t unicode, uint16_t osxKeycode,
uint32_t osxModifiers) {
fcitx::KeySym osx_unicode_to_fcitx_keysym(uint32_t unicode,
uint32_t osxModifiers,
uint16_t osxKeycode) {
for (const auto &pair : sym_mappings) {
if (pair.osxKeycode == osxKeycode) {
return pair.sym;
Expand Down
5 changes: 3 additions & 2 deletions macosfrontend/keycode.h
Original file line number Diff line number Diff line change
Expand Up @@ -246,8 +246,9 @@
#define OSX_MODIFIER_FUNCTION (1 << 23)
// clang-format on

fcitx::KeySym osx_unicode_to_fcitx_keysym(uint32_t unicode, uint16_t osxKeycode,
uint32_t osxModifiers);
fcitx::KeySym osx_unicode_to_fcitx_keysym(uint32_t unicode,
uint32_t osxModifiers,
uint16_t osxKeycode);
uint16_t osx_keycode_to_fcitx_keycode(uint16_t osxKeycode);
fcitx::KeyStates osx_modifiers_to_fcitx_keystates(uint32_t osxModifiers);

Expand Down
2 changes: 2 additions & 0 deletions macosfrontend/macosfrontend-public.h
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,8 @@
// Though being UInt, 32b is enough for modifiers
std::string process_key(ICUUID uuid, uint32_t unicode, uint32_t osxModifiers,
uint16_t osxKeycode, bool isRelease) noexcept;
std::string osx_key_to_fcitx_string(uint32_t unicode, uint32_t modifiers,
uint16_t code) noexcept;

ICUUID create_input_context(const char *appId, id client) noexcept;
void destroy_input_context(ICUUID uuid) noexcept;
Expand Down
22 changes: 16 additions & 6 deletions macosfrontend/macosfrontend.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -190,14 +190,24 @@ MacosInputContext::getCursorCoordinates(bool followCursor) {

} // namespace fcitx

std::string process_key(ICUUID uuid, uint32_t unicode, uint32_t osxModifiers,
uint16_t osxKeycode, bool isRelease) noexcept {
const fcitx::Key parsedKey{
osx_unicode_to_fcitx_keysym(unicode, osxKeycode, osxModifiers),
osx_modifiers_to_fcitx_keystates(osxModifiers),
osx_keycode_to_fcitx_keycode(osxKeycode),
fcitx::Key osx_key_to_fcitx_key(uint32_t unicode, uint32_t modifiers,
uint16_t code) noexcept {
return fcitx::Key{
osx_unicode_to_fcitx_keysym(unicode, modifiers, code),
osx_modifiers_to_fcitx_keystates(modifiers),
osx_keycode_to_fcitx_keycode(code),
};
}

std::string osx_key_to_fcitx_string(uint32_t unicode, uint32_t modifiers,
uint16_t code) noexcept {
return osx_key_to_fcitx_key(unicode, modifiers, code).toString();
}

std::string process_key(ICUUID uuid, uint32_t unicode, uint32_t osxModifiers,
uint16_t osxKeycode, bool isRelease) noexcept {
const fcitx::Key parsedKey =
osx_key_to_fcitx_key(unicode, osxModifiers, osxKeycode);
return with_fcitx([=](Fcitx &fcitx) {
auto that = dynamic_cast<fcitx::MacosFrontend *>(fcitx.frontend());
return that->keyEvent(uuid, parsedKey, isRelease);
Expand Down
16 changes: 16 additions & 0 deletions src/config/keycode.swift
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@
import Cocoa
import CxxFrontend

private func keyToUnicode(_ key: String) -> UInt32 {
if key.isEmpty {
return 0
}
let usv = key.unicodeScalars
return usv[usv.startIndex].value
}

func macKeyToFcitxString(_ key: String, _ modifier: NSEvent.ModifierFlags, _ code: UInt16) -> String
{
let unicode = keyToUnicode(key)
return String(osx_key_to_fcitx_string(unicode, UInt32(modifier.rawValue), code))
}
48 changes: 30 additions & 18 deletions src/config/keyrecorder.swift
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,9 @@ import SwiftUI

struct RecordingOverlay: NSViewRepresentable {
@Binding var recordedShortcut: String
@Binding var recordedKey: String
@Binding var recordedModifiers: NSEvent.ModifierFlags
@Binding var recordedCode: UInt16

func makeNSView(context: Context) -> NSView {
let view = KeyCaptureView()
Expand Down Expand Up @@ -56,12 +59,12 @@ struct RecordingOverlay: NSViewRepresentable {
0x67: "F11",
0x6f: "F12",
// cursor
0x7e: "",
0x7d: "",
0x7b: "",
0x7c: "",
0x74: "",
0x79: "",
0x7e: "",
0x7d: "",
0x7b: "",
0x7c: "",
0x74: "",
0x79: "",
0x73: "",
0x77: "",
// pc keyboard
Expand All @@ -72,33 +75,42 @@ struct RecordingOverlay: NSViewRepresentable {
]
private var parent: RecordingOverlay
private var key = ""
private var modifier = NSEvent.ModifierFlags()
private var keySym = ""
private var modifiers = NSEvent.ModifierFlags()
private var code: UInt16 = 0

init(_ parent: RecordingOverlay) {
self.parent = parent
}

func handleKeyCapture(key: String, code: Int) {
self.key = Coordinator.codeMap[code] ?? key

func handleKeyCapture(key: String, code: UInt16) {
self.key = key
self.keySym = Coordinator.codeMap[Int(code)] ?? key
self.code = code
updateParent()
}

func handleKeyCapture(modifier: NSEvent.ModifierFlags) {
if modifier.isDisjoint(with: [.command, .option, .control, .shift]) {
self.modifier = NSEvent.ModifierFlags()
func handleKeyCapture(modifiers: NSEvent.ModifierFlags, code: UInt16) {
if modifiers.isDisjoint(with: [.command, .option, .control, .shift]) {
self.modifiers = NSEvent.ModifierFlags()
self.code = 0
} else {
if modifier.isSuperset(of: self.modifier) {
if modifiers.isSuperset(of: self.modifiers) {
// Don't change on release
self.modifier = modifier
self.modifiers = modifiers
self.key = ""
self.keySym = ""
self.code = code
}
updateParent()
}
}

private func updateParent() {
parent.recordedShortcut = modifier.description + key
parent.recordedKey = key
parent.recordedModifiers = modifiers
parent.recordedCode = code
parent.recordedShortcut = modifiers.description + keySym
}
}
}
Expand All @@ -113,11 +125,11 @@ class KeyCaptureView: NSView {

override func keyDown(with event: NSEvent) {
coordinator?.handleKeyCapture(
key: event.charactersIgnoringModifiers ?? "", code: Int(event.keyCode))
key: event.charactersIgnoringModifiers ?? "", code: event.keyCode)
}

override func flagsChanged(with event: NSEvent) {
coordinator?.handleKeyCapture(modifier: event.modifierFlags)
coordinator?.handleKeyCapture(modifiers: event.modifierFlags, code: event.keyCode)
}
}

Expand Down
12 changes: 10 additions & 2 deletions src/config/optionviews.swift
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,10 @@ struct KeyOptionView: OptionView {
let overrideLabel: String? = nil
@ObservedObject var model: KeyOption
@State private var showRecorder = false
@State private var recordedShortcut: String = ""
@State private var recordedShortcut = ""
@State private var recordedKey = ""
@State private var recordedModifiers = NSEvent.ModifierFlags()
@State private var recordedCode: UInt16 = 0

var body: some View {
Button {
Expand All @@ -36,7 +39,11 @@ struct KeyOptionView: OptionView {
}.sheet(isPresented: $showRecorder) {
VStack {
Text(recordedShortcut)
.background(RecordingOverlay(recordedShortcut: $recordedShortcut))
.background(
RecordingOverlay(
recordedShortcut: $recordedShortcut, recordedKey: $recordedKey,
recordedModifiers: $recordedModifiers, recordedCode: $recordedCode)
)
.frame(minWidth: 200, minHeight: 50)
HStack {
Button {
Expand All @@ -45,6 +52,7 @@ struct KeyOptionView: OptionView {
Text("Cancel")
}
Button {
model.value = macKeyToFcitxString(recordedKey, recordedModifiers, recordedCode)
showRecorder = false
} label: {
Text("OK")
Expand Down

0 comments on commit b34b2e2

Please sign in to comment.