Condividi tramite


Visualizzare una bitmap fornita dall'app nell'immagine composita

[La funzionalità associata a questa pagina, DirectShow, è una funzionalità legacy. È stata sostituita da MediaPlayer, IMFMediaEnginee Acquisizione audio/video in Media Foundation. Queste funzionalità sono state ottimizzate per Windows 10 e Windows 11. Microsoft consiglia vivamente di usare un nuovo codice MediaPlayer, IMFMediaEngine e Acquisizione audio/video in Media Foundation anziché DirectShow, quando possibile. Microsoft suggerisce che il codice esistente che usa le API legacy venga riscritto per usare le nuove API, se possibile.

Le applicazioni possono usare la modalità di combinazione di VMR per visualizzare logo dei canali alfa blend, un'interfaccia utente o annunci parzialmente o completamente all'interno del rettangolo video. Poiché la fusione viene eseguita nell'hardware dal processore grafico, c'è un impatto minimo sulle prestazioni di riproduzione di Video Stream e non sono presenti elementi sfarfallio o strappi rilevabili. Le applicazioni possono modificare l'immagine visualizzata con la frequenza desiderata. Si noti che le modifiche vengono riflesse solo sullo schermo quando il grafico del filtro DirectShow si trova nello stato in esecuzione.

VmR usa il componente mixer per sovrapporre la bitmap all'immagine composita. Con VMR-7, l'applicazione deve forzare il vmR a caricare il mixer, anche se è presente un solo flusso video. Questo non è necessario con VMR-9 perché carica il suo mixer per impostazione predefinita.

Per combinare un'immagine bitmap statica con il flusso video, l'applicazione crea la macchina virtuale virtuale e la aggiunge al grafo e quindi chiama IVMRFilterConfig::SetNumberOfStreams. Il valore passato a questa funzione identifica il numero di pin di input che deve essere creato da VMR. Le applicazioni possono specificare qualsiasi valore compreso tra 1 e MAX_MIXER_STREAMS; Specificare un valore pari a 1 è valido se l'applicazione intende solo visualizzare un singolo flusso video. Anche se VMR-7 ha un singolo pin di input per impostazione predefinita, questo metodo deve essere chiamato per forzare il caricamento del componente mixer. VmR-9 carica il mixer e configura quattro pin per impostazione predefinita.

Per impostare la bitmap, usare l'interfacciaIVMRMixerBitmapin VMR-7 o nell'interfaccia IVMRMixerBitmap9 in VMR-9.

La bitmap può essere specificata da un handle a un contesto di dispositivo GDI (hDC) o da un'interfaccia DirectDraw Surface. Se l'applicazione vuole che l'immagine contenga informazioni alfa incorporate (note anche come per pixel alfa) deve inserire i dati dell'immagine in un'interfaccia DirectDraw Surface. Ciò è dovuto al fatto che attualmente non è possibile inserire informazioni alfa per pixel con un contesto di dispositivo GDI. La superficie DirectDraw deve essere RGB32 o ARGB32 e deve essere preferibilmente una superficie di memoria di sistema. Non è necessario che le dimensioni della superficie siano una potenza di 2.

VmR consente alle applicazioni di specificare la posizione e un valore complessivo di trasparenza per l'immagine. Il codice seguente illustra come passare i dati dell'immagine alla macchina virtuale per la fusione successiva:

HRESULT BlendApplicationImage( 
  HWND hwndApp,
  IVMRWindowlessControl* pWc,
  HBITMAP hbm
)
{
    LONG cx, cy;
    HRESULT hr;
    hr = pWc->GetNativeVideoSize(&cx, &cy, NULL, NULL);
    if (FAILED(hr))
        return hr;
    
    HDC hdc = GetDC(hwndApp);
    if (hdc == NULL)
    {
        return E_FAIL;
    }
    
    HDC hdcBmp = CreateCompatibleDC(hdc);
    ReleaseDC(hwndApp, hdc);
    
    if (hdcBmp == NULL)
    {
        return E_FAIL;
    }
    
    BITMAP bm;
    if (0 == GetObject(hbm, sizeof(bm), &bm))
    {
        DeleteDC(hdcBmp);
        return E_FAIL;
    }
    
    HBITMAP hbmOld = (HBITMAP)SelectObject(hdcBmp, hbm);
    if (hbmOld == 0)
    {
        DeleteDC(hdcBmp);
        return E_FAIL;
    }
    
    VMRALPHABITMAP bmpInfo;
    ZeroMemory(&bmpInfo, sizeof(bmpInfo) );
    bmpInfo.dwFlags = VMRBITMAP_HDC;
    bmpInfo.hdc = hdcBmp;
    
    // Show the entire bitmap in the top-left corner of the video image.
    SetRect(&bmpInfo.rSrc, 0, 0, bm.bmWidth, bm.bmHeight);
    bmpInfo.rDest.left = 0.f;
    bmpInfo.rDest.top = 0.f;
    bmpInfo.rDest.right = (float)bm.bmWidth / (float)cx;
    bmpInfo.rDest.bottom = (float)bm.bmHeight / (float)cy;
    
    // Set the transparency value (1.0 is opaque, 0.0 is transparent).
    bmpInfo.fAlpha = 0.2f;
    
    IVMRMixerBitmap* pBmp;
    hr = pWc->QueryInterface(IID_IVMRMixerBitmap, (LPVOID *)&pBmp);
    if (SUCCEEDED(hr)) 
    {
        pBmp->SetAlphaBitmap(&bmpInfo);
        pBmp->Release();
    }
    
    DeleteObject(SelectObject(hdcBmp, hbmOld));
    DeleteDC(hdcBmp);
    return hr;
}

I concetti illustrati in questo argomento sono illustrati nell'applicazione di esempio VMRPlayer Sample.

Creazione di animazioni semplici con l'immagine bitmap

Per creare un semplice logo bitmap animato, inserire tutte le "cornici" bitmap in un'unica immagine, come illustrato nella figura seguente.

strip di immagini vmr

Quando si imposta inizialmente la bitmap usando IVMRMixerBitmap::SetAlphaBitmap, se la bitmap si trova in un HDC, impostare il campo rSrc della struttura VMRALPHABITMAP per specificare le dimensioni dell'intera bitmap all'interno del HDC. I membri superiore superiore e sinistra della struttura sono impostati su 0 e la destra e membri inferiore sono la larghezza e l'altezza della bitmap. Se la bitmap si trova in una superficie DirectDraw, la dimensione della superficie è nota, quindi non è necessario specificare rSrc in questo metodo.

Quando si chiama IVMRMixerBitmap::UpdateAlphaBitmapParameters, usare il membro rSrc per le bitmap HDC e DirectDraw, per specificare il frame o il rettangolo specifico all'interno dell'immagine da visualizzare e impostare il flag VMRBITMAP_SRCRECT nel membro dwFlags.

uso della modalità di combinazione VMR