Dela via


Grafik (C++ AMP)

C++ AMP innehåller flera API:er i namnområdet Concurrency::graphics som du kan använda för att få åtkomst till strukturstöd på GPU:er. Några vanliga scenarier är:

  • Du kan använda texture klassen som en datacontainer för beräkning och utnyttja den rumsliga platsen för texturens cache och layouter för GPU-maskinvara. Rumslig lokalitet är egenskapen för dataelement som ligger fysiskt nära varandra.

  • Körtidmiljön ger effektiv interoperabilitet med icke-beräknande shaders. Pixel-, hörn-, tessellation- och skrovskuggare förbrukar eller producerar ofta texturer som du kan använda i dina C++ AMP-beräkningar.

  • Grafik-API:erna i C++ AMP ger alternativa sätt att komma åt delordspaketerade buffertar. Texturer som har format som representerar texels (texturelement) som består av 8-bitars eller 16-bitars skalär ger åtkomst till sådan packad datalagring.

Anmärkning

C++ AMP-huvuden är inaktuella från och med Visual Studio 2022 version 17.0. Om du inkluderar AMP headers uppstår byggfel. Definiera _SILENCE_AMP_DEPRECATION_WARNINGS innan du inkluderar AMP-huvuden för att undvika varningarna.

Norm- och unorm-typerna

Typerna norm och unorm är skalära typer som begränsar intervallet av float-värden. Detta kallas begränsning. Dessa typer kan uttryckligen konstrueras från andra skalära typer. Vid gjutning omvandlas värdet först till float och kläms sedan till respektive region som tillåts av norm [-1.0, 1.0] eller unorm [0.0, 1.0]. Konvertering av +/- oändlighet returnerar +/-1. Konvertering från NaN är odefinierad. A norm kan konstrueras implicit från en unorm och det går inte att förlora data. Den implicita konverteringsoperatorn till float definieras för dessa typer. Binära operatorer definieras mellan dessa typer och andra inbyggda skalärtyper som float och int: +, -, *, /, ==, !=, >, <, >=, <=. Operatorerna för sammansatt tilldelning stöds också: +=, -=, *=, /=. Operatorn unary negation (-) definieras för norm typer.

Kort vektorbibliotek

Det korta vektorbiblioteket innehåller några av funktionerna i den vektortyp som definieras i HLSL och som vanligtvis används för att definiera texels. En kort vektor är en datastruktur som innehåller ett till fyra värden av samma typ. De typer som stöds är double, float, int, norm, uintoch unorm. Typnamnen visas i följande tabell. För varje typ finns det också en motsvarande typedef som inte har ett understreck i namnet. De typer som har understreck finns i Concurrency::graphics-namnområdet. De typer som inte har understrecken finns i namnområdet Concurrency::graphics::d irect3d så att de är tydligt avgränsade från de grundläggande typerna med liknande namn som __int8 och __int16.

Typ Längd 2 Längd 3 Längd 4
dubbel dubbel_2

dubbel2
dubbel_3

dubbel3
dubbel_4

double4
flyta/sväva float_2

float2
float_3

float3
float_4

float4
Int int_2

int2
int_3

int3
int_4

int4
norm norm_2

norm2
norm_3

norm3
norm_4

Norm4
uint uint_2

uint2
uint_3

uint3
uint_4

uint4
Det kan bero på den specifika kontexten av "unorm," i tekniska sammanhang kan det ibland behöva en specifik översättning som "normalisering" eller liknande, beroende på den exakta meningen på engelska. unorm_2

unorm2
unorm_3

unorm3
unorm_4

unorm4

Operatörer

Om en operator definieras mellan två korta vektorer definieras den också mellan en kort vektor och en skalär. En av dessa måste också vara sant:

  • Skalärens typ måste vara samma som den korta vektorns elementtyp.

  • Skalärens typ kan implicit konverteras till vektorns elementtyp med hjälp av endast en användardefinierad konvertering.

Åtgärden utförs komponentmässigt mellan varje komponent i den korta vektorn och skalären. Här är de giltiga operatorerna:

Typ av operator Giltiga typer
Binära operatorer Giltig för alla typer: +, -, *, , /

Giltigt för heltalstyper: %, ^, |, &, <<, >>

De två vektorerna måste ha samma storlek och resultatet är en vektor med samma storlek.
Relationsoperatorer Giltig för alla typer: == och !=
Sammansatt tilldelningsoperator Giltig för alla typer: +=, -=, *=, /=

