Add FontCollection

This commit is contained in:
Nomango 2019-08-18 10:23:54 +08:00
parent a3fad67bfa
commit aec069b167
62 changed files with 1535 additions and 389 deletions

View File

@ -54,7 +54,8 @@ for:
- master
only_commits:
message: /\[build\]/
matrix:
environment:
matrix:
- APPVEYOR_BUILD_WORKER_IMAGE: Visual Studio 2019
VS_PLATFORM_TOOLSET: v142

View File

@ -11,7 +11,6 @@
<ClInclude Include="..\src\kiwano\2d\action\Animation.h" />
<ClInclude Include="..\src\kiwano\2d\Frame.h" />
<ClInclude Include="..\src\kiwano\2d\GifSprite.h" />
<ClInclude Include="..\src\kiwano\base\ComPtr.hpp" />
<ClInclude Include="..\src\kiwano\base\Director.h" />
<ClInclude Include="..\src\kiwano\base\types.h" />
<ClInclude Include="..\src\kiwano\core\basic_json.hpp" />
@ -48,7 +47,7 @@
<ClInclude Include="..\src\kiwano\base\Input.h" />
<ClInclude Include="..\src\kiwano\base\keys.hpp" />
<ClInclude Include="..\src\kiwano\base\Logger.h" />
<ClInclude Include="..\src\kiwano\base\Object.h" />
<ClInclude Include="..\src\kiwano\base\ObjectBase.h" />
<ClInclude Include="..\src\kiwano\base\RefCounter.hpp" />
<ClInclude Include="..\src\kiwano\base\Resource.h" />
<ClInclude Include="..\src\kiwano\base\SmartPtr.hpp" />
@ -58,7 +57,7 @@
<ClInclude Include="..\src\kiwano\base\Window.h" />
<ClInclude Include="..\src\kiwano\math\constants.hpp" />
<ClInclude Include="..\src\kiwano\math\ease.hpp" />
<ClInclude Include="..\src\kiwano\math\helper.h" />
<ClInclude Include="..\src\kiwano\math\math.h" />
<ClInclude Include="..\src\kiwano\math\Matrix.hpp" />
<ClInclude Include="..\src\kiwano\math\rand.h" />
<ClInclude Include="..\src\kiwano\math\Rect.hpp" />
@ -67,21 +66,22 @@
<ClInclude Include="..\src\kiwano\platform\Application.h" />
<ClInclude Include="..\src\kiwano\platform\modules.h" />
<ClInclude Include="..\src\kiwano\renderer\Color.h" />
<ClInclude Include="..\src\kiwano\renderer\D2DDeviceResources.h" />
<ClInclude Include="..\src\kiwano\renderer\D3D10DeviceResources.h" />
<ClInclude Include="..\src\kiwano\renderer\D3D11DeviceResources.h" />
<ClInclude Include="..\src\kiwano\renderer\D3DDeviceResourcesBase.h" />
<ClInclude Include="..\src\kiwano\renderer\Font.h" />
<ClInclude Include="..\src\kiwano\renderer\Geometry.h" />
<ClInclude Include="..\src\kiwano\renderer\GifImage.h" />
<ClInclude Include="..\src\kiwano\renderer\helper.hpp" />
<ClInclude Include="..\src\kiwano\renderer\Image.h" />
<ClInclude Include="..\src\kiwano\renderer\ImageCache.h" />
<ClInclude Include="..\src\kiwano\renderer\LayerArea.h" />
<ClInclude Include="..\src\kiwano\renderer\Renderer.h" />
<ClInclude Include="..\src\kiwano\renderer\RenderTarget.h" />
<ClInclude Include="..\src\kiwano\renderer\TextLayout.h" />
<ClInclude Include="..\src\kiwano\renderer\TextRenderer.h" />
<ClInclude Include="..\src\kiwano\renderer\win32\ComPtr.hpp" />
<ClInclude Include="..\src\kiwano\renderer\win32\D2DDeviceResources.h" />
<ClInclude Include="..\src\kiwano\renderer\win32\D3D10DeviceResources.h" />
<ClInclude Include="..\src\kiwano\renderer\win32\D3D11DeviceResources.h" />
<ClInclude Include="..\src\kiwano\renderer\win32\D3DDeviceResourcesBase.h" />
<ClInclude Include="..\src\kiwano\renderer\win32\FontCollectionLoader.h" />
<ClInclude Include="..\src\kiwano\renderer\win32\TextRenderer.h" />
<ClInclude Include="..\src\kiwano\third-party\StackWalker\StackWalker.h" />
<ClInclude Include="..\src\kiwano\third-party\tinyxml2\tinyxml2.h" />
<ClInclude Include="..\src\kiwano\ui\Button.h" />
@ -116,7 +116,7 @@
<ClCompile Include="..\src\kiwano\base\EventListener.cpp" />
<ClCompile Include="..\src\kiwano\base\Input.cpp" />
<ClCompile Include="..\src\kiwano\base\Logger.cpp" />
<ClCompile Include="..\src\kiwano\base\Object.cpp" />
<ClCompile Include="..\src\kiwano\base\ObjectBase.cpp" />
<ClCompile Include="..\src\kiwano\base\Resource.cpp" />
<ClCompile Include="..\src\kiwano\base\Director.cpp" />
<ClCompile Include="..\src\kiwano\base\Timer.cpp" />
@ -126,9 +126,6 @@
<ClCompile Include="..\src\kiwano\platform\Application.cpp" />
<ClCompile Include="..\src\kiwano\platform\modules.cpp" />
<ClCompile Include="..\src\kiwano\renderer\Color.cpp" />
<ClCompile Include="..\src\kiwano\renderer\D2DDeviceResources.cpp" />
<ClCompile Include="..\src\kiwano\renderer\D3D10DeviceResources.cpp" />
<ClCompile Include="..\src\kiwano\renderer\D3D11DeviceResources.cpp" />
<ClCompile Include="..\src\kiwano\renderer\Font.cpp" />
<ClCompile Include="..\src\kiwano\renderer\Geometry.cpp" />
<ClCompile Include="..\src\kiwano\renderer\GifImage.cpp" />
@ -138,7 +135,11 @@
<ClCompile Include="..\src\kiwano\renderer\Renderer.cpp" />
<ClCompile Include="..\src\kiwano\renderer\RenderTarget.cpp" />
<ClCompile Include="..\src\kiwano\renderer\TextLayout.cpp" />
<ClCompile Include="..\src\kiwano\renderer\TextRenderer.cpp" />
<ClCompile Include="..\src\kiwano\renderer\win32\D2DDeviceResources.cpp" />
<ClCompile Include="..\src\kiwano\renderer\win32\D3D10DeviceResources.cpp" />
<ClCompile Include="..\src\kiwano\renderer\win32\D3D11DeviceResources.cpp" />
<ClCompile Include="..\src\kiwano\renderer\win32\FontCollectionLoader.cpp" />
<ClCompile Include="..\src\kiwano\renderer\win32\TextRenderer.cpp" />
<ClCompile Include="..\src\kiwano\third-party\StackWalker\StackWalker.cpp" />
<ClCompile Include="..\src\kiwano\third-party\tinyxml2\tinyxml2.cpp" />
<ClCompile Include="..\src\kiwano\ui\Button.cpp" />
@ -201,7 +202,7 @@
<WarningLevel>Level3</WarningLevel>
<Optimization>Disabled</Optimization>
<TreatWarningAsError>true</TreatWarningAsError>
<DebugInformationFormat>None</DebugInformationFormat>
<DebugInformationFormat>EditAndContinue</DebugInformationFormat>
<MultiProcessorCompilation>true</MultiProcessorCompilation>
<MinimalRebuild>false</MinimalRebuild>
</ClCompile>
@ -218,7 +219,7 @@
<IntrinsicFunctions>true</IntrinsicFunctions>
<BufferSecurityCheck>false</BufferSecurityCheck>
<TreatWarningAsError>true</TreatWarningAsError>
<DebugInformationFormat>None</DebugInformationFormat>
<DebugInformationFormat>EditAndContinue</DebugInformationFormat>
<MultiProcessorCompilation>true</MultiProcessorCompilation>
<MinimalRebuild>false</MinimalRebuild>
</ClCompile>

View File

