aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/cru/platform/native/native_window.hpp6
-rw-r--r--include/cru/win/native/native_window.hpp2
-rw-r--r--src/win/native/native_window.cpp49
3 files changed, 56 insertions, 1 deletions
diff --git a/include/cru/platform/native/native_window.hpp b/include/cru/platform/native/native_window.hpp
index d4e608b4..8a067a4c 100644
--- a/include/cru/platform/native/native_window.hpp
+++ b/include/cru/platform/native/native_window.hpp
@@ -1,9 +1,11 @@
#pragma once
#include "../native_resource.hpp"
+#include "cru/common/event.hpp"
+
#include "../graphic_base.hpp"
#include "basic_types.hpp"
-#include "cru/common/event.hpp"
+#include "cursor.hpp"
#include "native_event.hpp"
namespace cru::platform::graph {
@@ -62,6 +64,8 @@ class NativeWindow : public NativeResource {
virtual bool CaptureMouse() = 0;
virtual bool ReleaseMouse() = 0;
+ virtual void SetCursor(std::shared_ptr<Cursor> cursor) = 0;
+
virtual void Repaint() = 0;
virtual graph::Painter* BeginPaint() = 0;
diff --git a/include/cru/win/native/native_window.hpp b/include/cru/win/native/native_window.hpp
index ccbdff40..cba5cc3e 100644
--- a/include/cru/win/native/native_window.hpp
+++ b/include/cru/win/native/native_window.hpp
@@ -56,6 +56,8 @@ class WinNativeWindow : public NativeWindow {
void Repaint() override;
graph::Painter* BeginPaint() override;
+ void SetCursor(std::shared_ptr<Cursor> cursor) override;
+
IEvent<std::nullptr_t>* DestroyEvent() override { return &destroy_event_; }
IEvent<std::nullptr_t>* PaintEvent() override { return &paint_event_; }
IEvent<Size>* ResizeEvent() override { return &resize_event_; }
diff --git a/src/win/native/native_window.cpp b/src/win/native/native_window.cpp
index f301f955..bda84ea9 100644
--- a/src/win/native/native_window.cpp
+++ b/src/win/native/native_window.cpp
@@ -1,6 +1,9 @@
#include "cru/win/native/native_window.hpp"
+#include "cru/common/format.hpp"
+#include "cru/platform/debug.hpp"
#include "cru/win/graph/direct/graph_factory.hpp"
+#include "cru/win/native/cursor.hpp"
#include "cru/win/native/exception.hpp"
#include "cru/win/native/ui_application.hpp"
#include "cru/win/native/window_class.hpp"
@@ -160,6 +163,52 @@ graph::Painter* WinNativeWindow::BeginPaint() {
return new WindowD2DPainter(this);
}
+void WinNativeWindow::SetCursor(std::shared_ptr<Cursor> cursor) {
+ if (!IsValid()) return;
+ assert(cursor);
+ WinCursor* c = static_cast<WinCursor*>(cursor.get());
+
+ auto outputError = [] {
+ DebugMessage(util::Format(util::Format(
+ L"Failed to set cursor. Last error code: {}.", ::GetLastError())));
+ };
+
+ if (!::SetWindowLongPtrW(hwnd_, GCLP_HCURSOR,
+ reinterpret_cast<LONG_PTR>(c->GetHandle()))) {
+ outputError();
+ return;
+ }
+
+ ::POINT point;
+ if (!::GetCursorPos(&point)) {
+ outputError();
+ return;
+ }
+
+ ::RECT rect;
+ if (!::GetClientRect(hwnd_, &rect)) {
+ outputError();
+ return;
+ }
+
+ ::POINT lefttop{rect.left, rect.top};
+ ::POINT rightbottom{rect.right, rect.bottom};
+ if (!::ClientToScreen(hwnd_, &lefttop)) {
+ outputError();
+ return;
+ }
+
+ if (!::ClientToScreen(hwnd_, &rightbottom)) {
+ outputError();
+ return;
+ }
+
+ if (point.x >= lefttop.x && point.y >= lefttop.y &&
+ point.x <= rightbottom.x && point.y <= rightbottom.y) {
+ ::SetCursor(c->GetHandle());
+ }
+}
+
bool WinNativeWindow::HandleNativeWindowMessage(HWND hwnd, UINT msg,
WPARAM w_param, LPARAM l_param,
LRESULT* result) {