Giltigt för heltalstyper: %=, ^=, |=, &=, <<=, >>=
Öknings- och minskningsoperatorer Giltig för alla typer: ++, --

Både prefix och postfix är giltiga.
Bitvis NOT-operator (~) Giltigt för heltalstyper.
Unär operator - Gäller för alla typer utom unorm och uint.

Swizzle-uttryck

Short Vector Library stöder accessor-konstruktionen vector_type.identifier för att komma åt komponenterna i en kort vektor. Den identifier, som kallas ett swizzle-uttryck, anger komponenterna i vektorn. Uttrycket kan vara ett l-värde eller ett r-värde. Enskilda tecken i identifieraren kan vara: x, y, z och w; eller r, g, b och a. "x" och "r" betyder den nollde komponenten, "y" och "g" betyder den första komponenten och så vidare. (Observera att "x" och "r" inte kan användas i samma identifierare.) Därför returnerar "rgba" och "xyzw" samma resultat. Enkomponentsåtkomster som "x" och "y" är skalära värdetyper. Multikomponentåtkomstorer är korta vektortyper. Om du till exempel skapar en int_4 vektor med namnet fourInts och har värdena 2, 4, 6 och 8 returnerar du fourInts.y heltal 4 och fourInts.rg returnerar ett int_2 objekt som har värdena 2 och 4.

Strukturklasser

Många GPU:er har maskinvara och cacheminnen som är optimerade för att hämta pixlar och texels och återge bilder och texturer. Klassen texture<T,N> , som är en containerklass för texelobjekt, exponerar strukturfunktionerna för dessa GPU:er. En texel kan vara:

  • En int, uint, float, double, norm, eller unorm skalär.

  • En kort vektor som har två eller fyra komponenter. Det enda undantaget är double_4, vilket inte är tillåtet.

Objektet texture kan ha rangordningen 1, 2 eller 3. Objektet texture kan endast avbildas med referens i lambda för ett anrop till parallel_for_each. Strukturen lagras på GPU:n som Direct3D-texturobjekt. Mer information om texturer och texels i Direct3D finns i Introduktion till texturer i Direct3D 11.

Den texeltyp som du använder kan vara ett av de många texturformat som används i grafikprogrammering. Ett RGBA-format kan till exempel använda 32 bitar, med 8 bitar vardera för skalärelementen R, G, B och A. Texturmaskinvaran för ett grafikkort kan komma åt de enskilda elementen baserat på formatet. Om du till exempel använder RGBA-formatet kan texturmaskinvaran extrahera varje 8-bitarselement till ett 32-bitarsformulär. I C++ AMP kan du ange bitar per skalärt element i din texel så att du automatiskt kan komma åt de enskilda skalärelementen i koden utan att använda bitväxling.

Instansiera texturobjekt

Du kan deklarera ett strukturobjekt utan initiering. I följande kodexempel deklareras flera strukturobjekt.

#include <amp.h>
#include <amp_graphics.h>
using namespace concurrency;
using namespace concurrency::graphics;

void declareTextures() {
    // Create a 16-texel texture of int.
    texture<int, 1> intTexture1(16);
    texture<int, 1> intTexture2(extent<1>(16));

    // Create a 16 x 32 texture of float_2.
    texture<float_2, 2> floatTexture1(16, 32);
    texture<float_2, 2> floatTexture2(extent<2>(16, 32));

    // Create a 2 x 4 x 8 texture of uint_4.
    texture<uint_4, 3> uintTexture1(2, 4, 8);
    texture<uint_4, 3> uintTexture2(extent<3>(2, 4, 8));
}

Du kan också använda en konstruktor för att deklarera och initiera ett texture objekt. Följande kodexempel instansierar ett texture objekt från en objektvektor float_4 . Bits per scalar-element är inställt på standardvärdet. Du kan inte använda den här konstruktorn med norm, unormeller de korta vektorerna norm för och unorm, eftersom de inte har några standardbitar per skalärt element.

#include <amp.h>
#include <amp_graphics.h>
#include <vector>
using namespace concurrency;
using namespace concurrency::graphics;

void initializeTexture() {
    std::vector<int_4> texels;
    for (int i = 0; i < 768 * 1024; i++) {
        int_4 i4(i, i, i, i);
        texels.push_back(i4);
    }

    texture<int_4, 2> aTexture(768, 1024, texels.begin(), texels.end());
}

