1

我正在使用FW1FontWrapper库来包装我的 DirectX 11 C++ 应用程序中使用的字体。

我想更改用 . 渲染的文本中的行距(两行文本之间的距离)FW1FontWrapper

我知道在 DirectX 中我可以使用它IDWriteTextFormat::SetLineSpacing(DWRITE_LINE_SPACING_METHOD_UNIFORM, 30.0f, 20.0f)

不幸的是,我不知道如何访问正确的IDWriteTextFormat结构。

我试图:

HRESULT hResult = FW1CreateFactory(FW1_VERSION, &FW1Factory);
hResult = FW1Factory->CreateFontWrapper(device, L"Arial", &fontWrapper);

//my attemp - first get the IDWriteFactory
IDWriteFactory *pDWriteFactory;
hResult = fontWrapper->GetDWriteFactory(&pDWriteFactory);

//and now the IDWriteTextFormat 
IDWriteTextFormat *pTextFormat;
hResult = pDWriteFactory->CreateTextFormat(L"Arial", NULL, 
    DWRITE_FONT_WEIGHT_NORMAL, DWRITE_FONT_STYLE_NORMAL, 
    DWRITE_FONT_STRETCH_NORMAL, 10.0f, L"", &pTextFormat);
pTextFormat->SetLineSpacing(DWRITE_LINE_SPACING_METHOD_UNIFORM, 100.f, 20.0f);

我想它不起作用,因为这样我创建和修改了new IDWriteTextFormat,而不是通过以下方式影响渲染的那个:

fontWrapper->DrawString(
   context,
   s2ws(content).c_str(),// String
   fontSize,// Font size
   startTextPosition.getX(),// X position
   startTextPosition.getY(),// Y position
   color,// Text color, 0xAaBbGgRr
   FW1_RESTORESTATE// Flags (for example FW1_RESTORESTATE to keep 
        //context states unchanged)
 );

那么,如何访问权限IDWriteTextFormat(我要修改的那个会影响渲染;不是新的那个)?

据我所知FW1FontWrapper,没有自己的方法来设置行距。

4

1 回答 1

5

查看 FW1FontWrapper 模块的源代码,您可以看到DrawString内部使用了IDWriteTextFormat您无法访问的默认值。

解决方案是使用DrawTextLayout而不是DrawString.

为此(使用您的变量名),首先创建工厂并IFW1FontWrapper在您现有的代码中:

HRESULT hResult = FW1CreateFactory(FW1_VERSION, &FW1Factory);
hResult = FW1Factory->CreateFontWrapper(device, L"Arial", &fontWrapper);

然后获取 DWrite 工厂并IDWriteTextFormat使用所需的行距创建(同样,这是您现有的代码):

// get the DirectWrite factory used by the font-wrapper
IDWriteFactory *pDWriteFactory;
hResult = fontWrapper->GetDWriteFactory(&pDWriteFactory);

// create an IDWriteTextFormat and set line spacing
IDWriteTextFormat *pTextFormat;
hResult = pDWriteFactory->CreateTextFormat(L"Arial", NULL, 
    DWRITE_FONT_WEIGHT_NORMAL, DWRITE_FONT_STYLE_NORMAL, 
    DWRITE_FONT_STRETCH_NORMAL, 10.0f, L"", &pTextFormat);
pTextFormat->SetLineSpacing(DWRITE_LINE_SPACING_METHOD_UNIFORM, 100.f, 20.0f);

接下来,IDWriteTextLayout为您的字符串创建一个(使用您的变量名)并使用IDWriteTextFormat上面创建的:

// create a DirectWrite text layout for the string
// using the above IDWriteTextFormat 
IDWriteTextLayout *pTextLayout;
unsigned int stringLength = s2ws(content).size();
hResult = pDWriteFactory->CreateTextLayout(
    s2ws(content).c_str(),
    stringLength,
    pTextFormat,
    0.0f,
    0.0f,
    &pTextLayout);

设置对象中的字体大小IDWriteTextLayout

// set the required font size
DWRITE_TEXT_RANGE allText = {0, stringLength};
pTextLayout->SetFontSize(fontSize, allText);

DrawTextLayout最后,使用(再次使用变量名)绘制文本:

// draw the text
fontWrapper->DrawTextLayout(
    context,
    pTextLayout,
    startTextPosition.getX(),
    startTextPosition.getX(),
    color,
    NULL,
    NULL,
    FW1_RESTORESTATE);

// tidy up interfaces
pTextLayout->Release();
pTextLayout = NULL;

我可能从您现有的代码中做出了一些错误的假设,但您可以看到如何IDWriteTextFormat通过IDWriteTextLayout实例使用您自己的代码,然后使用DrawTextLayout而不是DrawString. 我希望这有帮助。

于 2013-09-14T13:07:36.877 回答