Прозрачность текста в GDI - PullRequest
       34

Прозрачность текста в GDI

8 голосов
/ 27 августа 2009

Я создал растровое изображение, используя GDI +. Я рисую текст на этом растровом изображении, используя GDI Drawtext. С помощью Drawtext я не могу применить прозрачность. Любая помощь или код будет оценен.

Ответы [ 5 ]

13 голосов
/ 28 августа 2009

Если вы хотите нарисовать текст без фоновой заливки, SetBkMode(hdc,TRANSPARENT) скажет GDI оставить фон при рисовании текста.


Фактически отобразить цвет текста текста с помощью альфы ... будет сложнее. GDI на самом деле не поддерживает альфа-каналы в API. За пределами AlphaBlend фактически все, что он делает, это сохраняет канал. На самом деле недопустимо устанавливать для старших битов COLOREF значения альфа, поскольку старший байт фактически используется для флагов, чтобы указать, является ли COLOREF (а не значение RGB) записью палитры.

Так что, к сожалению, ваш единственный реальный путь вперед - это:

  1. Создание 32-битной DIBSection. ( CreateDIBSection ). Это дает вам HBITMAP, который гарантированно сможет хранить альфа-информацию. Если вы создаете растровое изображение с помощью одной из других функций создания растрового изображения, оно будет иметь цветовую глубину устройства, которая может быть не 32 бит / с.
  2. DrawText на DIBSection.
  3. Когда вы создали раздел DIBSection, вы получили указатель на фактическую память. На данный момент вам нужно пройти через память и установить альфа-значения. Я не думаю, что DrawText вообще что-то сделает с альфа-каналом. Я думаю о простой проверке компонентов RGB каждого DWORD растрового изображения - если они являются основным цветом, переписывают DWORD с 50% (или любым другим) альфа-значением в альфа-байте, если они имеют цвет фона, перезаписывают с 100% альфа в альфа-байт. *
  4. AlphaBlend растровое изображение в конечном пункте назначения. AlphaBlend требует предварительного умножения альфа-канала в источнике.

* Может быть достаточно просто установить DIBSection с 50% альфа перед выполнением DrawText и убедиться, что BKColor черный. Я не знаю, что DrawText может сделать с альфа-каналом, хотя. Требуются некоторые эксперименты.

8 голосов
/ 04 января 2013

ПРОСТОЕ и ЛЕГКОЕ решение:)

Если бы была эта проблема, я пытался изменить альфа-значения и предварительно умножить их, но была еще одна проблема - сглаженные шрифты и шрифты с открытым типом, где они не отображались правильно (некрасивые края). Так что я сделал ...

  1. Создайте свою сцену (растровые изображения, графику и т. Д.)
  2. BitBlt требуется прямоугольник из этой сцены (такой же, как ваш текстовый прямоугольник, из того места, где вы хотите, чтобы ваш текст был) в память DC с совместимым растровым изображением, выбранным в координатах 0,0 назначения
  3. Нарисуйте свой текст в этот прямоугольник в памяти DC.
  4. Теперь AlphaBlend этот прямоугольник без AC_SRC_ALPHA в BLENDFUNCTION и с нужным SourceConstantAlpha из этого DC памяти обратно в DC вашей сцены.

Я думаю, Вы поняли:)

0 голосов
/ 10 апреля 2014

Ограниченный ответ для конкретной ситуации:

Если у вас есть изображение с альфа-каналом и вы хотите нарисовать непрозрачный текст на локально непрозрачном фоне, сначала подготовьте 32-битное растровое изображение с помощью 32-битных кистей, созданных с помощью CreateDIBPatternBrushPt. Затем отсканируйте биты растрового изображения, инвертируя альфа-канал, нарисуйте текст, как обычно (включая SetBkMode до TRANSPARENT), затем снова инвертируйте альфа в растровом изображении. Вы можете пропустить первую инверсию, если инвертируете альфу своих кистей.

0 голосов
/ 14 апреля 2012

Хотя этот вопрос о том, чтобы сделать текст полупрозрачным, у меня была противоположная проблема.

DrawText был , делая текст в моем многослойном окне (UpdateLayeredWindow) полупрозрачным ... и я не хотел, чтобы это было.

Взгляните на этот другой вопрос ... так как в другом вопросе я публикую некоторый код, который вы могли бы легко изменить ... и это почти точно то, что предлагает Крис Бекке в своем ответе. *

0 голосов
/ 15 января 2011

Хммммм - пытаясь сделать то же самое здесь - интересно - я вижу, что когда вы создаете секцию DIB, вы указываете «маски», которые представляют собой маски R, G, B (и альфа).

ЕСЛИ это очень важно, если он действительно не изменяет альфа-канал, тогда вы можете указать маску по-разному для двух растровых заголовков. Один определяет RGB в соответствующих местах, другой заставляет их все иметь свои биты, назначенные альфа-каналу. (установите цвет текста в этом случае на белый), затем выполните рендеринг в два прохода, один для загрузки значений цвета, другой для загрузки значений альфа.

???? в любом случае просто размышляю:)

...