Översikt över ogenomskinlighetsmasker
Det här avsnittet beskriver hur du använder bitmappar och penslar för att definiera ogenomskinliga masker. Den innehåller följande avsnitt.
- Förutsättningar
- Vad är en ogenomskinlig mask?
- Använd en bitmapp som en ogenomskinlig mask med metoden FillOpacityMask
- Använda en pensel som en ogenomskinlig mask med metoden FillGeometry
- Tillämpa en opacitetsmask på ett lager
- Relaterade ämnen
Den här översikten förutsätter att du är bekant med grundläggande Direct2D-ritningsåtgärder enligt beskrivningen i Skapa ett enkelt Direct2D-program genomgång. Du bör också känna till de olika typerna av penslar enligt beskrivningen i Brushes Overview.
En ogenomskinlig mask är en mask, som beskrivs av en pensel eller bitmapp, som tillämpas på ett annat objekt för att göra objektet delvis eller helt transparent. En ogenomskinlig mask använder alfakanalinformation för att ange hur objektets källpixlar ska blandas i det slutliga målmålet. De transparenta delarna av masken anger de områden där den underliggande bilden är dold, medan de ogenomskinliga delarna av masken anger var det maskerade objektet är synligt.
Det finns flera sätt att använda en ogenomskinlig mask:
- Använd metoden ID2D1RenderTarget::FillOpacityMask. Metoden FillOpacityMask målar upp en rektangulär region för ett återgivningsmål och tillämpar sedan en opacitetsmask som definieras av en bitmapp. Använd den här metoden när din opacitetsmask är en bitmapp och du vill fylla en rektangulär region.
- Använd metoden ID2D1RenderTarget::FillGeometry. Metoden FillGeometry målar geometrins inre med angiven ID2D1BitmapBrushoch tillämpar sedan en ogenomskinlighetsmask som definieras av en pensel. Använd den här metoden när du vill använda en opacitetsmask på en geometri eller om du vill använda en pensel som en ogenomskinlig mask.
- Använd en ID2D1Layer- för att använda en ogenomskinlig mask. Använd den här metoden när du vill använda en ogenomskinlig mask på en grupp med ritningsinnehåll, inte bara en enda form eller bild. Mer information finns i översikten över lager.
Metoden FillOpacityMask målar en rektangulär region för ett återgivningsmål och tillämpar sedan en ogenomskinlighetsmask som definieras av en ID2D1Bitmap. Använd den här metoden när du har en bitmapp som du vill använda som en ogenomskinlig mask för en rektangulär region.
Följande diagram visar en effekt av att tillämpa opacitetsmasken (en ID2D1Bitmap med en bild av en blomma) på en ID2D1BitmapBrush med en bild av en ormbunkeväxt. Den resulterande bilden är en bitmapp av en växt som klippts till blomformen.
Följande kodexempel visar hur detta går till.
I det första exemplet läses följande bitmapp, m_pBitmapMask, in för användning som en bitmappsmask. Följande bild visar det resultat som produceras. Observera att även om den ogenomskinliga delen av bitmappen verkar svart, har färginformationen i bitmappen ingen effekt på ogenomskinlighetsmasken. endast ogenomskinlighetsinformationen för varje pixel i bitmappen används. De helt ogenomskinliga bildpunkterna i den här bitmappen har endast färgats svart i illustrativa syften.
I det här exemplet läses ID2D1Bitmap in av en hjälpmetod, LoadResourceBitmap, som definieras någon annanstans i exemplet.
if (SUCCEEDED(hr))
{
hr = LoadResourceBitmap(
m_pRenderTarget,
m_pWICFactory,
L"BitmapMask",
L"Image",
&m_pBitmapMask
);
}
I nästa exempel definieras penseln, m_pFernBitmapBrush, som opacitetsmasken tillämpas på. I det här exemplet används en ID2D1BitmapBrush- som innehåller en bild av en ormbunke, men du kan använda en ID2D1SolidColorBrush, ID2D1LinearGradientBrusheller ID2D1RadialGradientBrush i stället. Följande bild visar resultaten som skapas.
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
);
}
Nu när opacitetsmasken och penseln har definierats kan du använda metoden FillOpacityMask i programmets återgivningsmetod. När du anropar metoden FillOpacityMask måste du ange vilken typ av opacitetsmask du använder: D2D1_OPACITY_MASK_CONTENT_GRAPHICS, D2D1_OPACITY_MASK_CONTENT_TEXT_NATURALoch D2D1_OPACITY_MASK_CONTENT_TEXT_GDI_COMPATIBLE. För innebörden av dessa tre typer, se D2D1_OPACITY_MASK_CONTENT.
Anteckning
Från och med Windows 8 krävs inte D2D1_OPACITY_MASK_CONTENT. Se metoden ID2D1DeviceContext::FillOpacityMask, som inte har någon D2D1_OPACITY_MASK_CONTENT parameter.
I nästa exempel anges återgivningsmålets antialiaseringsläge till D2D1_ANTIALIAS_MODE_ALIASED så att opacitetsmasken fungerar korrekt. Den anropar sedan metoden FillOpacityMask och skickar den ogenomskinlighetsmasken (m_pBitmapMask), penseln som opacitetsmasken tillämpas på (m_pFernBitmapBrush), typen av innehåll inuti opacitetsmasken (D2D1_OPACITY_MASK_CONTENT_GRAPHICS) och det område som ska målas. Följande illustration visar de resultat som produceras.
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);
Koden har utelämnats från det här exemplet.
I föregående avsnitt beskrivs hur du använder en ID2D1Bitmap- som en ogenomskinlig mask. Direct2D innehåller också metoden ID2D1RenderTarget::FillGeometry, som låter dig specificera en pensel som en opacitetsmask när du fyller en ID2D1Geometry. På så sätt kan du skapa ogenomskinliga masker från toningar (med hjälp av ID2D1LinearGradientBrush eller ID2D1RadialGradientBrush) och bitmappar (med ID2D1Bitmap).
Metoden FillGeometry tar tre parametrar:
- Den första parametern, en ID2D1Geometry, definierar formen som ska målas.
- Den andra parametern, en ID2D1Brush, anger penseln som används för att måla geometrin. Den här parametern måste vara en ID2D1BitmapBrush- som har sina x- och y-extend-lägen inställda på D2D1_EXTEND_MODE_CLAMP.
- Den tredje parametern, en ID2D1Brush, anger en pensel som ska användas som opacitetsmask. Den här penseln kan vara en ID2D1LinearGradientBrush, ID2D1RadialGradientBrusheller en ID2D1BitmapBrush. (Tekniskt sett kan du använda en ID2D1SolidColorBrush, men att använda en pensel med en fast färg som en ogenomskinlig mask ger inte intressanta resultat.)
I följande avsnitt beskrivs hur du använder ID2D1LinearGradientBrush och ID2D1RadialGradientBrush objekt som ogenomskinlighetsmasker.
Följande diagrammet visar effekten av att tillämpa en linjär färgövergång på en rektangel som är fylld med en bitmapp med blommor.
Stegen nedan beskriver hur du återskapar den här effekten.
Definiera innehållet som ska maskeras. I följande exempel skapar man en ID2D1BitmapBrushoch m_pLinearFadeFlowersBitmap. "Utökningsläget x- och y- för m_pLinearFadeFlowersBitmap är inställda på D2D1_EXTEND_MODE_CLAMP så att det kan användas med en opacitetsmask av metoden 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++ }
Definiera opacitetsmasken. I nästa kodexempel skapas en diagonal linjär toningspensel (m_pLinearGradientBrush) som tonar från helt opakt svart vid position 0 till helt transparent vitt vid 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();
}
- Använd metoden FillGeometry. Det sista exemplet använder metoden FillGeometry till innehållsborsten för att fylla en ID2D1RectangleGeometry (m_pRectGeo) med en ID2D1BitmapBrush (m_pLinearFadeFlowersBitmap) och tillämpar en ogenomskinlig mask (m_pLinearGradientBrush).
m_pRenderTarget->FillGeometry(
m_pRectGeo,
m_pLinearFadeFlowersBitmapBrush,
m_pLinearGradientBrush
);
Koden har utelämnats från det här exemplet.
Följande figur visar den visuella effekten av att tillämpa en radiell färgövergång på en rektangel som är fylld med ett bitmapmönster av lövverk.
I det första exemplet skapas en ID2D1BitmapBrush, m_pRadialFadeFlowersBitmapBrush. Så att den kan användas med en opacitetsmask av metoden FillGeometry är x- och y-läget för m_pRadialFadeFlowersBitmapBrush inställda på 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++ |
---|
|
I nästa exempel definieras den radiella gradientpensel som ska användas som täthetsmask.
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();
}
Det sista kodexemplet använder ID2D1BitmapBrush (m_pRadialFadeFlowersBitmapBrush) och opacitetsmasken (m_pRadialGradientBrush) för att fylla en ID2D1RectangleGeometry (m_pRectGeo).
m_pRenderTarget->FillGeometry(
m_pRectGeo,
m_pRadialFadeFlowersBitmapBrush,
m_pRadialGradientBrush
);
Koden har utelämnats från det här exemplet.
När du anropar PushLayer för att skicka en ID2D1Layer till ett återgivningsmål kan du använda D2D1_LAYER_PARAMETERS struktur för att använda en pensel som en ogenomskinlig mask. I följande kodexempel används en ID2D1RadialGradientBrush som en opacitetsmask.
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;
}
För mer information om hur du använder lager, se Lageröversikt.
-
Översikt över lager