Du kan också deklarera och initiera ett texture objekt med hjälp av en överlagrad konstruktor som tar en pekare till källdata, storleken på källdata i bytes och antalet bitar per skalärt element.

void createTextureWithBPC() { // Create the source data.
    float source[1024* 2];
    for (int i = 0; i <1024* 2; i++) {
        source[i] = (float)i;
    }
    // Initialize the texture by using the size of source in bytes // and bits per scalar element.
    texture<float_2, 1> floatTexture(1024, source, (unsigned int)sizeof(source), 32U);
}

Texturerna i dessa exempel skapas i standardvyn för standardacceleratorn. Du kan använda andra överlagringar av konstruktorn om du vill ange ett accelerator_view objekt. Du kan inte skapa ett strukturobjekt på en PROCESSORaccelerator.

Det finns gränser för storleken på varje dimension av texture objektet, som du ser i följande tabell. Ett körningsfel genereras om du överskrider gränserna.

Textur Begränsning av storlek per dimension
textur<T,1> 16384
textur<T,2> 16384
textur<T,3> 2048

Läsa från texturobjekt

Du kan läsa från ett texture objekt med hjälp av textur::operator[], textur::operator() Operator eller textur::hämta-metod. De två operatorerna returnerar ett värde, inte en referens. Därför kan du inte skriva till ett texture-objekt med hjälp av texture::operator[].

void readTexture() {
    std::vector<int_2> src;
    for (int i = 0; i <16 *32; i++) {
        int_2 i2(i, i);

        src.push_back(i2);
    }

    std::vector<int_2> dst(16* 32);

    array_view<int_2, 2> arr(16, 32, dst);

    arr.discard_data();

    const texture<int_2, 2> tex9(16, 32, src.begin(), src.end());

    parallel_for_each(tex9.extent, [=, &tex9] (index<2> idx) restrict(amp) { // Use the subscript operator.
        arr[idx].x += tex9[idx].x; // Use the function () operator.
        arr[idx].x += tex9(idx).x; // Use the get method.
        arr[idx].y += tex9.get(idx).y; // Use the function () operator.
        arr[idx].y += tex9(idx[0], idx[1]).y;
    });

    arr.synchronize();
}

Följande kodexempel visar hur du lagrar texturkanaler i en kort vektor och sedan får åtkomst till enskilda skalärelement som egenskaper för den korta vektorn.

void UseBitsPerScalarElement() { // Create the image data. // Each unsigned int (32-bit) represents four 8-bit scalar elements(r,g,b,a values).
    const int image_height = 16;
    const int image_width = 16;
    std::vector<unsigned int> image(image_height* image_width);

    extent<2> image_extent(image_height, image_width);

    // By using uint_4 and 8 bits per channel, each 8-bit channel in the data source is // stored in one 32-bit component of a uint_4.
    texture<uint_4, 2> image_texture(image_extent, image.data(), image_extent.size()* 4U,  8U);

    // Use can access the RGBA values of the source data by using swizzling expressions of the uint_4.
    parallel_for_each(image_extent,
        [&image_texture](index<2> idx) restrict(amp)
        { // 4 bytes are automatically extracted when reading.
            uint_4 color = image_texture[idx];
            unsigned int r = color.r;
            unsigned int g = color.g;
            unsigned int b = color.b;
            unsigned int a = color.a;
        });
}

I följande tabell visas giltiga bitar per kanal för varje typ av sorteringsvektor.

Texturdatatyp Giltiga bitar per skalärt element
int, int_2, int_4

uint, uint_2, uint_4
8, 16, 32
int_3, uint_3 32
float, float_2, float_4 16, 32
float_3 32
dubbel, dubbel_2 64
norm, norm_2, norm_4

unorm, unorm_2, unorm, 4
8, 16

Skriva till texturobjekt

Använd metoden texture::set för att skriva till texture objekt. Ett texturobjekt kan vara skrivskyddat eller läs- och skrivbart. För att ett texturobjekt ska vara läsbart och skrivbart måste följande villkor vara sanna:

  • T har bara en skalär komponent. (Korta vektorer är inte tillåtna.)

  • T är inte double, normeller unorm.

  • Egendomen texture::bits_per_scalar_element är 32.