@ -37,6 +37,9 @@
<Filter Include="core">
<UniqueIdentifier>{86e2d0f2-a9d0-4456-b6a5-d480228bbf82}</UniqueIdentifier>
</Filter>
<Filter Include="renderer\win32">
<UniqueIdentifier>{30333461-e9bc-4709-84bd-ce6e0e1a3079}</UniqueIdentifier>
</Filter>
</ItemGroup>
<ItemGroup>
<ClInclude Include="..\src\kiwano\ui\Button.h">
@ -96,21 +99,6 @@
<ClInclude Include="..\src\kiwano\base\time.h">
<Filter>base</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\D2DDeviceResources.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\D3D10DeviceResources.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\D3D11DeviceResources.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\helper.hpp">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\TextRenderer.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\math\constants.hpp">
<Filter>math</Filter>
</ClInclude>
@ -140,9 +128,6 @@
</ClInclude>
<ClInclude Include="..\src\kiwano\config.h" />
<ClInclude Include="..\src\kiwano\macros.h" />
<ClInclude Include="..\src\kiwano\math\helper.h">
<Filter>math</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\math\Vec2.hpp">
<Filter>math</Filter>
</ClInclude>
@ -152,9 +137,6 @@
<ClInclude Include="..\src\kiwano\base\SmartPtr.hpp">
<Filter>base</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\base\Object.h">
<Filter>base</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\kiwano.h" />
<ClInclude Include="..\src\kiwano\utils\DataUtil.h">
<Filter>utils</Filter>
@ -174,9 +156,6 @@
<ClInclude Include="..\src\kiwano\utils\FileUtil.h">
<Filter>utils</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\D3DDeviceResourcesBase.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\base\types.h">
<Filter>base</Filter>
</ClInclude>
@ -198,12 +177,6 @@
<ClInclude Include="..\src\kiwano\2d\Frame.h">
<Filter>2d</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\GifImage.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\Image.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\2d\action\Action.h">
<Filter>2d\action</Filter>
</ClInclude>
@ -222,9 +195,6 @@
<ClInclude Include="..\src\kiwano\2d\action\Animation.h">
<Filter>2d\action</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\ImageCache.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\utils\ResourceCache.h">
<Filter>utils</Filter>
</ClInclude>
@ -255,9 +225,6 @@
<ClInclude Include="..\src\kiwano\core\vector.hpp">
<Filter>core</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\base\ComPtr.hpp">
<Filter>base</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\core\core.h">
<Filter>core</Filter>
</ClInclude>
@ -267,9 +234,6 @@
<ClInclude Include="..\src\kiwano\2d\ShapeActor.h">
<Filter>2d</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\Geometry.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\2d\action\ActionDelay.h">
<Filter>2d\action</Filter>
</ClInclude>
@ -282,14 +246,11 @@
<ClInclude Include="..\src\kiwano\base\Window.h">
<Filter>base</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\Renderer.h">
<Filter>renderer</Filter>
<ClInclude Include="..\src\kiwano\math\math.h">
<Filter>math</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\TextLayout.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\RenderTarget.h">
<Filter>renderer</Filter>
<ClInclude Include="..\src\kiwano\base\ObjectBase.h">
<Filter>base</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\Color.h">
<Filter>renderer</Filter>
@ -297,9 +258,51 @@
<ClInclude Include="..\src\kiwano\renderer\Font.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\Geometry.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\GifImage.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\Image.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\ImageCache.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\LayerArea.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\Renderer.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\TextLayout.h">
<Filter>renderer</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\win32\ComPtr.hpp">
<Filter>renderer\win32</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\win32\D2DDeviceResources.h">
<Filter>renderer\win32</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\win32\D3D10DeviceResources.h">
<Filter>renderer\win32</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\win32\D3D11DeviceResources.h">
<Filter>renderer\win32</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\win32\D3DDeviceResourcesBase.h">
<Filter>renderer\win32</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\win32\FontCollectionLoader.h">
<Filter>renderer\win32</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\win32\TextRenderer.h">
<Filter>renderer\win32</Filter>
</ClInclude>
<ClInclude Include="..\src\kiwano\renderer\RenderTarget.h">
<Filter>renderer</Filter>
</ClInclude>
</ItemGroup>
<ItemGroup>
<ClCompile Include="..\src\kiwano\ui\Button.cpp">
@ -335,18 +338,6 @@
<ClCompile Include="..\src\kiwano\base\time.cpp">
<Filter>base</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\D2DDeviceResources.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\D3D10DeviceResources.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\D3D11DeviceResources.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\TextRenderer.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\platform\Application.cpp">
<Filter>platform</Filter>
</ClCompile>
@ -359,9 +350,6 @@
<ClCompile Include="..\src\kiwano\base\Input.cpp">
<Filter>base</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\base\Object.cpp">
<Filter>base</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\utils\DataUtil.cpp">
<Filter>utils</Filter>
</ClCompile>
@ -398,12 +386,6 @@
<ClCompile Include="..\src\kiwano\2d\Frame.cpp">
<Filter>2d</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\GifImage.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\Image.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\2d\action\Action.cpp">
<Filter>2d\action</Filter>
</ClCompile>
@ -419,9 +401,6 @@
<ClCompile Include="..\src\kiwano\2d\action\Animation.cpp">
<Filter>2d\action</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\ImageCache.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\utils\ResourceCache.cpp">
<Filter>utils</Filter>
</ClCompile>
@ -434,9 +413,6 @@
<ClCompile Include="..\src\kiwano\2d\ShapeActor.cpp">
<Filter>2d</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\Geometry.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\2d\action\ActionDelay.cpp">
<Filter>2d\action</Filter>
</ClCompile>
@ -449,14 +425,8 @@
<ClCompile Include="..\src\kiwano\base\Window.cpp">
<Filter>base</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\Renderer.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\TextLayout.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\RenderTarget.cpp">
<Filter>renderer</Filter>
<ClCompile Include="..\src\kiwano\base\ObjectBase.cpp">
<Filter>base</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\Color.cpp">
<Filter>renderer</Filter>
@ -464,8 +434,44 @@
<ClCompile Include="..\src\kiwano\renderer\Font.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\Geometry.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\GifImage.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\Image.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\ImageCache.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\LayerArea.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\Renderer.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\TextLayout.cpp">
<Filter>renderer</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\win32\D2DDeviceResources.cpp">
<Filter>renderer\win32</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\win32\D3D10DeviceResources.cpp">
<Filter>renderer\win32</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\win32\D3D11DeviceResources.cpp">
<Filter>renderer\win32</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\win32\FontCollectionLoader.cpp">
<Filter>renderer\win32</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\win32\TextRenderer.cpp">
<Filter>renderer\win32</Filter>
</ClCompile>
<ClCompile Include="..\src\kiwano\renderer\RenderTarget.cpp">
<Filter>renderer</Filter>
</ClCompile>
</ItemGroup>
</Project>

View File

