diff options
Diffstat (limited to 'src/plugins/platforms/wasm')
| -rw-r--r-- | src/plugins/platforms/wasm/qwasmdrag.cpp | 66 | ||||
| -rw-r--r-- | src/plugins/platforms/wasm/qwasmdrag.h | 3 | ||||
| -rw-r--r-- | src/plugins/platforms/wasm/qwasmevent.cpp | 4 | ||||
| -rw-r--r-- | src/plugins/platforms/wasm/qwasmevent.h | 5 | ||||
| -rw-r--r-- | src/plugins/platforms/wasm/qwasmintegration.cpp | 2 | ||||
| -rw-r--r-- | src/plugins/platforms/wasm/qwasmkeytranslator.cpp | 42 | ||||
| -rw-r--r-- | src/plugins/platforms/wasm/qwasmkeytranslator.h | 13 | ||||
| -rw-r--r-- | src/plugins/platforms/wasm/qwasmscreen.cpp | 3 | ||||
| -rw-r--r-- | src/plugins/platforms/wasm/qwasmscreen.h | 3 | ||||
| -rw-r--r-- | src/plugins/platforms/wasm/qwasmwindow.cpp | 13 | ||||
| -rw-r--r-- | src/plugins/platforms/wasm/qwasmwindow.h | 5 |
11 files changed, 66 insertions, 93 deletions
diff --git a/src/plugins/platforms/wasm/qwasmdrag.cpp b/src/plugins/platforms/wasm/qwasmdrag.cpp index 730816b9a99..6447d1e399f 100644 --- a/src/plugins/platforms/wasm/qwasmdrag.cpp +++ b/src/plugins/platforms/wasm/qwasmdrag.cpp @@ -16,6 +16,9 @@ #include <QtCore/qtimer.h> #include <QFile> +#include <private/qshapedpixmapdndwindow_p.h> +#include <private/qdnd_p.h> + #include <functional> #include <string> #include <utility> @@ -91,16 +94,13 @@ Qt::DropAction QWasmDrag::drag(QDrag *drag) return Qt::IgnoreAction; Qt::DropAction dragResult = Qt::IgnoreAction; - if (qstdweb::haveJspi()) { - QEventLoop loop; - m_dragState = std::make_unique<DragState>(drag, window, [&loop]() { loop.quit(); }); - loop.exec(); - dragResult = m_dragState->dropAction; + if (qstdweb::haveAsyncify()) { + m_dragState = std::make_unique<DragState>(drag, window, [this]() { QSimpleDrag::cancelDrag(); }); + dragResult = QSimpleDrag::drag(drag); m_dragState.reset(); - } - - if (dragResult == Qt::IgnoreAction) + } else { dragResult = QBasicDrag::drag(drag); + } return dragResult; } @@ -110,13 +110,16 @@ void QWasmDrag::onNativeDragStarted(DragEvent *event) Q_ASSERT_X(event->type == EventType::DragStart, Q_FUNC_INFO, "The event is not a DragStart event"); - event->webEvent.call<void>("preventDefault"); - // It is possible for a drag start event to arrive from another window. if (!m_dragState || m_dragState->window != event->targetWindow) { event->cancelDragStart(); return; } + setExecutedDropAction(event->dropAction); + + // We have our own window + if (shapedPixmapWindow()) + shapedPixmapWindow()->setVisible(false); m_dragState->dragImage = std::make_unique<DragState::DragImage>( m_dragState->drag->pixmap(), m_dragState->drag->mimeData(), event->targetWindow); @@ -141,8 +144,10 @@ void QWasmDrag::onNativeDragOver(DragEvent *event) event->mouseButton, event->modifiers); event->acceptDragOver(); if (dragResponse.isAccepted()) { + setExecutedDropAction(dragResponse.acceptedAction()); event->dataTransfer.setDropAction(dragResponse.acceptedAction()); } else { + setExecutedDropAction(Qt::DropAction::IgnoreAction); event->dataTransfer.setDropAction(Qt::DropAction::IgnoreAction); } } @@ -170,19 +175,22 @@ void QWasmDrag::onNativeDrop(DragEvent *event) // files, but the browser expects that accepted state is set before any // async calls. event->acceptDrop(); + setExecutedDropAction(event->dropAction); + std::shared_ptr<DragState> dragState = m_dragState; - const auto dropCallback = [&m_dragState = m_dragState, wasmWindow, targetWindowPos, + const auto dropCallback = [dragState, wasmWindow, targetWindowPos, actions, mouseButton, modifiers](QMimeData *mimeData) { - - auto dropResponse = std::make_shared<QPlatformDropQtResponse>(true, Qt::DropAction::CopyAction); - *dropResponse = QWindowSystemInterface::handleDrop(wasmWindow->window(), mimeData, + if (mimeData) { + auto dropResponse = std::make_shared<QPlatformDropQtResponse>(true, Qt::DropAction::CopyAction); + *dropResponse = QWindowSystemInterface::handleDrop(wasmWindow->window(), mimeData, targetWindowPos, actions, mouseButton, modifiers); - if (dropResponse->isAccepted()) - m_dragState->dropAction = dropResponse->acceptedAction(); + if (dragState && dropResponse->isAccepted()) + dragState->dropAction = dropResponse->acceptedAction(); - delete mimeData; + delete mimeData; + } }; event->dataTransfer.toMimeDataWithFile(dropCallback); @@ -192,13 +200,35 @@ void QWasmDrag::onNativeDragFinished(DragEvent *event) { event->webEvent.call<void>("preventDefault"); m_dragState->dropAction = event->dropAction; + setExecutedDropAction(event->dropAction); m_dragState->quitEventLoopClosure(); } +void QWasmDrag::onNativeDragEnter(DragEvent *event) +{ + event->webEvent.call<void>("preventDefault"); + + // Already dragging + if (QDragManager::self() && QDragManager::self()->object()) + return; + + // Event coming from external browser, start a drag + if (m_dragState) + m_dragState->dropAction = event->dropAction; + + setExecutedDropAction(event->dropAction); + + QDrag *drag = new QDrag(this); + drag->setMimeData(new QMimeData()); + drag->exec(Qt::CopyAction | Qt::MoveAction, Qt::CopyAction); +} + void QWasmDrag::onNativeDragLeave(DragEvent *event) { event->webEvent.call<void>("preventDefault"); - m_dragState->dropAction = event->dropAction; + if (m_dragState) + m_dragState->dropAction = event->dropAction; + setExecutedDropAction(event->dropAction); event->dataTransfer.setDropAction(Qt::DropAction::IgnoreAction); } diff --git a/src/plugins/platforms/wasm/qwasmdrag.h b/src/plugins/platforms/wasm/qwasmdrag.h index e821470c913..5bb8ec66a3c 100644 --- a/src/plugins/platforms/wasm/qwasmdrag.h +++ b/src/plugins/platforms/wasm/qwasmdrag.h @@ -32,6 +32,7 @@ public: void onNativeDrop(DragEvent *event); void onNativeDragStarted(DragEvent *event); void onNativeDragFinished(DragEvent *event); + void onNativeDragEnter(DragEvent *event); void onNativeDragLeave(DragEvent *event); // QPlatformDrag: @@ -40,7 +41,7 @@ public: private: struct DragState; - std::unique_ptr<DragState> m_dragState; + std::shared_ptr<DragState> m_dragState; }; QT_END_NAMESPACE diff --git a/src/plugins/platforms/wasm/qwasmevent.cpp b/src/plugins/platforms/wasm/qwasmevent.cpp index e6d5a20a24d..676d9c8e155 100644 --- a/src/plugins/platforms/wasm/qwasmevent.cpp +++ b/src/plugins/platforms/wasm/qwasmevent.cpp @@ -112,7 +112,7 @@ bool Event::isTargetedForQtElement() const return topElementClassName.startsWith("qt-"); // .e.g. qt-window-canvas } -KeyEvent::KeyEvent(EventType type, emscripten::val event, QWasmDeadKeySupport *deadKeySupport) : Event(type, event) +KeyEvent::KeyEvent(EventType type, emscripten::val event) : Event(type, event) { const auto code = event["code"].as<std::string>(); const auto webKey = event["key"].as<std::string>(); @@ -137,8 +137,6 @@ KeyEvent::KeyEvent(EventType type, emscripten::val event, QWasmDeadKeySupport *d if (key == Qt::Key_Tab) text = "\t"; - - deadKeySupport->applyDeadKeyTranslations(this); } MouseEvent::MouseEvent(EventType type, emscripten::val event) : Event(type, event) diff --git a/src/plugins/platforms/wasm/qwasmevent.h b/src/plugins/platforms/wasm/qwasmevent.h index 9b6f11fd5da..07faee3fe4b 100644 --- a/src/plugins/platforms/wasm/qwasmevent.h +++ b/src/plugins/platforms/wasm/qwasmevent.h @@ -17,14 +17,13 @@ #include <emscripten/val.h> QT_BEGIN_NAMESPACE - -class QWasmDeadKeySupport; class QWindow; enum class EventType { DragEnd, DragOver, DragStart, + DragEnter, DragLeave, Drop, KeyDown, @@ -65,7 +64,7 @@ struct Event struct KeyEvent : public Event { - KeyEvent(EventType type, emscripten::val webEvent, QWasmDeadKeySupport *deadKeySupport); + KeyEvent(EventType type, emscripten::val webEvent); Qt::Key key; QFlags<Qt::KeyboardModifier> modifiers; diff --git a/src/plugins/platforms/wasm/qwasmintegration.cpp b/src/plugins/platforms/wasm/qwasmintegration.cpp index b56c57974d1..7417f316169 100644 --- a/src/plugins/platforms/wasm/qwasmintegration.cpp +++ b/src/plugins/platforms/wasm/qwasmintegration.cpp @@ -200,7 +200,7 @@ QWasmWindow *QWasmIntegration::createWindow(QWindow *window, WId nativeHandle) c { auto *wasmScreen = QWasmScreen::get(window->screen()); QWasmCompositor *compositor = wasmScreen->compositor(); - return new QWasmWindow(window, wasmScreen->deadKeySupport(), compositor, + return new QWasmWindow(window, compositor, m_backingStores.value(window), nativeHandle); } diff --git a/src/plugins/platforms/wasm/qwasmkeytranslator.cpp b/src/plugins/platforms/wasm/qwasmkeytranslator.cpp index 8f5240d2d0c..90a4ee807fb 100644 --- a/src/plugins/platforms/wasm/qwasmkeytranslator.cpp +++ b/src/plugins/platforms/wasm/qwasmkeytranslator.cpp @@ -250,46 +250,4 @@ std::optional<Qt::Key> QWasmKeyTranslator::mapWebKeyTextToQtKey(const char *toFi : std::optional<Qt::Key>(); } -QWasmDeadKeySupport::QWasmDeadKeySupport() = default; - -QWasmDeadKeySupport::~QWasmDeadKeySupport() = default; - -void QWasmDeadKeySupport::applyDeadKeyTranslations(KeyEvent *event) -{ - if (event->deadKey) { - m_activeDeadKey = event->key; - } else if (m_activeDeadKey != Qt::Key_unknown - && (((m_keyModifiedByDeadKeyOnPress == Qt::Key_unknown - && event->type == EventType::KeyDown)) - || (m_keyModifiedByDeadKeyOnPress == event->key - && event->type == EventType::KeyUp))) { - const Qt::Key baseKey = event->key; - const Qt::Key translatedKey = translateBaseKeyUsingDeadKey(baseKey, m_activeDeadKey); - if (translatedKey != Qt::Key_unknown) { - event->key = translatedKey; - - auto foundText = event->modifiers.testFlag(Qt::ShiftModifier) - ? findKeyTextByKeyId(DiacriticalCharsKeyToTextUppercase, event->key) - : findKeyTextByKeyId(DiacriticalCharsKeyToTextLowercase, event->key); - Q_ASSERT(foundText.has_value()); - event->text = foundText->size() == 1 ? *foundText : QString(); - } - - if (!event->text.isEmpty()) { - if (event->type == EventType::KeyDown) { - // Assume the first keypress with an active dead key is treated as modified, - // regardless of whether it has actually been modified or not. Take into account - // only events that produce actual key text. - if (!event->text.isEmpty()) - m_keyModifiedByDeadKeyOnPress = baseKey; - } else { - Q_ASSERT(event->type == EventType::KeyUp); - Q_ASSERT(m_keyModifiedByDeadKeyOnPress == baseKey); - m_keyModifiedByDeadKeyOnPress = Qt::Key_unknown; - m_activeDeadKey = Qt::Key_unknown; - } - } - } -} - QT_END_NAMESPACE diff --git a/src/plugins/platforms/wasm/qwasmkeytranslator.h b/src/plugins/platforms/wasm/qwasmkeytranslator.h index 11a89e61930..3e18bcb8802 100644 --- a/src/plugins/platforms/wasm/qwasmkeytranslator.h +++ b/src/plugins/platforms/wasm/qwasmkeytranslator.h @@ -17,18 +17,5 @@ namespace QWasmKeyTranslator { std::optional<Qt::Key> mapWebKeyTextToQtKey(const char *toFind); } -class QWasmDeadKeySupport -{ -public: - explicit QWasmDeadKeySupport(); - ~QWasmDeadKeySupport(); - - void applyDeadKeyTranslations(KeyEvent *event); - -private: - Qt::Key m_activeDeadKey = Qt::Key_unknown; - Qt::Key m_keyModifiedByDeadKeyOnPress = Qt::Key_unknown; -}; - QT_END_NAMESPACE #endif // QWASMKEYTRANSLATOR_H diff --git a/src/plugins/platforms/wasm/qwasmscreen.cpp b/src/plugins/platforms/wasm/qwasmscreen.cpp index a2c8306b13b..bbfc71edc54 100644 --- a/src/plugins/platforms/wasm/qwasmscreen.cpp +++ b/src/plugins/platforms/wasm/qwasmscreen.cpp @@ -30,8 +30,7 @@ QWasmScreen::QWasmScreen(const emscripten::val &containerOrCanvas) : m_container(containerOrCanvas), m_intermediateContainer(emscripten::val::undefined()), m_shadowContainer(emscripten::val::undefined()), - m_compositor(new QWasmCompositor(this)), - m_deadKeySupport(std::make_unique<QWasmDeadKeySupport>()) + m_compositor(new QWasmCompositor(this)) { auto document = m_container["ownerDocument"]; diff --git a/src/plugins/platforms/wasm/qwasmscreen.h b/src/plugins/platforms/wasm/qwasmscreen.h index a19818af2ff..6ddd4c736d0 100644 --- a/src/plugins/platforms/wasm/qwasmscreen.h +++ b/src/plugins/platforms/wasm/qwasmscreen.h @@ -22,7 +22,6 @@ class QPlatformOpenGLContext; class QWasmWindow; class QWasmBackingStore; class QWasmCompositor; -class QWasmDeadKeySupport; class QOpenGLContext; class QWasmScreen : public QObject, public QPlatformScreen, public QWasmWindowTreeNode<> @@ -41,7 +40,6 @@ public: QPointingDevice *tabletDevice() { return m_tabletDevice.get(); } QWasmCompositor *compositor(); - QWasmDeadKeySupport *deadKeySupport() { return m_deadKeySupport.get(); } QList<QWasmWindow *> allWindows() const; @@ -83,7 +81,6 @@ private: std::unique_ptr<QWasmCompositor> m_compositor; std::unique_ptr<QPointingDevice> m_touchDevice; std::unique_ptr<QPointingDevice> m_tabletDevice; - std::unique_ptr<QWasmDeadKeySupport> m_deadKeySupport; QRect m_geometry = QRect(0, 0, 100, 100); int m_depth = 32; QImage::Format m_format = QImage::Format_RGB32; diff --git a/src/plugins/platforms/wasm/qwasmwindow.cpp b/src/plugins/platforms/wasm/qwasmwindow.cpp index d318c977a90..6e8bd46ca58 100644 --- a/src/plugins/platforms/wasm/qwasmwindow.cpp +++ b/src/plugins/platforms/wasm/qwasmwindow.cpp @@ -40,13 +40,12 @@ QT_BEGIN_NAMESPACE Q_GUI_EXPORT int qt_defaultDpiX(); -QWasmWindow::QWasmWindow(QWindow *w, QWasmDeadKeySupport *deadKeySupport, +QWasmWindow::QWasmWindow(QWindow *w, QWasmCompositor *compositor, QWasmBackingStore *backingStore, WId nativeHandle) : QPlatformWindow(w), m_compositor(compositor), m_backingStore(backingStore), - m_deadKeySupport(deadKeySupport), m_document(dom::document()), m_decoratedWindow(m_document.call<emscripten::val>("createElement", emscripten::val("div"))), m_window(m_document.call<emscripten::val>("createElement", emscripten::val("div"))), @@ -204,6 +203,12 @@ void QWasmWindow::registerEventHandlers() QWasmDrag::instance()->onNativeDragFinished(&dragEvent); } ); + m_dragEnterCallback = QWasmEventHandler(m_window, "dragenter", + [this](emscripten::val event) { + DragEvent dragEvent(EventType::DragEnter, event, window()); + QWasmDrag::instance()->onNativeDragEnter(&dragEvent); + } + ); m_dragLeaveCallback = QWasmEventHandler(m_window, "dragleave", [this](emscripten::val event) { DragEvent dragEvent(EventType::DragLeave, event, window()); @@ -216,9 +221,9 @@ void QWasmWindow::registerEventHandlers() [this](emscripten::val event) { this->handleWheelEvent(event); }); m_keyDownCallback = QWasmEventHandler(m_window, "keydown", - [this](emscripten::val event) { this->handleKeyEvent(KeyEvent(EventType::KeyDown, event, m_deadKeySupport)); }); + [this](emscripten::val event) { this->handleKeyEvent(KeyEvent(EventType::KeyDown, event)); }); m_keyUpCallback =QWasmEventHandler(m_window, "keyup", - [this](emscripten::val event) {this->handleKeyEvent(KeyEvent(EventType::KeyUp, event, m_deadKeySupport)); }); + [this](emscripten::val event) {this->handleKeyEvent(KeyEvent(EventType::KeyUp, event)); }); m_inputCallback = QWasmEventHandler(m_window, "input", [this](emscripten::val event){ handleInputEvent(event); }); diff --git a/src/plugins/platforms/wasm/qwasmwindow.h b/src/plugins/platforms/wasm/qwasmwindow.h index 8e6e5021dcf..ca5c9132ca0 100644 --- a/src/plugins/platforms/wasm/qwasmwindow.h +++ b/src/plugins/platforms/wasm/qwasmwindow.h @@ -31,7 +31,6 @@ class EventCallback; struct KeyEvent; struct PointerEvent; -class QWasmDeadKeySupport; struct WheelEvent; Q_DECLARE_LOGGING_CATEGORY(qLcQpaWasmInputContext) @@ -41,7 +40,7 @@ class QWasmWindow final : public QPlatformWindow, public QNativeInterface::Private::QWasmWindow { public: - QWasmWindow(QWindow *w, QWasmDeadKeySupport *deadKeySupport, QWasmCompositor *compositor, + QWasmWindow(QWindow *w, QWasmCompositor *compositor, QWasmBackingStore *backingStore, WId nativeHandle); ~QWasmWindow() final; @@ -159,7 +158,6 @@ private: QWasmCompositor *m_compositor = nullptr; QWasmBackingStore *m_backingStore = nullptr; - QWasmDeadKeySupport *m_deadKeySupport; QRect m_normalGeometry {0, 0, 0 ,0}; emscripten::val m_document; @@ -197,6 +195,7 @@ private: QWasmEventHandler m_dragStartCallback; QWasmEventHandler m_dragEndCallback; QWasmEventHandler m_dropCallback; + QWasmEventHandler m_dragEnterCallback; QWasmEventHandler m_dragLeaveCallback; QWasmEventHandler m_wheelEventCallback; |
