Gui: Add support for hints in status bar

This commit is contained in:
Kacper Donat
2025-03-23 15:34:14 +01:00
parent 548af02619
commit aa47949f80
26 changed files with 1210 additions and 5 deletions

218
src/Gui/InputHintPy.cpp Normal file
View File

@@ -0,0 +1,218 @@
// SPDX-License-Identifier: LGPL-2.1-or-later
/****************************************************************************
* *
* Copyright (c) 2025 Kacper Donat <kacper@kadet.net> *
* *
* This file is part of FreeCAD. *
* *
* FreeCAD is free software: you can redistribute it and/or modify it *
* under the terms of the GNU Lesser General Public License as *
* published by the Free Software Foundation, either version 2.1 of the *
* License, or (at your option) any later version. *
* *
* FreeCAD 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 *
* Lesser General Public License for more details. *
* *
* You should have received a copy of the GNU Lesser General Public *
* License along with FreeCAD. If not, see *
* <https://www.gnu.org/licenses/>. *
* *
***************************************************************************/
#include "PreCompiled.h"
#include "InputHint.h"
#include "InputHintPy.h"
void Gui::registerUserInputEnumInPython(PyObject* module)
{
using enum Gui::InputHint::UserInput;
constexpr const char* name = "UserInput";
PyObject* py_enum_module = PyImport_ImportModule("enum");
if (!py_enum_module) {
return;
}
PyObject* py_constants_dict = PyDict_New();
// clang-format off
// this structure is repetition of each and every UserInput enum case
// it can be regenerated by copying and pasting all entries and performing one substitution:
// regex search: `(\w+) = .+?,` substitution: `{"$1", $1},`
const std::map<const char*, InputHint::UserInput> userInputEntries {
// Modifier
{"ModifierShift", ModifierShift},
{"ModifierCtrl", ModifierCtrl},
{"ModifierAlt", ModifierAlt},
{"ModifierMeta", ModifierMeta},
// Keyboard Keys
{"KeySpace", KeySpace},
{"KeyExclam", KeyExclam},
{"KeyQuoteDbl", KeyQuoteDbl},
{"KeyNumberSign", KeyNumberSign},
{"KeyDollar", KeyDollar},
{"KeyPercent", KeyPercent},
{"KeyAmpersand", KeyAmpersand},
{"KeyApostrophe", KeyApostrophe},
{"KeyParenLeft", KeyParenLeft},
{"KeyParenRight", KeyParenRight},
{"KeyAsterisk", KeyAsterisk},
{"KeyPlus", KeyPlus},
{"KeyComma", KeyComma},
{"KeyMinus", KeyMinus},
{"KeyPeriod", KeyPeriod},
{"KeySlash", KeySlash},
{"Key0", Key0},
{"Key1", Key1},
{"Key2", Key2},
{"Key3", Key3},
{"Key4", Key4},
{"Key5", Key5},
{"Key6", Key6},
{"Key7", Key7},
{"Key8", Key8},
{"Key9", Key9},
{"KeyColon", KeyColon},
{"KeySemicolon", KeySemicolon},
{"KeyLess", KeyLess},
{"KeyEqual", KeyEqual},
{"KeyGreater", KeyGreater},
{"KeyQuestion", KeyQuestion},
{"KeyAt", KeyAt},
{"KeyA", KeyA},
{"KeyB", KeyB},
{"KeyC", KeyC},
{"KeyD", KeyD},
{"KeyE", KeyE},
{"KeyF", KeyF},
{"KeyG", KeyG},
{"KeyH", KeyH},
{"KeyI", KeyI},
{"KeyJ", KeyJ},
{"KeyK", KeyK},
{"KeyL", KeyL},
{"KeyM", KeyM},
{"KeyN", KeyN},
{"KeyO", KeyO},
{"KeyP", KeyP},
{"KeyQ", KeyQ},
{"KeyR", KeyR},
{"KeyS", KeyS},
{"KeyT", KeyT},
{"KeyU", KeyU},
{"KeyV", KeyV},
{"KeyW", KeyW},
{"KeyX", KeyX},
{"KeyY", KeyY},
{"KeyZ", KeyZ},
{"KeyBracketLeft", KeyBracketLeft},
{"KeyBackslash", KeyBackslash},
{"KeyBracketRight", KeyBracketRight},
{"KeyAsciiCircum", KeyAsciiCircum},
{"KeyUnderscore", KeyUnderscore},
{"KeyQuoteLeft", KeyQuoteLeft},
{"KeyBraceLeft", KeyBraceLeft},
{"KeyBar", KeyBar},
{"KeyBraceRight", KeyBraceRight},
{"KeyAsciiTilde", KeyAsciiTilde},
// misc keys
{"KeyEscape", KeyEscape},
{"KeyTab", KeyTab},
{"KeyBacktab", KeyBacktab},
{"KeyBackspace", KeyBackspace},
{"KeyReturn", KeyReturn},
{"KeyEnter", KeyEnter},
{"KeyInsert", KeyInsert},
{"KeyDelete", KeyDelete},
{"KeyPause", KeyPause},
{"KeyPrintScr", KeyPrintScr},
{"KeySysReq", KeySysReq},
{"KeyClear", KeyClear},
// cursor movement
{"KeyHome", KeyHome},
{"KeyEnd", KeyEnd},
{"KeyLeft", KeyLeft},
{"KeyUp", KeyUp},
{"KeyRight", KeyRight},
{"KeyDown", KeyDown},
{"KeyPageUp", KeyPageUp},
{"KeyPageDown", KeyPageDown},
// modifiers
{"KeyShift", KeyShift},
{"KeyControl", KeyControl},
{"KeyMeta", KeyMeta},
{"KeyAlt", KeyAlt},
{"KeyCapsLock", KeyCapsLock},
{"KeyNumLock", KeyNumLock},
{"KeyScrollLock", KeyScrollLock},
// function keys
{"KeyF1", KeyF1},
{"KeyF2", KeyF2},
{"KeyF3", KeyF3},
{"KeyF4", KeyF4},
{"KeyF5", KeyF5},
{"KeyF6", KeyF6},
{"KeyF7", KeyF7},
{"KeyF8", KeyF8},
{"KeyF9", KeyF9},
{"KeyF10", KeyF10},
{"KeyF11", KeyF11},
{"KeyF12", KeyF12},
{"KeyF13", KeyF13},
{"KeyF14", KeyF14},
{"KeyF15", KeyF15},
{"KeyF16", KeyF16},
{"KeyF17", KeyF17},
{"KeyF18", KeyF18},
{"KeyF19", KeyF19},
{"KeyF20", KeyF20},
{"KeyF21", KeyF21},
{"KeyF22", KeyF22},
{"KeyF23", KeyF23},
{"KeyF24", KeyF24},
{"KeyF25", KeyF25},
{"KeyF26", KeyF26},
{"KeyF27", KeyF27},
{"KeyF28", KeyF28},
{"KeyF29", KeyF29},
{"KeyF30", KeyF30},
{"KeyF31", KeyF31},
{"KeyF32", KeyF32},
{"KeyF33", KeyF33},
{"KeyF34", KeyF34},
{"KeyF35", KeyF35},
// Mouse Keys
{"MouseMove", MouseMove},
{"MouseLeft", MouseLeft},
{"MouseRight", MouseRight},
{"MouseMiddle", MouseMiddle},
{"MouseScroll", MouseScroll},
{"MouseScrollUp", MouseScrollUp},
{"MouseScrollDown", MouseScrollDown},
};
// clang-format on
// Populate dictionary
for (const auto& [key, value] : userInputEntries) {
PyDict_SetItemString(py_constants_dict, key, PyLong_FromLong(static_cast<int>(value)));
}
PyObject* py_enum_class = PyObject_CallMethod(py_enum_module, "IntEnum", "sO", name, py_constants_dict);
Py_CLEAR(py_constants_dict);
Py_CLEAR(py_enum_module);
if (py_enum_class && PyModule_AddObject(module, name, py_enum_class) < 0) {
Py_CLEAR(py_enum_class);
}
}