wasm: call focus on window if not editable

We used to call focus on the input element even for things
like pushbuttons.

This will display a keyboard on android, instead call
focus on the focus window.

Fixes: QTBUG-133781
Pick-to: 6.9 6.8
Change-Id: Ide4d6ec21a14f17b40d3d3de077c0ab073682f19
Reviewed-by: Lorn Potter <lorn.potter@qt.io>
This commit is contained in:
Even Oscar Andersen 2025-02-17 12:26:05 +01:00
parent 8055a5c2db
commit 442e2f4aeb
4 changed files with 33 additions and 15 deletions

View File

@ -2,6 +2,7 @@
// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only
#include "qwasminputcontext.h"
#include "qwasmwindow.h"
#include <QRectF>
#include <QLoggingCategory>
@ -306,30 +307,35 @@ void QWasmInputContext::update(Qt::InputMethodQueries queries)
void QWasmInputContext::showInputPanel()
{
qCDebug(qLcQpaWasmInputContext) << Q_FUNC_INFO;
m_visibleInputPanel = true;
updateInputElement();
}
void QWasmInputContext::setInputText()
void QWasmInputContext::updateInputElement()
{
// If there is no focus object, remove focus
const QWindow *focusWindow = QGuiApplication::focusWindow();
if (!m_focusObject || !focusWindow) {
m_inputElement.call<void>("blur");
return;
}
// Mobile devices can dismiss keyboard/IME and focus is still on input.
// Successive clicks on the same input should open the keyboard/IME.
// We set the focus even if we do not have input method accepted
if (!m_inputMethodAccepted) {
// If there is no focus object, or no visible input panel, remove focus
const QWindow *focusWindow = QGuiApplication::focusWindow();
if (!m_focusObject || !focusWindow || !m_visibleInputPanel || !m_inputMethodAccepted) {
m_inputElement["style"].set("left", "0px");
m_inputElement["style"].set("top", "0px");
m_inputElement["style"].set("width", "1px");
m_inputElement["style"].set("height", "1px");
m_inputElement.set("value", "");
m_inputElement.call<void>("focus");
m_inputElement.call<void>("blur");
if (focusWindow && focusWindow->handle())
((QWasmWindow *)(focusWindow->handle()))->focus();
return;
}
Q_ASSERT(focusWindow);
Q_ASSERT(m_focusObject);
Q_ASSERT(m_visibleInputPanel);
Q_ASSERT(m_inputMethodAccepted);
// Set the geometry
@ -379,13 +385,18 @@ void QWasmInputContext::setFocusObject(QObject *object)
m_inputMethodAccepted = (object && inputMethodAccepted());
m_focusObject = object;
setInputText();
updateInputElement();
QPlatformInputContext::setFocusObject(object);
}
void QWasmInputContext::hideInputPanel()
{
qCDebug(qLcQpaWasmInputContext) << Q_FUNC_INFO;
m_visibleInputPanel = false;
// hide only if m_focusObject does not exist
if (!m_focusObject)
updateInputElement();
}
void QWasmInputContext::setPreeditString(QString preeditStr, int replaceSize)

View File

@ -43,12 +43,13 @@ public:
void setFocusObject(QObject *object) override;
private:
void setInputText();
void updateInputElement();
private:
QString m_preeditString;
int m_replaceSize = 0;
bool m_visibleInputPanel = false;
bool m_inputMethodAccepted = false;
QObject *m_focusObject = nullptr;
};

View File

@ -379,7 +379,8 @@ void QWasmWindow::setVisible(bool visible)
m_compositor->requestUpdateWindow(this, QRect(QPoint(0, 0), geometry().size()), QWasmCompositor::ExposeEventDelivery);
m_decoratedWindow["style"].set("display", visible ? "block" : "none");
if (window() == QGuiApplication::focusWindow())
m_canvas.call<void>("focus");
focus();
if (visible)
applyWindowState();
}
@ -907,11 +908,15 @@ void QWasmWindow::requestActivateWindow()
setAsActiveNode();
if (!QWasmIntegration::get()->inputContext())
m_canvas.call<void>("focus");
focus();
QPlatformWindow::requestActivateWindow();
}
void QWasmWindow::focus()
{
m_canvas.call<void>("focus");
}
bool QWasmWindow::setMouseGrabEnabled(bool grab)
{
Q_UNUSED(grab);

View File

@ -86,6 +86,7 @@ public:
bool windowEvent(QEvent *event) final;
void setMask(const QRegion &region) final;
void setParent(const QPlatformWindow *window) final;
void focus();
QWasmScreen *platformScreen() const;
void setBackingStore(QWasmBackingStore *store) { m_backingStore = store; }