From 2b74e3cd775231f96942c405f5560f86ff286f2b Mon Sep 17 00:00:00 2001 From: swittk Date: Mon, 22 Jun 2020 14:24:20 +0700 Subject: [PATCH] Added Support for QWheelEvent (#609) * Added QWheelEvent * removed x y Co-authored-by: Switt Kongdachalert --- CMakeLists.txt | 1 + .../QEvent/QWheelEvent/qwheelevent_wrap.h | 31 +++++ .../QEvent/QWheelEvent/qwheelevent_wrap.cpp | 116 ++++++++++++++++++ src/cpp/main.cpp | 2 + src/index.ts | 1 + src/lib/QtGui/QEvent/QWheelEvent.ts | 85 +++++++++++++ website/docs/api/generated/globals.md | 1 + website/sidebars.js | 1 + 8 files changed, 238 insertions(+) create mode 100644 src/cpp/include/nodegui/QtGui/QEvent/QWheelEvent/qwheelevent_wrap.h create mode 100644 src/cpp/lib/QtGui/QEvent/QWheelEvent/qwheelevent_wrap.cpp create mode 100644 src/lib/QtGui/QEvent/QWheelEvent.ts diff --git a/CMakeLists.txt b/CMakeLists.txt index 15f762716..9319f8c7b 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -45,6 +45,7 @@ add_library(${CORE_WIDGETS_ADDON} SHARED "${PROJECT_SOURCE_DIR}/src/cpp/lib/QtGui/QClipboard/qclipboard_wrap.cpp" "${PROJECT_SOURCE_DIR}/src/cpp/lib/QtGui/QEvent/QKeyEvent/qkeyevent_wrap.cpp" "${PROJECT_SOURCE_DIR}/src/cpp/lib/QtGui/QEvent/QMouseEvent/qmouseevent_wrap.cpp" + "${PROJECT_SOURCE_DIR}/src/cpp/lib/QtGui/QEvent/QWheelEvent/qwheelevent_wrap.cpp" "${PROJECT_SOURCE_DIR}/src/cpp/lib/QtGui/QFontDatabase/qfontdatabase_wrap.cpp" "${PROJECT_SOURCE_DIR}/src/cpp/lib/QtGui/QPicture/qpicture_wrap.cpp" "${PROJECT_SOURCE_DIR}/src/cpp/lib/QtGui/QPixmap/qpixmap_wrap.cpp" diff --git a/src/cpp/include/nodegui/QtGui/QEvent/QWheelEvent/qwheelevent_wrap.h b/src/cpp/include/nodegui/QtGui/QEvent/QWheelEvent/qwheelevent_wrap.h new file mode 100644 index 000000000..3b8a9a95d --- /dev/null +++ b/src/cpp/include/nodegui/QtGui/QEvent/QWheelEvent/qwheelevent_wrap.h @@ -0,0 +1,31 @@ +#pragma once + +#include + +#include + +#include "Extras/Export/export.h" +#include "core/Component/component_macro.h" + +class DLL_EXPORT QWheelEventWrap : public Napi::ObjectWrap { + COMPONENT_WRAPPED_METHODS_DECLARATION + + private: + QWheelEvent* instance; + + public: + static Napi::Object init(Napi::Env env, Napi::Object exports); + QWheelEventWrap(const Napi::CallbackInfo& info); + ~QWheelEventWrap(); + QWheelEvent* getInternalInstance(); + // class constructor + static Napi::FunctionReference constructor; + // wrapped methods + Napi::Value angleDelta(const Napi::CallbackInfo& info); + Napi::Value buttons(const Napi::CallbackInfo& info); + Napi::Value globalPosition(const Napi::CallbackInfo& info); + Napi::Value inverted(const Napi::CallbackInfo& info); + Napi::Value phase(const Napi::CallbackInfo& info); + Napi::Value pixelDelta(const Napi::CallbackInfo& info); + Napi::Value position(const Napi::CallbackInfo& info); +}; \ No newline at end of file diff --git a/src/cpp/lib/QtGui/QEvent/QWheelEvent/qwheelevent_wrap.cpp b/src/cpp/lib/QtGui/QEvent/QWheelEvent/qwheelevent_wrap.cpp new file mode 100644 index 000000000..66df0ee41 --- /dev/null +++ b/src/cpp/lib/QtGui/QEvent/QWheelEvent/qwheelevent_wrap.cpp @@ -0,0 +1,116 @@ +#include "QtGui/QEvent/QWheelEvent/qwheelevent_wrap.h" + +#include +#include +#include + +#include "Extras/Utils/nutils.h" + +Napi::FunctionReference QWheelEventWrap::constructor; + +Napi::Object QWheelEventWrap::init(Napi::Env env, Napi::Object exports) { + Napi::HandleScope scope(env); + char CLASSNAME[] = "QWheelEvent"; + Napi::Function func = DefineClass( + env, CLASSNAME, + {InstanceMethod("angleDelta", &QWheelEventWrap::angleDelta), + InstanceMethod("buttons", &QWheelEventWrap::buttons), + InstanceMethod("globalPosition", &QWheelEventWrap::globalPosition), + InstanceMethod("inverted", &QWheelEventWrap::inverted), + InstanceMethod("phase", &QWheelEventWrap::phase), + InstanceMethod("pixelDelta", &QWheelEventWrap::pixelDelta), + InstanceMethod("position", &QWheelEventWrap::position), + + COMPONENT_WRAPPED_METHODS_EXPORT_DEFINE(QWheelEventWrap)}); + constructor = Napi::Persistent(func); + exports.Set(CLASSNAME, func); + return exports; +} + +QWheelEvent* QWheelEventWrap::getInternalInstance() { return this->instance; } + +QWheelEventWrap::QWheelEventWrap(const Napi::CallbackInfo& info) + : Napi::ObjectWrap(info) { + Napi::Env env = info.Env(); + Napi::HandleScope scope(env); + if (info.Length() == 1) { + Napi::External eventObject = + info[0].As>(); + this->instance = static_cast(eventObject.Data()); + } else { + Napi::TypeError::New(env, "Wrong number of arguments") + .ThrowAsJavaScriptException(); + } + this->rawData = extrautils::configureComponent(this->getInternalInstance()); +} + +QWheelEventWrap::~QWheelEventWrap() { + // Do not destroy instance here. It will be done by Qt Event loop. +} + +Napi::Value QWheelEventWrap::angleDelta(const Napi::CallbackInfo& info) { + // Uses QPoint, not QPointF + Napi::Env env = info.Env(); + QPoint point = static_cast(this->instance->angleDelta()); + int x = static_cast(point.x()); + int y = static_cast(point.y()); + Napi::Object obj = Napi::Object::New(env); + obj.Set("x", Napi::Number::From(env, x)); + obj.Set("y", Napi::Number::From(env, y)); + return obj; +} + +Napi::Value QWheelEventWrap::buttons(const Napi::CallbackInfo& info) { + Napi::Env env = info.Env(); + int b = static_cast(this->instance->buttons()); + return Napi::Number::From(env, b); +} + +Napi::Value QWheelEventWrap::globalPosition(const Napi::CallbackInfo& info) { + // Uses QPointF, not QPoint + // qreal is typedef double unless configued with -qreal float option + Napi::Env env = info.Env(); + QPointF point = static_cast(this->instance->globalPosition()); + qreal x = static_cast(point.x()); + qreal y = static_cast(point.y()); + Napi::Object obj = Napi::Object::New(env); + obj.Set("x", Napi::Number::From(env, x)); + obj.Set("y", Napi::Number::From(env, y)); + return obj; +} + +Napi::Value QWheelEventWrap::inverted(const Napi::CallbackInfo& info) { + Napi::Env env = info.Env(); + bool b = static_cast(this->instance->inverted()); + return Napi::Boolean::From(env, b); +} + +Napi::Value QWheelEventWrap::phase(const Napi::CallbackInfo& info) { + Napi::Env env = info.Env(); + int p = static_cast(this->instance->phase()); + return Napi::Number::From(env, p); +} + +Napi::Value QWheelEventWrap::pixelDelta(const Napi::CallbackInfo& info) { + // Uses QPoint + Napi::Env env = info.Env(); + QPoint point = static_cast(this->instance->pixelDelta()); + int x = static_cast(point.x()); + int y = static_cast(point.y()); + Napi::Object obj = Napi::Object::New(env); + obj.Set("x", Napi::Number::From(env, x)); + obj.Set("y", Napi::Number::From(env, y)); + return obj; +} + +Napi::Value QWheelEventWrap::position(const Napi::CallbackInfo& info) { + // Uses QPointF + Napi::Env env = info.Env(); + QPointF point = static_cast(this->instance->position()); + qreal x = static_cast(point.x()); + qreal y = static_cast(point.y()); + Napi::Object obj = Napi::Object::New(env); + obj.Set("x", Napi::Number::From(env, x)); + obj.Set("y", Napi::Number::From(env, y)); + return obj; +} \ No newline at end of file diff --git a/src/cpp/main.cpp b/src/cpp/main.cpp index 14160cbaf..c11d0f463 100644 --- a/src/cpp/main.cpp +++ b/src/cpp/main.cpp @@ -19,6 +19,7 @@ #include "QtGui/QCursor/qcursor_wrap.h" #include "QtGui/QEvent/QKeyEvent/qkeyevent_wrap.h" #include "QtGui/QEvent/QMouseEvent/qmouseevent_wrap.h" +#include "QtGui/QEvent/QWheelEvent/qwheelevent_wrap.h" #include "QtGui/QFont/qfont_wrap.h" #include "QtGui/QFontDatabase/qfontdatabase_wrap.h" #include "QtGui/QIcon/qicon_wrap.h" @@ -166,6 +167,7 @@ Napi::Object Main(Napi::Env env, Napi::Object exports) { QLineEditWrap::init(env, exports); QKeyEventWrap::init(env, exports); QMouseEventWrap::init(env, exports); + QWheelEventWrap::init(env, exports); QPlainTextEditWrap::init(env, exports); QDialWrap::init(env, exports); QLabelWrap::init(env, exports); diff --git a/src/index.ts b/src/index.ts index 28609b930..a0dd51c5c 100644 --- a/src/index.ts +++ b/src/index.ts @@ -20,6 +20,7 @@ export { QFontDatabase, SystemFont, WritingSystem } from './lib/QtGui/QFontDatab // Events: Maybe a separate module ? export { QKeyEvent } from './lib/QtGui/QEvent/QKeyEvent'; export { QMouseEvent } from './lib/QtGui/QEvent/QMouseEvent'; +export { QWheelEvent } from './lib/QtGui/QEvent/QWheelEvent'; export { WidgetEventTypes } from './lib/core/EventWidget'; // Abstract: export { NodeWidget, QWidget, QWidgetSignals } from './lib/QtWidgets/QWidget'; diff --git a/src/lib/QtGui/QEvent/QWheelEvent.ts b/src/lib/QtGui/QEvent/QWheelEvent.ts new file mode 100644 index 000000000..8bc710e0b --- /dev/null +++ b/src/lib/QtGui/QEvent/QWheelEvent.ts @@ -0,0 +1,85 @@ +import addon from '../../utils/addon'; +import { NativeElement } from '../../core/Component'; + +export class QWheelEvent { + native: NativeElement; + constructor(event: NativeElement) { + this.native = new addon.QWheelEvent(event); + } + /** + * Returns the relative amount that the wheel was rotated, in eighths of a degree. + * A positive value indicates that the wheel was rotated forwards away from the user; + * a negative value indicates that the wheel was rotated backwards toward the user. + * + * angleDelta().y() provides the angle through which the common vertical mouse wheel was + * rotated since the previous event. + * angleDelta().x() provides the angle through which the horizontal mouse wheel was + * rotated, if the mouse has a horizontal wheel; otherwise it stays at zero. + * + * Some mice allow the user to tilt the wheel to perform horizontal scrolling, + * and some touchpads support a horizontal scrolling gesture; + * that will also appear in angleDelta().x(). + * + * Most mouse types work in steps of 15 degrees, + * in which case the delta value is a multiple of 120; i.e., + * 120 units * 1/8 = 15 degrees. + * + * However, some mice have finer-resolution wheels and + * send delta values that are less than 120 units (less than 15 degrees). + * To support this possibility, you can either cumulatively add the delta + * values from events until the value of 120 is reached, + * then scroll the widget, or you can partially scroll the widget in + * response to each wheel event. + * + * But to provide a more native feel, you should prefer pixelDelta() + * on platforms where it's available. + */ + angleDelta(): { x: number; y: number } { + return this.native.angleDelta(); + } + buttons(): number { + return this.native.buttons(); + } + /** + * Returns the global position of the mouse pointer at the time of + * the event. This is important on asynchronous window systems such + * as X11; whenever you move your widgets around in response to mouse + * events, globalPosition() can differ a lot from the current cursor + * position returned by QCursor::pos(). + */ + globalPosition(): { x: number; y: number } { + return this.native.globalPosition(); + } + /**Returns whether the delta values delivered with the event are inverted*/ + inverted(): boolean { + return this.native.inverted(); + } + /* + * Returns the scrolling phase of this wheel event + * Note: The Qt::ScrollBegin and Qt::ScrollEnd phases are currently supported only on macOS + */ + phase(): number { + return this.native.phase(); + } + + /** + * Returns the scrolling distance in pixels on screen. + * This value is provided on platforms that support + * high-resolution pixel-based delta values, such as macOS. + * The value should be used directly to scroll content on screen + * + * Note:On X11 this value is driver specific and unreliable, use angleDelta() instead + */ + pixelDelta(): { x: number; y: number } { + return this.native.pixelDelta(); + } + + /** + * Returns the position of the mouse cursor relative to the widget that received the event. + * If you move your widgets around in response to mouse events, use globalPosition() instead of this function. + * This function was introduced in Qt 5.14 + */ + position(): { x: number; y: number } { + return this.native.position(); + } +} diff --git a/website/docs/api/generated/globals.md b/website/docs/api/generated/globals.md index 9857c4a52..a414ea8df 100644 --- a/website/docs/api/generated/globals.md +++ b/website/docs/api/generated/globals.md @@ -226,6 +226,7 @@ sidebar_label: "Globals" * [QMessageBox](classes/qmessagebox.md) * [QModelIndex](classes/qmodelindex.md) * [QMouseEvent](classes/qmouseevent.md) +* [QWheelEvent](classes/qwheelevent.md) * [QMovie](classes/qmovie.md) * [QObject](classes/qobject.md) * [QPainter](classes/qpainter.md) diff --git a/website/sidebars.js b/website/sidebars.js index 411605a7b..fe297c392 100644 --- a/website/sidebars.js +++ b/website/sidebars.js @@ -65,6 +65,7 @@ module.exports = { 'api/generated/classes/qmessagebox', 'api/generated/classes/qmodelindex', 'api/generated/classes/qmouseevent', + 'api/generated/classes/qwheelevent', 'api/generated/classes/qmovie', 'api/generated/classes/qobject', 'api/generated/classes/qpainter',