Om inte alla tre är sanna är objektet texture skrivskyddat. De två första villkoren kontrolleras under kompilering. Ett kompileringsfel genereras om du har kod som försöker skriva till ett readonly texturobjekt. Villkoret för texture::bits_per_scalar_element identifieras vid körning, och vid försök att skriva till ett skrivskyddat objekt genererar körningen undantagsfelet texture.

I följande kodexempel skrivs värden till ett texturobjekt.

void writeTexture() {
    texture<int, 1> tex1(16);

    parallel_for_each(tex1.extent, [&tex1] (index<1> idx) restrict(amp) {
        tex1.set(idx, 0);
    });
}

Kopiera texturobjekt

Du kan kopiera mellan texturobjekt med hjälp av kopieringsfunktionen eller funktionen copy_async , som du ser i följande kodexempel.

void copyHostArrayToTexture() { // Copy from source array to texture object by using the copy function.
    float floatSource[1024* 2];
    for (int i = 0; i <1024* 2; i++) {
        floatSource[i] = (float)i;
    }
    texture<float_2, 1> floatTexture(1024);

    copy(floatSource, (unsigned int)sizeof(floatSource), floatTexture);

    // Copy from source array to texture object by using the copy function.
    char charSource[16* 16];
    for (int i = 0; i <16* 16; i++) {
        charSource[i] = (char)i;
    }
    texture<int, 2> charTexture(16, 16, 8U);

    copy(charSource, (unsigned int)sizeof(charSource), charTexture);
    // Copy from texture object to source array by using the copy function.
    copy(charTexture, charSource, (unsigned int)sizeof(charSource));
}

Du kan också kopiera från en textur till en annan med hjälp av metoden texture::copy_to . De två texturerna kan vara på olika accelerator_views. När du kopierar till ett writeonly_texture_view objekt kopieras data till det underliggande texture objektet. Bitarna per skalärt element och omfattningen måste vara desamma för käll- och målobjekten texture . Om dessa krav inte uppfylls, så utlöser körtiden ett undantag.

Texturvyerklasser

C++ AMP introducerar klassen texture_view i Visual Studio 2013. Texturvyer stöder samma texeltyper och rangordnar som texturklassen, men till skillnad från texturer ger de åtkomst till ytterligare maskinvarufunktioner som textursampling och mipmaps. Texturvyer stöder skrivskyddad, skrivskyddad och skrivskyddad åtkomst till underliggande texturdata.

  • Skrivskyddad åtkomst tillhandahålls av texture_view<const T, N> mallspecialiseringen, som stöder element som har 1, 2 eller 4 komponenter, textursampling och dynamisk åtkomst till ett antal mipmap-nivåer som bestäms när vyn instansieras.

  • Skrivskyddad åtkomst tillhandahålls av den icke-specialiserade mallklassen texture_view<T, N>, som stöder element som har antingen 2 eller 4 komponenter och kan komma åt en mipmap-nivå som bestäms när vyn instansieras. Den stöder inte sampling.

  • Läs-skrivåtkomst tillhandahålls av den icke-specialiserade mallklassen texture_view<T, N>, som, till exempel texturer, stöder element som bara har en komponent. vyn kan komma åt en mipmap-nivå som bestäms när den instansieras. Den stöder inte sampling.

Strukturvyer motsvarar matrisvyer, men ger inte den automatiska datahanterings- och förflyttningsfunktionen som array_view-klassen tillhandahåller över matrisklassen. A texture_view kan endast nås i acceleratorvyn där underliggande texturdata finns.

writeonly_texture_view föråldrad

För Visual Studio 2013 introducerar C++ AMP bättre stöd för maskinvarustrukturer, till exempel sampling och mipmaps, som inte kunde stödjas av writeonly_texture_view-klassen. Den nyligen introducerade texture_view klassen stödjer en superuppsättning av funktionaliteten i writeonly_texture_view; därför är writeonly_texture_view inaktuell.

Vi rekommenderar, åtminstone för ny kod, att du använder texture_view för att komma åt funktioner som tidigare tillhandahölls av writeonly_texture_view. Jämför följande två kodexempel som skriver till ett strukturobjekt som har två komponenter (int_2). Observera att i båda fallen måste vyn , wo_tv4fångas upp av värdet i lambda-uttrycket. Här är exemplet som använder den nya texture_view klassen:

void write2ComponentTexture() {
    texture<int_2, 1> tex4(16);

    texture_view<int_2, 1> wo_tv4(tex4);

    parallel_for_each(extent<1>(16), [=] (index<1> idx) restrict(amp) {
        wo_tv4.set(idx, int_2(1, 1));
    });
}

