Vue d'ensemble des masques d'opacité
Cette rubrique explique comment utiliser des bitmaps et des pinceaux pour définir des masques d’opacité. Elle contient les sections suivantes.
- Composants requis
- Qu’est-ce qu’un masque d’opacité ?
- Utiliser une bitmap comme masque d’opacité avec la méthode FillOpacityMask
- Utiliser un pinceau comme masque d’opacité avec la méthode FillGeometry
- Appliquer un masque d’opacité à un calque
- Rubriques connexes
Prérequis
Cette vue d’ensemble suppose que vous êtes familiarisé avec les opérations de dessin Direct2D de base, comme décrit dans la procédure pas à pas Créer une application Direct2D simple . Vous devez également être familiarisé avec les différents types de pinceaux, comme décrit dans la vue d’ensemble des pinceaux.
Qu’est-ce qu’un masque d’opacité ?
Un masque d’opacité est un masque, décrit par un pinceau ou une bitmap, qui est appliqué à un autre objet pour rendre cet objet partiellement ou complètement transparent. Un masque d’opacité utilise des informations de canal alpha pour spécifier la façon dont les pixels sources de l’objet sont fusionnés dans la cible de destination finale. Les parties transparentes du masque indiquent les zones où l’image sous-jacente est masquée, tandis que les parties opaques du masque indiquent où l’objet masqué est visible.
Il existe plusieurs façons d’appliquer un masque d’opacité :
- Utilisez la méthode ID2D1RenderTarget::FillOpacityMask . La méthode FillOpacityMask peint une zone rectangulaire d’une cible de rendu, puis applique un masque d’opacité, défini par une bitmap. Utilisez cette méthode lorsque votre masque d’opacité est une bitmap et que vous souhaitez remplir une zone rectangulaire.
- Utilisez la méthode ID2D1RenderTarget::FillGeometry . La méthode FillGeometry peint l’intérieur de la géométrie avec l’id2D1BitmapBrush spécifié, puis applique un masque d’opacité, défini par un pinceau. Utilisez cette méthode lorsque vous souhaitez appliquer un masque d’opacité à une géométrie ou utiliser un pinceau comme masque d’opacité.
- Utilisez un ID2D1Layer pour appliquer un masque d’opacité. Utilisez cette approche lorsque vous souhaitez appliquer un masque d’opacité à un groupe de contenu de dessin, et pas seulement à une seule forme ou image. Pour plus d’informations, consultez Vue d’ensemble des couches.
Utiliser une bitmap comme masque d’opacité avec la méthode FillOpacityMask
La méthode FillOpacityMask peint une région rectangulaire d’une cible de rendu, puis applique un masque d’opacité, défini par un ID2D1Bitmap. Utilisez cette méthode lorsque vous avez une bitmap que vous souhaitez utiliser comme masque d’opacité pour une région rectangulaire.
Le diagramme suivant montre un effet de l’application du masque d’opacité ( id2D1Bitmap avec une image d’une fleur) à un ID2D1BitmapBrush avec une image d’une plante de fougère. L’image obtenue est une image bitmap d’une plante coupée à la forme de fleur.
Les exemples de code suivants montrent comment procéder.
Le premier exemple charge la bitmap suivante, m_pBitmapMask, pour l’utiliser comme masque bitmap. L’illustration suivante montre la sortie produite. Notez que, bien que la partie opaque de la bitmap apparaisse en noir, les informations de couleur dans la bitmap n’ont aucun effet sur le masque d’opacité ; seules les informations d’opacité de chaque pixel de la bitmap sont utilisées. Les pixels entièrement opaques de cette bitmap ont été colorés en noir à titre d’illustration uniquement.
Dans cet exemple, l’ID2D1Bitmap est chargé par une méthode d’assistance, LoadResourceBitmap, définie ailleurs dans l’exemple.
if (SUCCEEDED(hr))
{
hr = LoadResourceBitmap(
m_pRenderTarget,
m_pWICFactory,
L"BitmapMask",
L"Image",
&m_pBitmapMask
);
}
L’exemple suivant définit le pinceau , m_pFernBitmapBrush, auquel le masque d’opacité est appliqué. Cet exemple utilise un ID2D1BitmapBrush qui contient une image d’une fougère, mais vous pouvez utiliser un ID2D1SolidColorBrush, ID2D1LinearGradientBrush ou ID2D1RadialGradientBrush à la place. L’illustration suivante montre la sortie produite.
if (SUCCEEDED(hr))
{
D2D1_BITMAP_BRUSH_PROPERTIES propertiesXClampYClamp =
D2D1::BitmapBrushProperties(
D2D1_EXTEND_MODE_CLAMP,
D2D1_EXTEND_MODE_CLAMP,
D2D1_BITMAP_INTERPOLATION_MODE_NEAREST_NEIGHBOR
);
hr = m_pRenderTarget->CreateBitmapBrush(
m_pFernBitmap,
propertiesXClampYClamp,
&m_pFernBitmapBrush
);
}
Maintenant que le masque d’opacité et le pinceau sont définis, vous pouvez utiliser la méthode FillOpacityMask dans la méthode de rendu de votre application. Lorsque vous appelez la méthode FillOpacityMask , vous devez spécifier le type de masque d’opacité que vous utilisez : D2D1_OPACITY_MASK_CONTENT_GRAPHICS, D2D1_OPACITY_MASK_CONTENT_TEXT_NATURAL et D2D1_OPACITY_MASK_CONTENT_TEXT_GDI_COMPATIBLE. Pour connaître les significations de ces trois types, consultez D2D1_OPACITY_MASK_CONTENT.
Notes
À compter de Windows 8, le D2D1_OPACITY_MASK_CONTENT n’est pas obligatoire. Consultez la méthode ID2D1DeviceContext::FillOpacityMask , qui n’a aucun paramètre D2D1_OPACITY_MASK_CONTENT .
L’exemple suivant définit le mode anticrénelage de la cible de rendu sur D2D1_ANTIALIAS_MODE_ALIASED afin que le masque d’opacité fonctionne correctement. Il appelle ensuite la méthode FillOpacityMask et lui transmet le masque d’opacité (m_pBitmapMask), le pinceau auquel le masque d’opacité est appliqué (m_pFernBitmapBrush), le type de contenu à l’intérieur du masque d’opacité (D2D1_OPACITY_MASK_CONTENT_GRAPHICS) et la zone à peindre. L’illustration suivante montre la sortie produite.
D2D1_RECT_F rcBrushRect = D2D1::RectF(5, 5, 155, 155);
// D2D1_ANTIALIAS_MODE_ALIASED must be set for FillOpacityMask to function properly
m_pRenderTarget->SetAntialiasMode(D2D1_ANTIALIAS_MODE_ALIASED);
m_pRenderTarget->FillOpacityMask(
m_pBitmapMask,
m_pFernBitmapBrush,
D2D1_OPACITY_MASK_CONTENT_GRAPHICS,
&rcBrushRect
);
m_pRenderTarget->SetAntialiasMode(D2D1_ANTIALIAS_MODE_PER_PRIMITIVE);
Le code a été omis dans cet exemple.
Utiliser un pinceau comme masque d’opacité avec la méthode FillGeometry
La section précédente a décrit comment utiliser un ID2D1Bitmap comme masque d’opacité. Direct2D fournit également la méthode ID2D1RenderTarget::FillGeometry , qui vous permet de spécifier éventuellement le pinceau comme masque d’opacité lorsque vous remplissez un ID2D1Geometry. Cela vous permet de créer des masques d’opacité à partir de dégradés (à l’aide de ID2D1LinearGradientBrush ou ID2D1RadialGradientBrush) et de bitmaps (à l’aide de ID2D1Bitmap).
La méthode FillGeometry prend trois paramètres :
- Le premier paramètre, id2D1Geometry, définit la forme à peindre.
- Le deuxième paramètre, id2D1Brush, spécifie le pinceau utilisé pour peindre la géométrie. Ce paramètre doit être un objet ID2D1BitmapBrush dont les modes d’extension x et y sont définis sur D2D1_EXTEND_MODE_CLAMP.
- Le troisième paramètre, id2D1Brush, spécifie un pinceau à utiliser comme masque d’opacité. Ce pinceau peut être id2D1LinearGradientBrush, ID2D1RadialGradientBrush ou ID2D1BitmapBrush. (Techniquement, vous pouvez utiliser un objet ID2D1SolidColorBrush, mais l’utilisation d’un pinceau de couleur unie comme masque d’opacité ne produit pas de résultats intéressants.)
Les sections suivantes décrivent comment utiliser des objets ID2D1LinearGradientBrush et ID2D1RadialGradientBrush en tant que masques d’opacité.
Utiliser un pinceau dégradé linéaire comme masque d’opacité
Le diagramme suivant montre l’effet de l’application d’un pinceau de dégradé linéaire à un rectangle rempli d’une bitmap de fleurs.
Les étapes suivantes décrivent comment recréer cet effet.
Définissez le contenu à masquer. L’exemple suivant crée un objet ID2D1BitmapBrush, m_pLinearFadeFlowersBitmap. Le mode d’extension x- et y- pour m_pLinearFadeFlowersBitmap sont définis sur D2D1_EXTEND_MODE_CLAMP afin qu’il puisse être utilisé avec un masque d’opacité par la méthode FillGeometry .
if (SUCCEEDED(hr)) { // Create the bitmap to be used by the bitmap brush. hr = LoadResourceBitmap( m_pRenderTarget, m_pWICFactory, L"LinearFadeFlowers", L"Image", &m_pLinearFadeFlowersBitmap ); } if (SUCCEEDED(hr)) { D2D1_BITMAP_BRUSH_PROPERTIES propertiesXClampYClamp = D2D1::BitmapBrushProperties( D2D1_EXTEND_MODE_CLAMP, D2D1_EXTEND_MODE_CLAMP, D2D1_BITMAP_INTERPOLATION_MODE_NEAREST_NEIGHBOR );
C++ if (SUCCEEDED(hr)) { hr = m_pRenderTarget->CreateBitmapBrush( m_pLinearFadeFlowersBitmap, propertiesXClampYClamp, &m_pLinearFadeFlowersBitmapBrush ); }
C++ }
Définissez le masque d’opacité. L’exemple de code suivant crée un pinceau de dégradé linéaire diagonal (m_pLinearGradientBrush) qui passe du noir entièrement opaque à la position 0 au blanc complètement transparent à la position 1.
if (SUCCEEDED(hr))
{
ID2D1GradientStopCollection *pGradientStops = NULL;
static const D2D1_GRADIENT_STOP gradientStops[] =
{
{ 0.f, D2D1::ColorF(D2D1::ColorF::Black, 1.0f) },
{ 1.f, D2D1::ColorF(D2D1::ColorF::White, 0.0f) },
};
hr = m_pRenderTarget->CreateGradientStopCollection(
gradientStops,
2,
&pGradientStops);
if (SUCCEEDED(hr))
{
hr = m_pRenderTarget->CreateLinearGradientBrush(
D2D1::LinearGradientBrushProperties(
D2D1::Point2F(0, 0),
D2D1::Point2F(150, 150)),
pGradientStops,
&m_pLinearGradientBrush);
}
pGradientStops->Release();
}
- Utilisez la méthode FillGeometry . Le dernier exemple utilise la méthode FillGeometry pour le pinceau de contenu pour remplir un ID2D1RectangleGeometry (m_pRectGeo) avec un ID2D1BitmapBrush (m_pLinearFadeFlowersBitmap) et applique un masque d’opacité (m_pLinearGradientBrush).
m_pRenderTarget->FillGeometry(
m_pRectGeo,
m_pLinearFadeFlowersBitmapBrush,
m_pLinearGradientBrush
);
Le code a été omis dans cet exemple.
Utiliser un pinceau dégradé radial comme masque d’opacité
Le diagramme suivant montre l’effet visuel de l’application d’un pinceau dégradé radial à un rectangle rempli d’une bitmap de feuillage.
Le premier exemple crée un objet ID2D1BitmapBrush, m_pRadialFadeFlowersBitmapBrush. Afin qu’il puisse être utilisé avec un masque d’opacité par la méthode FillGeometry , les modes d’extension x- et y- pour m_pRadialFadeFlowersBitmapBrush sont définis sur D2D1_EXTEND_MODE_CLAMP.
if (SUCCEEDED(hr))
{
// Create the bitmap to be used by the bitmap brush.
hr = LoadResourceBitmap(
m_pRenderTarget,
m_pWICFactory,
L"RadialFadeFlowers",
L"Image",
&m_pRadialFadeFlowersBitmap
);
}
if (SUCCEEDED(hr))
{
D2D1_BITMAP_BRUSH_PROPERTIES propertiesXClampYClamp =
D2D1::BitmapBrushProperties(
D2D1_EXTEND_MODE_CLAMP,
D2D1_EXTEND_MODE_CLAMP,
D2D1_BITMAP_INTERPOLATION_MODE_NEAREST_NEIGHBOR
);
C++ |
---|
|
C++ |
---|
|
L’exemple suivant définit le pinceau dégradé radial qui sera utilisé comme masque d’opacité.
if (SUCCEEDED(hr))
{
ID2D1GradientStopCollection *pGradientStops = NULL;
static const D2D1_GRADIENT_STOP gradientStops[] =
{
{ 0.f, D2D1::ColorF(D2D1::ColorF::Black, 1.0f) },
{ 1.f, D2D1::ColorF(D2D1::ColorF::White, 0.0f) },
};
hr = m_pRenderTarget->CreateGradientStopCollection(
gradientStops,
2,
&pGradientStops);
if (SUCCEEDED(hr))
{
hr = m_pRenderTarget->CreateRadialGradientBrush(
D2D1::RadialGradientBrushProperties(
D2D1::Point2F(75, 75),
D2D1::Point2F(0, 0),
75,
75),
pGradientStops,
&m_pRadialGradientBrush);
}
pGradientStops->Release();
}
L’exemple de code final utilise id2D1BitmapBrush (m_pRadialFadeFlowersBitmapBrush) et le masque d’opacité (m_pRadialGradientBrush) pour remplir un ID2D1RectangleGeometry (m_pRectGeo).
m_pRenderTarget->FillGeometry(
m_pRectGeo,
m_pRadialFadeFlowersBitmapBrush,
m_pRadialGradientBrush
);
Le code a été omis dans cet exemple.
Appliquer un masque d’opacité à un calque
Lorsque vous appelez PushLayer pour envoyer un objet ID2D1Layer à une cible de rendu, vous pouvez utiliser la structure D2D1_LAYER_PARAMETERS pour appliquer un pinceau en tant que masque d’opacité. L’exemple de code suivant utilise un ID2D1RadialGradientBrush comme masque d’opacité.
HRESULT DemoApp::RenderWithLayerWithOpacityMask(ID2D1RenderTarget *pRT)
{
HRESULT hr = S_OK;
// Create a layer.
ID2D1Layer *pLayer = NULL;
hr = pRT->CreateLayer(NULL, &pLayer);
if (SUCCEEDED(hr))
{
pRT->SetTransform(D2D1::Matrix3x2F::Translation(300, 250));
// Push the layer with the content bounds.
pRT->PushLayer(
D2D1::LayerParameters(
D2D1::InfiniteRect(),
NULL,
D2D1_ANTIALIAS_MODE_PER_PRIMITIVE,
D2D1::IdentityMatrix(),
1.0,
m_pRadialGradientBrush,
D2D1_LAYER_OPTIONS_NONE),
pLayer
);
pRT->DrawBitmap(m_pBambooBitmap, D2D1::RectF(0, 0, 190, 127));
pRT->FillRectangle(
D2D1::RectF(25.f, 25.f, 50.f, 50.f),
m_pSolidColorBrush
);
pRT->FillRectangle(
D2D1::RectF(50.f, 50.f, 75.f, 75.f),
m_pSolidColorBrush
);
pRT->FillRectangle(
D2D1::RectF(75.f, 75.f, 100.f, 100.f),
m_pSolidColorBrush
);
pRT->PopLayer();
}
SafeRelease(&pLayer);
return hr;
}
Pour plus d’informations sur l’utilisation des couches, consultez vue d’ensemble des couches.
Rubriques connexes