Drop pre-Win10 code from WinSkiaSalGraphicsImpl

Introduced in commit a1b18eba35 (Implement
Custom Font Collections on pre-Windows 10 systems, 2024-08-20).

Change-Id: I2aa16ae560d4dad8489e13289ad79d8be349b6b1
Reviewed-on: https://gerrit.libreoffice.org/c/core/+/178031
Tested-by: Jenkins
Reviewed-by: Mike Kaganski <mike.kaganski@collabora.com>
This commit is contained in:
Mike Kaganski 2024-12-07 16:41:20 +05:00
parent d751cbefb4
commit 93350f4694

View file

@ -37,24 +37,29 @@
namespace
{
sal::systools::COMReference<IDWriteFontCollection>
getDWritePrivateFontCollection_w10(IDWriteFontFile* fontFile)
getDWritePrivateFontCollection(IDWriteFontFace* fontFace)
{
UINT32 numberOfFiles;
sal::systools::ThrowIfFailed(fontFace->GetFiles(&numberOfFiles, nullptr), SAL_WHERE);
if (numberOfFiles != 1)
return {};
sal::systools::COMReference<IDWriteFontFile> fontFile;
sal::systools::ThrowIfFailed(fontFace->GetFiles(&numberOfFiles, &fontFile), SAL_WHERE);
static sal::systools::COMReference<IDWriteFactory3> dwriteFactory3 = [] {
IDWriteFactory* dwriteFactory = WinSalGraphics::getDWriteFactory();
sal::systools::COMReference<IDWriteFactory3> factory3;
dwriteFactory->QueryInterface(&factory3);
sal::systools::ThrowIfFailed(dwriteFactory->QueryInterface(&factory3), SAL_WHERE);
return factory3;
}();
if (!dwriteFactory3)
return {};
static sal::systools::COMReference<IDWriteFontSetBuilder> dwriteFontSetBuilder = [] {
sal::systools::COMReference<IDWriteFontSetBuilder> builder;
dwriteFactory3->CreateFontSetBuilder(&dwriteFontSetBuilder);
sal::systools::ThrowIfFailed(dwriteFactory3->CreateFontSetBuilder(&dwriteFontSetBuilder),
SAL_WHERE);
return builder;
}();
if (!dwriteFontSetBuilder)
return {};
BOOL isSupported;
DWRITE_FONT_FILE_TYPE fileType;
@ -84,163 +89,6 @@ getDWritePrivateFontCollection_w10(IDWriteFontFile* fontFile)
SAL_WHERE);
return { fc1.get() };
}
// The following is only needed until we bump baseline to Windows 10
template <class I> requires std::is_base_of_v<IUnknown, I> class IUnknown_Impl : public I
{
public:
virtual ~IUnknown_Impl() {}
// IUnknown
HRESULT STDMETHODCALLTYPE QueryInterface(REFIID iid, void** ppvObject) override
{
if (iid == IID_IUnknown || iid == __uuidof(I))
{
*ppvObject = this;
AddRef();
return S_OK;
}
*ppvObject = nullptr;
return E_NOINTERFACE;
}
ULONG STDMETHODCALLTYPE AddRef() override { return ++m_nRef; }
ULONG STDMETHODCALLTYPE Release() override
{
ULONG n = --m_nRef;
if (n == 0)
delete this;
return n;
};
private:
std::atomic<ULONG> m_nRef = 0;
};
// A simple loader class, which only stores the font files (to fulfill the requirement that
// "each key is ... valid until the loader is unregistered using the factory"), and creates
// instances of enumerator
class FontCollectionLoader_w7 : public IUnknown_Impl<IDWriteFontCollectionLoader>
{
public:
// IDWriteFontCollectionLoader
HRESULT STDMETHODCALLTYPE CreateEnumeratorFromKey(
IDWriteFactory* factory, void const* collectionKey, UINT32 collectionKeySize,
/* OUT */ IDWriteFontFileEnumerator** fontFileEnumerator) override;
private:
std::vector<sal::systools::COMReference<IDWriteFontFile>> m_fontFiles;
};
// A singleton class, that (1) caches IDWriteFactory, to avoid destruction order problems,
// (2) holds the FontCollectionLoader_w7 singleton, and (3) calls IDWriteFactory's
// (Un)RegisterFontCollectionLoader, because these can't be called from destructor of
// FontCollectionLoader_w7, because RegisterFontCollectionLoader calls AddRef.
struct FontCollectionLoader_w7_singleton_t
{
sal::systools::COMReference<IDWriteFactory> factory;
sal::systools::COMReference<FontCollectionLoader_w7> loader;
FontCollectionLoader_w7_singleton_t()
: factory(WinSalGraphics::getDWriteFactory())
, loader(new FontCollectionLoader_w7)
{
factory->RegisterFontCollectionLoader(loader);
}
~FontCollectionLoader_w7_singleton_t() { factory->UnregisterFontCollectionLoader(loader); }
};
// A simple enumerator class, which only operates on a single font file.
class FontFileEnumerator_w7 : public IUnknown_Impl<IDWriteFontFileEnumerator>
{
public:
FontFileEnumerator_w7(IDWriteFontFile* collectionKey)
: m_fontFile(collectionKey)
{
assert(collectionKey);
AddRef();
}
// IDWriteFontFileEnumerator
HRESULT STDMETHODCALLTYPE MoveNext(BOOL* hasCurrentFile) override;
HRESULT STDMETHODCALLTYPE GetCurrentFontFile(IDWriteFontFile** fontFile) override;
private:
sal::systools::COMReference<IDWriteFontFile> m_fontFile;
size_t m_nextIndex = 0;
};
HRESULT STDMETHODCALLTYPE FontCollectionLoader_w7::CreateEnumeratorFromKey(
IDWriteFactory* /*factory*/, void const* collectionKey, UINT32 collectionKeySize,
/* OUT */ IDWriteFontFileEnumerator** fontFileEnumerator)
{
if (!fontFileEnumerator)
return E_INVALIDARG;
*fontFileEnumerator = nullptr;
if (!collectionKey || collectionKeySize != sizeof(IDWriteFontFile*))
return E_INVALIDARG;
auto pFontFile = *static_cast<IDWriteFontFile* const*>(collectionKey);
auto it = std::find_if(m_fontFiles.begin(), m_fontFiles.end(),
[pFontFile](const auto& el) { return el.get() == pFontFile; });
if (it == m_fontFiles.end())
m_fontFiles.emplace_back(pFontFile); // cals AddRef
*fontFileEnumerator = new (std::nothrow) FontFileEnumerator_w7(pFontFile);
return *fontFileEnumerator ? S_OK : E_OUTOFMEMORY;
}
HRESULT STDMETHODCALLTYPE FontFileEnumerator_w7::MoveNext(BOOL* hasCurrentFile)
{
if (!hasCurrentFile)
return E_INVALIDARG;
*hasCurrentFile = m_nextIndex == 0 ? TRUE : FALSE;
++m_nextIndex;
return S_OK;
}
HRESULT STDMETHODCALLTYPE FontFileEnumerator_w7::GetCurrentFontFile(IDWriteFontFile** fontFile)
{
if (!fontFile)
return E_INVALIDARG;
if (m_nextIndex == 1)
{
*fontFile = m_fontFile;
m_fontFile->AddRef();
return S_OK;
}
*fontFile = nullptr;
return E_FAIL;
}
sal::systools::COMReference<IDWriteFontCollection>
getDWritePrivateFontCollection_w7(IDWriteFontFile* fontFile)
{
static FontCollectionLoader_w7_singleton_t singleton;
sal::systools::COMReference<IDWriteFontCollection> collection;
sal::systools::ThrowIfFailed(singleton.factory->CreateCustomFontCollection(
singleton.loader, &fontFile, sizeof(fontFile), &collection),
SAL_WHERE);
return collection;
}
// End of pre-Windows 10 compatibility code
sal::systools::COMReference<IDWriteFontCollection>
getDWritePrivateFontCollection(IDWriteFontFace* fontFace)
{
UINT32 numberOfFiles;
sal::systools::ThrowIfFailed(fontFace->GetFiles(&numberOfFiles, nullptr), SAL_WHERE);
if (numberOfFiles != 1)
return {};
sal::systools::COMReference<IDWriteFontFile> fontFile;
sal::systools::ThrowIfFailed(fontFace->GetFiles(&numberOfFiles, &fontFile), SAL_WHERE);
if (auto collection = getDWritePrivateFontCollection_w10(fontFile))
return collection;
return getDWritePrivateFontCollection_w7(fontFile);
}
}
using namespace SkiaHelper;
@ -363,6 +211,8 @@ WinSkiaSalGraphicsImpl::createDirectWriteTypeface(const WinFontInstance* pWinFon
// private fonts with this newly used font.
dwritePrivateCollection = getDWritePrivateFontCollection(fontFace);
if (!dwritePrivateCollection) // Not one file? Unsupported font?
return nullptr;
ThrowIfFailed(dwritePrivateCollection->GetFontFromFontFace(fontFace, &font), SAL_WHERE);
}
}