Och här är den inaktuella writeonly_texture_view klassen:

void write2ComponentTexture() {
    texture<int_2, 1> tex4(16);

    writeonly_texture_view<int_2, 1> wo_tv4(tex4);

    parallel_for_each(extent<1>(16), [=] (index<1> idx) restrict(amp) {
        wo_tv4.set(idx, int_2(1, 1));
    });
}

Som du ser är de två kodexemplen nästan identiska när allt du gör är att skriva till den primära mipmap-nivån. Om du använde writeonly_texture_view i befintlig kod och inte planerar att förbättra koden behöver du inte ändra den. Men om du funderar på att föra koden framåt föreslår vi att du skriver om den så att den används texture_view eftersom förbättringarna i den stöder nya funktioner för maskinvarustruktur. Läs vidare om du vill ha mer information om dessa nya funktioner.

Mer information om utfasningen av writeonly_texture_viewfinns i Översikt över designen för strukturvyn i C++ AMP på bloggen Parallell programmering i inbyggd kod.

Instansiera texturvyobjekt

Att deklarera en texture_view liknar att deklarera en array_view som är associerad med en matris. I följande kodexempel deklareras flera texture objekt och texture_view objekt som är associerade med dem.

#include <amp.h>
#include <amp_graphics.h>
using namespace concurrency;
using namespace concurrency::graphics;

void declareTextureViews()
{
    // Create a 16-texel texture of int, with associated texture_views.
    texture<int, 1> intTexture(16);
    texture_view<const int, 1> intTextureViewRO(intTexture);  // read-only
    texture_view<int, 1> intTextureViewRW(intTexture);        // read-write

    // Create a 16 x 32 texture of float_2, with associated texture_views.
    texture<float_2, 2> floatTexture(16, 32);
    texture_view<const float_2, 2> floatTextureViewRO(floatTexture);  // read-only
    texture_view<float_2, 2> floatTextureViewRO(floatTexture);        // write-only

    // Create a 2 x 4 x 8 texture of uint_4, with associated texture_views.
    texture<uint_4, 3> uintTexture(2, 4, 8);
    texture_view<const uint_4, 3> uintTextureViewRO(uintTexture);  // read-only
    texture_view<uint_4, 3> uintTextureViewWO(uintTexture);        // write-only
}

Observera hur en texturvy vars elementtyp inte är beständig och har en komponent är läs-skriv, men en texturvy vars elementtyp inte är beständig men som har mer än en komponent är skrivskyddad. Strukturvyer av konstanta elementtyper är alltid endast läsbara, men om elementtypen inte är konstant avgör antalet komponenter i elementet om det är skriv-läs (1 komponent) eller endast skrivbar (flera komponenter).

Elementtypen för en texture_view – dess konstanthet och även antalet komponenter som den har – spelar också en roll när det gäller att avgöra om vyn stöder textursampling och hur mipmap-nivåer kan nås.

Typ Komponenter Läs Skriv Provtagning Mipmap-åtkomst
<texture_view const T, N> 1, 2, 4 Ja Nej (1) Ja Ja, indexerbar. Omfånget bestäms vid instansiering.
<Texture_view T, N> 1

2, 4
Ja

Nej (2)
Ja

Ja
Nej (1)

Nej (1)
Ja, en nivå. Nivån bestäms vid instansiering.

Ja, en nivå. Nivån bestäms vid instansiering.

I den här tabellen kan du se att skrivskyddade texturvyer har fullt stöd för de nya funktionerna i utbyte mot att de inte kan skriva till vyn. Skrivbara texturvyer är begränsade eftersom de bara kan komma åt en mipmap-nivå. Texturvyer för läs- och skrivbara är ännu mer specialiserade än de skrivbara, eftersom de lägger till kravet att varje elementtyp i texturvyn bara får ha en komponent. Observera att sampling inte stöds för skrivbara texturvyer eftersom det är en läsorienterad åtgärd.

Läsa från texturvyobjekt

Att läsa osamplade texturdata via en texturvy är precis som att läsa dem från själva texturen, förutom att texturer fångas med referens, medan texturvyer fångas med värde. Följande två kodexempel visar; först genom att endast använda texture :

void write2ComponentTexture() {
    texture<int_2, 1> text_data(16);

    parallel_for_each(extent<1>(16), [&] (index<1> idx) restrict(amp) {
        tex_data.set(idx, int_2(1, 1));
    });
}

