aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/common/CMakeLists.txt2
-rw-r--r--src/common/logger.cpp37
-rw-r--r--src/platform/CMakeLists.txt6
-rw-r--r--src/platform/graph/CMakeLists.txt6
-rw-r--r--src/platform/native/CMakeLists.txt8
-rw-r--r--src/platform/native/cursor.cpp10
-rw-r--r--src/win/CMakeLists.txt3
-rw-r--r--src/win/debug_logger.hpp6
-rw-r--r--src/win/graph/direct/CMakeLists.txt8
-rw-r--r--src/win/graph/direct/brush.cpp7
-rw-r--r--src/win/graph/direct/factory.cpp (renamed from src/win/graph/direct/graph_factory.cpp)56
-rw-r--r--src/win/graph/direct/font.cpp20
-rw-r--r--src/win/graph/direct/geometry.cpp22
-rw-r--r--src/win/graph/direct/painter.cpp80
-rw-r--r--src/win/graph/direct/resource.cpp14
-rw-r--r--src/win/graph/direct/text_layout.cpp47
-rw-r--r--src/win/native/CMakeLists.txt1
-rw-r--r--src/win/native/ui_application.cpp8
-rw-r--r--src/win/string.cpp46
-rw-r--r--src/win/string_util.cpp20
20 files changed, 201 insertions, 206 deletions
diff --git a/src/common/CMakeLists.txt b/src/common/CMakeLists.txt
index afbbc139..516d5f1b 100644
--- a/src/common/CMakeLists.txt
+++ b/src/common/CMakeLists.txt
@@ -2,7 +2,7 @@ set(CRU_BASE_INCLUDE_DIR ${CRU_INCLUDE_DIR}/cru/common)
add_library(cru_base STATIC
logger.cpp
)
-target_sources(cru_base INTERFACE
+target_sources(cru_base PUBLIC
${CRU_BASE_INCLUDE_DIR}/base.hpp
${CRU_BASE_INCLUDE_DIR}/event.hpp
${CRU_BASE_INCLUDE_DIR}/format.hpp
diff --git a/src/common/logger.cpp b/src/common/logger.cpp
index 25223d91..6c1422f9 100644
--- a/src/common/logger.cpp
+++ b/src/common/logger.cpp
@@ -2,6 +2,7 @@
#include "cru/common/format.hpp"
+#include <array>
#include <cstdlib>
#include <ctime>
#include <memory>
@@ -11,7 +12,7 @@ namespace cru::log {
namespace {
Logger *CreateLogger() {
const auto logger = new Logger();
- logger->AddSource(new StdioLoggerSource());
+ logger->AddSource(std::make_unique<StdioLogSource>());
return logger;
}
} // namespace
@@ -21,45 +22,45 @@ Logger *Logger::GetInstance() {
return logger.get();
}
-Logger::~Logger() {
- for (const auto i : sources_) {
- delete i;
- }
+void Logger::AddSource(std::unique_ptr<ILogSource> source) {
+ sources_.push_back(std::move(source));
}
-void Logger::AddSource(ILoggerSource *source) { sources_.push_back(source); }
-
-void Logger::RemoveSource(ILoggerSource *source) { sources_.remove(source); }
+void Logger::RemoveSource(ILogSource *source) {
+ sources_.remove_if([source](const std::unique_ptr<ILogSource> &s) {
+ return s.get() == source;
+ });
+}
namespace {
-std::wstring_view LogLevelToString(LogLevel level) {
+std::string_view LogLevelToString(LogLevel level) {
switch (level) {
case LogLevel::Debug:
- return L"DEBUG";
+ return "DEBUG";
case LogLevel::Info:
- return L"INFO";
+ return "INFO";
case LogLevel::Warn:
- return L"WARN";
+ return "WARN";
case LogLevel::Error:
- return L"ERROR";
+ return "ERROR";
default:
std::abort();
}
}
} // namespace
-void Logger::Log(LogLevel level, const std::wstring_view &s) {
+void Logger::Log(LogLevel level, const std::string_view &s) {
#ifndef CRU_DEBUG
if (level == LogLevel::Debug) {
return;
}
#endif
- for (const auto source : sources_) {
+ for (const auto &source : sources_) {
auto now = std::time(nullptr);
- wchar_t buffer[50];
- std::wcsftime(buffer, 50, L"%c", std::localtime(&now));
+ std::array<char, 50> buffer;
+ std::strftime(buffer.data(), 50, "%c", std::localtime(&now));
- source->Write(level, util::Format(L"[{}] {}: {}\n", buffer,
+ source->Write(level, util::Format("[{}] {}: {}\n", buffer.data(),
LogLevelToString(level), s));
}
}
diff --git a/src/platform/CMakeLists.txt b/src/platform/CMakeLists.txt
index c9eef482..01952106 100644
--- a/src/platform/CMakeLists.txt
+++ b/src/platform/CMakeLists.txt
@@ -1,12 +1,12 @@
set(CRU_PLATFORM_BASE_INCLUDE_DIR ${CRU_INCLUDE_DIR}/cru/platform)
add_library(cru_platform_base INTERFACE)
target_sources(cru_platform_base INTERFACE
+ ${CRU_PLATFORM_BASE_INCLUDE_DIR}/check.hpp
${CRU_PLATFORM_BASE_INCLUDE_DIR}/exception.hpp
- ${CRU_PLATFORM_BASE_INCLUDE_DIR}/graphic_base.hpp
+ ${CRU_PLATFORM_BASE_INCLUDE_DIR}/graph_base.hpp
${CRU_PLATFORM_BASE_INCLUDE_DIR}/heap_debug.hpp
${CRU_PLATFORM_BASE_INCLUDE_DIR}/matrix.hpp
- ${CRU_PLATFORM_BASE_INCLUDE_DIR}/native_resource.hpp
- ${CRU_PLATFORM_BASE_INCLUDE_DIR}/string_util.hpp
+ ${CRU_PLATFORM_BASE_INCLUDE_DIR}/resource.hpp
)
target_link_libraries(cru_platform_base INTERFACE cru_base)
diff --git a/src/platform/graph/CMakeLists.txt b/src/platform/graph/CMakeLists.txt
index da76d296..dac28370 100644
--- a/src/platform/graph/CMakeLists.txt
+++ b/src/platform/graph/CMakeLists.txt
@@ -1,12 +1,14 @@
set(CRU_PLATFORM_GRAPH_INCLUDE_DIR ${CRU_INCLUDE_DIR}/cru/platform/graph)
add_library(cru_platform_graph INTERFACE)
target_sources(cru_platform_graph INTERFACE
+ ${CRU_PLATFORM_GRAPH_INCLUDE_DIR}/base.hpp
${CRU_PLATFORM_GRAPH_INCLUDE_DIR}/brush.hpp
${CRU_PLATFORM_GRAPH_INCLUDE_DIR}/font.hpp
${CRU_PLATFORM_GRAPH_INCLUDE_DIR}/geometry.hpp
- ${CRU_PLATFORM_GRAPH_INCLUDE_DIR}/graph_factory.hpp
+ ${CRU_PLATFORM_GRAPH_INCLUDE_DIR}/factory.hpp
+ ${CRU_PLATFORM_GRAPH_INCLUDE_DIR}/resource.hpp
${CRU_PLATFORM_GRAPH_INCLUDE_DIR}/painter.hpp
${CRU_PLATFORM_GRAPH_INCLUDE_DIR}/text_layout.hpp
- ${CRU_PLATFORM_GRAPH_INCLUDE_DIR}/util/painter_util.hpp
+ ${CRU_PLATFORM_GRAPH_INCLUDE_DIR}/util/painter.hpp
)
target_link_libraries(cru_platform_graph INTERFACE cru_platform_base)
diff --git a/src/platform/native/CMakeLists.txt b/src/platform/native/CMakeLists.txt
index 0e44fd55..bc7c4a63 100644
--- a/src/platform/native/CMakeLists.txt
+++ b/src/platform/native/CMakeLists.txt
@@ -1,12 +1,10 @@
set(CRU_PLATFORM_NATIVE_INCLUDE_DIR ${CRU_INCLUDE_DIR}/cru/platform/native)
-add_library(cru_platform_native STATIC
- cursor.cpp
-)
-target_sources(cru_platform_native PUBLIC
+add_library(cru_platform_native INTERFACE)
+target_sources(cru_platform_native INTERFACE
${CRU_PLATFORM_NATIVE_INCLUDE_DIR}/basic_types.hpp
${CRU_PLATFORM_NATIVE_INCLUDE_DIR}/cursor.hpp
${CRU_PLATFORM_NATIVE_INCLUDE_DIR}/native_event.hpp
${CRU_PLATFORM_NATIVE_INCLUDE_DIR}/native_window.hpp
${CRU_PLATFORM_NATIVE_INCLUDE_DIR}/ui_application.hpp
)
-target_link_libraries(cru_platform_native PUBLIC cru_platform_graph)
+target_link_libraries(cru_platform_native INTERFACE cru_platform_graph)
diff --git a/src/platform/native/cursor.cpp b/src/platform/native/cursor.cpp
deleted file mode 100644
index b12aec40..00000000
--- a/src/platform/native/cursor.cpp
+++ /dev/null
@@ -1,10 +0,0 @@
-#include "cru/platform/native/cursor.hpp"
-
-#include "cru/platform/native/ui_application.hpp"
-
-namespace cru::platform::native {
-std::shared_ptr<Cursor> GetSystemCursor(SystemCursor type) {
- return UiApplication::GetInstance()->GetCursorManager()->GetSystemCursor(
- type);
-}
-} // namespace cru::platform::native
diff --git a/src/win/CMakeLists.txt b/src/win/CMakeLists.txt
index 8c58954d..5727e4c0 100644
--- a/src/win/CMakeLists.txt
+++ b/src/win/CMakeLists.txt
@@ -5,10 +5,11 @@ add_library(cru_win_base STATIC
exception.cpp
heap_debug.cpp
- string_util.cpp
+ string.cpp
)
target_sources(cru_win_base PUBLIC
${CRU_WIN_BASE_INCLUDE_DIR}/exception.hpp
+ ${CRU_WIN_BASE_INCLUDE_DIR}/string.hpp
${CRU_WIN_BASE_INCLUDE_DIR}/win_pre_config.hpp
)
target_compile_definitions(cru_win_base PUBLIC UNICODE _UNICODE) # use unicode
diff --git a/src/win/debug_logger.hpp b/src/win/debug_logger.hpp
index ab6a2266..53c4859b 100644
--- a/src/win/debug_logger.hpp
+++ b/src/win/debug_logger.hpp
@@ -4,7 +4,7 @@
namespace cru::platform::win {
-class WinDebugLoggerSource : public ::cru::log::ILoggerSource {
+class WinDebugLoggerSource : public ::cru::log::ILogSource {
public:
WinDebugLoggerSource() = default;
@@ -13,8 +13,8 @@ class WinDebugLoggerSource : public ::cru::log::ILoggerSource {
~WinDebugLoggerSource() = default;
- void Write(::cru::log::LogLevel level, const std::wstring_view& s) override {
- ::OutputDebugStringW(s.data());
+ void Write(::cru::log::LogLevel level, const std::string_view& s) override {
+ ::OutputDebugStringA(s.data());
}
};
} // namespace cru::platform::win
diff --git a/src/win/graph/direct/CMakeLists.txt b/src/win/graph/direct/CMakeLists.txt
index fa5e3a99..b277fa32 100644
--- a/src/win/graph/direct/CMakeLists.txt
+++ b/src/win/graph/direct/CMakeLists.txt
@@ -4,21 +4,21 @@ add_library(cru_win_graph_direct STATIC
brush.cpp
font.cpp
geometry.cpp
- graph_factory.cpp
+ factory.cpp
painter.cpp
+ resource.cpp
text_layout.cpp
)
target_sources(cru_win_graph_direct PUBLIC
${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/brush.hpp
${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/com_resource.hpp
${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/convert_util.hpp
- ${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/direct_factory.hpp
${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/exception.hpp
${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/font.hpp
${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/geometry.hpp
- ${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/graph_factory.hpp
+ ${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/factory.hpp
${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/painter.hpp
- ${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/platform_id.hpp
+ ${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/resource.hpp
${CRU_WIN_GRAPH_DIRECT_INCLUDE_DIR}/text_layout.hpp
)
target_link_libraries(cru_win_graph_direct PUBLIC D3D11 D2d1 DWrite cru_win_base cru_platform_graph)
diff --git a/src/win/graph/direct/brush.cpp b/src/win/graph/direct/brush.cpp
index 1f17cd03..17024a66 100644
--- a/src/win/graph/direct/brush.cpp
+++ b/src/win/graph/direct/brush.cpp
@@ -2,17 +2,18 @@
#include "cru/win/graph/direct/convert_util.hpp"
#include "cru/win/graph/direct/exception.hpp"
+#include "cru/win/graph/direct/factory.hpp"
#include <cassert>
namespace cru::platform::graph::win::direct {
-D2DSolidColorBrush::D2DSolidColorBrush(IDirectFactory* factory) {
- assert(factory);
+D2DSolidColorBrush::D2DSolidColorBrush(DirectGraphFactory* factory)
+ : DirectGraphResource(factory) {
ThrowIfFailed(factory->GetD2D1DeviceContext()->CreateSolidColorBrush(
Convert(color_), &brush_));
}
-void D2DSolidColorBrush::OnSetColor(const Color& color) {
+void D2DSolidColorBrush::SetColor(const Color& color) {
brush_->SetColor(Convert(color));
}
} // namespace cru::platform::graph::win::direct
diff --git a/src/win/graph/direct/graph_factory.cpp b/src/win/graph/direct/factory.cpp
index 49752d0b..7882c3ee 100644
--- a/src/win/graph/direct/graph_factory.cpp
+++ b/src/win/graph/direct/factory.cpp
@@ -1,4 +1,4 @@
-#include "cru/win/graph/direct/graph_factory.hpp"
+#include "cru/win/graph/direct/factory.hpp"
#include "cru/win/graph/direct/brush.hpp"
#include "cru/win/graph/direct/exception.hpp"
@@ -11,37 +11,6 @@
#include <utility>
namespace cru::platform::graph::win::direct {
-namespace {
-DirectGraphFactory* instance = nullptr;
-}
-} // namespace cru::platform::graph::win::direct
-
-namespace cru::platform::graph {
-void GraphFactoryAutoDeleteExitHandler() {
- const auto i =
- ::cru::platform::graph::win::direct::instance; // avoid long namespace
- // prefix
- if (i == nullptr) return;
- if (i->IsAutoDelete()) delete i;
-}
-
-GraphFactory* GraphFactory::CreateInstance() {
- auto& i = ::cru::platform::graph::win::direct::instance; // avoid long
- // namespace prefix
- assert(i == nullptr);
- i = new ::cru::platform::graph::win::direct::DirectGraphFactory();
- std::atexit(&GraphFactoryAutoDeleteExitHandler);
- return i;
-}
-
-GraphFactory* GraphFactory::GetInstance() {
- return ::cru::platform::graph::win::direct::instance;
-}
-} // namespace cru::platform::graph
-
-namespace cru::platform::graph::win::direct {
-DirectGraphFactory* DirectGraphFactory::GetInstance() { return instance; }
-
DirectGraphFactory::DirectGraphFactory() {
UINT creation_flags = D3D11_CREATE_DEVICE_BGRA_SUPPORT;
@@ -89,23 +58,22 @@ DirectGraphFactory::DirectGraphFactory() {
&dwrite_system_font_collection_));
}
-DirectGraphFactory::~DirectGraphFactory() { instance = nullptr; }
-
-D2DSolidColorBrush* DirectGraphFactory::CreateSolidColorBrush() {
- return new D2DSolidColorBrush(this);
+std::unique_ptr<ISolidColorBrush> DirectGraphFactory::CreateSolidColorBrush() {
+ return std::make_unique<D2DSolidColorBrush>(this);
}
-D2DGeometryBuilder* DirectGraphFactory::CreateGeometryBuilder() {
- return new D2DGeometryBuilder(this);
+std::unique_ptr<IGeometryBuilder> DirectGraphFactory::CreateGeometryBuilder() {
+ return std::make_unique<D2DGeometryBuilder>(this);
}
-DWriteFont* DirectGraphFactory::CreateFont(
- const std::wstring_view& font_family, float font_size) {
- return new DWriteFont(this, font_family, font_size);
+std::unique_ptr<IFont> DirectGraphFactory::CreateFont(
+ const std::string_view& font_family, float font_size) {
+ return std::make_unique<DWriteFont>(this, font_family, font_size);
}
-DWriteTextLayout* DirectGraphFactory::CreateTextLayout(
- std::shared_ptr<Font> font, std::wstring text) {
- return new DWriteTextLayout(this, std::move(font), std::move(text));
+std::unique_ptr<ITextLayout> DirectGraphFactory::CreateTextLayout(
+ std::shared_ptr<IFont> font, std::string text) {
+ return std::make_unique<DWriteTextLayout>(this, std::move(font),
+ std::move(text));
}
} // namespace cru::platform::graph::win::direct
diff --git a/src/win/graph/direct/font.cpp b/src/win/graph/direct/font.cpp
index 5d7b4483..8e881f84 100644
--- a/src/win/graph/direct/font.cpp
+++ b/src/win/graph/direct/font.cpp
@@ -1,25 +1,29 @@
#include "cru/win/graph/direct/font.hpp"
-#include "cru/win/exception.hpp"
#include "cru/win/graph/direct/exception.hpp"
+#include "cru/win/graph/direct/factory.hpp"
+#include "cru/win/string.hpp"
#include <array>
#include <cassert>
#include <utility>
namespace cru::platform::graph::win::direct {
-DWriteFont::DWriteFont(IDirectFactory* factory,
- const std::wstring_view& font_family, float font_size) {
- assert(factory);
+DWriteFont::DWriteFont(DirectGraphFactory* factory,
+ const std::string_view& font_family, float font_size)
+ : DirectGraphResource(factory) {
+ // Get locale
std::array<wchar_t, LOCALE_NAME_MAX_LENGTH> buffer;
if (!::GetUserDefaultLocaleName(buffer.data(),
static_cast<int>(buffer.size())))
- throw platform::win::Win32Error(::GetLastError(), "Failed to get locale.");
+ throw platform::win::Win32Error(
+ ::GetLastError(), "Failed to get locale when create dwrite font.");
+
+ const std::wstring&& wff = cru::platform::win::ToUtf16String(font_family);
ThrowIfFailed(factory->GetDWriteFactory()->CreateTextFormat(
- font_family.data(), nullptr, DWRITE_FONT_WEIGHT_NORMAL,
- DWRITE_FONT_STYLE_NORMAL, DWRITE_FONT_STRETCH_NORMAL, font_size,
- buffer.data(), &text_format_));
+ wff.data(), nullptr, DWRITE_FONT_WEIGHT_NORMAL, DWRITE_FONT_STYLE_NORMAL,
+ DWRITE_FONT_STRETCH_NORMAL, font_size, buffer.data(), &text_format_));
ThrowIfFailed(text_format_->SetTextAlignment(DWRITE_TEXT_ALIGNMENT_CENTER));
ThrowIfFailed(
diff --git a/src/win/graph/direct/geometry.cpp b/src/win/graph/direct/geometry.cpp
index 470addee..5540edab 100644
--- a/src/win/graph/direct/geometry.cpp
+++ b/src/win/graph/direct/geometry.cpp
@@ -2,16 +2,22 @@
#include "cru/win/graph/direct/convert_util.hpp"
#include "cru/win/graph/direct/exception.hpp"
+#include "cru/win/graph/direct/factory.hpp"
#include <cassert>
namespace cru::platform::graph::win::direct {
-D2DGeometryBuilder::D2DGeometryBuilder(IDirectFactory* factory) {
- assert(factory);
+D2DGeometryBuilder::D2DGeometryBuilder(DirectGraphFactory* factory)
+ : DirectGraphResource(factory) {
ThrowIfFailed(factory->GetD2D1Factory()->CreatePathGeometry(&geometry_));
ThrowIfFailed(geometry_->Open(&geometry_sink_));
}
+void D2DGeometryBuilder::CheckValidation() {
+ if (!IsValid())
+ throw ReuseException("The geometry builder is already disposed.");
+}
+
void D2DGeometryBuilder::BeginFigure(const Point& point) {
CheckValidation();
geometry_sink_->BeginFigure(Convert(point), D2D1_FIGURE_BEGIN_FILLED);
@@ -35,19 +41,19 @@ void D2DGeometryBuilder::CloseFigure(bool close) {
: D2D1_FIGURE_END_OPEN);
}
-Geometry* D2DGeometryBuilder::Build() {
+std::unique_ptr<IGeometry> D2DGeometryBuilder::Build() {
CheckValidation();
ThrowIfFailed(geometry_sink_->Close());
geometry_sink_ = nullptr;
- const auto geometry = new D2DGeometry(std::move(geometry_));
+ auto geometry =
+ std::make_unique<D2DGeometry>(GetDirectFactory(), std::move(geometry_));
geometry_ = nullptr;
return geometry;
}
-D2DGeometry::D2DGeometry(Microsoft::WRL::ComPtr<ID2D1PathGeometry> geometry) {
- assert(geometry);
- geometry_ = std::move(geometry);
-}
+D2DGeometry::D2DGeometry(DirectGraphFactory* factory,
+ Microsoft::WRL::ComPtr<ID2D1PathGeometry> geometry)
+ : DirectGraphResource(factory), geometry_(std::move(geometry)) {}
bool D2DGeometry::FillContains(const Point& point) {
BOOL result;
diff --git a/src/win/graph/direct/painter.cpp b/src/win/graph/direct/painter.cpp
index 6fbbf957..fb2a6e7f 100644
--- a/src/win/graph/direct/painter.cpp
+++ b/src/win/graph/direct/painter.cpp
@@ -1,5 +1,6 @@
#include "cru/win/graph/direct/painter.hpp"
+#include "cru/platform/check.hpp"
#include "cru/win/graph/direct/brush.hpp"
#include "cru/win/graph/direct/convert_util.hpp"
#include "cru/win/graph/direct/exception.hpp"
@@ -10,89 +11,63 @@
#include <type_traits>
namespace cru::platform::graph::win::direct {
-
-namespace {
-template <typename T, typename U, typename = void>
-struct is_static_castable : std::false_type {};
-
-template <typename T, typename U>
-struct is_static_castable<
- T, U, std::void_t<decltype(static_cast<U>(std::declval<T>()))>>
- : std::true_type {};
-
-template <typename TDes, typename TSrc>
-TDes* CheckAndCast(TSrc* src) {
- assert(src);
- assert(IsDirectResource(src));
- if constexpr (is_static_castable<TSrc*, TDes*>::value)
- return static_cast<TDes*>(src);
- else {
- TDes* d = dynamic_cast<TDes*>(src);
- assert(d);
- return d;
- }
-}
-} // namespace
-
D2DPainter::D2DPainter(ID2D1RenderTarget* render_target) {
assert(render_target);
render_target_ = render_target;
}
platform::Matrix D2DPainter::GetTransform() {
- assert(IsValid());
+ CheckValidation();
D2D1_MATRIX_3X2_F m;
render_target_->GetTransform(&m);
return Convert(m);
}
void D2DPainter::SetTransform(const platform::Matrix& matrix) {
- assert(IsValid());
+ CheckValidation();
render_target_->SetTransform(Convert(matrix));
}
void D2DPainter::Clear(const Color& color) {
- assert(IsValid());
+ CheckValidation();
render_target_->Clear(Convert(color));
}
-void D2DPainter::StrokeRectangle(const Rect& rectangle, Brush* brush,
+void D2DPainter::StrokeRectangle(const Rect& rectangle, IBrush* brush,
float width) {
- assert(IsValid());
- const auto b = CheckAndCast<ID2DBrush>(brush);
+ CheckValidation();
+ const auto b = CheckPlatform<ID2DBrush>(brush, GetPlatformId());
render_target_->DrawRectangle(Convert(rectangle), b->GetD2DBrushInterface(),
width);
}
-void D2DPainter::FillRectangle(const Rect& rectangle, Brush* brush) {
- assert(IsValid());
- const auto b = CheckAndCast<ID2DBrush>(brush);
+void D2DPainter::FillRectangle(const Rect& rectangle, IBrush* brush) {
+ CheckValidation();
+ const auto b = CheckPlatform<ID2DBrush>(brush, GetPlatformId());
render_target_->FillRectangle(Convert(rectangle), b->GetD2DBrushInterface());
}
-void D2DPainter::StrokeGeometry(Geometry* geometry, Brush* brush, float width) {
- assert(IsValid());
- const auto g = CheckAndCast<D2DGeometry>(geometry);
- const auto b = CheckAndCast<ID2DBrush>(brush);
-
+void D2DPainter::StrokeGeometry(IGeometry* geometry, IBrush* brush,
+ float width) {
+ CheckValidation();
+ const auto g = CheckPlatform<D2DGeometry>(geometry, GetPlatformId());
+ const auto b = CheckPlatform<ID2DBrush>(brush, GetPlatformId());
render_target_->DrawGeometry(g->GetComInterface(), b->GetD2DBrushInterface(),
width);
}
-void D2DPainter::FillGeometry(Geometry* geometry, Brush* brush) {
- assert(IsValid());
- const auto g = CheckAndCast<D2DGeometry>(geometry);
- const auto b = CheckAndCast<ID2DBrush>(brush);
-
+void D2DPainter::FillGeometry(IGeometry* geometry, IBrush* brush) {
+ CheckValidation();
+ const auto g = CheckPlatform<D2DGeometry>(geometry, GetPlatformId());
+ const auto b = CheckPlatform<ID2DBrush>(brush, GetPlatformId());
render_target_->FillGeometry(g->GetComInterface(), b->GetD2DBrushInterface());
}
-void D2DPainter::DrawText(const Point& offset, TextLayout* text_layout,
- Brush* brush) {
- assert(IsValid());
- const auto t = CheckAndCast<DWriteTextLayout>(text_layout);
- const auto b = CheckAndCast<ID2DBrush>(brush);
-
+void D2DPainter::DrawText(const Point& offset, ITextLayout* text_layout,
+ IBrush* brush) {
+ CheckValidation();
+ const auto t = CheckPlatform<DWriteTextLayout>(text_layout, GetPlatformId());
+ const auto b = CheckPlatform<ID2DBrush>(brush, GetPlatformId());
render_target_->DrawTextLayout(Convert(offset), t->GetComInterface(),
b->GetD2DBrushInterface());
}
@@ -103,4 +78,11 @@ void D2DPainter::EndDraw() {
DoEndDraw();
}
}
+
+void D2DPainter::CheckValidation() {
+ if (!is_drawing_) {
+ throw cru::platform::ReuseException(
+ "Can't do that on painter after end drawing.");
+ }
+}
} // namespace cru::platform::graph::win::direct
diff --git a/src/win/graph/direct/resource.cpp b/src/win/graph/direct/resource.cpp
new file mode 100644
index 00000000..2acc91e4
--- /dev/null
+++ b/src/win/graph/direct/resource.cpp
@@ -0,0 +1,14 @@
+#include "cru/win/graph/direct/resource.hpp"
+
+#include "cru/win/graph/direct/factory.hpp"
+
+#include <cassert>
+
+namespace cru::platform::graph::win::direct {
+DirectGraphResource::DirectGraphResource(DirectGraphFactory* factory)
+ : factory_(factory) {
+ assert(factory);
+}
+
+IGraphFactory* DirectGraphResource::GetGraphFactory() { return factory_; }
+} // namespace cru::platform::graph::win::direct
diff --git a/src/win/graph/direct/text_layout.cpp b/src/win/graph/direct/text_layout.cpp
index 23a14b2a..a1750799 100644
--- a/src/win/graph/direct/text_layout.cpp
+++ b/src/win/graph/direct/text_layout.cpp
@@ -1,46 +1,49 @@
#include "cru/win/graph/direct/text_layout.hpp"
+#include "cru/platform/check.hpp"
#include "cru/win/graph/direct/exception.hpp"
+#include "cru/win/graph/direct/factory.hpp"
+#include "cru/win/graph/direct/font.hpp"
+#include "cru/win/string.hpp"
#include <cassert>
#include <utility>
namespace cru::platform::graph::win::direct {
-DWriteTextLayout::DWriteTextLayout(IDirectFactory* factory,
- std::shared_ptr<Font> font,
- std::wstring text)
- : text_(std::move(text)) {
- assert(factory);
+DWriteTextLayout::DWriteTextLayout(DirectGraphFactory* factory,
+ std::shared_ptr<IFont> font,
+ std::string text)
+ : DirectGraphResource(factory), text_(std::move(text)) {
assert(font);
- assert(IsDirectResource(font.get()));
- factory_ = factory;
- font_ = std::static_pointer_cast<DWriteFont>(font);
+ font_ = CheckPlatform<DWriteFont>(font, GetPlatformId());
+
+ w_text_ = cru::platform::win::ToUtf16String(text_);
ThrowIfFailed(factory->GetDWriteFactory()->CreateTextLayout(
- text_.c_str(), static_cast<UINT32>(text_.size()),
+ w_text_.c_str(), static_cast<UINT32>(w_text_.size()),
font_->GetComInterface(), max_width_, max_height_, &text_layout_));
}
-std::wstring DWriteTextLayout::GetText() { return text_; }
+DWriteTextLayout::~DWriteTextLayout() = default;
+
+std::string DWriteTextLayout::GetText() { return text_; }
-void DWriteTextLayout::SetText(std::wstring new_text) {
+void DWriteTextLayout::SetText(std::string new_text) {
text_.swap(new_text);
- ThrowIfFailed(factory_->GetDWriteFactory()->CreateTextLayout(
- text_.c_str(), static_cast<UINT32>(text_.size()),
+ w_text_ = cru::platform::win::ToUtf16String(text_);
+ ThrowIfFailed(GetDirectFactory()->GetDWriteFactory()->CreateTextLayout(
+ w_text_.c_str(), static_cast<UINT32>(w_text_.size()),
font_->GetComInterface(), max_width_, max_height_, &text_layout_));
}
-std::shared_ptr<Font> DWriteTextLayout::GetFont() {
- return std::static_pointer_cast<Font>(font_);
+std::shared_ptr<IFont> DWriteTextLayout::GetFont() {
+ return std::dynamic_pointer_cast<IFont>(font_);
}
-void DWriteTextLayout::SetFont(std::shared_ptr<Font> font) {
- assert(IsDirectResource(font.get()));
- auto f = std::static_pointer_cast<DWriteFont>(font);
-
- f.swap(font_);
- ThrowIfFailed(factory_->GetDWriteFactory()->CreateTextLayout(
- text_.c_str(), static_cast<UINT32>(text_.size()),
+void DWriteTextLayout::SetFont(std::shared_ptr<IFont> font) {
+ font_ = CheckPlatform<DWriteFont>(font, GetPlatformId());
+ ThrowIfFailed(GetDirectFactory()->GetDWriteFactory()->CreateTextLayout(
+ w_text_.c_str(), static_cast<UINT32>(w_text_.size()),
font_->GetComInterface(), max_width_, max_height_, &text_layout_));
}
diff --git a/src/win/native/CMakeLists.txt b/src/win/native/CMakeLists.txt
index 08acc739..0e7e5b4e 100644
--- a/src/win/native/CMakeLists.txt
+++ b/src/win/native/CMakeLists.txt
@@ -22,7 +22,6 @@ target_sources(cru_win_native PUBLIC
${CRU_WIN_NATIVE_INCLUDE_DIR}/exception.hpp
${CRU_WIN_NATIVE_INCLUDE_DIR}/god_window.hpp
${CRU_WIN_NATIVE_INCLUDE_DIR}/native_window.hpp
- ${CRU_WIN_NATIVE_INCLUDE_DIR}/platform_id.hpp
${CRU_WIN_NATIVE_INCLUDE_DIR}/ui_application.hpp
${CRU_WIN_NATIVE_INCLUDE_DIR}/window_class.hpp
${CRU_WIN_NATIVE_INCLUDE_DIR}/window_native_message_event_args.hpp
diff --git a/src/win/native/ui_application.cpp b/src/win/native/ui_application.cpp
index c2d3ac2c..0bbe9c03 100644
--- a/src/win/native/ui_application.cpp
+++ b/src/win/native/ui_application.cpp
@@ -107,16 +107,16 @@ void WinUiApplication::CancelTimer(unsigned long id) {
timer_manager_->KillTimer(static_cast<UINT_PTR>(id));
}
-std::vector<NativeWindow*> WinUiApplication::GetAllWindow() {
+std::vector<INativeWindow*> WinUiApplication::GetAllWindow() {
const auto&& windows = window_manager_->GetAllWindows();
- std::vector<NativeWindow*> result;
+ std::vector<INativeWindow*> result;
for (const auto w : windows) {
- result.push_back(static_cast<NativeWindow*>(w));
+ result.push_back(static_cast<INativeWindow*>(w));
}
return result;
}
-NativeWindow* WinUiApplication::CreateWindow(NativeWindow* parent) {
+INativeWindow* WinUiApplication::CreateWindow(INativeWindow* parent) {
WinNativeWindow* p = nullptr;
if (parent != nullptr) {
p = dynamic_cast<WinNativeWindow*>(parent);
diff --git a/src/win/string.cpp b/src/win/string.cpp
new file mode 100644
index 00000000..84906f6b
--- /dev/null
+++ b/src/win/string.cpp
@@ -0,0 +1,46 @@
+#include "cru/win/string.hpp"
+
+#include "cru/win/exception.hpp"
+
+namespace cru::platform::win {
+std::string ToUtf8String(const std::wstring_view& string) {
+ if (string.empty()) return std::string{};
+
+ const auto length =
+ ::WideCharToMultiByte(CP_UTF8, WC_ERR_INVALID_CHARS, string.data(), -1,
+ nullptr, 0, nullptr, nullptr);
+ if (length == 0) {
+ throw Win32Error(::GetLastError(),
+ "Failed to convert wide string to UTF-8.");
+ }
+
+ std::string result;
+ result.resize(length);
+ if (::WideCharToMultiByte(CP_UTF8, WC_ERR_INVALID_CHARS, string.data(), -1,
+ result.data(), static_cast<int>(result.size()),
+ nullptr, nullptr) == 0)
+ throw Win32Error(::GetLastError(),
+ "Failed to convert wide string to UTF-8.");
+ return result;
+}
+
+std::wstring ToUtf16String(const std::string_view& string) {
+ if (string.empty()) return std::wstring{};
+
+ const auto length = ::MultiByteToWideChar(CP_UTF8, MB_ERR_INVALID_CHARS,
+ string.data(), -1, nullptr, 0);
+ if (length == 0) {
+ throw Win32Error(::GetLastError(),
+ "Failed to convert wide string to UTF-16.");
+ }
+
+ std::wstring result;
+ result.resize(length);
+ if (::MultiByteToWideChar(CP_UTF8, MB_ERR_INVALID_CHARS, string.data(), -1,
+ result.data(),
+ static_cast<int>(result.size())) == 0)
+ throw win::Win32Error(::GetLastError(),
+ "Failed to convert wide string to UTF-16.");
+ return result;
+}
+} // namespace cru::platform::win
diff --git a/src/win/string_util.cpp b/src/win/string_util.cpp
deleted file mode 100644
index dd513b12..00000000
--- a/src/win/string_util.cpp
+++ /dev/null
@@ -1,20 +0,0 @@
-#include "cru/platform/string_util.hpp"
-
-#include "cru/win/exception.hpp"
-
-namespace cru::platform {
-std::string ToUtf8String(const std::wstring_view& string) {
- if (string.empty()) return std::string();
-
- const auto length = ::WideCharToMultiByte(CP_UTF8, 0, string.data(), -1,
- nullptr, 0, nullptr, nullptr);
- std::string result;
- result.resize(length);
- if (::WideCharToMultiByte(CP_UTF8, 0, string.data(), -1, result.data(),
- static_cast<int>(result.size()), nullptr,
- nullptr) == 0)
- throw win::Win32Error(::GetLastError(),
- "Failed to convert wide string to UTF-8.");
- return result;
-}
-} // namespace cru::platform