aboutsummaryrefslogtreecommitdiff
path: root/src/win
diff options
context:
space:
mode:
authorcrupest <crupest@outlook.com>2022-01-12 21:35:08 +0800
committercrupest <crupest@outlook.com>2022-01-12 21:35:08 +0800
commit7a42d92c10a4bc686244668dd0e3f903f30f2fae (patch)
treee48fc4a47afa5eadbdf54cec6d2b73110f500680 /src/win
parent882d843083895f4905571dc273e801ee18fd5984 (diff)
downloadcru-7a42d92c10a4bc686244668dd0e3f903f30f2fae.tar.gz
cru-7a42d92c10a4bc686244668dd0e3f903f30f2fae.tar.bz2
cru-7a42d92c10a4bc686244668dd0e3f903f30f2fae.zip
...
Diffstat (limited to 'src/win')
-rw-r--r--src/win/DebugLogger.hpp5
-rw-r--r--src/win/Exception.cpp9
-rw-r--r--src/win/StdOutLogger.hpp5
-rw-r--r--src/win/graphics/direct/Painter.cpp40
-rw-r--r--src/win/graphics/direct/TextLayout.cpp39
-rw-r--r--src/win/gui/InputMethod.cpp14
-rw-r--r--src/win/gui/UiApplication.cpp22
-rw-r--r--src/win/gui/Window.cpp209
-rw-r--r--src/win/gui/WindowManager.cpp3
9 files changed, 240 insertions, 106 deletions
diff --git a/src/win/DebugLogger.hpp b/src/win/DebugLogger.hpp
index 598ee9e8..5e78af22 100644
--- a/src/win/DebugLogger.hpp
+++ b/src/win/DebugLogger.hpp
@@ -13,10 +13,11 @@ class WinDebugLoggerSource : public ::cru::log::ILogSource {
~WinDebugLoggerSource() = default;
- void Write(::cru::log::LogLevel level, const std::u16string& s) override {
+ void Write(::cru::log::LogLevel level, StringView s) override {
CRU_UNUSED(level)
- ::OutputDebugStringW(reinterpret_cast<const wchar_t*>(s.c_str()));
+ String m = s.ToString();
+ ::OutputDebugStringW(reinterpret_cast<const wchar_t*>(m.c_str()));
}
};
} // namespace cru::platform::win
diff --git a/src/win/Exception.cpp b/src/win/Exception.cpp
index a7b0927a..cf55c191 100644
--- a/src/win/Exception.cpp
+++ b/src/win/Exception.cpp
@@ -7,10 +7,9 @@ namespace cru::platform::win {
inline String HResultMakeMessage(HRESULT h_result,
std::optional<String> message) {
if (message.has_value())
- return fmt::format(FMT_STRING(L"HRESULT: {:#08x}. Message: {}"), h_result,
- message->WinCStr());
+ return Format(L"HRESULT: {}. Message: {}", h_result, message->WinCStr());
else
- return fmt::format(FMT_STRING(L"HRESULT: {:#08x}."), h_result);
+ return Format(L"HRESULT: {}.", h_result);
}
HResultError::HResultError(HRESULT h_result)
@@ -25,8 +24,8 @@ HResultError::HResultError(HRESULT h_result,
h_result_(h_result) {}
inline String Win32MakeMessage(DWORD error_code, String message) {
- return fmt::format(L"Last error code: {:#04x}.\nMessage: {}\n", error_code,
- message.WinCStr());
+ return Format(L"Last error code: {}.\nMessage: {}\n", error_code,
+ message.WinCStr());
}
Win32Error::Win32Error(std::string_view message)
diff --git a/src/win/StdOutLogger.hpp b/src/win/StdOutLogger.hpp
index bff8b30e..b3a22dd5 100644
--- a/src/win/StdOutLogger.hpp
+++ b/src/win/StdOutLogger.hpp
@@ -15,10 +15,11 @@ class WinStdOutLoggerSource : public ::cru::log::ILogSource {
~WinStdOutLoggerSource() = default;
- void Write(::cru::log::LogLevel level, const std::u16string& s) override {
+ void Write(::cru::log::LogLevel level, StringView s) override {
CRU_UNUSED(level)
- std::fputws(reinterpret_cast<const wchar_t*>(s.c_str()), stdout);
+ String m = s.ToString();
+ std::fputws(reinterpret_cast<const wchar_t*>(m.c_str()), stdout);
}
};
} // namespace cru::platform::win
diff --git a/src/win/graphics/direct/Painter.cpp b/src/win/graphics/direct/Painter.cpp
index 26ef92ec..5db60fd1 100644
--- a/src/win/graphics/direct/Painter.cpp
+++ b/src/win/graphics/direct/Painter.cpp
@@ -27,6 +27,10 @@ void D2DPainter::SetTransform(const platform::Matrix& matrix) {
render_target_->SetTransform(Convert(matrix));
}
+void D2DPainter::ConcatTransform(const Matrix& matrix) {
+ SetTransform(GetTransform() * matrix);
+}
+
void D2DPainter::Clear(const Color& color) {
CheckValidation();
render_target_->Clear(Convert(color));
@@ -54,6 +58,24 @@ void D2DPainter::FillRectangle(const Rect& rectangle, IBrush* brush) {
render_target_->FillRectangle(Convert(rectangle), b->GetD2DBrushInterface());
}
+void D2DPainter::StrokeEllipse(const Rect& outline_rect, IBrush* brush,
+ float width) {
+ CheckValidation();
+ const auto b = CheckPlatform<ID2DBrush>(brush, GetPlatformId());
+ render_target_->DrawEllipse(
+ D2D1::Ellipse(Convert(outline_rect.GetCenter()),
+ outline_rect.width / 2.0f, outline_rect.height / 2.0f),
+ b->GetD2DBrushInterface(), width);
+}
+void D2DPainter::FillEllipse(const Rect& outline_rect, IBrush* brush) {
+ CheckValidation();
+ const auto b = CheckPlatform<ID2DBrush>(brush, GetPlatformId());
+ render_target_->FillEllipse(
+ D2D1::Ellipse(Convert(outline_rect.GetCenter()),
+ outline_rect.width / 2.0f, outline_rect.height / 2.0f),
+ b->GetD2DBrushInterface());
+}
+
void D2DPainter::StrokeGeometry(IGeometry* geometry, IBrush* brush,
float width) {
CheckValidation();
@@ -96,6 +118,24 @@ void D2DPainter::PopLayer() {
layers_.pop_back();
}
+void D2DPainter::PushState() {
+ Microsoft::WRL::ComPtr<ID2D1Factory> factory = nullptr;
+ render_target_->GetFactory(&factory);
+
+ Microsoft::WRL::ComPtr<ID2D1DrawingStateBlock> state_block;
+ factory->CreateDrawingStateBlock(&state_block);
+ render_target_->SaveDrawingState(state_block.Get());
+
+ drawing_state_stack_.push_back(std::move(state_block));
+}
+
+void D2DPainter::PopState() {
+ Expects(!drawing_state_stack_.empty());
+ auto drawing_state = drawing_state_stack_.back();
+ drawing_state_stack_.pop_back();
+ render_target_->RestoreDrawingState(drawing_state.Get());
+}
+
void D2DPainter::EndDraw() {
if (is_drawing_) {
is_drawing_ = false;
diff --git a/src/win/graphics/direct/TextLayout.cpp b/src/win/graphics/direct/TextLayout.cpp
index 6ece8ed1..bec4a972 100644
--- a/src/win/graphics/direct/TextLayout.cpp
+++ b/src/win/graphics/direct/TextLayout.cpp
@@ -1,4 +1,5 @@
#include "cru/win/graphics/direct/TextLayout.hpp"
+#include <dwrite.h>
#include "cru/common/Logger.hpp"
#include "cru/platform/Check.hpp"
@@ -55,6 +56,44 @@ void DWriteTextLayout::SetMaxHeight(float max_height) {
ThrowIfFailed(text_layout_->SetMaxHeight(max_height_));
}
+bool DWriteTextLayout::IsEditMode() { return edit_mode_; }
+
+void DWriteTextLayout::SetEditMode(bool enable) {
+ edit_mode_ = enable;
+ // TODO: Implement this.
+}
+
+Index DWriteTextLayout::GetLineIndexFromCharIndex(Index char_index) {
+ if (char_index < 0 || char_index >= text_.size()) {
+ return -1;
+ }
+
+ auto line_index = 0;
+ for (Index i = 0; i < char_index; ++i) {
+ if (text_[i] == u'\n') {
+ line_index++;
+ }
+ }
+
+ return line_index;
+}
+
+float DWriteTextLayout::GetLineHeight(Index line_index) {
+ Index count = GetLineCount();
+ std::vector<DWRITE_LINE_METRICS> line_metrics(count);
+
+ UINT32 actual_line_count = 0;
+ text_layout_->GetLineMetrics(line_metrics.data(), static_cast<UINT32>(count),
+ &actual_line_count);
+ return line_metrics[line_index].height;
+}
+
+Index DWriteTextLayout::GetLineCount() {
+ UINT32 line_count = 0;
+ text_layout_->GetLineMetrics(nullptr, 0, &line_count);
+ return line_count;
+}
+
Rect DWriteTextLayout::GetTextBounds(bool includingTrailingSpace) {
DWRITE_TEXT_METRICS metrics;
ThrowIfFailed(text_layout_->GetMetrics(&metrics));
diff --git a/src/win/gui/InputMethod.cpp b/src/win/gui/InputMethod.cpp
index cc237e88..47e17109 100644
--- a/src/win/gui/InputMethod.cpp
+++ b/src/win/gui/InputMethod.cpp
@@ -104,19 +104,19 @@ CompositionClauses GetCompositionClauses(HIMC imm_context, int target_start,
return result;
}
-std::u16string GetString(HIMC imm_context) {
+String GetString(HIMC imm_context) {
LONG string_size =
::ImmGetCompositionString(imm_context, GCS_COMPSTR, NULL, 0);
- std::u16string result((string_size / sizeof(char16_t)), 0);
+ String result((string_size / sizeof(char16_t)), 0);
::ImmGetCompositionString(imm_context, GCS_COMPSTR, result.data(),
string_size);
return result;
}
-std::u16string GetResultString(HIMC imm_context) {
+String GetResultString(HIMC imm_context) {
LONG string_size =
::ImmGetCompositionString(imm_context, GCS_RESULTSTR, NULL, 0);
- std::u16string result((string_size / sizeof(char16_t)), 0);
+ String result((string_size / sizeof(char16_t)), 0);
::ImmGetCompositionString(imm_context, GCS_RESULTSTR, result.data(),
string_size);
return result;
@@ -217,9 +217,7 @@ IEvent<std::nullptr_t>* WinInputMethodContext::CompositionEvent() {
return &composition_event_;
}
-IEvent<std::u16string_view>* WinInputMethodContext::TextEvent() {
- return &text_event_;
-}
+IEvent<StringView>* WinInputMethodContext::TextEvent() { return &text_event_; }
void WinInputMethodContext::OnWindowNativeMessage(
WindowNativeMessageEventArgs& args) {
@@ -275,7 +273,7 @@ void WinInputMethodContext::OnWindowNativeMessage(
}
}
-std::u16string WinInputMethodContext::GetResultString() {
+String WinInputMethodContext::GetResultString() {
auto himc = GetHIMC();
auto result = win::GetResultString(himc.Get());
return result;
diff --git a/src/win/gui/UiApplication.cpp b/src/win/gui/UiApplication.cpp
index 12480417..cb0f0a4c 100644
--- a/src/win/gui/UiApplication.cpp
+++ b/src/win/gui/UiApplication.cpp
@@ -99,24 +99,22 @@ std::vector<INativeWindow*> WinUiApplication::GetAllWindow() {
return result;
}
-INativeWindow* WinUiApplication::CreateWindow(INativeWindow* parent,
- CreateWindowFlag flag) {
- WinNativeWindow* p = nullptr;
- if (parent != nullptr) {
- p = CheckPlatform<WinNativeWindow>(parent, GetPlatformId());
- }
- return new WinNativeWindow(this, window_manager_->GetGeneralWindowClass(),
- flag & CreateWindowFlags::NoCaptionAndBorder
- ? WS_POPUP
- : WS_OVERLAPPEDWINDOW,
- p);
+INativeWindow* WinUiApplication::CreateWindow() {
+ return new WinNativeWindow(this);
}
-cru::platform::graphics::IGraphicsFactory* WinUiApplication::GetGraphicsFactory() {
+cru::platform::graphics::IGraphicsFactory*
+WinUiApplication::GetGraphicsFactory() {
return graph_factory_.get();
}
ICursorManager* WinUiApplication::GetCursorManager() {
return cursor_manager_.get();
}
+
+IClipboard* WinUiApplication::GetClipboard() {
+ // TODO: Implement this.
+ return nullptr;
+}
+
} // namespace cru::platform::gui::win
diff --git a/src/win/gui/Window.cpp b/src/win/gui/Window.cpp
index 4c75a319..20f86aff 100644
--- a/src/win/gui/Window.cpp
+++ b/src/win/gui/Window.cpp
@@ -5,6 +5,7 @@
#include "cru/platform/Check.hpp"
#include "cru/platform/gui/Base.hpp"
#include "cru/platform/gui/DebugFlags.hpp"
+#include "cru/platform/gui/Window.hpp"
#include "cru/win/graphics/direct/WindowPainter.hpp"
#include "cru/win/gui/Cursor.hpp"
#include "cru/win/gui/Exception.hpp"
@@ -13,104 +14,129 @@
#include "cru/win/gui/UiApplication.hpp"
#include "cru/win/gui/WindowClass.hpp"
-#include <imm.h>
#include <windowsx.h>
-#include <memory>
namespace cru::platform::gui::win {
-WinNativeWindow::WinNativeWindow(WinUiApplication* application,
- WindowClass* window_class, DWORD window_style,
- WinNativeWindow* parent)
- : application_(application), parent_window_(parent) {
- Expects(application); // application can't be null.
-
- if (parent != nullptr) {
- throw new std::runtime_error("Can't use a invalid window as parent.");
- }
+namespace {
+inline int DipToPixel(const float dip, const float dpi) {
+ return static_cast<int>(dip * dpi / 96.0f);
+}
- const auto window_manager = application->GetWindowManager();
+inline float PixelToDip(const int pixel, const float dpi) {
+ return static_cast<float>(pixel) * 96.0f / dpi;
+}
- hwnd_ = CreateWindowExW(
- 0, window_class->GetName(), L"", window_style, CW_USEDEFAULT,
- CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT,
- parent == nullptr ? nullptr : parent->GetWindowHandle(), nullptr,
- application->GetInstanceHandle(), nullptr);
+DWORD CalcWindowStyle(WindowStyleFlag flag) {
+ return flag & WindowStyleFlags::NoCaptionAndBorder ? WS_POPUP
+ : WS_OVERLAPPEDWINDOW;
+}
- if (hwnd_ == nullptr)
- throw Win32Error(::GetLastError(), "Failed to create window.");
+Rect CalcWindowRectFromClient(const Rect& rect, WindowStyleFlag style_flag,
+ float dpi) {
+ RECT r;
+ r.left = DipToPixel(rect.left, dpi);
+ r.top = DipToPixel(rect.top, dpi);
+ r.right = DipToPixel(rect.GetRight(), dpi);
+ r.bottom = DipToPixel(rect.GetBottom(), dpi);
+ if (!AdjustWindowRectEx(&r, CalcWindowStyle(style_flag), FALSE, 0))
+ throw Win32Error(::GetLastError(), "Failed to invoke AdjustWindowRectEx.");
- auto dpi = ::GetDpiForWindow(hwnd_);
- if (dpi == 0)
- throw Win32Error(::GetLastError(), "Failed to get dpi of window.");
- dpi_ = static_cast<float>(dpi);
- log::Debug(u"Dpi of window is {}.", dpi_);
+ Rect result =
+ Rect::FromVertices(PixelToDip(r.left, dpi), PixelToDip(r.top, dpi),
+ PixelToDip(r.right, dpi), PixelToDip(r.bottom, dpi));
+ return result;
+}
- window_manager->RegisterWindow(hwnd_, this);
+} // namespace
- SetCursor(application->GetCursorManager()->GetSystemCursor(
- cru::platform::gui::SystemCursorType::Arrow));
+WinNativeWindow::WinNativeWindow(WinUiApplication* application)
+ : application_(application) {
+ Expects(application); // application can't be null.
+}
- window_render_target_ =
- std::make_unique<graphics::win::direct::D2DWindowRenderTarget>(
- application->GetDirectFactory(), hwnd_);
- window_render_target_->SetDpi(dpi_, dpi_);
+WinNativeWindow::~WinNativeWindow() { Close(); }
- input_method_context_ = std::make_unique<WinInputMethodContext>(this);
- input_method_context_->DisableIME();
+void WinNativeWindow::Close() {
+ if (hwnd_) ::DestroyWindow(hwnd_);
}
-WinNativeWindow::~WinNativeWindow() {
- if (!sync_flag_) {
- sync_flag_ = true;
- Close();
+void WinNativeWindow::SetStyleFlag(WindowStyleFlag flag) {
+ if (flag == style_flag_) return;
+
+ style_flag_ = flag;
+ if (hwnd_) {
+ SetWindowLongPtrW(hwnd_, GWL_STYLE,
+ static_cast<LONG_PTR>(CalcWindowStyle(style_flag_)));
}
}
-void WinNativeWindow::Close() { ::DestroyWindow(hwnd_); }
+void WinNativeWindow::SetVisibility(WindowVisibilityType visibility) {
+ if (visibility == visibility_) return;
+ visibility_ = visibility;
-bool WinNativeWindow::IsVisible() { return ::IsWindowVisible(hwnd_); }
+ if (!hwnd_) {
+ RecreateWindow();
+ }
-void WinNativeWindow::SetVisible(bool is_visible) {
- is_visible ? ShowWindow(hwnd_, SW_SHOWNORMAL) : ShowWindow(hwnd_, SW_HIDE);
-}
-Size WinNativeWindow::GetClientSize() {
- const auto pixel_rect = GetClientRectPixel();
- return Size(PixelToDip(pixel_rect.right), PixelToDip(pixel_rect.bottom));
+ if (visibility == WindowVisibilityType::Show) {
+ ShowWindow(hwnd_, SW_SHOWNORMAL);
+ } else if (visibility == WindowVisibilityType::Hide) {
+ ShowWindow(hwnd_, SW_HIDE);
+ } else if (visibility == WindowVisibilityType::Minimize) {
+ ShowWindow(hwnd_, SW_MINIMIZE);
+ }
}
+Size WinNativeWindow::GetClientSize() { return GetClientRect().GetSize(); }
+
void WinNativeWindow::SetClientSize(const Size& size) {
- const auto window_style =
- static_cast<DWORD>(GetWindowLongPtr(hwnd_, GWL_STYLE));
- const auto window_ex_style =
- static_cast<DWORD>(GetWindowLongPtr(hwnd_, GWL_EXSTYLE));
+ client_rect_.SetSize(size);
- RECT rect;
- rect.left = 0;
- rect.top = 0;
- rect.right = DipToPixel(size.width);
- rect.bottom = DipToPixel(size.height);
- if (!AdjustWindowRectEx(&rect, window_style, FALSE, window_ex_style))
- throw Win32Error(::GetLastError(), "Failed to invoke AdjustWindowRectEx.");
+ if (hwnd_) {
+ RECT rect =
+ DipToPixel(CalcWindowRectFromClient(client_rect_, style_flag_, dpi_));
- if (!SetWindowPos(hwnd_, nullptr, 0, 0, rect.right - rect.left,
- rect.bottom - rect.top, SWP_NOZORDER | SWP_NOMOVE))
- throw Win32Error(::GetLastError(), "Failed to invoke SetWindowPos.");
+ if (!SetWindowPos(hwnd_, nullptr, 0, 0, rect.right - rect.left,
+ rect.bottom - rect.top, SWP_NOZORDER | SWP_NOMOVE))
+ throw Win32Error(::GetLastError(), "Failed to invoke SetWindowPos.");
+ }
}
-Rect WinNativeWindow::GetWindowRect() {
- RECT rect;
- if (!::GetWindowRect(hwnd_, &rect))
- throw Win32Error(::GetLastError(), "Failed to invoke GetWindowRect.");
+Rect WinNativeWindow::GetClientRect() { return client_rect_; }
- return Rect::FromVertices(PixelToDip(rect.left), PixelToDip(rect.top),
- PixelToDip(rect.right), PixelToDip(rect.bottom));
+void WinNativeWindow::SetClientRect(const Rect& rect) {
+ client_rect_ = rect;
+
+ if (hwnd_) {
+ RECT rect =
+ DipToPixel(CalcWindowRectFromClient(client_rect_, style_flag_, dpi_));
+
+ if (!SetWindowPos(hwnd_, nullptr, 0, 0, rect.right - rect.left,
+ rect.bottom - rect.top, SWP_NOZORDER | SWP_NOMOVE))
+ throw Win32Error(::GetLastError(), "Failed to invoke SetWindowPos.");
+ }
+}
+
+Rect WinNativeWindow::GetWindowRect() {
+ if (hwnd_) {
+ RECT rect;
+ if (!::GetWindowRect(hwnd_, &rect))
+ throw Win32Error(::GetLastError(), "Failed to invoke GetWindowRect.");
+
+ return Rect::FromVertices(PixelToDip(rect.left), PixelToDip(rect.top),
+ PixelToDip(rect.right), PixelToDip(rect.bottom));
+ } else {
+ return {};
+ }
}
void WinNativeWindow::SetWindowRect(const Rect& rect) {
- if (!SetWindowPos(hwnd_, nullptr, DipToPixel(rect.left), DipToPixel(rect.top),
- DipToPixel(rect.GetRight()), DipToPixel(rect.GetBottom()),
- SWP_NOZORDER))
- throw Win32Error(::GetLastError(), "Failed to invoke SetWindowPos.");
+ if (hwnd_) {
+ if (!SetWindowPos(hwnd_, nullptr, DipToPixel(rect.left),
+ DipToPixel(rect.top), DipToPixel(rect.GetRight()),
+ DipToPixel(rect.GetBottom()), SWP_NOZORDER))
+ throw Win32Error(::GetLastError(), "Failed to invoke SetWindowPos.");
+ }
}
Point WinNativeWindow::GetMousePosition() {
@@ -154,6 +180,8 @@ void WinNativeWindow::SetCursor(std::shared_ptr<ICursor> cursor) {
cursor_ = CheckPlatform<WinCursor>(cursor, GetPlatformId());
+ if (hwnd_) return;
+
if (!::SetClassLongPtrW(hwnd_, GCLP_HCURSOR,
reinterpret_cast<LONG_PTR>(cursor_->GetHandle()))) {
log::TagWarn(log_tag,
@@ -163,7 +191,7 @@ void WinNativeWindow::SetCursor(std::shared_ptr<ICursor> cursor) {
return;
}
- if (!IsVisible()) return;
+ if (GetVisibility() != WindowVisibilityType::Show) return;
auto lg = [](const std::u16string_view& reason) {
log::TagWarn(
@@ -361,19 +389,48 @@ bool WinNativeWindow::HandleNativeWindowMessage(HWND hwnd, UINT msg,
RECT WinNativeWindow::GetClientRectPixel() {
RECT rect;
- if (!GetClientRect(hwnd_, &rect))
+ if (!::GetClientRect(hwnd_, &rect))
throw Win32Error(::GetLastError(), "Failed to invoke GetClientRect.");
return rect;
}
+void WinNativeWindow::RecreateWindow() {
+ const auto window_manager = application_->GetWindowManager();
+ auto window_class = window_manager->GetGeneralWindowClass();
+
+ hwnd_ = CreateWindowExW(
+ 0, window_class->GetName(), L"", CalcWindowStyle(style_flag_),
+ CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT, CW_USEDEFAULT,
+ parent_window_ == nullptr ? nullptr : parent_window_->GetWindowHandle(),
+ nullptr, application_->GetInstanceHandle(), nullptr);
+
+ if (hwnd_ == nullptr)
+ throw Win32Error(::GetLastError(), "Failed to create window.");
+
+ auto dpi = ::GetDpiForWindow(hwnd_);
+ if (dpi == 0)
+ throw Win32Error(::GetLastError(), "Failed to get dpi of window.");
+ dpi_ = static_cast<float>(dpi);
+ log::Debug(u"Dpi of window is {}.", dpi_);
+
+ window_manager->RegisterWindow(hwnd_, this);
+
+ SetCursor(application_->GetCursorManager()->GetSystemCursor(
+ cru::platform::gui::SystemCursorType::Arrow));
+
+ window_render_target_ =
+ std::make_unique<graphics::win::direct::D2DWindowRenderTarget>(
+ application_->GetDirectFactory(), hwnd_);
+ window_render_target_->SetDpi(dpi_, dpi_);
+
+ input_method_context_ = std::make_unique<WinInputMethodContext>(this);
+ input_method_context_->DisableIME();
+}
+
void WinNativeWindow::OnDestroyInternal() {
destroy_event_.Raise(nullptr);
application_->GetWindowManager()->UnregisterWindow(hwnd_);
hwnd_ = nullptr;
- if (!sync_flag_) {
- sync_flag_ = true;
- delete this;
- }
}
void WinNativeWindow::OnPaintInternal() {
@@ -399,7 +456,7 @@ void WinNativeWindow::OnSetFocusInternal() {
void WinNativeWindow::OnKillFocusInternal() {
has_focus_ = false;
- focus_event_.Raise(FocusChangeType::Lost);
+ focus_event_.Raise(FocusChangeType::Lose);
}
void WinNativeWindow::OnMouseMoveInternal(const POINT point) {
diff --git a/src/win/gui/WindowManager.cpp b/src/win/gui/WindowManager.cpp
index 4e84e967..31b868b9 100644
--- a/src/win/gui/WindowManager.cpp
+++ b/src/win/gui/WindowManager.cpp
@@ -37,7 +37,8 @@ void WindowManager::UnregisterWindow(HWND hwnd) {
const auto find_result = window_map_.find(hwnd);
Expects(find_result != window_map_.end()); // The hwnd is not in the map.
window_map_.erase(find_result);
- if (window_map_.empty()) application_->RequestQuit(0);
+ if (window_map_.empty() && application_->IsQuitOnAllWindowClosed())
+ application_->RequestQuit(0);
}
WinNativeWindow* WindowManager::FromHandle(HWND hwnd) {