Och här är samma exempel, förutom att det nu använder texture_view klassen:

void write2ComponentTexture() {
    texture<int_2, 1> tex_data(16);

    texture_view<int_2, 1> tex_view(tex_data);

    parallel_for_each(extent<1>(16), [=] (index<1> idx) restrict(amp) {
        tex_view.set(idx, int_2(1, 1));
    });
}

Texturvyer vars element baseras på flyttalstyper – till exempel flyttal, float_2 eller float_4 – kan också läsas med hjälp av textursampling för att dra nytta av maskinvarustöd för olika filtreringslägen och adresslägen. C++ AMP stöder de två filtreringslägen som är vanligast i beräkningsscenarier – punktfiltrering (närmaste granne) och linjär filtrering (viktat medelvärde)– och fyra adresseringslägen – omslutna, speglade, klämda och kantlinjer. Mer information om adresslägen finns i address_mode-enumerationen.

Förutom lägen som C++ AMP stöder direkt kan du komma åt andra filtreringslägen och adresseringslägen för den underliggande plattformen genom att använda interop-API:erna för att använda en texturexempel som skapades direkt med plattforms-API:erna. Direct3D stöder till exempel andra filtreringslägen, till exempel anisotropisk filtrering, och kan använda olika adresseringsläge för varje dimension av en struktur. Du kan skapa en texturexempel vars koordinater omsluts lodrätt, speglas vågrätt och samplas med anisotropisk filtrering med hjälp av Direct3D-API:erna, och sedan använda samplern i C++ AMP-koden med hjälp av interop-API:et make_sampler . Mer information finns i Textursampling i C++ AMP på bloggen Parallell programmering i inbyggd kod.

Strukturvyer stöder också läsning av mipmaps. Skrivskyddade texturvyer (de som har en konstant elementtyp) ger störst flexibilitet eftersom man dynamiskt kan provta ett antal mip-nivåer som bestäms vid instansiering, och eftersom element med 1, 2 eller 4 komponenter stöds. Texturvyer med läs- och skrivmöjligheter som innehåller element med en komponent stöder också mipmaps, men endast på en nivå som bestäms vid instansieringen. Mer information finns i Textur med Mipmaps på bloggen Parallell programmering i inbyggd kod.

Skriva till texturvyobjekt

Använd metoden texture_view::get för att skriva till det underliggande texture genom texture_view-objektet. En texturvy kan vara skrivskyddad, läs-/skrivbar eller endast skrivbar. För att en texturvy ska vara skrivbar måste den ha en elementtyp som inte är beständig. För att en texturvy ska vara läsbar och skrivbar får dess elementtyp också bara ha en komponent. Annars är texturvy endast läsbar. Du kan bara komma åt en mipmap-nivå för en struktur i taget via en strukturvy, och nivån anges när vyn instansieras.

Det här exemplet visar hur du skriver till den näst mest detaljerade mipmap-nivån för en struktur som har 4 mipmap-nivåer. Den mest detaljerade mipmap-nivån är nivå 0.

// Create a texture that has 4 mipmap levels : 16x16, 8x8, 4x4, 2x2
texture<int, 2> tex(extent<2>(16, 16), 16U, 4);

// Create a writable texture view to the second mipmap level :4x4
texture_view<int, 2> w_view(tex, 1);

parallel_for_each(w_view.extent, [=](index<2> idx) restrict(amp)
{
    w_view.set(idx, 123);
});

Samverkan

C++ AMP-körningen stöder samverkan mellan texture<T,1> och gränssnittet ID3D11Texture1D, mellan texture<T,2> och ID3D11Texture2D-gränssnittet och mellan texture<T,3> och gränssnittet ID3D11Texture3D. Metoden get_texture tar ett texture objekt och returnerar ett IUnknown gränssnitt. Metoden make_texture tar ett IUnknown gränssnitt och ett accelerator_view objekt och returnerar ett texture objekt.

Se även

double_2-klass
double_3 klass
double_4 klass
float_2-klass
float_3-klass
float_4-klass
int_2-klass
int_3-klass
int_4-klass
norm_2-klass
norm_3-klass
norm_4-klass
short_vector Struktur
short_vector_traits Struktur
uint_2-klass
uint_3-klass
uint_4-klass
unorm_2-klass
unorm_3-klass
unorm_4-klass