9#include <QInputMethodEvent>
26#define LOC QString("MythUITextEdit: ")
44 LOG(VB_GENERAL, LOG_ERR,
LOC +
"selected state doesn't exist");
50 LOG(VB_GENERAL, LOG_ERR,
LOC +
"active state doesn't exist");
91 const QString &
filename, QDomElement &element,
bool showWarnings)
95 if (element.tagName() ==
"area")
99 else if (element.tagName() ==
"keyboardposition")
103 if (pos ==
"aboveedit") {
105 }
else if (pos ==
"belowedit") {
107 }
else if (pos ==
"screentop") {
109 }
else if (pos ==
"screenbottom") {
111 }
else if (pos ==
"screencenter") {
115 QString(
"Unknown popup position '%1'").arg(pos));
156 LOG(VB_GENERAL, LOG_ERR,
LOC +
"Missing text element.");
159 LOG(VB_GENERAL, LOG_ERR,
LOC +
"Missing cursor element.");
162 LOG(VB_GENERAL, LOG_WARNING,
LOC +
"Missing background element.");
173 LOG(VB_GENERAL, LOG_ERR,
LOC +
"active state doesn't exist");
177 int height = fm.height();
182 int width = int(((
float)height / (
float)imageArea.height())
183 * (
float)imageArea.width());
227 for (
const auto& c : std::as_const(text))
240 const QChar *unichar = character.unicode();
243 if (!unichar->isPrint())
274 newmessage.append(str);
286 newmessage.remove(position, 1);
363 QClipboard *clipboard = QApplication::clipboard();
370 QClipboard *clipboard = QApplication::clipboard();
372 if (!clipboard->supportsSelection())
373 mode = QClipboard::Clipboard;
384 map[
keyCombo(Qt::Key_Dead_Grave, Qt::Key_A)] = Qt::Key_Agrave;
385 map[
keyCombo(Qt::Key_Dead_Acute, Qt::Key_A)] = Qt::Key_Aacute;
386 map[
keyCombo(Qt::Key_Dead_Circumflex, Qt::Key_A)] = Qt::Key_Acircumflex;
387 map[
keyCombo(Qt::Key_Dead_Tilde, Qt::Key_A)] = Qt::Key_Atilde;
388 map[
keyCombo(Qt::Key_Dead_Diaeresis, Qt::Key_A)] = Qt::Key_Adiaeresis;
389 map[
keyCombo(Qt::Key_Dead_Abovering, Qt::Key_A)] = Qt::Key_Aring;
391 map[
keyCombo(Qt::Key_Dead_Cedilla, Qt::Key_C)] = Qt::Key_Ccedilla;
393 map[
keyCombo(Qt::Key_Dead_Grave, Qt::Key_E)] = Qt::Key_Egrave;
394 map[
keyCombo(Qt::Key_Dead_Acute, Qt::Key_E)] = Qt::Key_Eacute;
395 map[
keyCombo(Qt::Key_Dead_Circumflex, Qt::Key_E)] = Qt::Key_Ecircumflex;
396 map[
keyCombo(Qt::Key_Dead_Diaeresis, Qt::Key_E)] = Qt::Key_Ediaeresis;
398 map[
keyCombo(Qt::Key_Dead_Grave, Qt::Key_I)] = Qt::Key_Igrave;
399 map[
keyCombo(Qt::Key_Dead_Acute, Qt::Key_I)] = Qt::Key_Iacute;
400 map[
keyCombo(Qt::Key_Dead_Circumflex, Qt::Key_I)] = Qt::Key_Icircumflex;
401 map[
keyCombo(Qt::Key_Dead_Diaeresis, Qt::Key_I)] = Qt::Key_Idiaeresis;
403 map[
keyCombo(Qt::Key_Dead_Tilde, Qt::Key_N)] = Qt::Key_Ntilde;
405 map[
keyCombo(Qt::Key_Dead_Grave, Qt::Key_O)] = Qt::Key_Ograve;
406 map[
keyCombo(Qt::Key_Dead_Acute, Qt::Key_O)] = Qt::Key_Oacute;
407 map[
keyCombo(Qt::Key_Dead_Circumflex, Qt::Key_O)] = Qt::Key_Ocircumflex;
408 map[
keyCombo(Qt::Key_Dead_Tilde, Qt::Key_O)] = Qt::Key_Otilde;
409 map[
keyCombo(Qt::Key_Dead_Diaeresis, Qt::Key_O)] = Qt::Key_Odiaeresis;
411 map[
keyCombo(Qt::Key_Dead_Grave, Qt::Key_U)] = Qt::Key_Ugrave;
412 map[
keyCombo(Qt::Key_Dead_Acute, Qt::Key_U)] = Qt::Key_Uacute;
413 map[
keyCombo(Qt::Key_Dead_Circumflex, Qt::Key_U)] = Qt::Key_Ucircumflex;
414 map[
keyCombo(Qt::Key_Dead_Diaeresis, Qt::Key_U)] = Qt::Key_Udiaeresis;
416 map[
keyCombo(Qt::Key_Dead_Acute, Qt::Key_Y)] = Qt::Key_Yacute;
417 map[
keyCombo(Qt::Key_Dead_Diaeresis, Qt::Key_Y)] = Qt::Key_ydiaeresis;
427 if (!
m_isIMEinput && (event->commitString().isEmpty() || event->preeditString().isEmpty()))
433 printf(
"IME: %s->%s PREEDIT=\"%s\" COMMIT=\"%s\"\n"
434 , (_bak) ?
"ON" :
"OFF"
436 , event->preeditString().toUtf8().constData()
437 , event->commitString().toUtf8().constData());
471 bool handled =
false;
476 Qt::KeyboardModifiers modifiers =
event->modifiers();
477 int keynum =
event->key();
479 if (keynum >= Qt::Key_Shift && keynum <= Qt::Key_CapsLock)
485 if (((modifiers & Qt::GroupSwitchModifier) != 0U) &&
486 (keynum >= Qt::Key_Dead_Grave) && (keynum <= Qt::Key_Dead_Horn))
496 LOG(VB_GUI, LOG_DEBUG, QString(
"Compose key: %1 Key: %2")
497 .arg(QString::number(
m_composeKey, 16), QString::number(keynum, 16)));
504 character = QChar(keycode);
506 if ((modifiers & Qt::ShiftModifier) != 0U)
507 character = character.toUpper();
509 character = character.toLower();
510 LOG(VB_GUI, LOG_DEBUG, QString(
"Found match for dead-key combo - %1").arg(character));
515 if (character.isEmpty())
516 character =
event->text();
521 for (
int i = 0; i < actions.size() && !handled; i++)
524 const QString&
action = actions[i];
531 else if (
action ==
"RIGHT")
539 else if (
action ==
"DOWN")
543 else if (
action ==
"PAGEUP")
547 else if (
action ==
"PAGEDOWN")
551 else if (
action ==
"DELETE")
555 else if (
action ==
"BACKSPACE")
559 else if (
action ==
"NEWLINE")
566 else if (
action ==
"SELECT" && keynum != Qt::Key_Space
567 &&
GetMythDB()->GetNumSetting(
"UseVirtualKeyboard", 1) == 1)
585 else if (
action ==
"COPY")
589 else if (
action ==
"PASTE")
609 bool handled =
false;
626 LOG(VB_GENERAL, LOG_ERR,
LOC +
"ERROR, bad parsing");
647 textedit->CopyFrom(
this);
A custom event that represents a mouse gesture.
Gesture GetGesture() const
Qt::MouseButton GetButton() const
bool TranslateKeyPress(const QString &Context, QKeyEvent *Event, QStringList &Actions, bool AllowJumps=true)
Get a list of actions for a keypress in the given context.
MythScreenStack * GetStack(const QString &Stackname)
Wrapper around QRect allowing us to handle percentage and other relative values for areas in mythui.
virtual void AddScreen(MythScreenType *screen, bool allowFade=true)
std::chrono::milliseconds restart(void)
Returns milliseconds elapsed since last start() or restart() and resets the count.
std::chrono::milliseconds elapsed(void)
Returns milliseconds elapsed since last start() or restart()
void start(void)
starts measuring elapsed time.
Image widget, displays a single image or multiple images in sequence.
void ForceSize(QSize size)
Force the dimensions of the widget and image to the given size.
This widget is used for grouping other widgets for display when a particular named state is called.
bool DisplayState(const QString &name)
A text entry and edit widget.
bool gestureEvent(MythGestureEvent *event) override
Mouse click/movement handler, receives mouse gesture events from the QCoreApplication event loop.
MythUIImage * m_cursorImage
bool InsertCharacter(const QString &character)
bool keyPressEvent(QKeyEvent *event) override
Key event handler.
void SetInitialStates(void)
void PasteTextFromClipboard(QClipboard::Mode mode=QClipboard::Clipboard)
bool UpdateTmpString(const QString &str)
void SetText(const QString &text, bool moveCursor=true)
void RemoveCharacter(int position)
MythUITextEdit(MythUIType *parent, const QString &name)
PopupPosition m_keyboardPosition
void SetMaxLength(int length)
void CopyTextToClipboard(void)
void CreateCopy(MythUIType *parent) override
Copy the state of this widget to the one given, it must be of the same type.
MythUIStateType * m_backgroundState
void Reset(void) override
Reset the widget to it's original state, should not reset changes made by the theme.
void InsertText(const QString &text)
bool ParseElement(const QString &filename, QDomElement &element, bool showWarnings) override
Parse the xml definition of this widget setting the state of the object accordingly.
void Pulse(void) override
Pulse is called 70 times a second to trigger a single frame of an animation.
void CutTextToClipboard(void)
void Finalize(void) override
Perform any post-xml parsing initialisation tasks.
bool MoveCursor(MoveDirection moveDir)
void CopyFrom(MythUIType *base) override
Copy this widgets state from another.
bool inputMethodEvent(QInputMethodEvent *event) override
Input Method event handler.
All purpose text widget, displays a text string.
int MoveCursor(int lines)
QPoint CursorPosition(int text_offset)
const MythFontProperties * GetFontProperties()
void SetCutDown(Qt::TextElideMode mode)
virtual void SetText(const QString &text)
The base class on which all widgets and screens are based.
bool IsVisible(bool recurse=false) const
virtual void SetVisible(bool visible)
virtual void SetArea(const MythRect &rect)
virtual void CopyFrom(MythUIType *base)
Copy this widgets state from another.
virtual void Pulse(void)
Pulse is called 70 times a second to trigger a single frame of an animation.
virtual MythRect GetFullArea(void) const
void SetPosition(int x, int y)
Convenience method, calls SetPosition(const MythPoint&) Override that instead to change functionality...
MythUIType * GetChild(const QString &name) const
Get a named child of this UIType.
virtual bool ParseElement(const QString &filename, QDomElement &element, bool showWarnings)
Parse the xml definition of this widget setting the state of the object accordingly.
A popup onscreen keyboard for easy alphanumeric and text entry using a remote control or mouse.
static MythRect parseRect(const QString &text, bool normalize=true)
static QString getFirstText(QDomElement &element)
A C++ ripoff of the stroke library for MythTV.
#define LOG(_MASK_, _LEVEL_, _QSTRING_)
MythMainWindow * GetMythMainWindow(void)
QPair< int, int > keyCombo
static QMap< keyCombo, int > gDeadKeyMap
static void LoadDeadKeys(QMap< QPair< int, int >, int > &map)
#define VERBOSE_XML(type, level, filename, element, msg)