[PATCH 2/2] dwrite: Move text format object implementation to a separate file.

Nikolay Sivov nsivov at codeweavers.com
Thu Jan 20 04:37:45 CST 2022


Signed-off-by: Nikolay Sivov <nsivov at codeweavers.com>
---
 dlls/dwrite/Makefile.in      |    1 +
 dlls/dwrite/dwrite_private.h |   70 +++
 dlls/dwrite/format.c         |  926 ++++++++++++++++++++++++++++++
 dlls/dwrite/layout.c         | 1045 ++--------------------------------
 4 files changed, 1043 insertions(+), 999 deletions(-)
 create mode 100644 dlls/dwrite/format.c

diff --git a/dlls/dwrite/Makefile.in b/dlls/dwrite/Makefile.in
index 1c1611f8e16..f5332cea713 100644
--- a/dlls/dwrite/Makefile.in
+++ b/dlls/dwrite/Makefile.in
@@ -10,6 +10,7 @@ C_SRCS = \
 	bracket.c \
 	direction.c \
 	font.c \
+	format.c \
 	freetype.c \
 	gdiinterop.c \
 	layout.c \
diff --git a/dlls/dwrite/dwrite_private.h b/dlls/dwrite/dwrite_private.h
index 141b57fbaee..91b2bb3241c 100644
--- a/dlls/dwrite/dwrite_private.h
+++ b/dlls/dwrite/dwrite_private.h
@@ -353,6 +353,76 @@ extern float fontface_get_scaled_design_advance(struct dwrite_fontface *fontface
         float emsize, float ppdip, const DWRITE_MATRIX *transform, UINT16 glyph, BOOL is_sideways) DECLSPEC_HIDDEN;
 extern struct dwrite_fontface *unsafe_impl_from_IDWriteFontFace(IDWriteFontFace *iface) DECLSPEC_HIDDEN;
 
