PDA

View Full Version : QML virtual keyboard + TextEdit



nick85
14th January 2014, 11:12
Hi all,

I'm attempting to build a virtual keyboard in my QML application (Qt 4.8.5 and QML 1.1).
What I really need is to simulate key events when pressing a key buttons of virtual keyboard.

I searched online for some solutions but I don't find a clear one.
The solution most listed seems to be to create a custom c++ class (with an Invokable method) that should simulate the key press and release event.

Surprisingly I did not find any example about it so I tried to build it but, into sendEvent call (bool QCoreApplication::sendEvent ( QObject * receiver, QEvent * event ) [static]), I don't know what set as receiver... or better I don't know how to pass the QML TextEdit "instance" as receiver.

How to do it?
Or otherwise there is another way to do it?


Part of my class code:


void KeyEmitter::simulateKey(QString keyName)
{
// getting selected keycode
Qt::Key keycode = _getKeyCodeFromName(keyName);
if ( keycode == Qt::Key_unknown )
{
#ifdef DEBUG_ENABLED
qDebug() << "Cannot resolve keycode associated to " << keyName;
#endif
return;
}

QObject * receiver = NULL; // ???

if (keyName.length() == 1 && keyName[0].unicode() >= 'A' && keyName[0].unicode() <= 'Z')
{
QKeyEvent keyPressEvent(QEvent::KeyPress, keycode, Qt::ShiftModifier, keyName);
QApplication::sendEvent(receiver, &keyPressEvent);

QKeyEvent keyReleaseEvent(QEvent::KeyRelease, keycode, Qt::ShiftModifier, keyName);
QApplication::sendEvent(receiver, &keyReleaseEvent);
}
else
{
QKeyEvent keyPressEvent(QEvent::KeyPress, keycode, Qt::NoModifier, keyName);
QApplication::sendEvent(receiver, &keyPressEvent);

QKeyEvent keyReleaseEvent(QEvent::KeyRelease, keycode, Qt::NoModifier, keyName);
QApplication::sendEvent(receiver, &keyReleaseEvent);
}

#ifdef DEBUG_ENABLED
qDebug() << "Simulated key " << qPrintable(keyName);
#endif
}

Thanks in advance


UPDATE

I found a similar issue with mouse event in this post : http://stackoverflow.com/questions/7517700/how-to-simulate-mouse-clicks-in-qml

I tried to pass the viewer as receiver in my application and it works!

Summarizing....
Into main:

int main(int argc, char *argv[])
{
[...]
QmlApplicationViewer viewer;
[...]
QScopedPointer<KeyEmitter> keyEmitter(new KeyEmitter(&viewer));
viewer.rootContext()->setContextProperty("keyEmitter", keyEmitter.data());
[...]
}

Into KeyEmitter class:

class KeyEmitter : public QObject
{
Q_OBJECT

public:

KeyEmitter*(QObject * receiver*, QObject * parent = NULL); // Added passing of receiver

Q_INVOKABLE void simulateKey(QString keyName);
[...]

private:

QObject * _receiver;
[...]
};

into QML:

IconButton // is an implementation of a "standard" button
{
id: abutton
text: "a"
onClicked: keyEmitter.simulateKey(text)
}

shtdown
12th September 2014, 12:44
Hi,

thanks for posting your solution after you got it working :) I've got a few difficulties with my KeyEmitter class. Have you still got access to your code and could post the whole class code?

Thank you in advance