@ -20,7 +20,7 @@
#pragma once
#include <kiwano/core/intrusive_ptr.hpp>
#include <kiwano/base/Object.h>
#include <kiwano/base/ObjectBase.h>
#include "Sound.h"
namespace kiwano
@ -31,7 +31,7 @@ namespace kiwano
// 音乐播放器
class KGE_API Player
: protected Object
: protected ObjectBase
{
using MusicMap = Map<size_t, SoundPtr>;

View File

@ -20,7 +20,7 @@
#pragma once
#include <kiwano/core/intrusive_ptr.hpp>
#include <kiwano/base/Object.h>
#include <kiwano/base/ObjectBase.h>
#include <kiwano/base/Resource.h>
#include <xaudio2.h>
@ -32,7 +32,7 @@ namespace kiwano
// 音乐对象
class KGE_API Sound
: public Object
: public ObjectBase
{
public:
Sound();

View File

@ -24,9 +24,9 @@
#include <kiwano/macros.h>
#include <kiwano/core/string.hpp>
#include <kiwano/base/ComPtr.hpp>
#include <kiwano/base/Resource.h>
#include <kiwano/base/Logger.h>
#include <kiwano/renderer/win32/ComPtr.hpp>
#include <kiwano/platform/modules.h>
#include "audio-modules.h"
#include "Transcoder.h"

View File

@ -21,7 +21,7 @@
#pragma once
#include <kiwano/core/Function.hpp>
#include <kiwano/core/basic_json.hpp>
#include <kiwano/base/Object.h>
#include <kiwano/base/ObjectBase.h>
namespace kiwano
{
@ -30,7 +30,7 @@ namespace kiwano
typedef Function<void(HttpRequestPtr, HttpResponsePtr)> ResponseCallback;
class KGE_API HttpRequest
: public Object
: public ObjectBase
{
public:
enum class Type

View File

@ -21,14 +21,14 @@
#pragma once
#include <kiwano/core/Function.hpp>
#include <kiwano/core/basic_json.hpp>
#include <kiwano/base/Object.h>
#include <kiwano/base/ObjectBase.h>
namespace kiwano
{
namespace network
{
class KGE_API HttpResponse
: public Object
: public ObjectBase
{
public:
inline HttpResponse(HttpRequestPtr request)

View File

@ -71,7 +71,7 @@ namespace kiwano
OnUpdate(dt);
}
if (!children_.is_empty())
if (!children_.item_empty())
{
ActorPtr next;
for (auto child = children_.first_item(); child; child = next)
@ -89,7 +89,7 @@ namespace kiwano
UpdateTransform();
if (children_.is_empty())
if (children_.item_empty())
{
OnRender(renderer);
}
@ -407,7 +407,7 @@ namespace kiwano
{
if (!IsName(name))
{
Object::SetName(name);
ObjectBase::SetName(name);
hash_name_ = std::hash<String>{}(name);
}
}
@ -609,7 +609,7 @@ namespace kiwano
{
KGE_ASSERT(child && "Actor::RemoveChild failed, NULL pointer exception");
if (children_.is_empty())
if (children_.item_empty())
return;
if (child)
@ -622,7 +622,7 @@ namespace kiwano
void Actor::RemoveChildren(String const& child_name)
{
if (children_.is_empty())
if (children_.item_empty())
{
return;
}

View File

@ -32,7 +32,7 @@ namespace kiwano
// ½ÇÉ«
class KGE_API Actor
: public Object
: public ObjectBase
, public TimerManager
, public ActionManager
, public EventDispatcher

View File

@ -82,9 +82,9 @@ namespace kiwano
ss << "Fps: " << frame_time_.size() << std::endl;
#if defined(KGE_DEBUG)
if (Object::IsTracingLeaks())
if (ObjectBase::IsTracingLeaks())
{
ss << "Objects: " << Object::__GetTracingObjects().size() << std::endl;
ss << "Objects: " << ObjectBase::__GetTracingObjects().size() << std::endl;
}
#endif

View File

@ -25,7 +25,7 @@ namespace kiwano
{
// ֡ͼÏñ
class KGE_API Frame
: public Object
: public ObjectBase
{
public:
Frame();

View File

@ -25,7 +25,7 @@ namespace kiwano
{
// ÐòÁÐÖ¡
class KGE_API FrameSequence
: public Object
: public ObjectBase
{
public:
FrameSequence();

View File

@ -29,7 +29,7 @@ namespace kiwano
// 舞台过渡
class KGE_API Transition
: public Object
: public ObjectBase
{
friend class Director;

View File

@ -28,7 +28,7 @@ namespace kiwano
class ActionManager;
class KGE_API Action
: public Object
: public ObjectBase
, protected intrusive_list_item<ActionPtr>
{
friend class ActionManager;

View File

@ -45,7 +45,7 @@ namespace kiwano
void ActionGroup::Init(ActorPtr target)
{
if (actions_.is_empty())
if (actions_.item_empty())
{
Done();
return;
@ -135,7 +135,7 @@ namespace kiwano
ActionPtr ActionGroup::Reverse() const
{
auto group = new (std::nothrow) ActionGroup();
if (group && !actions_.is_empty())
if (group && !actions_.item_empty())
{
for (auto action = actions_.last_item(); action; action = action->prev_item())
{

View File

@ -26,7 +26,7 @@ namespace kiwano
{
void ActionManager::UpdateActions(ActorPtr target, Duration dt)
{
if (actions_.is_empty() || !target)
if (actions_.item_empty() || !target)
return;
ActionPtr next;
@ -55,7 +55,7 @@ namespace kiwano
ActionPtr ActionManager::GetAction(String const & name)
{
if (actions_.is_empty())
if (actions_.item_empty())
return nullptr;
for (auto action = actions_.first_item().get(); action; action = action->next_item().get())
@ -66,7 +66,7 @@ namespace kiwano
void ActionManager::ResumeAllActions()
{
if (actions_.is_empty())
if (actions_.item_empty())
return;
for (auto action = actions_.first_item().get(); action; action = action->next_item().get())
@ -77,7 +77,7 @@ namespace kiwano
void ActionManager::PauseAllActions()
{
if (actions_.is_empty())
if (actions_.item_empty())
return;
for (auto action = actions_.first_item().get(); action; action = action->next_item().get())
@ -88,7 +88,7 @@ namespace kiwano
void ActionManager::StopAllActions()
{
if (actions_.is_empty())
if (actions_.item_empty())
return;
for (auto action = actions_.first_item().get(); action; action = action->next_item().get())

View File

@ -23,10 +23,9 @@
#include "../base/time.h"
#include "../base/RefCounter.hpp"
#include "../base/SmartPtr.hpp"
#include "../base/ComPtr.hpp"
#include "../base/Object.h"
#include "../base/ObjectBase.h"
#include "../base/types.h"
#include "../math/helper.h"
#include "../math/math.h"
#include "../renderer/Color.h"
namespace kiwano

View File

@ -19,7 +19,7 @@
// THE SOFTWARE.
#pragma once
#include "Object.h"
#include "ObjectBase.h"
#include <thread>
#include <mutex>
@ -31,7 +31,7 @@ namespace kiwano
typedef Function<void()> AsyncTaskCallback;
class AsyncTask
: public Object
: public ObjectBase
{
public:
AsyncTask();

View File

@ -25,7 +25,7 @@ namespace kiwano
{
void EventDispatcher::Dispatch(Event& evt)
{
if (listeners_.is_empty())
if (listeners_.item_empty())
return;
EventListenerPtr next;

View File

@ -21,7 +21,7 @@
#pragma once
#include "../core/core.h"
#include "../base/SmartPtr.hpp"
#include "Object.h"
#include "ObjectBase.h"
#include "Event.hpp"
namespace kiwano
@ -34,7 +34,7 @@ namespace kiwano
// 事件监听器
class KGE_API EventListener
: public Object
: public ObjectBase
, protected intrusive_list_item<EventListenerPtr>
{
friend class EventDispatcher;

View File

@ -21,7 +21,7 @@
#pragma once
#include "../macros.h"
#include "../core/core.h"
#include "../math/helper.h"
#include "../math/math.h"
#include "keys.hpp"
#include "Component.h"

View File

@ -18,7 +18,7 @@
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.
#include "Object.h"
#include "ObjectBase.h"
#include "Logger.h"
#include <typeinfo>
@ -27,12 +27,12 @@ namespace kiwano
namespace
{
bool tracing_leaks = false;
Vector<Object*> tracing_objects;
Vector<ObjectBase*> tracing_objects;
}
unsigned int Object::last_object_id = 0;
unsigned int ObjectBase::last_object_id = 0;
Object::Object()
ObjectBase::ObjectBase()
: tracing_leak_(false)
, user_data_(nullptr)
, name_(nullptr)
@ -40,34 +40,34 @@ namespace kiwano
{
#ifdef KGE_DEBUG
Object::__AddObjectToTracingList(this);
ObjectBase::__AddObjectToTracingList(this);
#endif
}
Object::~Object()
ObjectBase::~ObjectBase()
{
if (name_)
delete name_;
#ifdef KGE_DEBUG
Object::__RemoveObjectFromTracingList(this);
ObjectBase::__RemoveObjectFromTracingList(this);
#endif
}
void * Object::GetUserData() const
void * ObjectBase::GetUserData() const
{
return user_data_;
}
void Object::SetUserData(void * data)
void ObjectBase::SetUserData(void * data)
{
user_data_ = data;
}
void Object::SetName(String const & name)
void ObjectBase::SetName(String const & name)
{
if (IsName(name))
return;
@ -88,29 +88,29 @@ namespace kiwano
*name_ = name;
}
String Object::DumpObject()
String ObjectBase::DumpObject()
{
String name = kiwano::string_to_wide(typeid(*this).name());
return String::format(L"{ class=\"%s\" id=%d refcount=%d name=\"%s\" }",
name.c_str(), GetObjectID(), GetRefCount(), GetName().c_str());
}
bool Object::IsTracingLeaks()
bool ObjectBase::IsTracingLeaks()
{
return tracing_leaks;
}
void Object::StartTracingLeaks()
void ObjectBase::StartTracingLeaks()
{
tracing_leaks = true;
}
void Object::StopTracingLeaks()
void ObjectBase::StopTracingLeaks()
{
tracing_leaks = false;
}
void Object::DumpTracingObjects()
void ObjectBase::DumpTracingObjects()
{
KGE_LOG(L"-------------------------- All Objects --------------------------");
for (const auto object : tracing_objects)
@ -120,12 +120,12 @@ namespace kiwano
KGE_LOG(L"------------------------- Total size: %d -------------------------", tracing_objects.size());
}
Vector<Object*>& kiwano::Object::__GetTracingObjects()
Vector<ObjectBase*>& kiwano::ObjectBase::__GetTracingObjects()
{
return tracing_objects;
}
void Object::__AddObjectToTracingList(Object * obj)
void ObjectBase::__AddObjectToTracingList(ObjectBase * obj)
{
#ifdef KGE_DEBUG
@ -138,7 +138,7 @@ namespace kiwano
#endif
}
void Object::__RemoveObjectFromTracingList(Object * obj)
void ObjectBase::__RemoveObjectFromTracingList(ObjectBase * obj)
{
#ifdef KGE_DEBUG

View File

@ -26,15 +26,15 @@
namespace kiwano
{
KGE_DECLARE_SMART_PTR(Object);
KGE_DECLARE_SMART_PTR(ObjectBase);
class KGE_API Object
class KGE_API ObjectBase
: public RefCounter
{
public:
Object();
ObjectBase();
virtual ~Object();
virtual ~ObjectBase();
void* GetUserData() const;
@ -60,11 +60,11 @@ namespace kiwano
static void DumpTracingObjects();
public:
static Vector<Object*>& __GetTracingObjects();
static Vector<ObjectBase*>& __GetTracingObjects();
static void __AddObjectToTracingList(Object*);
static void __AddObjectToTracingList(ObjectBase*);
static void __RemoveObjectFromTracingList(Object*);
static void __RemoveObjectFromTracingList(ObjectBase*);
private:
bool tracing_leak_;

View File

@ -25,7 +25,7 @@ namespace kiwano
{
Resource::Resource(LPCWSTR file_name)
: type_(Type::File)
, bin_name_(nullptr)
, bin_id_(0)
, bin_type_(nullptr)
{
if (file_name)
@ -34,16 +34,16 @@ namespace kiwano
Resource::Resource(String const& file_name)
: type_(Type::File)
, bin_name_(nullptr)
, bin_id_(0)
, bin_type_(nullptr)
{
if (!file_name.empty())
file_name_ = new (std::nothrow) String(file_name);
}
Resource::Resource(LPCWSTR name, LPCWSTR type)
Resource::Resource(UINT id, LPCWSTR type)
: type_(Type::Binary)
, bin_name_(name)
, bin_id_(id)
, bin_type_(type)
{
}
@ -61,9 +61,7 @@ namespace kiwano
size_t Resource::GetHashCode() const
{
if (type_ == Type::File)
return GetFileName().hash();
return std::hash<LPCWSTR>{}(bin_name_);
return (type_ == Type::File) ? GetFileName().hash() : static_cast<size_t>(bin_id_);
}
Resource & Resource::operator=(Resource const & rhs)
@ -86,7 +84,7 @@ namespace kiwano
}
else
{
bin_name_ = rhs.bin_name_;
bin_id_ = rhs.bin_id_;
bin_type_ = rhs.bin_type_;
}
}
@ -104,7 +102,7 @@ namespace kiwano
HGLOBAL res_data;
HRSRC res_info;
res_info = FindResourceW(nullptr, bin_name_, bin_type_);
res_info = FindResourceW(nullptr, MAKEINTRESOURCE(bin_id_), bin_type_);
if (res_info == nullptr)
{
KGE_ERROR_LOG(L"FindResource failed");

View File

@ -28,7 +28,7 @@ namespace kiwano
//
// 资源可以是文件类型,也可以是保存在 exe 中的二进制资源
// 例如, 一份音频资源的类型为 L"WAVE", 名称标识符为 IDR_WAVE_1,
// 那么可以这样指定该资源: Resource res(MAKEINTRESOURCE(IDR_WAVE_1), L"WAVE");
// 那么可以这样指定该资源: Resource res(IDR_WAVE_1, L"WAVE");
//
// 了解资源的更多信息: https://docs.microsoft.com/en-us/windows/desktop/menurc/resources
//
@ -46,7 +46,7 @@ namespace kiwano
);
Resource(
LPCWSTR name, /* 资源名称 */
UINT id, /* 资源名称 */
LPCWSTR type /* 资源类型 */
);
@ -56,19 +56,20 @@ namespace kiwano
virtual ~Resource();
inline bool IsFileType() const { return type_ == Type::File; }
inline String GetFileName() const { if (file_name_) return *file_name_; return String(); }
bool Load(
LPVOID& buffer,
DWORD& buffer_size
) const;
bool Load(LPVOID& buffer, DWORD& buffer_size) const;
size_t GetHashCode() const;
Resource& operator= (Resource const& rhs);
inline bool IsFileType() const { return type_ == Type::File; }
inline String GetFileName() const { return file_name_ ? (*file_name_) : L""; }
inline UINT GetResourceId() const { return bin_id_; }
inline LPCWSTR GetResourceType() const { return bin_type_; }
private:
Type type_;
union
@ -80,7 +81,7 @@ namespace kiwano
struct
{
LPCWSTR bin_name_;
UINT bin_id_;
LPCWSTR bin_type_;
};
};

View File

@ -19,7 +19,7 @@
// THE SOFTWARE.
#pragma once
#include "Object.h"
#include "ObjectBase.h"
#include "time.h"
#include <functional>
@ -31,7 +31,7 @@ namespace kiwano
// 定时任务
class KGE_API Timer
: public Object
: public ObjectBase
, protected intrusive_list_item<TimerPtr>
{
friend class TimerManager;

View File

@ -25,7 +25,7 @@ namespace kiwano
{
void TimerManager::UpdateTimers(Duration dt)
{
if (timers_.is_empty())
if (timers_.item_empty())
return;
TimerPtr next;
@ -54,7 +54,7 @@ namespace kiwano
void TimerManager::StopTimers(String const& name)
{
if (timers_.is_empty())
if (timers_.item_empty())
return;
for (auto timer = timers_.first_item().get(); timer; timer = timer->next_item().get())
@ -68,7 +68,7 @@ namespace kiwano
void TimerManager::StartTimers(String const& name)
{
if (timers_.is_empty())
if (timers_.item_empty())
return;
for (auto timer = timers_.first_item().get(); timer; timer = timer->next_item().get())
@ -82,7 +82,7 @@ namespace kiwano
void TimerManager::RemoveTimers(String const& name)
{
if (timers_.is_empty())
if (timers_.item_empty())
return;
TimerPtr next;
@ -98,7 +98,7 @@ namespace kiwano
void TimerManager::StopAllTimers()
{
if (timers_.is_empty())
if (timers_.item_empty())
return;
for (auto timer = timers_.first_item().get(); timer; timer = timer->next_item().get())
@ -109,7 +109,7 @@ namespace kiwano
void TimerManager::StartAllTimers()
{
if (timers_.is_empty())
if (timers_.item_empty())
return;
for (auto timer = timers_.first_item().get(); timer; timer = timer->next_item().get())

View File

@ -21,7 +21,7 @@
#pragma once
#include "../macros.h"
#include "../core/core.h"
#include "../math/helper.h"
#include "../math/math.h"
#include "types.h"
namespace kiwano

View File

@ -21,7 +21,7 @@
#pragma once
#include "../macros.h"
#include "../core/core.h"
#include "../math/helper.h"
#include "../math/math.h"
#include "types.h"
namespace kiwano

View File

@ -82,7 +82,7 @@ public:
T& last_item() { return last_; }
bool is_empty() const { return !first_; }
bool item_empty() const { return !first_; }
void push_back_item(T const& child)
{

View File

@ -64,11 +64,9 @@
#include "renderer/Image.h"
#include "renderer/GifImage.h"
#include "renderer/TextLayout.h"
#include "renderer/TextRenderer.h"
#include "renderer/Geometry.h"
#include "renderer/LayerArea.h"
#include "renderer/ImageCache.h"
#include "renderer/RenderTarget.h"
#include "renderer/Renderer.h"
@ -81,11 +79,8 @@
#include "base/input.h"
#include "base/Director.h"
#include "base/Logger.h"
#include "base/SmartPtr.hpp"
#include "base/ComPtr.hpp"
#include "base/Object.h"
#include "base/ObjectBase.h"
#include "base/Event.hpp"
#include "base/EventListener.h"
#include "base/EventDispatcher.h"

View File

@ -99,7 +99,7 @@ namespace kiwano
inline value_type GetBottom() const { return origin.y + size.y; }
inline bool is_empty() const { return origin.IsOrigin() && size.IsOrigin(); }
inline bool IsEmpty() const { return origin.IsOrigin() && size.IsOrigin(); }
inline bool ContainsPoint(const Vec2T<value_type>& point) const
{

View File

@ -24,6 +24,7 @@
#include "../base/Logger.h"
#include "../base/input.h"
#include "../base/Director.h"
#include "../renderer/ImageCache.h"
#include "../renderer/Renderer.h"
#include "../utils/ResourceCache.h"
#include <windowsx.h> // GET_X_LPARAM, GET_Y_LPARAM
@ -147,8 +148,10 @@ namespace kiwano
void Application::Destroy()
{
// Clear all stages
// Clear all resources
Director::GetInstance()->ClearStages();
ResourceCache::GetInstance()->Clear();
ImageCache::GetInstance()->Clear();
if (inited_)
{
@ -164,6 +167,7 @@ namespace kiwano
// Destroy all instances
Director::DestroyInstance();
ResourceCache::DestroyInstance();
ImageCache::DestroyInstance();
Input::DestroyInstance();
Renderer::DestroyInstance();
Window::DestroyInstance();

View File

@ -1,90 +0,0 @@
// Copyright (c) 2016-2018 Kiwano - Nomango
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.
#pragma once
#include "helper.hpp"
#include "Font.h"
#include "../base/Resource.h"
#include "../2d/TextStyle.hpp"
#include <dwrite.h>
#include <d2d1.h>
#include <d2d1_1.h>
namespace kiwano
{
MIDL_INTERFACE("5706684a-bf6d-4b03-b627-094758a33032")
KGE_API ID2DDeviceResources
: public IUnknown
{
public:
static HRESULT Create(ID2DDeviceResources** device_resources);
virtual HRESULT CreateBitmapFromFile(
_Out_ ComPtr<ID2D1Bitmap>& bitmap,
_In_ String const& file_path
) = 0;
virtual HRESULT CreateBitmapFromResource(
_Out_ ComPtr<ID2D1Bitmap>& bitmap,
_In_ Resource const& res
) = 0;
virtual HRESULT CreateTextFormat(
_Out_ ComPtr<IDWriteTextFormat>& text_format,
_In_ Font const& font
) const = 0;
virtual HRESULT CreateTextLayout(
_Out_ ComPtr<IDWriteTextLayout>& text_layout,
_In_ String const& text,
_In_ TextStyle const& text_style,
_In_ ComPtr<IDWriteTextFormat> const& text_format
) const = 0;
virtual ID2D1StrokeStyle* GetStrokeStyle(StrokeStyle stroke) const = 0;
virtual HRESULT SetD2DDevice(
_In_ ComPtr<ID2D1Device> const& device
) = 0;
virtual void SetTargetBitmap(
_In_ ComPtr<ID2D1Bitmap1> const& target
) = 0;
virtual void DiscardResources() = 0;
inline ID2D1Factory1* GetFactory() const { KGE_ASSERT(factory_); return factory_.get(); }
inline IWICImagingFactory* GetWICImagingFactory() const { KGE_ASSERT(imaging_factory_); return imaging_factory_.get(); }
inline IDWriteFactory* GetDWriteFactory() const { KGE_ASSERT(dwrite_factory_); return dwrite_factory_.get(); }
inline ID2D1Device* GetDevice() const { KGE_ASSERT(device_); return device_.get(); }
inline ID2D1DeviceContext* GetDeviceContext() const { KGE_ASSERT(device_context_); return device_context_.get(); }
inline ID2D1Bitmap1* GetTargetBitmap() const { KGE_ASSERT(target_bitmap_); return target_bitmap_.get(); }
protected:
ComPtr<ID2D1Factory1> factory_;
ComPtr<ID2D1Device> device_;
ComPtr<ID2D1DeviceContext> device_context_;
ComPtr<ID2D1Bitmap1> target_bitmap_;
ComPtr<IWICImagingFactory> imaging_factory_;
ComPtr<IDWriteFactory> dwrite_factory_;
};
}

View File

@ -19,14 +19,41 @@
// THE SOFTWARE.
#include "Font.h"
#include "Renderer.h"
namespace kiwano
{
Font::Font(const String& family, float size, unsigned int weight, bool italic)
//
// FontCollection
//
FontCollection::FontCollection()
{
}
FontCollection::FontCollection(Resource const& res)
{
Load(res);
}
bool FontCollection::Load(Resource const& res)
{
Renderer::GetInstance()->CreateFontFromResource(*this, res);
return false;
}
//
// Font
//
Font::Font(const String& family, float size, unsigned int weight, bool italic, FontCollection collection)
: family(family)
, size(size)
, weight(weight)
, italic(italic)
, collection(collection)
{
}
}

View File

@ -20,6 +20,9 @@
#pragma once
#include "../core/core.h"
#include "../base/Resource.h"
#include "win32/ComPtr.hpp"
#include <dwrite.h>
namespace kiwano
{
@ -37,6 +40,28 @@ namespace kiwano
ExtraBlack = 950
};
// ×ÖÌ弯
class FontCollection
{
public:
FontCollection();
FontCollection(Resource const& res);
// ´Ó×ÊÔ´¼ÓÔØ×ÖÌ弯
bool Load(Resource const& res);
public:
inline ComPtr<IDWriteFontCollection> GetFontCollection() const { return collection_; }
inline void SetFontCollection(ComPtr<IDWriteFontCollection> collection) { collection_ = collection; }
protected:
ComPtr<IDWriteFontCollection> collection_;
};
// 字体
class Font
{
@ -45,13 +70,15 @@ namespace kiwano
float size; // 字号
unsigned int weight; // 粗细值
bool italic; // 是否斜体
FontCollection collection; // ×ÖÌ弯
public:
Font(
const String& family = L"",
float size = 18,
unsigned int weight = FontWeight::Normal,
bool italic = false
const String& family = L"",
float size = 18,
unsigned int weight = FontWeight::Normal,
bool italic = false,
FontCollection collection = FontCollection()
);
};
}

View File

@ -19,8 +19,7 @@
// THE SOFTWARE.
#pragma once
#include "../base/SmartPtr.hpp"
#include "D2DDeviceResources.h"
#include "win32/D2DDeviceResources.h"
namespace kiwano
{

View File

@ -26,7 +26,7 @@ namespace kiwano
// GIF ͼÏñ
KGE_DECLARE_SMART_PTR(GifImage);
class KGE_API GifImage
: public Object
: public ObjectBase
{
public:
GifImage();

View File

@ -19,8 +19,7 @@
// THE SOFTWARE.
#pragma once
#include "../base/Resource.h"
#include "D2DDeviceResources.h" // ID2D1Bitmap
#include "win32/D2DDeviceResources.h"
namespace kiwano
{

View File

@ -19,7 +19,6 @@
// THE SOFTWARE.
#pragma once
#include "../core/singleton.hpp"
#include "Image.h"
#include "GifImage.h"

View File

@ -19,7 +19,6 @@
// THE SOFTWARE.
#pragma once
#include "D2DDeviceResources.h"
#include "Geometry.h"
namespace kiwano

View File

@ -19,12 +19,12 @@
// THE SOFTWARE.
#pragma once
#include "D2DDeviceResources.h"
#include "../base/time.h"
#include "Image.h"
#include "Geometry.h"
#include "TextLayout.h"
#include "TextRenderer.h"
#include "LayerArea.h"
#include "win32/TextRenderer.h"
namespace kiwano
{
@ -168,9 +168,9 @@ namespace kiwano
void IncreasePrimitivesCount() const;
inline Status const& GetStatus() const { return status_; }
inline Status const& GetStatus() const { return status_; }
inline ComPtr<ID2D1RenderTarget> GetRenderTarget() const { return render_target_; }
inline ComPtr<ID2D1RenderTarget> GetRenderTarget() const { return render_target_; }
public:
RenderTarget();

View File

@ -41,52 +41,97 @@ namespace kiwano
KGE_LOG(L"Creating device resources");
hwnd_ = Window::GetInstance()->GetHandle();
output_size_ = Window::GetInstance()->GetSize();
ThrowIfFailed(hwnd_ ? S_OK : E_FAIL);
d2d_res_ = nullptr;
d3d_res_ = nullptr;
drawing_state_block_ = nullptr;
ThrowIfFailed(
ID2DDeviceResources::Create(
&d2d_res_
)
);
HRESULT hr = hwnd_ ? S_OK : E_FAIL;
ThrowIfFailed(
// Direct2D device resources
if (SUCCEEDED(hr))
{
hr = ID2DDeviceResources::Create(&d2d_res_);
}
// Direct3D device resources
if (SUCCEEDED(hr))
{
#if defined(KGE_USE_DIRECTX10)
ID3D10DeviceResources::Create(
hr = ID3D10DeviceResources::Create(
&d3d_res_,
d2d_res_.get(),
hwnd_
)
);
#else
ID3D11DeviceResources::Create(
hr = ID3D11DeviceResources::Create(
&d3d_res_,
d2d_res_.get(),
hwnd_
)
);
#endif
);
}
ThrowIfFailed(
d2d_res_->GetFactory()->CreateDrawingStateBlock(
// DrawingStateBlock
if (SUCCEEDED(hr))
{
hr = d2d_res_->GetFactory()->CreateDrawingStateBlock(
&drawing_state_block_
)
);
);
}
ThrowIfFailed(
CreateDeviceResources()
);
// Other device resources
if (SUCCEEDED(hr))
{
hr = CreateDeviceResources();
}
output_size_ = Window::GetInstance()->GetSize();
// FontFileLoader and FontCollectionLoader
if (SUCCEEDED(hr))
{
hr = IFontCollectionLoader::Create(&font_collection_loader_);
}
if (SUCCEEDED(hr))
{
hr = d2d_res_->GetDWriteFactory()->RegisterFontCollectionLoader(font_collection_loader_.get());
}
// ResourceFontFileLoader and ResourceFontCollectionLoader
if (SUCCEEDED(hr))
{
hr = IResourceFontFileLoader::Create(&res_font_file_loader_);
}
if (SUCCEEDED(hr))
{
hr = d2d_res_->GetDWriteFactory()->RegisterFontFileLoader(res_font_file_loader_.get());
}
if (SUCCEEDED(hr))
{
hr = IResourceFontCollectionLoader::Create(&res_font_collection_loader_, res_font_file_loader_.get());
}
if (SUCCEEDED(hr))
{
hr = d2d_res_->GetDWriteFactory()->RegisterFontCollectionLoader(res_font_collection_loader_.get());
}
ThrowIfFailed(hr);
}
void Renderer::DestroyComponent()
{
KGE_LOG(L"Destroying device resources");
d2d_res_->GetDWriteFactory()->UnregisterFontFileLoader(res_font_file_loader_.get());
res_font_file_loader_.reset();
d2d_res_->GetDWriteFactory()->UnregisterFontCollectionLoader(res_font_collection_loader_.get());
res_font_collection_loader_.reset();
drawing_state_block_.reset();
solid_color_brush_.reset();
d2d_res_.reset();
@ -287,6 +332,53 @@ namespace kiwano
}
}
void Renderer::CreateFontFromResource(FontCollection& collection, Resource const& res)
{
HRESULT hr = S_OK;
if (!d2d_res_)
{
hr = E_UNEXPECTED;
}
ComPtr<IDWriteFontCollection> font_collection;
if (res.IsFileType())
{
String file_path = res.GetFileName();
if (!FileUtil::ExistsFile(file_path.c_str()))
{
KGE_WARNING_LOG(L"Font file '%s' not found!", file_path.c_str());
hr = E_FAIL;
}
hr = d2d_res_->GetDWriteFactory()->CreateCustomFontCollection(
font_collection_loader_.get(),
reinterpret_cast<const void*>(&file_path),
sizeof(file_path),
&font_collection
);
}
else
{
UINT id = res.GetResourceId();
hr = d2d_res_->GetDWriteFactory()->CreateCustomFontCollection(
res_font_collection_loader_.get(),
reinterpret_cast<const void*>(&id),
sizeof(id),
&font_collection
);
}
if (SUCCEEDED(hr))
{
collection.SetFontCollection(font_collection);
}
if (FAILED(hr))
{
KGE_WARNING_LOG(L"Load font failed with HRESULT of %08X!", hr);
}
}
void Renderer::CreateTextFormat(TextFormat& format, Font const& font)
{
HRESULT hr = S_OK;

View File

@ -19,18 +19,15 @@
// THE SOFTWARE.
#pragma once
#include "../base/time.h"
#include "../base/Component.h"
#include "../base/Resource.h"
#include "../2d/include-forwards.h"
#include "helper.hpp"
#include "win32/FontCollectionLoader.h"
#include "RenderTarget.h"
#include "GifImage.h"
#if defined(KGE_USE_DIRECTX10)
# include "D3D10DeviceResources.h"
#else
# include "D3D11DeviceResources.h"
# include "win32/D3D11DeviceResources.h"
#endif
namespace kiwano
@ -71,6 +68,11 @@ namespace kiwano
Resource const& res
);
void CreateFontFromResource(
FontCollection& collection,
Resource const& res
);
void CreateTextFormat(
TextFormat& format,
Font const& font
@ -166,5 +168,9 @@ namespace kiwano
ComPtr<ID2DDeviceResources> d2d_res_;
ComPtr<ID3DDeviceResources> d3d_res_;
ComPtr<ID2D1DrawingStateBlock> drawing_state_block_;
ComPtr<IFontCollectionLoader> font_collection_loader_;
ComPtr<IResourceFontFileLoader> res_font_file_loader_;
ComPtr<IResourceFontCollectionLoader> res_font_collection_loader_;
};
}

View File

@ -19,7 +19,6 @@
// THE SOFTWARE.
#pragma once
#include "D2DDeviceResources.h"
#include "Font.h"
#include "../2d/TextStyle.hpp"

View File

@ -19,7 +19,7 @@
// THE SOFTWARE.
#pragma once
#include "../core/intrusive_ptr.hpp"
#include "../../core/intrusive_ptr.hpp"
#include <Unknwnbase.h>
#include <type_traits>

View File

@ -19,9 +19,8 @@
// THE SOFTWARE.
#include "D2DDeviceResources.h"
#include "ImageCache.h"
#include "../base/Logger.h"
#include "../utils/FileUtil.h"
#include "../../base/Logger.h"
#include "../../utils/FileUtil.h"
#pragma comment(lib, "d2d1.lib")
#pragma comment(lib, "dwrite.lib")
@ -108,7 +107,10 @@ namespace kiwano
{
res->AddRef();
DX::SafeRelease(*device_resources);
if (*device_resources)
{
(*device_resources)->Release();
}
(*device_resources) = res;
}
else
@ -172,8 +174,6 @@ namespace kiwano
void D2DDeviceResources::DiscardResources()
{
ImageCache::GetInstance()->Clear();
factory_.reset();
device_.reset();
device_context_.reset();
@ -191,9 +191,9 @@ namespace kiwano
{
HRESULT hr = S_OK;
ComPtr<ID2D1Factory1> d2d_factory;
ComPtr<IWICImagingFactory> imaging_factory;
ComPtr<IDWriteFactory> dwrite_factory;
ComPtr<ID2D1Factory1> d2d_factory;
ComPtr<IWICImagingFactory> imaging_factory;
ComPtr<IDWriteFactory> dwrite_factory;
D2D1_FACTORY_OPTIONS options;
ZeroMemory(&options, sizeof(D2D1_FACTORY_OPTIONS));
@ -236,9 +236,9 @@ namespace kiwano
{
dwrite_factory_ = dwrite_factory;
ComPtr<ID2D1StrokeStyle> d2d_miter_stroke_style;
ComPtr<ID2D1StrokeStyle> d2d_bevel_stroke_style;
ComPtr<ID2D1StrokeStyle> d2d_round_stroke_style;
ComPtr<ID2D1StrokeStyle> d2d_miter_stroke_style;
ComPtr<ID2D1StrokeStyle> d2d_bevel_stroke_style;
ComPtr<ID2D1StrokeStyle> d2d_round_stroke_style;
D2D1_STROKE_STYLE_PROPERTIES stroke_style = D2D1::StrokeStyleProperties(
D2D1_CAP_STYLE_FLAT,
@ -466,12 +466,12 @@ namespace kiwano
ComPtr<IDWriteTextFormat> output;
HRESULT hr = dwrite_factory_->CreateTextFormat(
font.family.c_str(),
nullptr,
font.collection.GetFontCollection().get(),
DWRITE_FONT_WEIGHT(font.weight),
font.italic ? DWRITE_FONT_STYLE_ITALIC : DWRITE_FONT_STYLE_NORMAL,
DWRITE_FONT_STRETCH_NORMAL,
font.size,
L"",
L"en-us",
&output
);

View File

@ -19,10 +19,14 @@
// THE SOFTWARE.
#pragma once
#include "../base/ComPtr.hpp"
#include "../math/helper.h"
#include "Color.h"
#include "../Font.h"
#include "../Color.h"
#include "../../math/math.h"
#include "../../base/Resource.h"
#include "../../2d/TextStyle.hpp"
#include <dwrite.h>
#include <d2d1.h>
#include <d2d1_1.h>
namespace kiwano
{
@ -38,6 +42,16 @@ namespace kiwano
}
}
template <typename T>
inline T* SafeAcquire(T* ptr)
{
if (ptr != nullptr)
{
ptr->AddRef();
}
return ptr;
}
//
// Point2F
//
@ -150,3 +164,65 @@ namespace kiwano
}
}
}
namespace kiwano
{
MIDL_INTERFACE("5706684a-bf6d-4b03-b627-094758a33032")
KGE_API ID2DDeviceResources
: public IUnknown
{
public:
static HRESULT Create(ID2DDeviceResources** device_resources);
virtual HRESULT CreateBitmapFromFile(
_Out_ ComPtr<ID2D1Bitmap>& bitmap,
_In_ String const& file_path
) = 0;
virtual HRESULT CreateBitmapFromResource(
_Out_ ComPtr<ID2D1Bitmap>& bitmap,
_In_ Resource const& res
) = 0;
virtual HRESULT CreateTextFormat(
_Out_ ComPtr<IDWriteTextFormat>& text_format,
_In_ Font const& font
) const = 0;
virtual HRESULT CreateTextLayout(
_Out_ ComPtr<IDWriteTextLayout>& text_layout,
_In_ String const& text,
_In_ TextStyle const& text_style,
_In_ ComPtr<IDWriteTextFormat> const& text_format
) const = 0;
virtual ID2D1StrokeStyle* GetStrokeStyle(StrokeStyle stroke) const = 0;
virtual HRESULT SetD2DDevice(
_In_ ComPtr<ID2D1Device> const& device
) = 0;
virtual void SetTargetBitmap(
_In_ ComPtr<ID2D1Bitmap1> const& target
) = 0;
virtual void DiscardResources() = 0;
inline ID2D1Factory1* GetFactory() const { KGE_ASSERT(factory_); return factory_.get(); }
inline IWICImagingFactory* GetWICImagingFactory() const { KGE_ASSERT(imaging_factory_); return imaging_factory_.get(); }
inline IDWriteFactory* GetDWriteFactory() const { KGE_ASSERT(dwrite_factory_); return dwrite_factory_.get(); }
inline ID2D1Device* GetDevice() const { KGE_ASSERT(device_); return device_.get(); }
inline ID2D1DeviceContext* GetDeviceContext() const { KGE_ASSERT(device_context_); return device_context_.get(); }
inline ID2D1Bitmap1* GetTargetBitmap() const { KGE_ASSERT(target_bitmap_); return target_bitmap_.get(); }
protected:
ComPtr<ID2D1Factory1> factory_;
ComPtr<ID2D1Device> device_;
ComPtr<ID2D1DeviceContext> device_context_;
ComPtr<ID2D1Bitmap1> target_bitmap_;
ComPtr<IWICImagingFactory> imaging_factory_;
ComPtr<IDWriteFactory> dwrite_factory_;
};
}

View File

@ -20,7 +20,7 @@
#include "D3D10DeviceResources.h"
#include "../base/Logger.h"
#include "../../base/Logger.h"
#pragma comment(lib, "d3d10_1.lib")
@ -163,7 +163,10 @@ namespace kiwano
{
res->AddRef();
DX::SafeRelease(*device_resources);
if (*device_resources)
{
(*device_resources)->Release();
}
(*device_resources) = res;
}
else

View File

@ -20,7 +20,7 @@
#pragma once
#include "../macros.h"
#include "../../macros.h"
#include "D2DDeviceResources.h"
#include "D3DDeviceResourcesBase.h"

View File

@ -20,7 +20,7 @@
#include "D3D11DeviceResources.h"
#include "../base/Logger.h"
#include "../../base/Logger.h"
#include <versionhelpers.h> // IsWindows10OrGreater
#pragma comment(lib, "d3d11.lib")
@ -140,7 +140,10 @@ namespace kiwano
{
res->AddRef();
DX::SafeRelease(*device_resources);
if (*device_resources)
{
(*device_resources)->Release();
}
(*device_resources) = res;
}
else

View File

@ -20,7 +20,7 @@
#pragma once
#include "../macros.h"
#include "../../macros.h"
#include "D2DDeviceResources.h"
#include "D3DDeviceResourcesBase.h"

View File

@ -19,16 +19,12 @@
// THE SOFTWARE.
#pragma once
#include "../macros.h"
#include "../math/helper.h"
#include "Color.h"
#include <Unknwnbase.h>
namespace kiwano
{
MIDL_INTERFACE("fb99fa64-d9cf-4e0e-9c75-90514797b01d")
KGE_API ID3DDeviceResourcesBase : public IUnknown
ID3DDeviceResourcesBase : public IUnknown
{
public:
virtual HRESULT Present(bool vsync) = 0;

View File

@ -0,0 +1,908 @@
// Copyright (c) 2016-2018 Kiwano - Nomango
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// _Out_ OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.
#include "FontCollectionLoader.h"
namespace kiwano
{
////////////////////////////////////////////////////////////////////////////////////////
//
// FontCollectionLoader
//
////////////////////////////////////////////////////////////////////////////////////////
class FontCollectionLoader
: public IFontCollectionLoader
{
public:
FontCollectionLoader()
: refCount_(0)
{
}
// IUnknown methods
virtual HRESULT STDMETHODCALLTYPE QueryInterface(REFIID iid, void** ppvObject);
virtual ULONG STDMETHODCALLTYPE AddRef();
virtual ULONG STDMETHODCALLTYPE Release();
// IDWriteFontCollectionLoader methods
virtual HRESULT STDMETHODCALLTYPE CreateEnumeratorFromKey(
IDWriteFactory* pFactory,
void const* collectionKey,
UINT32 collectionKeySize,
_Out_ IDWriteFontFileEnumerator** fontFileEnumerator
);
private:
ULONG refCount_;
};
HRESULT IFontCollectionLoader::Create(_Out_ IFontCollectionLoader** ppCollectionLoader)
{
HRESULT hr = S_OK;
if (!ppCollectionLoader)
{
hr = E_POINTER;
}
if (SUCCEEDED(hr))
{
FontCollectionLoader* pCollectionLoader = new (std::nothrow) FontCollectionLoader;
hr = pCollectionLoader ? S_OK : E_OUTOFMEMORY;
if (SUCCEEDED(hr))
{
DX::SafeRelease(*ppCollectionLoader);
(*ppCollectionLoader) = DX::SafeAcquire(pCollectionLoader);
}
}
return hr;
}
HRESULT STDMETHODCALLTYPE FontCollectionLoader::QueryInterface(REFIID iid, void** ppvObject)
{
if (iid == IID_IUnknown || iid == __uuidof(IDWriteFontCollectionLoader))
{
*ppvObject = this;
AddRef();
return S_OK;
}
else
{
*ppvObject = NULL;
return E_NOINTERFACE;
}
}
ULONG STDMETHODCALLTYPE FontCollectionLoader::AddRef()
{
return InterlockedIncrement(&refCount_);
}
ULONG STDMETHODCALLTYPE FontCollectionLoader::Release()
{
ULONG newCount = InterlockedDecrement(&refCount_);
if (newCount == 0)
delete this;
return newCount;
}
HRESULT STDMETHODCALLTYPE FontCollectionLoader::CreateEnumeratorFromKey(
IDWriteFactory* pFactory,
void const* collectionKey,
UINT32 collectionKeySize,
_Out_ IDWriteFontFileEnumerator** fontFileEnumerator
)
{
HRESULT hr = S_OK;
if (collectionKey == NULL || collectionKeySize != sizeof(String))
hr = E_INVALIDARG;
if (SUCCEEDED(hr))
{
IFontFileEnumerator* pEnumerator = NULL;
hr = IFontFileEnumerator::Create(&pEnumerator, pFactory);
if (SUCCEEDED(hr))
{
String const* filePath = static_cast<String const*>(collectionKey);
UINT32 const fileCount = collectionKeySize / sizeof(String);
hr = pEnumerator->SetFilePaths(filePath, fileCount);
}
if (SUCCEEDED(hr))
{
*fontFileEnumerator = DX::SafeAcquire(pEnumerator);
}
}
return hr;
}
////////////////////////////////////////////////////////////////////////////////////////
//
// FontFileEnumerator
//
////////////////////////////////////////////////////////////////////////////////////////
class FontFileEnumerator
: public IFontFileEnumerator
{
public:
FontFileEnumerator();
STDMETHOD(Initialize)(
IDWriteFactory* pFactory
);
STDMETHOD(SetFilePaths)(
String const* filePath,
UINT32 const fileCount
);
~FontFileEnumerator()
{
DX::SafeRelease(currentFile_);
DX::SafeRelease(pFactory_);
}
// IUnknown methods
virtual HRESULT STDMETHODCALLTYPE QueryInterface(REFIID iid, _Out_ void** ppvObject);
virtual ULONG STDMETHODCALLTYPE AddRef();
virtual ULONG STDMETHODCALLTYPE Release();
// IDWriteFontFileEnumerator methods
virtual HRESULT STDMETHODCALLTYPE MoveNext(_Out_ BOOL* hasCurrentFile);
virtual HRESULT STDMETHODCALLTYPE GetCurrentFontFile(_Out_ IDWriteFontFile** fontFile);
private:
ULONG refCount_;
IDWriteFactory* pFactory_;
IDWriteFontFile* currentFile_;
Vector<String> filePaths_;
size_t nextIndex_;
};
HRESULT IFontFileEnumerator::Create(_Out_ IFontFileEnumerator** ppEnumerator, IDWriteFactory* pFactory)
{
HRESULT hr = S_OK;
if (!ppEnumerator)
{
hr = E_POINTER;
}
if (SUCCEEDED(hr))
{
FontFileEnumerator* pEnumerator = new (std::nothrow) FontFileEnumerator;
hr = pEnumerator ? S_OK : E_OUTOFMEMORY;
if (SUCCEEDED(hr))
{
hr = pEnumerator->Initialize(pFactory);
}
if (SUCCEEDED(hr))
{
DX::SafeRelease(*ppEnumerator);
(*ppEnumerator) = DX::SafeAcquire(pEnumerator);
}
}
return hr;
}
FontFileEnumerator::FontFileEnumerator()
: refCount_(0)
, pFactory_(NULL)
, currentFile_(NULL)
, nextIndex_(0)
{
}
STDMETHODIMP FontFileEnumerator::Initialize(
IDWriteFactory* pFactory
)
{
if (pFactory)
{
pFactory_ = DX::SafeAcquire(pFactory);
return S_OK;
}
return E_INVALIDARG;
}
STDMETHODIMP FontFileEnumerator::SetFilePaths(
String const* filePath,
UINT32 const fileCount
)
{
try
{
filePaths_.assign(filePath, filePath + fileCount);
}
catch (std::bad_alloc&)
{
return E_OUTOFMEMORY;
}
catch (...)
{
return E_FAIL;
}
return S_OK;
}
HRESULT STDMETHODCALLTYPE FontFileEnumerator::QueryInterface(REFIID iid, _Out_ void** ppvObject)
{
if (iid == IID_IUnknown || iid == __uuidof(IDWriteFontFileEnumerator))
{
*ppvObject = this;
AddRef();
return S_OK;
}
else
{
*ppvObject = NULL;
return E_NOINTERFACE;
}
}
ULONG STDMETHODCALLTYPE FontFileEnumerator::AddRef()
{
return InterlockedIncrement(&refCount_);
}
ULONG STDMETHODCALLTYPE FontFileEnumerator::Release()
{
ULONG newCount = InterlockedDecrement(&refCount_);
if (newCount == 0)
delete this;
return newCount;
}
HRESULT STDMETHODCALLTYPE FontFileEnumerator::MoveNext(_Out_ BOOL* hasCurrentFile)
{
HRESULT hr = S_OK;
*hasCurrentFile = FALSE;
DX::SafeRelease(currentFile_);
if (nextIndex_ < filePaths_.size())
{
hr = pFactory_->CreateFontFileReference(
filePaths_[nextIndex_].c_str(),
NULL,
&currentFile_
);
if (SUCCEEDED(hr))
{
*hasCurrentFile = TRUE;
++nextIndex_;
}
}
return hr;
}
HRESULT STDMETHODCALLTYPE FontFileEnumerator::GetCurrentFontFile(_Out_ IDWriteFontFile** fontFile)
{
*fontFile = DX::SafeAcquire(currentFile_);
return (currentFile_ != NULL) ? S_OK : E_FAIL;
}
////////////////////////////////////////////////////////////////////////////////////////
//
// ResourceFontCollectionLoader
//
////////////////////////////////////////////////////////////////////////////////////////
class ResourceFontCollectionLoader
: public IResourceFontCollectionLoader
{
public:
ResourceFontCollectionLoader(IDWriteFontFileLoader* pFileLoader)
: refCount_(0)
, pFileLoader_(pFileLoader)
{
}
// IUnknown methods
virtual HRESULT STDMETHODCALLTYPE QueryInterface(REFIID iid, void** ppvObject);
virtual ULONG STDMETHODCALLTYPE AddRef();
virtual ULONG STDMETHODCALLTYPE Release();
// IDWriteFontCollectionLoader methods
virtual HRESULT STDMETHODCALLTYPE CreateEnumeratorFromKey(
IDWriteFactory* pFactory,
void const* collectionKey,
UINT32 collectionKeySize,
_Out_ IDWriteFontFileEnumerator** fontFileEnumerator
);
private:
ULONG refCount_;
IDWriteFontFileLoader* pFileLoader_;
};
HRESULT IResourceFontCollectionLoader::Create(_Out_ IResourceFontCollectionLoader** ppCollectionLoader, IDWriteFontFileLoader* pFileLoader)
{
HRESULT hr = S_OK;
if (!ppCollectionLoader)
{
hr = E_POINTER;
}
if (SUCCEEDED(hr))
{
ResourceFontCollectionLoader* pCollectionLoader = new (std::nothrow) ResourceFontCollectionLoader(pFileLoader);
hr = pCollectionLoader ? S_OK : E_OUTOFMEMORY;
if (SUCCEEDED(hr))
{
DX::SafeRelease(*ppCollectionLoader);
(*ppCollectionLoader) = DX::SafeAcquire(pCollectionLoader);
}
}
return hr;
}
HRESULT STDMETHODCALLTYPE ResourceFontCollectionLoader::QueryInterface(REFIID iid, void** ppvObject)
{
if (iid == IID_IUnknown || iid == __uuidof(IDWriteFontCollectionLoader))
{
*ppvObject = this;
AddRef();
return S_OK;
}
else
{
*ppvObject = NULL;
return E_NOINTERFACE;
}
}
ULONG STDMETHODCALLTYPE ResourceFontCollectionLoader::AddRef()
{
return InterlockedIncrement(&refCount_);
}
ULONG STDMETHODCALLTYPE ResourceFontCollectionLoader::Release()
{
ULONG newCount = InterlockedDecrement(&refCount_);
if (newCount == 0)
delete this;
return newCount;
}
HRESULT STDMETHODCALLTYPE ResourceFontCollectionLoader::CreateEnumeratorFromKey(
IDWriteFactory* pFactory,
void const* collectionKey,
UINT32 collectionKeySize,
_Out_ IDWriteFontFileEnumerator** fontFileEnumerator
)
{
HRESULT hr = S_OK;
if (collectionKey == NULL || collectionKeySize % sizeof(UINT) != 0)
hr = E_INVALIDARG;
if (SUCCEEDED(hr))
{
IResourceFontFileEnumerator* pEnumerator = NULL;
hr = IResourceFontFileEnumerator::Create(&pEnumerator, pFactory, pFileLoader_);
if (SUCCEEDED(hr))
{
UINT const* resourceID = static_cast<const UINT*>(collectionKey);
UINT32 const resourceCount = collectionKeySize / sizeof(UINT);
hr = pEnumerator->SetResources(resourceID, resourceCount);
}
if (SUCCEEDED(hr))
{
*fontFileEnumerator = DX::SafeAcquire(pEnumerator);
}
}
return hr;
}
////////////////////////////////////////////////////////////////////////////////////////
//
// ResourceFontFileLoader
//
////////////////////////////////////////////////////////////////////////////////////////
class ResourceFontFileLoader
: public IResourceFontFileLoader
{
public:
ResourceFontFileLoader()
: refCount_(0)
{
}
// IUnknown methods
virtual HRESULT STDMETHODCALLTYPE QueryInterface(REFIID iid, void** ppvObject);
virtual ULONG STDMETHODCALLTYPE AddRef();
virtual ULONG STDMETHODCALLTYPE Release();
// IDWriteFontFileLoader methods
virtual HRESULT STDMETHODCALLTYPE CreateStreamFromKey(
void const* fontFileReferenceKey,
UINT32 fontFileReferenceKeySize,
_Out_ IDWriteFontFileStream** fontFileStream
);
private:
ULONG refCount_;
};
HRESULT IResourceFontFileLoader::Create(_Out_ IResourceFontFileLoader** ppFileLoader)
{
HRESULT hr = S_OK;
if (!ppFileLoader)
{
hr = E_POINTER;
}
if (SUCCEEDED(hr))
{
ResourceFontFileLoader* pFileLoader = new (std::nothrow) ResourceFontFileLoader;
hr = pFileLoader ? S_OK : E_OUTOFMEMORY;
if (SUCCEEDED(hr))
{
(*ppFileLoader) = DX::SafeAcquire(pFileLoader);
}
}
return hr;
}
HRESULT STDMETHODCALLTYPE ResourceFontFileLoader::QueryInterface(REFIID iid, void** ppvObject)
{
if (iid == IID_IUnknown || iid == __uuidof(IDWriteFontFileLoader))
{
*ppvObject = this;
AddRef();
return S_OK;
}
else
{
*ppvObject = NULL;
return E_NOINTERFACE;
}
}
ULONG STDMETHODCALLTYPE ResourceFontFileLoader::AddRef()
{
return InterlockedIncrement(&refCount_);
}
ULONG STDMETHODCALLTYPE ResourceFontFileLoader::Release()
{
ULONG newCount = InterlockedDecrement(&refCount_);
if (newCount == 0)
delete this;
return newCount;
}
HRESULT STDMETHODCALLTYPE ResourceFontFileLoader::CreateStreamFromKey(
void const* fontFileReferenceKey,
UINT32 fontFileReferenceKeySize,
_Out_ IDWriteFontFileStream** fontFileStream
)
{
HRESULT hr = S_OK;
// Make sure the key is the right size.
if (fontFileReferenceKeySize != sizeof(UINT))
hr = E_INVALIDARG;
if (SUCCEEDED(hr))
{
// Create the pFileStream object.
IResourceFontFileStream* pFileStream = NULL;
UINT resourceID = *static_cast<UINT const*>(fontFileReferenceKey);
hr = IResourceFontFileStream::Create(&pFileStream, resourceID);
if (SUCCEEDED(hr))
{
DX::SafeRelease(*fontFileStream);
*fontFileStream = DX::SafeAcquire(pFileStream);
}
}
return hr;
}
////////////////////////////////////////////////////////////////////////////////////////
//
// ResourceFontFileEnumerator
//
////////////////////////////////////////////////////////////////////////////////////////
class ResourceFontFileEnumerator
: public IResourceFontFileEnumerator
{
public:
ResourceFontFileEnumerator();
STDMETHOD(Initialize)(
IDWriteFactory* pFactory,
IDWriteFontFileLoader* pLoader
);
STDMETHOD(SetResources)(
UINT const* resourceID,
UINT32 const resourceCount
);
~ResourceFontFileEnumerator()
{
DX::SafeRelease(currentFile_);
DX::SafeRelease(pFactory_);
}
// IUnknown methods
virtual HRESULT STDMETHODCALLTYPE QueryInterface(REFIID iid, _Out_ void** ppvObject);
virtual ULONG STDMETHODCALLTYPE AddRef();
virtual ULONG STDMETHODCALLTYPE Release();
// IDWriteFontFileEnumerator methods
virtual HRESULT STDMETHODCALLTYPE MoveNext(_Out_ BOOL* hasCurrentFile);
virtual HRESULT STDMETHODCALLTYPE GetCurrentFontFile(_Out_ IDWriteFontFile** fontFile);
private:
ULONG refCount_;
IDWriteFactory* pFactory_;
IDWriteFontFile* currentFile_;
IDWriteFontFileLoader* pLoader_;
Vector<UINT> resourceIDs_;
size_t nextIndex_;
};
HRESULT IResourceFontFileEnumerator::Create(_Out_ IResourceFontFileEnumerator** ppEnumerator, IDWriteFactory* pFactory, IDWriteFontFileLoader* pFileLoader)
{
HRESULT hr = S_OK;
if (!ppEnumerator)
{
hr = E_POINTER;
}
if (SUCCEEDED(hr))
{
ResourceFontFileEnumerator* pEnumerator = new (std::nothrow) ResourceFontFileEnumerator;
hr = pEnumerator ? S_OK : E_OUTOFMEMORY;
if (SUCCEEDED(hr))
{
hr = pEnumerator->Initialize(pFactory, pFileLoader);
}
if (SUCCEEDED(hr))
{
DX::SafeRelease(*ppEnumerator);
(*ppEnumerator) = DX::SafeAcquire(pEnumerator);
}
}
return hr;
}
ResourceFontFileEnumerator::ResourceFontFileEnumerator()
: refCount_(0)
, pFactory_(NULL)
, currentFile_(NULL)
, nextIndex_(0)
, pLoader_(NULL)
{
}
STDMETHODIMP ResourceFontFileEnumerator::Initialize(
IDWriteFactory* pFactory,
IDWriteFontFileLoader* pLoader
)
{
if (pFactory && pLoader)
{
pFactory_ = DX::SafeAcquire(pFactory);
pLoader_ = DX::SafeAcquire(pLoader);
return S_OK;
}
return E_INVALIDARG;
}
STDMETHODIMP ResourceFontFileEnumerator::SetResources(
UINT const* resourceID,
UINT32 const resourceCount
)
{
try
{
resourceIDs_.assign(resourceID, resourceID + resourceCount);
}
catch (std::bad_alloc&)
{
return E_OUTOFMEMORY;
}
catch (...)
{
return E_FAIL;
}
return S_OK;
}
HRESULT STDMETHODCALLTYPE ResourceFontFileEnumerator::QueryInterface(REFIID iid, _Out_ void** ppvObject)
{
if (iid == IID_IUnknown || iid == __uuidof(IDWriteFontFileEnumerator))
{
*ppvObject = this;
AddRef();
return S_OK;
}
else
{
*ppvObject = NULL;
return E_NOINTERFACE;
}
}
ULONG STDMETHODCALLTYPE ResourceFontFileEnumerator::AddRef()
{
return InterlockedIncrement(&refCount_);
}
ULONG STDMETHODCALLTYPE ResourceFontFileEnumerator::Release()
{
ULONG newCount = InterlockedDecrement(&refCount_);
if (newCount == 0)
delete this;
return newCount;
}
HRESULT STDMETHODCALLTYPE ResourceFontFileEnumerator::MoveNext(_Out_ BOOL* hasCurrentFile)
{
HRESULT hr = S_OK;
*hasCurrentFile = FALSE;
DX::SafeRelease(currentFile_);
if (nextIndex_ < resourceIDs_.size())
{
hr = pFactory_->CreateCustomFontFileReference(
&resourceIDs_[nextIndex_],
sizeof(UINT),
pLoader_,
&currentFile_
);
if (SUCCEEDED(hr))
{
*hasCurrentFile = TRUE;
++nextIndex_;
}
}
return hr;
}
HRESULT STDMETHODCALLTYPE ResourceFontFileEnumerator::GetCurrentFontFile(_Out_ IDWriteFontFile** fontFile)
{
*fontFile = DX::SafeAcquire(currentFile_);
return (currentFile_ != NULL) ? S_OK : E_FAIL;
}
////////////////////////////////////////////////////////////////////////////////////////
//
// ResourceFontFileStream
//
////////////////////////////////////////////////////////////////////////////////////////
class ResourceFontFileStream
: public IResourceFontFileStream
{
public:
ResourceFontFileStream();
STDMETHOD(Initialize)(
const UINT resourceID
);
// IUnknown methods
virtual HRESULT STDMETHODCALLTYPE QueryInterface(REFIID iid, void** ppvObject);
virtual ULONG STDMETHODCALLTYPE AddRef();
virtual ULONG STDMETHODCALLTYPE Release();
// IDWriteFontFileStream methods
virtual HRESULT STDMETHODCALLTYPE ReadFileFragment(
void const** fragmentStart,
UINT64 fileOffset,
UINT64 fragmentSize,
_Out_ void** fragmentContext
);
virtual void STDMETHODCALLTYPE ReleaseFileFragment(
void* fragmentContext
);
virtual HRESULT STDMETHODCALLTYPE GetFileSize(
_Out_ UINT64* fileSize
);
virtual HRESULT STDMETHODCALLTYPE GetLastWriteTime(
_Out_ UINT64* lastWriteTime
);
bool IsInitialized()
{
return resourcePtr_ != NULL;
}
private:
ULONG refCount_;
LPVOID resourcePtr_;
DWORD resourceSize_;
};
HRESULT IResourceFontFileStream::Create(_Out_ IResourceFontFileStream** ppStream, const UINT resourceID)
{
HRESULT hr = S_OK;
if (!ppStream)
{
hr = E_POINTER;
}
if (SUCCEEDED(hr))
{
ResourceFontFileStream* pFileStream = new (std::nothrow) ResourceFontFileStream;
hr = pFileStream ? S_OK : E_OUTOFMEMORY;
if (SUCCEEDED(hr))
{
hr = pFileStream->Initialize(resourceID);
}
if (SUCCEEDED(hr))
{
DX::SafeRelease(*ppStream);
(*ppStream) = DX::SafeAcquire(pFileStream);
}
}
return hr;
}
ResourceFontFileStream::ResourceFontFileStream()
: refCount_(0)
, resourcePtr_(NULL)
, resourceSize_(0)
{
}
STDMETHODIMP ResourceFontFileStream::Initialize(
const UINT resourceID
)
{
HRESULT hr = S_OK;
if (!Resource{ resourceID, RT_FONT }.Load(resourcePtr_, resourceSize_))
{
hr = E_FAIL;
}
return hr;
}
// IUnknown methods
HRESULT STDMETHODCALLTYPE ResourceFontFileStream::QueryInterface(REFIID iid, void** ppvObject)
{
if (iid == IID_IUnknown || iid == __uuidof(IDWriteFontFileStream))
{
*ppvObject = this;
AddRef();
return S_OK;
}
else
{
*ppvObject = NULL;
return E_NOINTERFACE;
}
}
ULONG STDMETHODCALLTYPE ResourceFontFileStream::AddRef()
{
return InterlockedIncrement(&refCount_);
}
ULONG STDMETHODCALLTYPE ResourceFontFileStream::Release()
{
ULONG newCount = InterlockedDecrement(&refCount_);
if (newCount == 0)
delete this;
return newCount;
}
HRESULT STDMETHODCALLTYPE ResourceFontFileStream::ReadFileFragment(
void const** fragmentStart,
UINT64 fileOffset,
UINT64 fragmentSize,
_Out_ void** fragmentContext
)
{
// The pLoader is responsible for doing a bounds check.
if (fileOffset <= resourceSize_ &&
fragmentSize <= resourceSize_ - fileOffset)
{
*fragmentStart = static_cast<BYTE const*>(resourcePtr_) + static_cast<size_t>(fileOffset);
*fragmentContext = NULL;
return S_OK;
}
else
{
*fragmentStart = NULL;
*fragmentContext = NULL;
return E_FAIL;
}
}
void STDMETHODCALLTYPE ResourceFontFileStream::ReleaseFileFragment(
void* fragmentContext
)
{
}
HRESULT STDMETHODCALLTYPE ResourceFontFileStream::GetFileSize(
_Out_ UINT64* fileSize
)
{
*fileSize = resourceSize_;
return S_OK;
}
HRESULT STDMETHODCALLTYPE ResourceFontFileStream::GetLastWriteTime(
_Out_ UINT64* lastWriteTime
)
{
*lastWriteTime = 0;
return E_NOTIMPL;
}
}

View File

@ -0,0 +1,99 @@
// Copyright (c) 2016-2018 Kiwano - Nomango
//
// Permission is hereby granted, free of charge, to any person obtaining a copy
// of this software and associated documentation files (the "Software"), to deal
// in the Software without restriction, including without limitation the rights
// to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
// copies of the Software, and to permit persons to whom the Software is
// furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in
// all copies or substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITH_Out_ WARRANTY OF ANY KIND, EXPRESS OR
// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
// AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
// _Out_ OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.
#pragma once
#include "D2DDeviceResources.h"
namespace kiwano
{
interface DWRITE_DECLARE_INTERFACE("7EC7A55A-1964-4098-83E0-EFA7C12C6EF7")
IFontCollectionLoader : public IDWriteFontCollectionLoader
{
public:
static HRESULT Create(
_Out_ IFontCollectionLoader** ppCollectionLoader
);
};
interface DWRITE_DECLARE_INTERFACE("0A1A3F2A-85F2-41BB-80FD-EC01271740C4")
IFontFileEnumerator : public IDWriteFontFileEnumerator
{
public:
static HRESULT Create(
_Out_ IFontFileEnumerator** ppEnumerator,
IDWriteFactory* pFactory
);
STDMETHOD(SetFilePaths)(
String const* filePath,
UINT32 const fileCount
) PURE;
};
interface DWRITE_DECLARE_INTERFACE("F2C411F0-2FB0-4D0E-8C73-D2B8F30137A4")
IResourceFontCollectionLoader : public IDWriteFontCollectionLoader
{
public:
static HRESULT Create(
_Out_ IResourceFontCollectionLoader** ppCollectionLoader,
IDWriteFontFileLoader * pFileLoader
);
};
interface DWRITE_DECLARE_INTERFACE("08D21408-6FC1-4E36-A4EB-4DA16BE3399E")
IResourceFontFileLoader : public IDWriteFontFileLoader
{
public:
static HRESULT Create(
_Out_ IResourceFontFileLoader** ppFileLoader
);
};
interface DWRITE_DECLARE_INTERFACE("0AD0EC74-7503-46E8-8899-520175ECCB4A")
IResourceFontFileEnumerator : public IDWriteFontFileEnumerator
{
public:
static HRESULT Create(
_Out_ IResourceFontFileEnumerator** ppEnumerator,
IDWriteFactory* pFactory,
IDWriteFontFileLoader* pFileLoader
);
STDMETHOD(SetResources)(
UINT const* resourceID,
UINT32 const resourceCount
) PURE;
};
interface DWRITE_DECLARE_INTERFACE("A6267450-27F3-4948-995F-FF8345A72F88")
IResourceFontFileStream : public IDWriteFontFileStream
{
public:
static HRESULT Create(
_Out_ IResourceFontFileStream** ppStream,
const UINT resourceID
);
};
}

View File

@ -98,7 +98,7 @@ namespace kiwano
unsigned long STDMETHODCALLTYPE AddRef();
unsigned long STDMETHODCALLTYPE Release();
HRESULT STDMETHODCALLTYPE QueryInterface(
IID const& riid,
REFIID riid,
void** ppvObject
);
@ -454,24 +454,6 @@ namespace kiwano
return E_NOTIMPL;
}
STDMETHODIMP_(unsigned long) TextRenderer::AddRef()
{
return InterlockedIncrement(&cRefCount_);
}
STDMETHODIMP_(unsigned long) TextRenderer::Release()
{
unsigned long newCount = InterlockedDecrement(&cRefCount_);
if (newCount == 0)
{
delete this;
return 0;
}
return newCount;
}
STDMETHODIMP TextRenderer::IsPixelSnappingDisabled(
__maybenull void* clientDrawingContext,
__out BOOL* isDisabled)
@ -506,8 +488,26 @@ namespace kiwano
return S_OK;
}
STDMETHODIMP_(unsigned long) TextRenderer::AddRef()
{
return InterlockedIncrement(&cRefCount_);
}
STDMETHODIMP_(unsigned long) TextRenderer::Release()
{
unsigned long newCount = InterlockedDecrement(&cRefCount_);
if (newCount == 0)
{
delete this;
return 0;
}
return newCount;
}
STDMETHODIMP TextRenderer::QueryInterface(
IID const& riid,
REFIID riid,
void** ppvObject)
{
if (__uuidof(ITextRenderer) == riid)

View File

@ -19,13 +19,12 @@
// THE SOFTWARE.
#pragma once
#include "helper.hpp"
#include <dwrite.h>
#include "D2DDeviceResources.h"
namespace kiwano
{
interface DWRITE_DECLARE_INTERFACE("b293e798-9916-4096-a3c1-e5d4039dfa64") ITextRenderer
: public IDWriteTextRenderer
interface DWRITE_DECLARE_INTERFACE("b293e798-9916-4096-a3c1-e5d4039dfa64")
ITextRenderer : public IDWriteTextRenderer
{
public:
static KGE_API HRESULT Create(

View File

@ -79,4 +79,4 @@ namespace kiwano
return (dwAttrib != INVALID_FILE_ATTRIBUTES &&
(dwAttrib & FILE_ATTRIBUTE_DIRECTORY));
}
}
}

View File

@ -323,7 +323,7 @@ namespace kiwano
return 0;
}
bool ResourceCache::AddObj(String const& id, ObjectPtr obj)
bool ResourceCache::AddObjectBase(String const& id, ObjectBasePtr obj)
{
if (obj)
{

View File

@ -76,7 +76,7 @@ namespace kiwano
size_t AddFrameSequence(String const& id, FrameSequencePtr frames);
// 添加对象
bool AddObj(String const& id, ObjectPtr obj);
bool AddObjectBase(String const& id, ObjectBasePtr obj);
// 获取图片资源
FramePtr GetFrame(String const& id) const;
@ -108,6 +108,6 @@ namespace kiwano
virtual ~ResourceCache();
protected:
UnorderedMap<String, ObjectPtr> cache_;
UnorderedMap<String, ObjectBasePtr> cache_;
};
}