+struct dwrite_textformat_data
+{
+    WCHAR *family_name;
+    unsigned int family_len;
+    WCHAR *locale;
+    unsigned int locale_len;
+
+    DWRITE_FONT_WEIGHT weight;
+    DWRITE_FONT_STYLE style;
+    DWRITE_FONT_STRETCH stretch;
+
+    DWRITE_PARAGRAPH_ALIGNMENT paralign;
+    DWRITE_READING_DIRECTION readingdir;
+    DWRITE_WORD_WRAPPING wrapping;
+    BOOL last_line_wrapping;
+    DWRITE_TEXT_ALIGNMENT textalignment;
+    DWRITE_FLOW_DIRECTION flow;
+    DWRITE_VERTICAL_GLYPH_ORIENTATION vertical_orientation;
+    DWRITE_OPTICAL_ALIGNMENT optical_alignment;
+    DWRITE_LINE_SPACING spacing;
+    DWRITE_AUTOMATIC_FONT_AXES automatic_axes;
+
+    float fontsize;
+    float tabstop;
+
+    DWRITE_TRIMMING trimming;
+    IDWriteInlineObject *trimmingsign;
+
+    IDWriteFontCollection *collection;
+    IDWriteFontFallback *fallback;
+
+    DWRITE_FONT_AXIS_VALUE *axis_values;
+    unsigned int axis_values_count;
+};
+
+struct dwrite_textformat
+{
+    IDWriteTextFormat3 IDWriteTextFormat3_iface;
+    LONG refcount;
+    struct dwrite_textformat_data format;
+};
+
+struct dwrite_textformat *unsafe_impl_from_IDWriteTextFormat(IDWriteTextFormat *iface) DECLSPEC_HIDDEN;
+void release_format_data(struct dwrite_textformat_data *data) DECLSPEC_HIDDEN;
+
+HRESULT format_set_vertical_orientation(struct dwrite_textformat_data *format,
+        DWRITE_VERTICAL_GLYPH_ORIENTATION orientation, BOOL *changed) DECLSPEC_HIDDEN;
+HRESULT format_set_fontfallback(struct dwrite_textformat_data *format, IDWriteFontFallback *fallback) DECLSPEC_HIDDEN;
+HRESULT format_get_fontfallback(const struct dwrite_textformat_data *format, IDWriteFontFallback **fallback) DECLSPEC_HIDDEN;
+HRESULT format_set_font_axisvalues(struct dwrite_textformat_data *format,
+        DWRITE_FONT_AXIS_VALUE const *axis_values, unsigned int num_values) DECLSPEC_HIDDEN;
+HRESULT format_get_font_axisvalues(struct dwrite_textformat_data *format,
+        DWRITE_FONT_AXIS_VALUE *axis_values, unsigned int num_values) DECLSPEC_HIDDEN;
+HRESULT format_set_optical_alignment(struct dwrite_textformat_data *format,
+        DWRITE_OPTICAL_ALIGNMENT alignment) DECLSPEC_HIDDEN;
+HRESULT format_set_trimming(struct dwrite_textformat_data *format, DWRITE_TRIMMING const *trimming,
+        IDWriteInlineObject *trimming_sign, BOOL *changed) DECLSPEC_HIDDEN;
+HRESULT format_set_flowdirection(struct dwrite_textformat_data *format,
+        DWRITE_FLOW_DIRECTION direction, BOOL *changed) DECLSPEC_HIDDEN;
+HRESULT format_set_readingdirection(struct dwrite_textformat_data *format,
+        DWRITE_READING_DIRECTION direction, BOOL *changed) DECLSPEC_HIDDEN;
+HRESULT format_set_wordwrapping(struct dwrite_textformat_data *format, DWRITE_WORD_WRAPPING wrapping,
+        BOOL *changed) DECLSPEC_HIDDEN;
+HRESULT format_set_paralignment(struct dwrite_textformat_data *format,
+        DWRITE_PARAGRAPH_ALIGNMENT alignment, BOOL *changed) DECLSPEC_HIDDEN;
+HRESULT format_set_textalignment(struct dwrite_textformat_data *format, DWRITE_TEXT_ALIGNMENT alignment,
+        BOOL *changed) DECLSPEC_HIDDEN;
+HRESULT format_set_linespacing(struct dwrite_textformat_data *format,
+        DWRITE_LINE_SPACING const *spacing, BOOL *changed) DECLSPEC_HIDDEN;
+
 /* Opentype font table functions */
 struct dwrite_font_props
 {
diff --git a/dlls/dwrite/format.c b/dlls/dwrite/format.c
new file mode 100644
index 00000000000..01f7b7f8786
--- /dev/null
+++ b/dlls/dwrite/format.c
@@ -0,0 +1,926 @@
+/*
+ * Copyright 2012, 2014-2021 Nikolay Sivov for CodeWeavers
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 2.1 of the License, or (at your option) any later version.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public
+ * License along with this library; if not, write to the Free Software
+ * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
+ */
+
+#define COBJMACROS
+
+#include "dwrite_private.h"
+
+#include "wine/debug.h"
+
+WINE_DEFAULT_DEBUG_CHANNEL(dwrite);
+
+struct dwrite_trimmingsign
+{
+    IDWriteInlineObject IDWriteInlineObject_iface;
+    LONG refcount;
+
+    IDWriteTextLayout *layout;
+};
+
+static inline struct dwrite_trimmingsign *impl_from_IDWriteInlineObject(IDWriteInlineObject *iface)
+{
+    return CONTAINING_RECORD(iface, struct dwrite_trimmingsign, IDWriteInlineObject_iface);
+}
+
+void release_format_data(struct dwrite_textformat_data *data)
+{
+    if (data->collection)
+        IDWriteFontCollection_Release(data->collection);
+    if (data->fallback)
+        IDWriteFontFallback_Release(data->fallback);
+    if (data->trimmingsign)
+        IDWriteInlineObject_Release(data->trimmingsign);
+    free(data->family_name);
+    free(data->locale);
+    free(data->axis_values);
+}
+
+static inline struct dwrite_textformat *impl_from_IDWriteTextFormat3(IDWriteTextFormat3 *iface)
+{
+    return CONTAINING_RECORD(iface, struct dwrite_textformat, IDWriteTextFormat3_iface);
+}
+
+HRESULT format_set_textalignment(struct dwrite_textformat_data *format, DWRITE_TEXT_ALIGNMENT alignment,
+        BOOL *changed)
+{
+    if ((UINT32)alignment > DWRITE_TEXT_ALIGNMENT_JUSTIFIED)
+        return E_INVALIDARG;
+    if (changed) *changed = format->textalignment != alignment;
+    format->textalignment = alignment;
+    return S_OK;
+}
+
+HRESULT format_set_paralignment(struct dwrite_textformat_data *format, DWRITE_PARAGRAPH_ALIGNMENT alignment, BOOL *changed)
+{
+    if ((UINT32)alignment > DWRITE_PARAGRAPH_ALIGNMENT_CENTER)
+        return E_INVALIDARG;
+    if (changed) *changed = format->paralign != alignment;
+    format->paralign = alignment;
+    return S_OK;
+}
+
+HRESULT format_set_readingdirection(struct dwrite_textformat_data *format, DWRITE_READING_DIRECTION direction, BOOL *changed)
+{
+    if ((UINT32)direction > DWRITE_READING_DIRECTION_BOTTOM_TO_TOP)
+        return E_INVALIDARG;
+    if (changed) *changed = format->readingdir != direction;
+    format->readingdir = direction;
+    return S_OK;
+}
+
+HRESULT format_set_wordwrapping(struct dwrite_textformat_data *format, DWRITE_WORD_WRAPPING wrapping, BOOL *changed)
+{
+    if ((UINT32)wrapping > DWRITE_WORD_WRAPPING_CHARACTER)
+        return E_INVALIDARG;
+    if (changed) *changed = format->wrapping != wrapping;
+    format->wrapping = wrapping;
+    return S_OK;
+}
+
+HRESULT format_set_flowdirection(struct dwrite_textformat_data *format, DWRITE_FLOW_DIRECTION direction, BOOL *changed)
+{
+    if ((UINT32)direction > DWRITE_FLOW_DIRECTION_RIGHT_TO_LEFT)
+        return E_INVALIDARG;
+    if (changed) *changed = format->flow != direction;
+    format->flow = direction;
+    return S_OK;
+}
+
+HRESULT format_set_trimming(struct dwrite_textformat_data *format, DWRITE_TRIMMING const *trimming,
+        IDWriteInlineObject *trimming_sign, BOOL *changed)
+{
+    if (changed)
+        *changed = FALSE;
+
+    if ((UINT32)trimming->granularity > DWRITE_TRIMMING_GRANULARITY_WORD)
+        return E_INVALIDARG;
+
+    if (changed) {
+        *changed = !!memcmp(&format->trimming, trimming, sizeof(*trimming));
+        if (format->trimmingsign != trimming_sign)
+            *changed = TRUE;
+    }
+
+    format->trimming = *trimming;
+    if (format->trimmingsign)
+        IDWriteInlineObject_Release(format->trimmingsign);
+    format->trimmingsign = trimming_sign;
+    if (format->trimmingsign)
+        IDWriteInlineObject_AddRef(format->trimmingsign);
+    return S_OK;
+}
+
+HRESULT format_set_linespacing(struct dwrite_textformat_data *format, DWRITE_LINE_SPACING const *spacing, BOOL *changed)
+{
+    if (spacing->height < 0.0f || spacing->leadingBefore < 0.0f || spacing->leadingBefore > 1.0f ||
+        (UINT32)spacing->method > DWRITE_LINE_SPACING_METHOD_PROPORTIONAL)
+        return E_INVALIDARG;
+
+    if (changed)
+        *changed = memcmp(spacing, &format->spacing, sizeof(*spacing));
+
+    format->spacing = *spacing;
+    return S_OK;
+}
+
+HRESULT format_set_font_axisvalues(struct dwrite_textformat_data *format, DWRITE_FONT_AXIS_VALUE const *axis_values,
+        unsigned int num_values)
+{
+    free(format->axis_values);
+    format->axis_values = NULL;
+    format->axis_values_count = 0;
+
+    if (num_values)
+    {
+        if (!(format->axis_values = calloc(num_values, sizeof(*axis_values))))
+            return E_OUTOFMEMORY;
+        memcpy(format->axis_values, axis_values, num_values * sizeof(*axis_values));
+        format->axis_values_count = num_values;
+    }
+
+    return S_OK;
+}
+
+HRESULT format_get_font_axisvalues(struct dwrite_textformat_data *format, DWRITE_FONT_AXIS_VALUE *axis_values,
+        unsigned int num_values)
+{
+    if (!format->axis_values_count)
+    {
+        if (num_values) memset(axis_values, 0, num_values * sizeof(*axis_values));
+        return S_OK;
+    }
+
+    if (num_values < format->axis_values_count)
+        return E_NOT_SUFFICIENT_BUFFER;
+
+    memcpy(axis_values, format->axis_values, min(num_values, format->axis_values_count) * sizeof(*axis_values));
+
+    return S_OK;
+}
+
+HRESULT format_get_fontfallback(const struct dwrite_textformat_data *format, IDWriteFontFallback **fallback)
+{
+    *fallback = format->fallback;
+    if (*fallback)
+        IDWriteFontFallback_AddRef(*fallback);
+    return S_OK;
+}
+
+HRESULT format_set_fontfallback(struct dwrite_textformat_data *format, IDWriteFontFallback *fallback)
+{
+    if (format->fallback)
+        IDWriteFontFallback_Release(format->fallback);
+    format->fallback = fallback;
+    if (fallback)
+        IDWriteFontFallback_AddRef(fallback);
+    return S_OK;
+}
+
+HRESULT format_set_optical_alignment(struct dwrite_textformat_data *format, DWRITE_OPTICAL_ALIGNMENT alignment)
+{
+    if ((UINT32)alignment > DWRITE_OPTICAL_ALIGNMENT_NO_SIDE_BEARINGS)
+        return E_INVALIDARG;
+    format->optical_alignment = alignment;
+    return S_OK;
+}
+
+HRESULT format_set_vertical_orientation(struct dwrite_textformat_data *format, DWRITE_VERTICAL_GLYPH_ORIENTATION orientation,
+        BOOL *changed)
+{
+    if ((UINT32)orientation > DWRITE_VERTICAL_GLYPH_ORIENTATION_STACKED)
+        return E_INVALIDARG;
+
+    if (changed)
+        *changed = format->vertical_orientation != orientation;
+
+    format->vertical_orientation = orientation;
+    return S_OK;
+}
+
+static HRESULT WINAPI dwritetextformat_QueryInterface(IDWriteTextFormat3 *iface, REFIID riid, void **obj)
+{
+    TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), obj);
+
+    if (IsEqualIID(riid, &IID_IDWriteTextFormat3) ||
+        IsEqualIID(riid, &IID_IDWriteTextFormat2) ||
+        IsEqualIID(riid, &IID_IDWriteTextFormat1) ||
+        IsEqualIID(riid, &IID_IDWriteTextFormat)  ||
+        IsEqualIID(riid, &IID_IUnknown))
+    {
+        *obj = iface;
+        IDWriteTextFormat3_AddRef(iface);
+        return S_OK;
+    }
+
+    WARN("%s not implemented.\n", debugstr_guid(riid));
+
+    *obj = NULL;
+
+    return E_NOINTERFACE;
+}
+
+static ULONG WINAPI dwritetextformat_AddRef(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+    ULONG refcount = InterlockedIncrement(&format->refcount);
+
+    TRACE("%p, refcount %d.\n", iface, refcount);
+
+    return refcount;
+}
+
+static ULONG WINAPI dwritetextformat_Release(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+    ULONG refcount = InterlockedDecrement(&format->refcount);
+
+    TRACE("%p, refcount %d.\n", iface, refcount);
+
+    if (!refcount)
+    {
+        release_format_data(&format->format);
+        free(format);
+    }
+
+    return refcount;
+}
+
+static HRESULT WINAPI dwritetextformat_SetTextAlignment(IDWriteTextFormat3 *iface, DWRITE_TEXT_ALIGNMENT alignment)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %d.\n", iface, alignment);
+
+    return format_set_textalignment(&format->format, alignment, NULL);
+}
+
+static HRESULT WINAPI dwritetextformat_SetParagraphAlignment(IDWriteTextFormat3 *iface,
+        DWRITE_PARAGRAPH_ALIGNMENT alignment)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %d.\n", iface, alignment);
+
+    return format_set_paralignment(&format->format, alignment, NULL);
+}
+
+static HRESULT WINAPI dwritetextformat_SetWordWrapping(IDWriteTextFormat3 *iface, DWRITE_WORD_WRAPPING wrapping)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %d.\n", iface, wrapping);
+
+    return format_set_wordwrapping(&format->format, wrapping, NULL);
+}
+
+static HRESULT WINAPI dwritetextformat_SetReadingDirection(IDWriteTextFormat3 *iface, DWRITE_READING_DIRECTION direction)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %d.\n", iface, direction);
+
+    return format_set_readingdirection(&format->format, direction, NULL);
+}
+
+static HRESULT WINAPI dwritetextformat_SetFlowDirection(IDWriteTextFormat3 *iface, DWRITE_FLOW_DIRECTION direction)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %d.\n", iface, direction);
+
+    return format_set_flowdirection(&format->format, direction, NULL);
+}
+
+static HRESULT WINAPI dwritetextformat_SetIncrementalTabStop(IDWriteTextFormat3 *iface, float tabstop)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %f.\n", iface, tabstop);
+
+    if (tabstop <= 0.0f)
+        return E_INVALIDARG;
+
+    format->format.tabstop = tabstop;
+    return S_OK;
+}
+
+static HRESULT WINAPI dwritetextformat_SetTrimming(IDWriteTextFormat3 *iface, DWRITE_TRIMMING const *trimming,
+        IDWriteInlineObject *trimming_sign)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p, %p.\n", iface, trimming, trimming_sign);
+
+    return format_set_trimming(&format->format, trimming, trimming_sign, NULL);
+}
+
+static HRESULT WINAPI dwritetextformat_SetLineSpacing(IDWriteTextFormat3 *iface, DWRITE_LINE_SPACING_METHOD method,
+        float height, float baseline)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+    DWRITE_LINE_SPACING spacing;
+
+    TRACE("%p, %d, %f, %f.\n", iface, method, height, baseline);
+
+    spacing = format->format.spacing;
+    spacing.method = method;
+    spacing.height = height;
+    spacing.baseline = baseline;
+
+    return format_set_linespacing(&format->format, &spacing, NULL);
+}
+
+static DWRITE_TEXT_ALIGNMENT WINAPI dwritetextformat_GetTextAlignment(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.textalignment;
+}
+
+static DWRITE_PARAGRAPH_ALIGNMENT WINAPI dwritetextformat_GetParagraphAlignment(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.paralign;
+}
+
+static DWRITE_WORD_WRAPPING WINAPI dwritetextformat_GetWordWrapping(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.wrapping;
+}
+
+static DWRITE_READING_DIRECTION WINAPI dwritetextformat_GetReadingDirection(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.readingdir;
+}
+
+static DWRITE_FLOW_DIRECTION WINAPI dwritetextformat_GetFlowDirection(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.flow;
+}
+
+static float WINAPI dwritetextformat_GetIncrementalTabStop(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.tabstop;
+}
+
+static HRESULT WINAPI dwritetextformat_GetTrimming(IDWriteTextFormat3 *iface, DWRITE_TRIMMING *options,
+        IDWriteInlineObject **trimming_sign)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p, %p.\n", iface, options, trimming_sign);
+
+    *options = format->format.trimming;
+    if ((*trimming_sign = format->format.trimmingsign))
+        IDWriteInlineObject_AddRef(*trimming_sign);
+
+    return S_OK;
+}
+
+static HRESULT WINAPI dwritetextformat_GetLineSpacing(IDWriteTextFormat3 *iface, DWRITE_LINE_SPACING_METHOD *method,
+        float *spacing, float *baseline)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p, %p, %p.\n", iface, method, spacing, baseline);
+
+    *method = format->format.spacing.method;
+    *spacing = format->format.spacing.height;
+    *baseline = format->format.spacing.baseline;
+    return S_OK;
+}
+
+static HRESULT WINAPI dwritetextformat_GetFontCollection(IDWriteTextFormat3 *iface, IDWriteFontCollection **collection)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p.\n", iface, collection);
+
+    *collection = format->format.collection;
+    IDWriteFontCollection_AddRef(*collection);
+
+    return S_OK;
+}
+
+static UINT32 WINAPI dwritetextformat_GetFontFamilyNameLength(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.family_len;
+}
+
+static HRESULT WINAPI dwritetextformat_GetFontFamilyName(IDWriteTextFormat3 *iface, WCHAR *name, UINT32 size)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p, %u.\n", iface, name, size);
+
+    if (size <= format->format.family_len)
+        return E_NOT_SUFFICIENT_BUFFER;
+    wcscpy(name, format->format.family_name);
+    return S_OK;
+}
+
+static DWRITE_FONT_WEIGHT WINAPI dwritetextformat_GetFontWeight(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.weight;
+}
+
+static DWRITE_FONT_STYLE WINAPI dwritetextformat_GetFontStyle(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.style;
+}
+
+static DWRITE_FONT_STRETCH WINAPI dwritetextformat_GetFontStretch(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.stretch;
+}
+
+static float WINAPI dwritetextformat_GetFontSize(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.fontsize;
+}
+
+static UINT32 WINAPI dwritetextformat_GetLocaleNameLength(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.locale_len;
+}
+
+static HRESULT WINAPI dwritetextformat_GetLocaleName(IDWriteTextFormat3 *iface, WCHAR *name, UINT32 size)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p %u.\n", iface, name, size);
+
+    if (size <= format->format.locale_len)
+        return E_NOT_SUFFICIENT_BUFFER;
+    wcscpy(name, format->format.locale);
+    return S_OK;
+}
+
+static HRESULT WINAPI dwritetextformat1_SetVerticalGlyphOrientation(IDWriteTextFormat3 *iface,
+        DWRITE_VERTICAL_GLYPH_ORIENTATION orientation)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %d.\n", iface, orientation);
+
+    return format_set_vertical_orientation(&format->format, orientation, NULL);
+}
+
+static DWRITE_VERTICAL_GLYPH_ORIENTATION WINAPI dwritetextformat1_GetVerticalGlyphOrientation(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.vertical_orientation;
+}
+
+static HRESULT WINAPI dwritetextformat1_SetLastLineWrapping(IDWriteTextFormat3 *iface, BOOL lastline_wrapping_enabled)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %d.\n", iface, lastline_wrapping_enabled);
+
+    format->format.last_line_wrapping = !!lastline_wrapping_enabled;
+    return S_OK;
+}
+
+static BOOL WINAPI dwritetextformat1_GetLastLineWrapping(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.last_line_wrapping;
+}
+
+static HRESULT WINAPI dwritetextformat1_SetOpticalAlignment(IDWriteTextFormat3 *iface, DWRITE_OPTICAL_ALIGNMENT alignment)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %d.\n", iface, alignment);
+
+    return format_set_optical_alignment(&format->format, alignment);
+}
+
+static DWRITE_OPTICAL_ALIGNMENT WINAPI dwritetextformat1_GetOpticalAlignment(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.optical_alignment;
+}
+
+static HRESULT WINAPI dwritetextformat1_SetFontFallback(IDWriteTextFormat3 *iface, IDWriteFontFallback *fallback)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p.\n", iface, fallback);
+
+    return format_set_fontfallback(&format->format, fallback);
+}
+
+static HRESULT WINAPI dwritetextformat1_GetFontFallback(IDWriteTextFormat3 *iface, IDWriteFontFallback **fallback)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p.\n", iface, fallback);
+
+    return format_get_fontfallback(&format->format, fallback);
+}
+
+static HRESULT WINAPI dwritetextformat2_SetLineSpacing(IDWriteTextFormat3 *iface, DWRITE_LINE_SPACING const *spacing)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p.\n", iface, spacing);
+
+    return format_set_linespacing(&format->format, spacing, NULL);
+}
+
+static HRESULT WINAPI dwritetextformat2_GetLineSpacing(IDWriteTextFormat3 *iface, DWRITE_LINE_SPACING *spacing)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p.\n", iface, spacing);
+
+    *spacing = format->format.spacing;
+    return S_OK;
+}
+
+static HRESULT WINAPI dwritetextformat3_SetFontAxisValues(IDWriteTextFormat3 *iface,
+        DWRITE_FONT_AXIS_VALUE const *axis_values, UINT32 num_values)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p, %u.\n", iface, axis_values, num_values);
+
+    return format_set_font_axisvalues(&format->format, axis_values, num_values);
+}
+
+static UINT32 WINAPI dwritetextformat3_GetFontAxisValueCount(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.axis_values_count;
+}
+
+static HRESULT WINAPI dwritetextformat3_GetFontAxisValues(IDWriteTextFormat3 *iface,
+        DWRITE_FONT_AXIS_VALUE *axis_values, UINT32 num_values)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %p, %u.\n", iface, axis_values, num_values);
+
+    return format_get_font_axisvalues(&format->format, axis_values, num_values);
+}
+
+static DWRITE_AUTOMATIC_FONT_AXES WINAPI dwritetextformat3_GetAutomaticFontAxes(IDWriteTextFormat3 *iface)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p.\n", iface);
+
+    return format->format.automatic_axes;
+}
+
+static HRESULT WINAPI dwritetextformat3_SetAutomaticFontAxes(IDWriteTextFormat3 *iface, DWRITE_AUTOMATIC_FONT_AXES axes)
+{
+    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
+
+    TRACE("%p, %d.\n", iface, axes);
+
+    format->format.automatic_axes = axes;
+
+    return S_OK;
+}
+
+static const IDWriteTextFormat3Vtbl dwritetextformatvtbl =
+{
+    dwritetextformat_QueryInterface,
+    dwritetextformat_AddRef,
+    dwritetextformat_Release,
+    dwritetextformat_SetTextAlignment,
+    dwritetextformat_SetParagraphAlignment,
+    dwritetextformat_SetWordWrapping,
+    dwritetextformat_SetReadingDirection,
+    dwritetextformat_SetFlowDirection,
+    dwritetextformat_SetIncrementalTabStop,
+    dwritetextformat_SetTrimming,
+    dwritetextformat_SetLineSpacing,
+    dwritetextformat_GetTextAlignment,
+    dwritetextformat_GetParagraphAlignment,
+    dwritetextformat_GetWordWrapping,
+    dwritetextformat_GetReadingDirection,
+    dwritetextformat_GetFlowDirection,
+    dwritetextformat_GetIncrementalTabStop,
+    dwritetextformat_GetTrimming,
+    dwritetextformat_GetLineSpacing,
+    dwritetextformat_GetFontCollection,
+    dwritetextformat_GetFontFamilyNameLength,
+    dwritetextformat_GetFontFamilyName,
+    dwritetextformat_GetFontWeight,
+    dwritetextformat_GetFontStyle,
+    dwritetextformat_GetFontStretch,
+    dwritetextformat_GetFontSize,
+    dwritetextformat_GetLocaleNameLength,
+    dwritetextformat_GetLocaleName,
+    dwritetextformat1_SetVerticalGlyphOrientation,
+    dwritetextformat1_GetVerticalGlyphOrientation,
+    dwritetextformat1_SetLastLineWrapping,
+    dwritetextformat1_GetLastLineWrapping,
+    dwritetextformat1_SetOpticalAlignment,
+    dwritetextformat1_GetOpticalAlignment,
+    dwritetextformat1_SetFontFallback,
+    dwritetextformat1_GetFontFallback,
+    dwritetextformat2_SetLineSpacing,
+    dwritetextformat2_GetLineSpacing,
+    dwritetextformat3_SetFontAxisValues,
+    dwritetextformat3_GetFontAxisValueCount,
+    dwritetextformat3_GetFontAxisValues,
+    dwritetextformat3_GetAutomaticFontAxes,
+    dwritetextformat3_SetAutomaticFontAxes,
+};
+
+struct dwrite_textformat *unsafe_impl_from_IDWriteTextFormat(IDWriteTextFormat *iface)
+{
+    return (iface->lpVtbl == (IDWriteTextFormatVtbl *)&dwritetextformatvtbl) ?
+        CONTAINING_RECORD(iface, struct dwrite_textformat, IDWriteTextFormat3_iface) : NULL;
+}
+
+HRESULT create_textformat(const WCHAR *family_name, IDWriteFontCollection *collection, DWRITE_FONT_WEIGHT weight,
+        DWRITE_FONT_STYLE style, DWRITE_FONT_STRETCH stretch, float size, const WCHAR *locale, IDWriteTextFormat **format)
+{
+    struct dwrite_textformat *object;
+
+    *format = NULL;
+
+    if (size <= 0.0f)
+        return E_INVALIDARG;
+
+    if (((UINT32)weight > DWRITE_FONT_WEIGHT_ULTRA_BLACK) ||
+        ((UINT32)stretch > DWRITE_FONT_STRETCH_ULTRA_EXPANDED) ||
+        ((UINT32)style > DWRITE_FONT_STYLE_ITALIC))
+        return E_INVALIDARG;
+
+    if (!(object = calloc(1, sizeof(*object))))
+        return E_OUTOFMEMORY;
+
+    object->IDWriteTextFormat3_iface.lpVtbl = &dwritetextformatvtbl;
+    object->refcount = 1;
+    object->format.family_name = wcsdup(family_name);
+    object->format.family_len = wcslen(family_name);
+    object->format.locale = wcsdup(locale);
+    object->format.locale_len = wcslen(locale);
+    /* Force locale name to lower case, layout will inherit this modified value. */
+    wcslwr(object->format.locale);
+    object->format.weight = weight;
+    object->format.style = style;
+    object->format.fontsize = size;
+    object->format.tabstop = 4.0f * size;
+    object->format.stretch = stretch;
+    object->format.last_line_wrapping = TRUE;
+    object->format.collection = collection;
+    IDWriteFontCollection_AddRef(object->format.collection);
+
+    *format = (IDWriteTextFormat *)&object->IDWriteTextFormat3_iface;
+
+    return S_OK;
+}
+
+static HRESULT WINAPI dwritetrimmingsign_QueryInterface(IDWriteInlineObject *iface, REFIID riid, void **obj)
+{
+    TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), obj);
+
+    if (IsEqualIID(riid, &IID_IUnknown) || IsEqualIID(riid, &IID_IDWriteInlineObject)) {
+        *obj = iface;
+        IDWriteInlineObject_AddRef(iface);
+        return S_OK;
+    }
+
+    WARN("%s not implemented.\n", debugstr_guid(riid));
+
+    *obj = NULL;
+    return E_NOINTERFACE;
+}
+
+static ULONG WINAPI dwritetrimmingsign_AddRef(IDWriteInlineObject *iface)
+{
+    struct dwrite_trimmingsign *sign = impl_from_IDWriteInlineObject(iface);
+    ULONG refcount = InterlockedIncrement(&sign->refcount);
+
+    TRACE("%p, refcount %d.\n", iface, refcount);
+
+    return refcount;
+}
+
+static ULONG WINAPI dwritetrimmingsign_Release(IDWriteInlineObject *iface)
+{
+    struct dwrite_trimmingsign *sign = impl_from_IDWriteInlineObject(iface);
+    ULONG refcount = InterlockedDecrement(&sign->refcount);
+
+    TRACE("%p, refcount %d.\n", iface, refcount);
+
+    if (!refcount)
+    {
+        IDWriteTextLayout_Release(sign->layout);
+        free(sign);
+    }
+
+    return refcount;
+}
+
+static HRESULT WINAPI dwritetrimmingsign_Draw(IDWriteInlineObject *iface, void *context, IDWriteTextRenderer *renderer,
+        float originX, float originY, BOOL is_sideways, BOOL is_rtl, IUnknown *effect)
+{
+    struct dwrite_trimmingsign *sign = impl_from_IDWriteInlineObject(iface);
+    DWRITE_LINE_METRICS line;
+    UINT32 line_count;
+
+    TRACE("%p, %p, %p, %.2f, %.2f, %d, %d, %p.\n", iface, context, renderer, originX, originY,
+            is_sideways, is_rtl, effect);
+
+    IDWriteTextLayout_GetLineMetrics(sign->layout, &line, 1, &line_count);
+    return IDWriteTextLayout_Draw(sign->layout, context, renderer, originX, originY - line.baseline);
+}
+
+static HRESULT WINAPI dwritetrimmingsign_GetMetrics(IDWriteInlineObject *iface, DWRITE_INLINE_OBJECT_METRICS *ret)
+{
+    struct dwrite_trimmingsign *sign = impl_from_IDWriteInlineObject(iface);
+    DWRITE_TEXT_METRICS metrics;
+    HRESULT hr;
+
+    TRACE("%p, %p.\n", iface, ret);
+
+    hr = IDWriteTextLayout_GetMetrics(sign->layout, &metrics);
+    if (FAILED(hr))
+    {
+        memset(ret, 0, sizeof(*ret));
+        return hr;
+    }
+
+    ret->width = metrics.width;
+    ret->height = 0.0f;
+    ret->baseline = 0.0f;
+    ret->supportsSideways = FALSE;
+    return S_OK;
+}
+
+static HRESULT WINAPI dwritetrimmingsign_GetOverhangMetrics(IDWriteInlineObject *iface, DWRITE_OVERHANG_METRICS *overhangs)
+{
+    struct dwrite_trimmingsign *sign = impl_from_IDWriteInlineObject(iface);
+
+    TRACE("%p, %p.\n", iface, overhangs);
+
+    return IDWriteTextLayout_GetOverhangMetrics(sign->layout, overhangs);
+}
+
+static HRESULT WINAPI dwritetrimmingsign_GetBreakConditions(IDWriteInlineObject *iface, DWRITE_BREAK_CONDITION *before,
+        DWRITE_BREAK_CONDITION *after)
+{
+    TRACE("%p, %p, %p.\n", iface, before, after);
+
+    *before = *after = DWRITE_BREAK_CONDITION_NEUTRAL;
+    return S_OK;
+}
+
+static const IDWriteInlineObjectVtbl dwritetrimmingsignvtbl =
+{
+    dwritetrimmingsign_QueryInterface,
+    dwritetrimmingsign_AddRef,
+    dwritetrimmingsign_Release,
+    dwritetrimmingsign_Draw,
+    dwritetrimmingsign_GetMetrics,
+    dwritetrimmingsign_GetOverhangMetrics,
+    dwritetrimmingsign_GetBreakConditions
+};
+
+static inline BOOL is_reading_direction_horz(DWRITE_READING_DIRECTION direction)
+{
+    return (direction == DWRITE_READING_DIRECTION_LEFT_TO_RIGHT) ||
+           (direction == DWRITE_READING_DIRECTION_RIGHT_TO_LEFT);
+}
+
+static inline BOOL is_reading_direction_vert(DWRITE_READING_DIRECTION direction)
+{
+    return (direction == DWRITE_READING_DIRECTION_TOP_TO_BOTTOM) ||
+           (direction == DWRITE_READING_DIRECTION_BOTTOM_TO_TOP);
+}
+
+static inline BOOL is_flow_direction_horz(DWRITE_FLOW_DIRECTION direction)
+{
+    return (direction == DWRITE_FLOW_DIRECTION_LEFT_TO_RIGHT) ||
+           (direction == DWRITE_FLOW_DIRECTION_RIGHT_TO_LEFT);
+}
+
+static inline BOOL is_flow_direction_vert(DWRITE_FLOW_DIRECTION direction)
+{
+    return (direction == DWRITE_FLOW_DIRECTION_TOP_TO_BOTTOM) ||
+           (direction == DWRITE_FLOW_DIRECTION_BOTTOM_TO_TOP);
+}
+
+HRESULT create_trimmingsign(IDWriteFactory7 *factory, IDWriteTextFormat *format, IDWriteInlineObject **sign)
+{
+    struct dwrite_trimmingsign *object;
+    DWRITE_READING_DIRECTION reading;
+    DWRITE_FLOW_DIRECTION flow;
+    HRESULT hr;
+
+    *sign = NULL;
+
+    if (!format)
+        return E_INVALIDARG;
+
+    /* Validate reading/flow direction here, layout creation won't complain about
+       invalid combinations. */
+    reading = IDWriteTextFormat_GetReadingDirection(format);
+    flow = IDWriteTextFormat_GetFlowDirection(format);
+
+    if ((is_reading_direction_horz(reading) && is_flow_direction_horz(flow)) ||
+        (is_reading_direction_vert(reading) && is_flow_direction_vert(flow)))
+        return DWRITE_E_FLOWDIRECTIONCONFLICTS;
+
+    if (!(object = calloc(1, sizeof(*object))))
+        return E_OUTOFMEMORY;
+
+    object->IDWriteInlineObject_iface.lpVtbl = &dwritetrimmingsignvtbl;
+    object->refcount = 1;
+
+    hr = IDWriteFactory7_CreateTextLayout(factory, L"\x2026", 1, format, 0.0f, 0.0f, &object->layout);
+    if (FAILED(hr))
+    {
+        free(object);
+        return hr;
+    }
+
+    IDWriteTextLayout_SetWordWrapping(object->layout, DWRITE_WORD_WRAPPING_NO_WRAP);
+    IDWriteTextLayout_SetParagraphAlignment(object->layout, DWRITE_PARAGRAPH_ALIGNMENT_NEAR);
+    IDWriteTextLayout_SetTextAlignment(object->layout, DWRITE_TEXT_ALIGNMENT_LEADING);
+
+    *sign = &object->IDWriteInlineObject_iface;
+
+    return S_OK;
+}
diff --git a/dlls/dwrite/layout.c b/dlls/dwrite/layout.c
index 2b5e8433d2d..d4aa49c6a6c 100644
--- a/dlls/dwrite/layout.c
+++ b/dlls/dwrite/layout.c
@@ -1,6 +1,4 @@
 /*
- *    Text format and layout
- *
  * Copyright 2012, 2014-2021 Nikolay Sivov for CodeWeavers
  *
  * This library is free software; you can redistribute it and/or
@@ -32,41 +30,6 @@
 
 WINE_DEFAULT_DEBUG_CHANNEL(dwrite);
 
-struct dwrite_textformat_data
-{
-    WCHAR *family_name;
-    UINT32 family_len;
-    WCHAR *locale;
-    UINT32 locale_len;
-
-    DWRITE_FONT_WEIGHT weight;
-    DWRITE_FONT_STYLE style;
-    DWRITE_FONT_STRETCH stretch;
-
-    DWRITE_PARAGRAPH_ALIGNMENT paralign;
-    DWRITE_READING_DIRECTION readingdir;
-    DWRITE_WORD_WRAPPING wrapping;
-    BOOL last_line_wrapping;
-    DWRITE_TEXT_ALIGNMENT textalignment;
-    DWRITE_FLOW_DIRECTION flow;
-    DWRITE_VERTICAL_GLYPH_ORIENTATION vertical_orientation;
-    DWRITE_OPTICAL_ALIGNMENT optical_alignment;
-    DWRITE_LINE_SPACING spacing;
-    DWRITE_AUTOMATIC_FONT_AXES automatic_axes;
-
-    FLOAT fontsize;
-    FLOAT tabstop;
-
-    DWRITE_TRIMMING trimming;
-    IDWriteInlineObject *trimmingsign;
-
-    IDWriteFontCollection *collection;
-    IDWriteFontFallback *fallback;
-
-    DWRITE_FONT_AXIS_VALUE *axis_values;
-    unsigned int axis_values_count;
-};
-
 enum layout_range_attr_kind {
     LAYOUT_RANGE_ATTR_WEIGHT,
     LAYOUT_RANGE_ATTR_STYLE,
@@ -298,21 +261,6 @@ struct dwrite_textlayout
     DWRITE_MATRIX transform;
 };
 
-struct dwrite_textformat
-{
-    IDWriteTextFormat3 IDWriteTextFormat3_iface;
-    LONG refcount;
-    struct dwrite_textformat_data format;
-};
-
-struct dwrite_trimmingsign
-{
-    IDWriteInlineObject IDWriteInlineObject_iface;
-    LONG refcount;
-
-    IDWriteTextLayout *layout;
-};
-
 struct dwrite_typography {
     IDWriteTypography IDWriteTypography_iface;
     LONG refcount;
@@ -322,24 +270,12 @@ struct dwrite_typography {
     size_t count;
 };
 
-static const IDWriteTextFormat3Vtbl dwritetextformatvtbl;
-
-static void release_format_data(struct dwrite_textformat_data *data)
-{
-    if (data->collection) IDWriteFontCollection_Release(data->collection);
-    if (data->fallback) IDWriteFontFallback_Release(data->fallback);
-    if (data->trimmingsign) IDWriteInlineObject_Release(data->trimmingsign);
-    free(data->family_name);
-    free(data->locale);
-    free(data->axis_values);
-}
-
 static inline struct dwrite_textlayout *impl_from_IDWriteTextLayout4(IDWriteTextLayout4 *iface)
 {
     return CONTAINING_RECORD(iface, struct dwrite_textlayout, IDWriteTextLayout4_iface);
 }
 
-static inline struct dwrite_textlayout *impl_layout_from_IDWriteTextFormat3(IDWriteTextFormat3 *iface)
+static inline struct dwrite_textlayout *impl_from_IDWriteTextFormat3(IDWriteTextFormat3 *iface)
 {
     return CONTAINING_RECORD(iface, struct dwrite_textlayout, IDWriteTextFormat3_iface);
 }
@@ -354,18 +290,6 @@ static inline struct dwrite_textlayout *impl_from_IDWriteTextAnalysisSource1(IDW
     return CONTAINING_RECORD(iface, struct dwrite_textlayout, IDWriteTextAnalysisSource1_iface);
 }
 
-static inline struct dwrite_textformat *impl_from_IDWriteTextFormat3(IDWriteTextFormat3 *iface)
-{
-    return CONTAINING_RECORD(iface, struct dwrite_textformat, IDWriteTextFormat3_iface);
-}
-
-static struct dwrite_textformat *unsafe_impl_from_IDWriteTextFormat(IDWriteTextFormat*);
-
-static inline struct dwrite_trimmingsign *impl_from_IDWriteInlineObject(IDWriteInlineObject *iface)
-{
-    return CONTAINING_RECORD(iface, struct dwrite_trimmingsign, IDWriteInlineObject_iface);
-}
-
 static inline struct dwrite_typography *impl_from_IDWriteTypography(IDWriteTypography *iface)
 {
     return CONTAINING_RECORD(iface, struct dwrite_typography, IDWriteTypography_iface);
@@ -381,169 +305,6 @@ static inline BOOL is_layout_gdi_compatible(struct dwrite_textlayout *layout)
     return layout->measuringmode != DWRITE_MEASURING_MODE_NATURAL;
 }
 
-static inline HRESULT format_set_textalignment(struct dwrite_textformat_data *format, DWRITE_TEXT_ALIGNMENT alignment,
-    BOOL *changed)
-{
-    if ((UINT32)alignment > DWRITE_TEXT_ALIGNMENT_JUSTIFIED)
-        return E_INVALIDARG;
-    if (changed) *changed = format->textalignment != alignment;
-    format->textalignment = alignment;
-    return S_OK;
-}
-
-static inline HRESULT format_set_paralignment(struct dwrite_textformat_data *format,
-    DWRITE_PARAGRAPH_ALIGNMENT alignment, BOOL *changed)
-{
-    if ((UINT32)alignment > DWRITE_PARAGRAPH_ALIGNMENT_CENTER)
-        return E_INVALIDARG;
-    if (changed) *changed = format->paralign != alignment;
-    format->paralign = alignment;
-    return S_OK;
-}
-
-static inline HRESULT format_set_readingdirection(struct dwrite_textformat_data *format,
-    DWRITE_READING_DIRECTION direction, BOOL *changed)
-{
-    if ((UINT32)direction > DWRITE_READING_DIRECTION_BOTTOM_TO_TOP)
-        return E_INVALIDARG;
-    if (changed) *changed = format->readingdir != direction;
-    format->readingdir = direction;
-    return S_OK;
-}
-
-static inline HRESULT format_set_wordwrapping(struct dwrite_textformat_data *format,
-    DWRITE_WORD_WRAPPING wrapping, BOOL *changed)
-{
-    if ((UINT32)wrapping > DWRITE_WORD_WRAPPING_CHARACTER)
-        return E_INVALIDARG;
-    if (changed) *changed = format->wrapping != wrapping;
-    format->wrapping = wrapping;
-    return S_OK;
-}
-
-static inline HRESULT format_set_flowdirection(struct dwrite_textformat_data *format,
-    DWRITE_FLOW_DIRECTION direction, BOOL *changed)
-{
-    if ((UINT32)direction > DWRITE_FLOW_DIRECTION_RIGHT_TO_LEFT)
-        return E_INVALIDARG;
-    if (changed) *changed = format->flow != direction;
-    format->flow = direction;
-    return S_OK;
-}
-
-static inline HRESULT format_set_trimming(struct dwrite_textformat_data *format,
-    DWRITE_TRIMMING const *trimming, IDWriteInlineObject *trimming_sign, BOOL *changed)
-{
-    if (changed)
-        *changed = FALSE;
-
-    if ((UINT32)trimming->granularity > DWRITE_TRIMMING_GRANULARITY_WORD)
-        return E_INVALIDARG;
-
-    if (changed) {
-        *changed = !!memcmp(&format->trimming, trimming, sizeof(*trimming));
-        if (format->trimmingsign != trimming_sign)
-            *changed = TRUE;
-    }
-
-    format->trimming = *trimming;
-    if (format->trimmingsign)
-        IDWriteInlineObject_Release(format->trimmingsign);
-    format->trimmingsign = trimming_sign;
-    if (format->trimmingsign)
-        IDWriteInlineObject_AddRef(format->trimmingsign);
-    return S_OK;
-}
-
-static inline HRESULT format_set_linespacing(struct dwrite_textformat_data *format,
-    DWRITE_LINE_SPACING const *spacing, BOOL *changed)
-{
-    if (spacing->height < 0.0f || spacing->leadingBefore < 0.0f || spacing->leadingBefore > 1.0f ||
-        (UINT32)spacing->method > DWRITE_LINE_SPACING_METHOD_PROPORTIONAL)
-        return E_INVALIDARG;
-
-    if (changed)
-        *changed = memcmp(spacing, &format->spacing, sizeof(*spacing));
-
-    format->spacing = *spacing;
-    return S_OK;
-}
-
-static HRESULT format_set_font_axisvalues(struct dwrite_textformat_data *format,
-        DWRITE_FONT_AXIS_VALUE const *axis_values, unsigned int num_values)
-{
-    free(format->axis_values);
-    format->axis_values = NULL;
-    format->axis_values_count = 0;
-
-    if (num_values)
-    {
-        if (!(format->axis_values = calloc(num_values, sizeof(*axis_values))))
-            return E_OUTOFMEMORY;
-        memcpy(format->axis_values, axis_values, num_values * sizeof(*axis_values));
-        format->axis_values_count = num_values;
-    }
-
-    return S_OK;
-}
-
-static HRESULT format_get_font_axisvalues(struct dwrite_textformat_data *format,
-        DWRITE_FONT_AXIS_VALUE *axis_values, unsigned int num_values)
-{
-    if (!format->axis_values_count)
-    {
-        if (num_values) memset(axis_values, 0, num_values * sizeof(*axis_values));
-        return S_OK;
-    }
-
-    if (num_values < format->axis_values_count)
-        return E_NOT_SUFFICIENT_BUFFER;
-
-    memcpy(axis_values, format->axis_values, min(num_values, format->axis_values_count) * sizeof(*axis_values));
-
-    return S_OK;
-}
-
-static HRESULT get_fontfallback_from_format(const struct dwrite_textformat_data *format, IDWriteFontFallback **fallback)
-{
-    *fallback = format->fallback;
-    if (*fallback)
-        IDWriteFontFallback_AddRef(*fallback);
-    return S_OK;
-}
-
-static HRESULT set_fontfallback_for_format(struct dwrite_textformat_data *format, IDWriteFontFallback *fallback)
-{
-    if (format->fallback)
-        IDWriteFontFallback_Release(format->fallback);
-    format->fallback = fallback;
-    if (fallback)
-        IDWriteFontFallback_AddRef(fallback);
-    return S_OK;
-}
-
-static HRESULT format_set_optical_alignment(struct dwrite_textformat_data *format,
-    DWRITE_OPTICAL_ALIGNMENT alignment)
-{
-    if ((UINT32)alignment > DWRITE_OPTICAL_ALIGNMENT_NO_SIDE_BEARINGS)
-        return E_INVALIDARG;
-    format->optical_alignment = alignment;
-    return S_OK;
-}
-
-static HRESULT format_set_vertical_orientation(struct dwrite_textformat_data *format,
-        DWRITE_VERTICAL_GLYPH_ORIENTATION orientation, BOOL *changed)
-{
-    if ((UINT32)orientation > DWRITE_VERTICAL_GLYPH_ORIENTATION_STACKED)
-        return E_INVALIDARG;
-
-    if (changed)
-        *changed = format->vertical_orientation != orientation;
-
-    format->vertical_orientation = orientation;
-    return S_OK;
-}
-
 static BOOL is_run_rtl(const struct layout_effective_run *run)
 {
     return run->run->u.regular.run.bidiLevel & 1;
@@ -4311,7 +4072,7 @@ static HRESULT WINAPI dwritetextlayout2_SetFontFallback(IDWriteTextLayout4 *ifac
 
     TRACE("%p, %p.\n", iface, fallback);
 
-    return set_fontfallback_for_format(&layout->format, fallback);
+    return format_set_fontfallback(&layout->format, fallback);
 }
 
 static HRESULT WINAPI dwritetextlayout2_GetFontFallback(IDWriteTextLayout4 *iface, IDWriteFontFallback **fallback)
@@ -4320,7 +4081,7 @@ static HRESULT WINAPI dwritetextlayout2_GetFontFallback(IDWriteTextLayout4 *ifac
 
     TRACE("%p, %p.\n", iface, fallback);
 
-    return get_fontfallback_from_format(&layout->format, fallback);
+    return format_get_fontfallback(&layout->format, fallback);
 }
 
 static HRESULT WINAPI dwritetextlayout3_InvalidateLayout(IDWriteTextLayout4 *iface)
@@ -4538,7 +4299,7 @@ static const IDWriteTextLayout4Vtbl dwritetextlayoutvtbl =
 
 static HRESULT WINAPI dwritetextformat_layout_QueryInterface(IDWriteTextFormat3 *iface, REFIID riid, void **obj)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), obj);
 
@@ -4547,20 +4308,20 @@ static HRESULT WINAPI dwritetextformat_layout_QueryInterface(IDWriteTextFormat3
 
 static ULONG WINAPI dwritetextformat_layout_AddRef(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     return IDWriteTextLayout4_AddRef(&layout->IDWriteTextLayout4_iface);
 }
 
 static ULONG WINAPI dwritetextformat_layout_Release(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     return IDWriteTextLayout4_Release(&layout->IDWriteTextLayout4_iface);
 }
 
 static HRESULT WINAPI dwritetextformat_layout_SetTextAlignment(IDWriteTextFormat3 *iface,
         DWRITE_TEXT_ALIGNMENT alignment)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     BOOL changed;
     HRESULT hr;
 
@@ -4584,7 +4345,7 @@ static HRESULT WINAPI dwritetextformat_layout_SetTextAlignment(IDWriteTextFormat
 static HRESULT WINAPI dwritetextformat_layout_SetParagraphAlignment(IDWriteTextFormat3 *iface,
         DWRITE_PARAGRAPH_ALIGNMENT alignment)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     BOOL changed;
     HRESULT hr;
 
@@ -4607,7 +4368,7 @@ static HRESULT WINAPI dwritetextformat_layout_SetParagraphAlignment(IDWriteTextF
 
 static HRESULT WINAPI dwritetextformat_layout_SetWordWrapping(IDWriteTextFormat3 *iface, DWRITE_WORD_WRAPPING wrapping)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     BOOL changed;
     HRESULT hr;
 
@@ -4626,7 +4387,7 @@ static HRESULT WINAPI dwritetextformat_layout_SetWordWrapping(IDWriteTextFormat3
 static HRESULT WINAPI dwritetextformat_layout_SetReadingDirection(IDWriteTextFormat3 *iface,
         DWRITE_READING_DIRECTION direction)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     BOOL changed;
     HRESULT hr;
 
@@ -4645,7 +4406,7 @@ static HRESULT WINAPI dwritetextformat_layout_SetReadingDirection(IDWriteTextFor
 static HRESULT WINAPI dwritetextformat_layout_SetFlowDirection(IDWriteTextFormat3 *iface,
         DWRITE_FLOW_DIRECTION direction)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     BOOL changed;
     HRESULT hr;
 
@@ -4663,7 +4424,7 @@ static HRESULT WINAPI dwritetextformat_layout_SetFlowDirection(IDWriteTextFormat
 
 static HRESULT WINAPI dwritetextformat_layout_SetIncrementalTabStop(IDWriteTextFormat3 *iface, FLOAT tabstop)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %.8e.\n", iface, tabstop);
 
@@ -4677,7 +4438,7 @@ static HRESULT WINAPI dwritetextformat_layout_SetIncrementalTabStop(IDWriteTextF
 static HRESULT WINAPI dwritetextformat_layout_SetTrimming(IDWriteTextFormat3 *iface, DWRITE_TRIMMING const *trimming,
     IDWriteInlineObject *trimming_sign)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     BOOL changed;
     HRESULT hr;
 
@@ -4694,7 +4455,7 @@ static HRESULT WINAPI dwritetextformat_layout_SetTrimming(IDWriteTextFormat3 *if
 static HRESULT WINAPI dwritetextformat_layout_SetLineSpacing(IDWriteTextFormat3 *iface,
         DWRITE_LINE_SPACING_METHOD method, FLOAT height, FLOAT baseline)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     DWRITE_LINE_SPACING spacing;
 
     TRACE("%p, %d, %.8e, %.8e.\n", iface, method, height, baseline);
@@ -4708,7 +4469,7 @@ static HRESULT WINAPI dwritetextformat_layout_SetLineSpacing(IDWriteTextFormat3
 
 static DWRITE_TEXT_ALIGNMENT WINAPI dwritetextformat_layout_GetTextAlignment(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4717,7 +4478,7 @@ static DWRITE_TEXT_ALIGNMENT WINAPI dwritetextformat_layout_GetTextAlignment(IDW
 
 static DWRITE_PARAGRAPH_ALIGNMENT WINAPI dwritetextformat_layout_GetParagraphAlignment(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4726,7 +4487,7 @@ static DWRITE_PARAGRAPH_ALIGNMENT WINAPI dwritetextformat_layout_GetParagraphAli
 
 static DWRITE_WORD_WRAPPING WINAPI dwritetextformat_layout_GetWordWrapping(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4735,7 +4496,7 @@ static DWRITE_WORD_WRAPPING WINAPI dwritetextformat_layout_GetWordWrapping(IDWri
 
 static DWRITE_READING_DIRECTION WINAPI dwritetextformat_layout_GetReadingDirection(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4744,7 +4505,7 @@ static DWRITE_READING_DIRECTION WINAPI dwritetextformat_layout_GetReadingDirecti
 
 static DWRITE_FLOW_DIRECTION WINAPI dwritetextformat_layout_GetFlowDirection(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4753,7 +4514,7 @@ static DWRITE_FLOW_DIRECTION WINAPI dwritetextformat_layout_GetFlowDirection(IDW
 
 static FLOAT WINAPI dwritetextformat_layout_GetIncrementalTabStop(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4763,7 +4524,7 @@ static FLOAT WINAPI dwritetextformat_layout_GetIncrementalTabStop(IDWriteTextFor
 static HRESULT WINAPI dwritetextformat_layout_GetTrimming(IDWriteTextFormat3 *iface, DWRITE_TRIMMING *options,
     IDWriteInlineObject **trimming_sign)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %p, %p.\n", iface, options, trimming_sign);
 
@@ -4777,7 +4538,7 @@ static HRESULT WINAPI dwritetextformat_layout_GetTrimming(IDWriteTextFormat3 *if
 static HRESULT WINAPI dwritetextformat_layout_GetLineSpacing(IDWriteTextFormat3 *iface,
         DWRITE_LINE_SPACING_METHOD *method, FLOAT *spacing, FLOAT *baseline)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %p, %p, %p.\n", iface, method, spacing, baseline);
 
@@ -4790,7 +4551,7 @@ static HRESULT WINAPI dwritetextformat_layout_GetLineSpacing(IDWriteTextFormat3
 static HRESULT WINAPI dwritetextformat_layout_GetFontCollection(IDWriteTextFormat3 *iface,
         IDWriteFontCollection **collection)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %p.\n", iface, collection);
 
@@ -4802,7 +4563,7 @@ static HRESULT WINAPI dwritetextformat_layout_GetFontCollection(IDWriteTextForma
 
 static UINT32 WINAPI dwritetextformat_layout_GetFontFamilyNameLength(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4811,7 +4572,7 @@ static UINT32 WINAPI dwritetextformat_layout_GetFontFamilyNameLength(IDWriteText
 
 static HRESULT WINAPI dwritetextformat_layout_GetFontFamilyName(IDWriteTextFormat3 *iface, WCHAR *name, UINT32 size)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %p, %u.\n", iface, name, size);
 
@@ -4822,7 +4583,7 @@ static HRESULT WINAPI dwritetextformat_layout_GetFontFamilyName(IDWriteTextForma
 
 static DWRITE_FONT_WEIGHT WINAPI dwritetextformat_layout_GetFontWeight(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4831,7 +4592,7 @@ static DWRITE_FONT_WEIGHT WINAPI dwritetextformat_layout_GetFontWeight(IDWriteTe
 
 static DWRITE_FONT_STYLE WINAPI dwritetextformat_layout_GetFontStyle(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4840,7 +4601,7 @@ static DWRITE_FONT_STYLE WINAPI dwritetextformat_layout_GetFontStyle(IDWriteText
 
 static DWRITE_FONT_STRETCH WINAPI dwritetextformat_layout_GetFontStretch(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4849,7 +4610,7 @@ static DWRITE_FONT_STRETCH WINAPI dwritetextformat_layout_GetFontStretch(IDWrite
 
 static FLOAT WINAPI dwritetextformat_layout_GetFontSize(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4858,7 +4619,7 @@ static FLOAT WINAPI dwritetextformat_layout_GetFontSize(IDWriteTextFormat3 *ifac
 
 static UINT32 WINAPI dwritetextformat_layout_GetLocaleNameLength(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4867,7 +4628,7 @@ static UINT32 WINAPI dwritetextformat_layout_GetLocaleNameLength(IDWriteTextForm
 
 static HRESULT WINAPI dwritetextformat_layout_GetLocaleName(IDWriteTextFormat3 *iface, WCHAR *name, UINT32 size)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %p, %u.\n", iface, name, size);
 
@@ -4879,7 +4640,7 @@ static HRESULT WINAPI dwritetextformat_layout_GetLocaleName(IDWriteTextFormat3 *
 static HRESULT WINAPI dwritetextformat1_layout_SetVerticalGlyphOrientation(IDWriteTextFormat3 *iface,
         DWRITE_VERTICAL_GLYPH_ORIENTATION orientation)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %d.\n", iface, orientation);
 
@@ -4888,7 +4649,7 @@ static HRESULT WINAPI dwritetextformat1_layout_SetVerticalGlyphOrientation(IDWri
 
 static DWRITE_VERTICAL_GLYPH_ORIENTATION WINAPI dwritetextformat1_layout_GetVerticalGlyphOrientation(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4898,7 +4659,7 @@ static DWRITE_VERTICAL_GLYPH_ORIENTATION WINAPI dwritetextformat1_layout_GetVert
 static HRESULT WINAPI dwritetextformat1_layout_SetLastLineWrapping(IDWriteTextFormat3 *iface,
         BOOL lastline_wrapping_enabled)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %d.\n", iface, lastline_wrapping_enabled);
 
@@ -4908,7 +4669,7 @@ static HRESULT WINAPI dwritetextformat1_layout_SetLastLineWrapping(IDWriteTextFo
 
 static BOOL WINAPI dwritetextformat1_layout_GetLastLineWrapping(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4918,7 +4679,7 @@ static BOOL WINAPI dwritetextformat1_layout_GetLastLineWrapping(IDWriteTextForma
 static HRESULT WINAPI dwritetextformat1_layout_SetOpticalAlignment(IDWriteTextFormat3 *iface,
         DWRITE_OPTICAL_ALIGNMENT alignment)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %d.\n", iface, alignment);
 
@@ -4927,7 +4688,7 @@ static HRESULT WINAPI dwritetextformat1_layout_SetOpticalAlignment(IDWriteTextFo
 
 static DWRITE_OPTICAL_ALIGNMENT WINAPI dwritetextformat1_layout_GetOpticalAlignment(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4937,7 +4698,7 @@ static DWRITE_OPTICAL_ALIGNMENT WINAPI dwritetextformat1_layout_GetOpticalAlignm
 static HRESULT WINAPI dwritetextformat1_layout_SetFontFallback(IDWriteTextFormat3 *iface,
         IDWriteFontFallback *fallback)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %p.\n", iface, fallback);
 
@@ -4947,7 +4708,7 @@ static HRESULT WINAPI dwritetextformat1_layout_SetFontFallback(IDWriteTextFormat
 static HRESULT WINAPI dwritetextformat1_layout_GetFontFallback(IDWriteTextFormat3 *iface,
         IDWriteFontFallback **fallback)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %p.\n", iface, fallback);
 
@@ -4957,20 +4718,20 @@ static HRESULT WINAPI dwritetextformat1_layout_GetFontFallback(IDWriteTextFormat
 static HRESULT WINAPI dwritetextformat2_layout_SetLineSpacing(IDWriteTextFormat3 *iface,
         DWRITE_LINE_SPACING const *spacing)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     return IDWriteTextLayout4_SetLineSpacing(&layout->IDWriteTextLayout4_iface, spacing);
 }
 
 static HRESULT WINAPI dwritetextformat2_layout_GetLineSpacing(IDWriteTextFormat3 *iface, DWRITE_LINE_SPACING *spacing)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     return IDWriteTextLayout4_GetLineSpacing(&layout->IDWriteTextLayout4_iface, spacing);
 }
 
 static HRESULT WINAPI dwritetextformat3_layout_SetFontAxisValues(IDWriteTextFormat3 *iface,
         DWRITE_FONT_AXIS_VALUE const *axis_values, UINT32 num_values)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %p, %u.\n", iface, axis_values, num_values);
 
@@ -4979,7 +4740,7 @@ static HRESULT WINAPI dwritetextformat3_layout_SetFontAxisValues(IDWriteTextForm
 
 static UINT32 WINAPI dwritetextformat3_layout_GetFontAxisValueCount(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p.\n", iface);
 
@@ -4989,7 +4750,7 @@ static UINT32 WINAPI dwritetextformat3_layout_GetFontAxisValueCount(IDWriteTextF
 static HRESULT WINAPI dwritetextformat3_layout_GetFontAxisValues(IDWriteTextFormat3 *iface,
         DWRITE_FONT_AXIS_VALUE *axis_values, UINT32 num_values)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
 
     TRACE("%p, %p, %u.\n", iface, axis_values, num_values);
 
@@ -4998,14 +4759,14 @@ static HRESULT WINAPI dwritetextformat3_layout_GetFontAxisValues(IDWriteTextForm
 
 static DWRITE_AUTOMATIC_FONT_AXES WINAPI dwritetextformat3_layout_GetAutomaticFontAxes(IDWriteTextFormat3 *iface)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     return IDWriteTextLayout4_GetAutomaticFontAxes(&layout->IDWriteTextLayout4_iface);
 }
 
 static HRESULT WINAPI dwritetextformat3_layout_SetAutomaticFontAxes(IDWriteTextFormat3 *iface,
         DWRITE_AUTOMATIC_FONT_AXES axes)
 {
-    struct dwrite_textlayout *layout = impl_layout_from_IDWriteTextFormat3(iface);
+    struct dwrite_textlayout *layout = impl_from_IDWriteTextFormat3(iface);
     return IDWriteTextLayout4_SetAutomaticFontAxes(&layout->IDWriteTextLayout4_iface, axes);
 }
 
@@ -5520,720 +5281,6 @@ HRESULT create_textlayout(const struct textlayout_desc *desc, IDWriteTextLayout
     return hr;
 }
 
-static HRESULT WINAPI dwritetrimmingsign_QueryInterface(IDWriteInlineObject *iface, REFIID riid, void **obj)
-{
-    TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), obj);
-
-    if (IsEqualIID(riid, &IID_IUnknown) || IsEqualIID(riid, &IID_IDWriteInlineObject)) {
-        *obj = iface;
-        IDWriteInlineObject_AddRef(iface);
-        return S_OK;
-    }
-
-    WARN("%s not implemented.\n", debugstr_guid(riid));
-
-    *obj = NULL;
-    return E_NOINTERFACE;
-}
-
-static ULONG WINAPI dwritetrimmingsign_AddRef(IDWriteInlineObject *iface)
-{
-    struct dwrite_trimmingsign *sign = impl_from_IDWriteInlineObject(iface);
-    ULONG refcount = InterlockedIncrement(&sign->refcount);
-
-    TRACE("%p, refcount %d.\n", iface, refcount);
-
-    return refcount;
-}
-
-static ULONG WINAPI dwritetrimmingsign_Release(IDWriteInlineObject *iface)
-{
-    struct dwrite_trimmingsign *sign = impl_from_IDWriteInlineObject(iface);
-    ULONG refcount = InterlockedDecrement(&sign->refcount);
-
-    TRACE("%p, refcount %d.\n", iface, refcount);
-
-    if (!refcount)
-    {
-        IDWriteTextLayout_Release(sign->layout);
-        free(sign);
-    }
-
-    return refcount;
-}
-
-static HRESULT WINAPI dwritetrimmingsign_Draw(IDWriteInlineObject *iface, void *context, IDWriteTextRenderer *renderer,
-    FLOAT originX, FLOAT originY, BOOL is_sideways, BOOL is_rtl, IUnknown *effect)
-{
-    struct dwrite_trimmingsign *sign = impl_from_IDWriteInlineObject(iface);
-    DWRITE_LINE_METRICS line;
-    UINT32 line_count;
-
-    TRACE("%p, %p, %p, %.2f, %.2f, %d, %d, %p.\n", iface, context, renderer, originX, originY,
-            is_sideways, is_rtl, effect);
-
-    IDWriteTextLayout_GetLineMetrics(sign->layout, &line, 1, &line_count);
-    return IDWriteTextLayout_Draw(sign->layout, context, renderer, originX, originY - line.baseline);
-}
-
-static HRESULT WINAPI dwritetrimmingsign_GetMetrics(IDWriteInlineObject *iface, DWRITE_INLINE_OBJECT_METRICS *ret)
-{
-    struct dwrite_trimmingsign *sign = impl_from_IDWriteInlineObject(iface);
-    DWRITE_TEXT_METRICS metrics;
-    HRESULT hr;
-
-    TRACE("%p, %p.\n", iface, ret);
-
-    hr = IDWriteTextLayout_GetMetrics(sign->layout, &metrics);
-    if (FAILED(hr))
-    {
-        memset(ret, 0, sizeof(*ret));
-        return hr;
-    }
-
-    ret->width = metrics.width;
-    ret->height = 0.0f;
-    ret->baseline = 0.0f;
-    ret->supportsSideways = FALSE;
-    return S_OK;
-}
-
-static HRESULT WINAPI dwritetrimmingsign_GetOverhangMetrics(IDWriteInlineObject *iface, DWRITE_OVERHANG_METRICS *overhangs)
-{
-    struct dwrite_trimmingsign *sign = impl_from_IDWriteInlineObject(iface);
-
-    TRACE("%p, %p.\n", iface, overhangs);
-
-    return IDWriteTextLayout_GetOverhangMetrics(sign->layout, overhangs);
-}
-
-static HRESULT WINAPI dwritetrimmingsign_GetBreakConditions(IDWriteInlineObject *iface, DWRITE_BREAK_CONDITION *before,
-        DWRITE_BREAK_CONDITION *after)
-{
-    TRACE("%p, %p, %p.\n", iface, before, after);
-
-    *before = *after = DWRITE_BREAK_CONDITION_NEUTRAL;
-    return S_OK;
-}
-
-static const IDWriteInlineObjectVtbl dwritetrimmingsignvtbl =
-{
-    dwritetrimmingsign_QueryInterface,
-    dwritetrimmingsign_AddRef,
-    dwritetrimmingsign_Release,
-    dwritetrimmingsign_Draw,
-    dwritetrimmingsign_GetMetrics,
-    dwritetrimmingsign_GetOverhangMetrics,
-    dwritetrimmingsign_GetBreakConditions
-};
-
-static inline BOOL is_reading_direction_horz(DWRITE_READING_DIRECTION direction)
-{
-    return (direction == DWRITE_READING_DIRECTION_LEFT_TO_RIGHT) ||
-           (direction == DWRITE_READING_DIRECTION_RIGHT_TO_LEFT);
-}
-
-static inline BOOL is_reading_direction_vert(DWRITE_READING_DIRECTION direction)
-{
-    return (direction == DWRITE_READING_DIRECTION_TOP_TO_BOTTOM) ||
-           (direction == DWRITE_READING_DIRECTION_BOTTOM_TO_TOP);
-}
-
-static inline BOOL is_flow_direction_horz(DWRITE_FLOW_DIRECTION direction)
-{
-    return (direction == DWRITE_FLOW_DIRECTION_LEFT_TO_RIGHT) ||
-           (direction == DWRITE_FLOW_DIRECTION_RIGHT_TO_LEFT);
-}
-
-static inline BOOL is_flow_direction_vert(DWRITE_FLOW_DIRECTION direction)
-{
-    return (direction == DWRITE_FLOW_DIRECTION_TOP_TO_BOTTOM) ||
-           (direction == DWRITE_FLOW_DIRECTION_BOTTOM_TO_TOP);
-}
-
-HRESULT create_trimmingsign(IDWriteFactory7 *factory, IDWriteTextFormat *format, IDWriteInlineObject **sign)
-{
-    static const WCHAR ellipsisW = 0x2026;
-    struct dwrite_trimmingsign *object;
-    DWRITE_READING_DIRECTION reading;
-    DWRITE_FLOW_DIRECTION flow;
-    HRESULT hr;
-
-    *sign = NULL;
-
-    if (!format)
-        return E_INVALIDARG;
-
-    /* Validate reading/flow direction here, layout creation won't complain about
-       invalid combinations. */
-    reading = IDWriteTextFormat_GetReadingDirection(format);
-    flow = IDWriteTextFormat_GetFlowDirection(format);
-
-    if ((is_reading_direction_horz(reading) && is_flow_direction_horz(flow)) ||
-        (is_reading_direction_vert(reading) && is_flow_direction_vert(flow)))
-        return DWRITE_E_FLOWDIRECTIONCONFLICTS;
-
-    if (!(object = calloc(1, sizeof(*object))))
-        return E_OUTOFMEMORY;
-
-    object->IDWriteInlineObject_iface.lpVtbl = &dwritetrimmingsignvtbl;
-    object->refcount = 1;
-
-    hr = IDWriteFactory7_CreateTextLayout(factory, &ellipsisW, 1, format, 0.0f, 0.0f, &object->layout);
-    if (FAILED(hr))
-    {
-        free(object);
-        return hr;
-    }
-
-    IDWriteTextLayout_SetWordWrapping(object->layout, DWRITE_WORD_WRAPPING_NO_WRAP);
-    IDWriteTextLayout_SetParagraphAlignment(object->layout, DWRITE_PARAGRAPH_ALIGNMENT_NEAR);
-    IDWriteTextLayout_SetTextAlignment(object->layout, DWRITE_TEXT_ALIGNMENT_LEADING);
-
-    *sign = &object->IDWriteInlineObject_iface;
-
-    return S_OK;
-}
-
-static HRESULT WINAPI dwritetextformat_QueryInterface(IDWriteTextFormat3 *iface, REFIID riid, void **obj)
-{
-    TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), obj);
-
-    if (IsEqualIID(riid, &IID_IDWriteTextFormat3) ||
-        IsEqualIID(riid, &IID_IDWriteTextFormat2) ||
-        IsEqualIID(riid, &IID_IDWriteTextFormat1) ||
-        IsEqualIID(riid, &IID_IDWriteTextFormat)  ||
-        IsEqualIID(riid, &IID_IUnknown))
-    {
-        *obj = iface;
-        IDWriteTextFormat3_AddRef(iface);
-        return S_OK;
-    }
-
-    WARN("%s not implemented.\n", debugstr_guid(riid));
-
-    *obj = NULL;
-
-    return E_NOINTERFACE;
-}
-
-static ULONG WINAPI dwritetextformat_AddRef(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-    ULONG refcount = InterlockedIncrement(&format->refcount);
-
-    TRACE("%p, refcount %d.\n", iface, refcount);
-
-    return refcount;
-}
-
-static ULONG WINAPI dwritetextformat_Release(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-    ULONG refcount = InterlockedDecrement(&format->refcount);
-
-    TRACE("%p, refcount %d.\n", iface, refcount);
-
-    if (!refcount)
-    {
-        release_format_data(&format->format);
-        free(format);
-    }
-
-    return refcount;
-}
-
-static HRESULT WINAPI dwritetextformat_SetTextAlignment(IDWriteTextFormat3 *iface, DWRITE_TEXT_ALIGNMENT alignment)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %d.\n", iface, alignment);
-
-    return format_set_textalignment(&format->format, alignment, NULL);
-}
-
-static HRESULT WINAPI dwritetextformat_SetParagraphAlignment(IDWriteTextFormat3 *iface,
-        DWRITE_PARAGRAPH_ALIGNMENT alignment)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %d.\n", iface, alignment);
-
-    return format_set_paralignment(&format->format, alignment, NULL);
-}
-
-static HRESULT WINAPI dwritetextformat_SetWordWrapping(IDWriteTextFormat3 *iface, DWRITE_WORD_WRAPPING wrapping)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %d.\n", iface, wrapping);
-
-    return format_set_wordwrapping(&format->format, wrapping, NULL);
-}
-
-static HRESULT WINAPI dwritetextformat_SetReadingDirection(IDWriteTextFormat3 *iface, DWRITE_READING_DIRECTION direction)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %d.\n", iface, direction);
-
-    return format_set_readingdirection(&format->format, direction, NULL);
-}
-
-static HRESULT WINAPI dwritetextformat_SetFlowDirection(IDWriteTextFormat3 *iface, DWRITE_FLOW_DIRECTION direction)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %d.\n", iface, direction);
-
-    return format_set_flowdirection(&format->format, direction, NULL);
-}
-
-static HRESULT WINAPI dwritetextformat_SetIncrementalTabStop(IDWriteTextFormat3 *iface, FLOAT tabstop)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %f.\n", iface, tabstop);
-
-    if (tabstop <= 0.0f)
-        return E_INVALIDARG;
-
-    format->format.tabstop = tabstop;
-    return S_OK;
-}
-
-static HRESULT WINAPI dwritetextformat_SetTrimming(IDWriteTextFormat3 *iface, DWRITE_TRIMMING const *trimming,
-    IDWriteInlineObject *trimming_sign)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p, %p.\n", iface, trimming, trimming_sign);
-
-    return format_set_trimming(&format->format, trimming, trimming_sign, NULL);
-}
-
-static HRESULT WINAPI dwritetextformat_SetLineSpacing(IDWriteTextFormat3 *iface, DWRITE_LINE_SPACING_METHOD method,
-    FLOAT height, FLOAT baseline)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-    DWRITE_LINE_SPACING spacing;
-
-    TRACE("%p, %d, %f, %f.\n", iface, method, height, baseline);
-
-    spacing = format->format.spacing;
-    spacing.method = method;
-    spacing.height = height;
-    spacing.baseline = baseline;
-
-    return format_set_linespacing(&format->format, &spacing, NULL);
-}
-
-static DWRITE_TEXT_ALIGNMENT WINAPI dwritetextformat_GetTextAlignment(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.textalignment;
-}
-
-static DWRITE_PARAGRAPH_ALIGNMENT WINAPI dwritetextformat_GetParagraphAlignment(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.paralign;
-}
-
-static DWRITE_WORD_WRAPPING WINAPI dwritetextformat_GetWordWrapping(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.wrapping;
-}
-
-static DWRITE_READING_DIRECTION WINAPI dwritetextformat_GetReadingDirection(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.readingdir;
-}
-
-static DWRITE_FLOW_DIRECTION WINAPI dwritetextformat_GetFlowDirection(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.flow;
-}
-
-static FLOAT WINAPI dwritetextformat_GetIncrementalTabStop(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.tabstop;
-}
-
-static HRESULT WINAPI dwritetextformat_GetTrimming(IDWriteTextFormat3 *iface, DWRITE_TRIMMING *options,
-    IDWriteInlineObject **trimming_sign)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p, %p.\n", iface, options, trimming_sign);
-
-    *options = format->format.trimming;
-    if ((*trimming_sign = format->format.trimmingsign))
-        IDWriteInlineObject_AddRef(*trimming_sign);
-
-    return S_OK;
-}
-
-static HRESULT WINAPI dwritetextformat_GetLineSpacing(IDWriteTextFormat3 *iface, DWRITE_LINE_SPACING_METHOD *method,
-    FLOAT *spacing, FLOAT *baseline)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p, %p, %p.\n", iface, method, spacing, baseline);
-
-    *method = format->format.spacing.method;
-    *spacing = format->format.spacing.height;
-    *baseline = format->format.spacing.baseline;
-    return S_OK;
-}
-
-static HRESULT WINAPI dwritetextformat_GetFontCollection(IDWriteTextFormat3 *iface, IDWriteFontCollection **collection)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p.\n", iface, collection);
-
-    *collection = format->format.collection;
-    IDWriteFontCollection_AddRef(*collection);
-
-    return S_OK;
-}
-
-static UINT32 WINAPI dwritetextformat_GetFontFamilyNameLength(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.family_len;
-}
-
-static HRESULT WINAPI dwritetextformat_GetFontFamilyName(IDWriteTextFormat3 *iface, WCHAR *name, UINT32 size)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p, %u.\n", iface, name, size);
-
-    if (size <= format->format.family_len)
-        return E_NOT_SUFFICIENT_BUFFER;
-    wcscpy(name, format->format.family_name);
-    return S_OK;
-}
-
-static DWRITE_FONT_WEIGHT WINAPI dwritetextformat_GetFontWeight(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.weight;
-}
-
-static DWRITE_FONT_STYLE WINAPI dwritetextformat_GetFontStyle(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.style;
-}
-
-static DWRITE_FONT_STRETCH WINAPI dwritetextformat_GetFontStretch(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.stretch;
-}
-
-static FLOAT WINAPI dwritetextformat_GetFontSize(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.fontsize;
-}
-
-static UINT32 WINAPI dwritetextformat_GetLocaleNameLength(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.locale_len;
-}
-
-static HRESULT WINAPI dwritetextformat_GetLocaleName(IDWriteTextFormat3 *iface, WCHAR *name, UINT32 size)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p %u.\n", iface, name, size);
-
-    if (size <= format->format.locale_len)
-        return E_NOT_SUFFICIENT_BUFFER;
-    wcscpy(name, format->format.locale);
-    return S_OK;
-}
-
-static HRESULT WINAPI dwritetextformat1_SetVerticalGlyphOrientation(IDWriteTextFormat3 *iface,
-        DWRITE_VERTICAL_GLYPH_ORIENTATION orientation)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %d.\n", iface, orientation);
-
-    return format_set_vertical_orientation(&format->format, orientation, NULL);
-}
-
-static DWRITE_VERTICAL_GLYPH_ORIENTATION WINAPI dwritetextformat1_GetVerticalGlyphOrientation(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.vertical_orientation;
-}
-
-static HRESULT WINAPI dwritetextformat1_SetLastLineWrapping(IDWriteTextFormat3 *iface, BOOL lastline_wrapping_enabled)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %d.\n", iface, lastline_wrapping_enabled);
-
-    format->format.last_line_wrapping = !!lastline_wrapping_enabled;
-    return S_OK;
-}
-
-static BOOL WINAPI dwritetextformat1_GetLastLineWrapping(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.last_line_wrapping;
-}
-
-static HRESULT WINAPI dwritetextformat1_SetOpticalAlignment(IDWriteTextFormat3 *iface, DWRITE_OPTICAL_ALIGNMENT alignment)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %d.\n", iface, alignment);
-
-    return format_set_optical_alignment(&format->format, alignment);
-}
-
-static DWRITE_OPTICAL_ALIGNMENT WINAPI dwritetextformat1_GetOpticalAlignment(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.optical_alignment;
-}
-
-static HRESULT WINAPI dwritetextformat1_SetFontFallback(IDWriteTextFormat3 *iface, IDWriteFontFallback *fallback)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p.\n", iface, fallback);
-
-    return set_fontfallback_for_format(&format->format, fallback);
-}
-
-static HRESULT WINAPI dwritetextformat1_GetFontFallback(IDWriteTextFormat3 *iface, IDWriteFontFallback **fallback)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p.\n", iface, fallback);
-
-    return get_fontfallback_from_format(&format->format, fallback);
-}
-
-static HRESULT WINAPI dwritetextformat2_SetLineSpacing(IDWriteTextFormat3 *iface, DWRITE_LINE_SPACING const *spacing)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p.\n", iface, spacing);
-
-    return format_set_linespacing(&format->format, spacing, NULL);
-}
-
-static HRESULT WINAPI dwritetextformat2_GetLineSpacing(IDWriteTextFormat3 *iface, DWRITE_LINE_SPACING *spacing)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p.\n", iface, spacing);
-
-    *spacing = format->format.spacing;
-    return S_OK;
-}
-
-static HRESULT WINAPI dwritetextformat3_SetFontAxisValues(IDWriteTextFormat3 *iface,
-        DWRITE_FONT_AXIS_VALUE const *axis_values, UINT32 num_values)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p, %u.\n", iface, axis_values, num_values);
-
-    return format_set_font_axisvalues(&format->format, axis_values, num_values);
-}
-
-static UINT32 WINAPI dwritetextformat3_GetFontAxisValueCount(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.axis_values_count;
-}
-
-static HRESULT WINAPI dwritetextformat3_GetFontAxisValues(IDWriteTextFormat3 *iface,
-        DWRITE_FONT_AXIS_VALUE *axis_values, UINT32 num_values)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %p, %u.\n", iface, axis_values, num_values);
-
-    return format_get_font_axisvalues(&format->format, axis_values, num_values);
-}
-
-static DWRITE_AUTOMATIC_FONT_AXES WINAPI dwritetextformat3_GetAutomaticFontAxes(IDWriteTextFormat3 *iface)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p.\n", iface);
-
-    return format->format.automatic_axes;
-}
-
-static HRESULT WINAPI dwritetextformat3_SetAutomaticFontAxes(IDWriteTextFormat3 *iface, DWRITE_AUTOMATIC_FONT_AXES axes)
-{
-    struct dwrite_textformat *format = impl_from_IDWriteTextFormat3(iface);
-
-    TRACE("%p, %d.\n", iface, axes);
-
-    format->format.automatic_axes = axes;
-
-    return S_OK;
-}
-
-static const IDWriteTextFormat3Vtbl dwritetextformatvtbl =
-{
-    dwritetextformat_QueryInterface,
-    dwritetextformat_AddRef,
-    dwritetextformat_Release,
-    dwritetextformat_SetTextAlignment,
-    dwritetextformat_SetParagraphAlignment,
-    dwritetextformat_SetWordWrapping,
-    dwritetextformat_SetReadingDirection,
-    dwritetextformat_SetFlowDirection,
-    dwritetextformat_SetIncrementalTabStop,
-    dwritetextformat_SetTrimming,
-    dwritetextformat_SetLineSpacing,
-    dwritetextformat_GetTextAlignment,
-    dwritetextformat_GetParagraphAlignment,
-    dwritetextformat_GetWordWrapping,
-    dwritetextformat_GetReadingDirection,
-    dwritetextformat_GetFlowDirection,
-    dwritetextformat_GetIncrementalTabStop,
-    dwritetextformat_GetTrimming,
-    dwritetextformat_GetLineSpacing,
-    dwritetextformat_GetFontCollection,
-    dwritetextformat_GetFontFamilyNameLength,
-    dwritetextformat_GetFontFamilyName,
-    dwritetextformat_GetFontWeight,
-    dwritetextformat_GetFontStyle,
-    dwritetextformat_GetFontStretch,
-    dwritetextformat_GetFontSize,
-    dwritetextformat_GetLocaleNameLength,
-    dwritetextformat_GetLocaleName,
-    dwritetextformat1_SetVerticalGlyphOrientation,
-    dwritetextformat1_GetVerticalGlyphOrientation,
-    dwritetextformat1_SetLastLineWrapping,
-    dwritetextformat1_GetLastLineWrapping,
-    dwritetextformat1_SetOpticalAlignment,
-    dwritetextformat1_GetOpticalAlignment,
-    dwritetextformat1_SetFontFallback,
-    dwritetextformat1_GetFontFallback,
-    dwritetextformat2_SetLineSpacing,
-    dwritetextformat2_GetLineSpacing,
-    dwritetextformat3_SetFontAxisValues,
-    dwritetextformat3_GetFontAxisValueCount,
-    dwritetextformat3_GetFontAxisValues,
-    dwritetextformat3_GetAutomaticFontAxes,
-    dwritetextformat3_SetAutomaticFontAxes,
-};
-
-static struct dwrite_textformat *unsafe_impl_from_IDWriteTextFormat(IDWriteTextFormat *iface)
-{
-    return (iface->lpVtbl == (IDWriteTextFormatVtbl*)&dwritetextformatvtbl) ?
-        CONTAINING_RECORD(iface, struct dwrite_textformat, IDWriteTextFormat3_iface) : NULL;
-}
-
-HRESULT create_textformat(const WCHAR *family_name, IDWriteFontCollection *collection, DWRITE_FONT_WEIGHT weight,
-        DWRITE_FONT_STYLE style, DWRITE_FONT_STRETCH stretch, FLOAT size, const WCHAR *locale, IDWriteTextFormat **format)
-{
-    struct dwrite_textformat *object;
-
-    *format = NULL;
-
-    if (size <= 0.0f)
-        return E_INVALIDARG;
-
-    if (((UINT32)weight > DWRITE_FONT_WEIGHT_ULTRA_BLACK) ||
-        ((UINT32)stretch > DWRITE_FONT_STRETCH_ULTRA_EXPANDED) ||
-        ((UINT32)style > DWRITE_FONT_STYLE_ITALIC))
-        return E_INVALIDARG;
-
-    if (!(object = calloc(1, sizeof(*object))))
-        return E_OUTOFMEMORY;
-
-    object->IDWriteTextFormat3_iface.lpVtbl = &dwritetextformatvtbl;
-    object->refcount = 1;
-    object->format.family_name = wcsdup(family_name);
-    object->format.family_len = wcslen(family_name);
-    object->format.locale = wcsdup(locale);
-    object->format.locale_len = wcslen(locale);
-    /* Force locale name to lower case, layout will inherit this modified value. */
-    wcslwr(object->format.locale);
-    object->format.weight = weight;
-    object->format.style = style;
-    object->format.fontsize = size;
-    object->format.tabstop = 4.0f * size;
-    object->format.stretch = stretch;
-    object->format.last_line_wrapping = TRUE;
-    object->format.collection = collection;
-    IDWriteFontCollection_AddRef(object->format.collection);
-
-    *format = (IDWriteTextFormat *)&object->IDWriteTextFormat3_iface;
-
-    return S_OK;
-}
-
 static HRESULT WINAPI dwritetypography_QueryInterface(IDWriteTypography *iface, REFIID riid, void **obj)
 {
     TRACE("%p, %s, %p.\n", iface, debugstr_guid(riid), obj);
-- 
2.34.1




More information about the wine-devel mailing list