AGB  ·  Datenschutz  ·  Impressum  







Anmelden
Nützliche Links
Registrieren
Zurück Delphi-PRAXiS Programmierung allgemein Multimedia Delphi VMR9 custom allocator-presenter
Thema durchsuchen
Ansicht
Themen-Optionen

VMR9 custom allocator-presenter

Ein Thema von TERWI · begonnen am 17. Jan 2018 · letzter Beitrag vom 19. Jan 2018
Antwort Antwort
Seite 1 von 2  1 2      
Benutzerbild von TERWI
TERWI

Registriert seit: 29. Mär 2008
Ort: D-49626
381 Beiträge
 
Delphi 11 Alexandria
 
#1

VMR9 custom allocator-presenter

  Alt 17. Jan 2018, 20:39
In Bezug zu meinem Post DirectX Multi-in Streams mit VMR9 und GMFBridge, DSPack hab ich noch Fragen zum VMR9 custom allocator-presenter.

Damals wie heute lese ich immer wieder die Aussage im MSDN:
Zitat:
Note: When the VMR mixes multiple video streams, the filter graph does not seek correctly. If you need to seek multiple video streams, you must create separate filter graphs that share the same custom allocator-presenter object.
Soll das bedeuten: .... Mach dir mal eben schnell 'nen Presenter und kipp da deine(n) Stream(s) rein - dann haste alles in einen 'Video-Fenster' ... ??!!

Im DSPack gib es eine Allocator-Demo, die auch funzt und sehr nett das Video-Bild als Scheibe im 3D-Raum drehen lässt !

Ich hätt's aber gerne ohne 3D-Gimmicks 'moveless' - was ja auch s weit klappt, aber ... irgendwie bekomme ich kein wirklichliches Vollbild und der Inhalt "hängt irgendwie auf halb-acht" im Raum/Fenster .... Nett, aber so unbrauchbar.

Ich habe (leider noch) keinen Plan, wie das da bewerkstelligt wird, auch fleissiges lesen/suchen im WWW hat mich nicht wirklich weitergebracht.
Entweder alles nur kopiertes unfertiges Dummzeug ohne Funktion oder extrem C-kryptsich nur für diejenigen, welche schon min. 1x Papst waren.

Kann hier vielleicht der eine oder andere aus der Gamer-Ecke o. ä helfen ?

Geändert von TERWI (18. Jan 2018 um 13:21 Uhr)
  Mit Zitat antworten Zitat
TiGü

Registriert seit: 6. Apr 2011
Ort: Berlin
3.070 Beiträge
 
Delphi 10.4 Sydney
 
#2

AW: VMR9 custom allocator-presenter

  Alt 18. Jan 2018, 10:05
Bei solchen komplexen Themen, die einiges Wissen an Direct3D und DirectShow erfordern, ist es sicherlich hilfreich, wenn du uns ein minimales Beispielprojekt sowie entsprechende Videodateien zur Verfügung stellst.

In einem Programmierforum ohne Quelltext helfen und diskutieren zu wollen ist ein bisschen wie Schwimmen aufn Trockenen.

Vielleicht ist es nur eine kleine Sache, eventuell wird nur ein HRESULT nicht vernünftig auswertet oder beim Initialisieren fehlt ein Wert und du siehst es vor lauter Betriebsblindheit nicht mehr.
  Mit Zitat antworten Zitat
EWeiss
(Gast)

n/a Beiträge
 
#3

AW: VMR9 custom allocator-presenter

  Alt 18. Jan 2018, 10:35
Zitat:
Soll das bedeuten: .... Mach dir mal eben schnell 'nen Presenter und kipp da deine(n) Stream(s) rein - dann haste alles in einen 'Video-Fenster' ... ??!!
Ich würde mich mal über alternativen insbesondere LAV Filtern\Splitter informieren vielleicht gibt es da schon etwas passendes.
Mein Player unterstützt das alles insbesondere Madvr und LAV Filtern. EVR -> VMR9
Habe mich aber um solche Spielereien bisher nicht gekümmert da ich mich auf ein Video Konzentrieren will.

Zitat:
Direct3D und DirectShow
Direct3D hat damit weniger bis gar nichts zu tun.

gruss

Geändert von EWeiss (18. Jan 2018 um 16:11 Uhr)
  Mit Zitat antworten Zitat
TiGü

Registriert seit: 6. Apr 2011
Ort: Berlin
3.070 Beiträge
 
Delphi 10.4 Sydney
 
#4

AW: VMR9 custom allocator-presenter

  Alt 18. Jan 2018, 11:51
Zitat:
Direct3D und DirectShow
Direct3D hat damit weniger bis gar nichts zu tun.
https://msdn.microsoft.com/en-us/lib...(v=vs.85).aspx
Einfach mal zählen, wie oft der Begriff "Direct3D" vorkommt, danke!
  Mit Zitat antworten Zitat
EWeiss
(Gast)

n/a Beiträge
 
#5

AW: VMR9 custom allocator-presenter

  Alt 18. Jan 2018, 14:08
Zitat:
Direct3D und DirectShow
Direct3D hat damit weniger bis gar nichts zu tun.
https://msdn.microsoft.com/en-us/lib...(v=vs.85).aspx
Einfach mal zählen, wie oft der Begriff "Direct3D" vorkommt, danke!
Ja und was hat das mit Videos zu tun ?
Ich benötige es nicht einmal. Einfach mal zählen wie oft das in Zusammenhang mit Videos zum tragen kommt. danke

EDIT:
Sorry.. Bin jetzt von meiner Anwendung.
Natürlich verwendet meine DLL es.

gruss

Geändert von EWeiss (18. Jan 2018 um 16:13 Uhr)
  Mit Zitat antworten Zitat
Benutzerbild von TERWI
TERWI

Registriert seit: 29. Mär 2008
Ort: D-49626
381 Beiträge
 
Delphi 11 Alexandria
 
#6

AW: VMR9 custom allocator-presenter

  Alt 18. Jan 2018, 14:15
Zitat:
wenn du uns ein minimales Beispielprojekt sowie entsprechende Videodateien zur Verfügung stellst.
Kann ich gerne machen. Das beeinhaltet dann allerdings die Vorraussetzung der Installation des DSPack's (bekannt ?) und die Verwendung der darin enthaltenen Klassen TFilterGraph und TVideoWindow, wenn man die benannte Demo (aus dem DSPack) '\DEMOS\D6-D7\VMR\VMR9ALLOCATOR\PlayFile' zum laufen bekommen will.
Daraus mal "eben schnell was extrahieren" geht z 100% in die Hose, weil sehr komplex und sehr verflochten....
Im Prinzip ist die Demo allerdings identisch mit der MS-WIN7-SDK Demo '\multimedia\directshow\vmr9\vmr9allocator' und betriff im wesentlichen die Dateien 'Allocator.cpp/.pas' und 'PlaneScene.cpp/.pas'.

Laufen tut die Demo mit jedem x-beliegiegen Video - wenn man wie EWeiss anmerkte, die LAV-Filter verwendet. Der LAVSplitterSource-Filter frisst fast alles. Ich habs hier mit div. .AVI, .MPG und .TS probiert.

Das Prinzip, so wie ich es bisher herausgebrezelt habe:
Das VideoWindow muss explizit zur Nutzung von VMR9 im Renderless-Mode gesetzt werden. Dazu muss man noch eine TAllocator-Klasse an's Window übergeben.
Der VMR9 ruft dann bei jedem Frame die Funktion "PresentImage" und hilfsweise die Funktion "PresentHelper" auf. Siehe hier auszugsweise im org. DSPack-File 'Allocator-pas':
Delphi-Quellcode:
function TAllocator.PresentImage(dwUserID: DWORD;
  lpPresInfo: PVMR9PresentationInfo): HResult;
var
  hr: HRESULT;
  AMonitor: HMONITOR;
  function FailRet(hr: HResult): boolean;
  begin
    PresentImage := hr;
    Result := Failed(hr);
  end;
begin
  FObjectLock.Enter;
  try
    // if we are in the middle of the display change
    if NeedToHandleDisplayChange then
    begin
        // NOTE: this piece of code is left as a user exercise.
        // The D3DDevice here needs to be switched
        // to the device that is using another adapter
    end;

    hr := PresentHelper(lpPresInfo);

    // IMPORTANT: device can be lost when user changes the resolution
    // or when (s)he presses Ctrl + Alt + Delete.
    // We need to restore our video memory after that
    if (hr = D3DERR_DEVICELOST) then
    begin
      if (FD3DDev.TestCooperativeLevel = D3DERR_DEVICENOTRESET) then
      begin
        DeleteSurfaces;
        if FailRet(CreateDevice) then exit;
        AMonitor := FD3D.GetAdapterMonitor(D3DADAPTER_DEFAULT);
        if FailRet(FlpIVMRSurfAllocNotify.ChangeD3DDevice(FD3DDev, AMonitor)) then exit;
      end;
      hr := S_OK;
    end;
    result := hr;
  finally
    FObjectLock.Leave;
  end;
end;

function TAllocator.PresentHelper(
  lpPresInfo: PVMR9PresentationInfo): HRESULT;
var
  surface: IDirect3DSurface9;
  texture: IDirect3DTexture9;
  function FailRet(hr: HResult): boolean;
  begin
    PresentHelper := hr;
    Result := Failed(hr);
  end;
begin
  // parameter validation
  if (lpPresInfo = nil) then
  begin
    result := E_POINTER;
    exit;
  end else
  if (lpPresInfo.lpSurf = nil) then
  begin
    result := E_POINTER;
    exit;
  end;

  FObjectLock.Enter;
  try
    FD3DDev.SetRenderTarget(0, FrenderTarget);
    // if we created a private texture
    // blt the decoded image onto the texture.
    if(FprivateTexture <> nil) then
    begin
      if FailRet(FprivateTexture.GetSurfaceLevel(0 , surface)) then exit;

      // copy the full surface onto the texture's surface
      if FailRet(FD3DDev.StretchRect(lpPresInfo.lpSurf, nil,
                           surface, nil,
                           D3DTEXF_NONE)) then exit;

      if FailRet(Fscene.DrawScene(FD3DDev, FprivateTexture)) then exit;
    end
    else // this is the case where we have got the textures allocated by VMR
         // all we need to do is to get them from the surface
    begin
      if FailRet(lpPresInfo.lpSurf.GetContainer(IID_IDirect3DTexture9, Pointer(texture))) then exit;
      if FailRet(Fscene.DrawScene(FD3DDev, texture)) then exit;
    end;
    if FailRet(FD3DDev.Present(nil, nil, 0, nil)) then exit;
// result := hr;
  finally
    Pointer(texture) := nil;
    FObjectLock.leave;
  end;
end;
Letztendlich wird im File 'PlaneScene.pas' (Auszug) die Funktion "DrawScene" aufgerufen und dort YXZ-Werte in Matrizen und Transformationen "verwurstet", was die Drehung der "Video-Scheibe" veranlasst ..... die ich gerne da raus hätte !
Delphi-Quellcode:
function TPlaneScene.DrawScene(d3ddev: IDirect3DDevice9;
  texture: IDirect3DTexture9): HRESULT;
  function FailRet(hr: HResult): boolean;
  begin
    DrawScene := hr;
    Result := Failed(hr);
  end;
var
  dwCurrentTime: DWord;
  difference: Int64;
  x, y, z: Single;
  mask0, mask3: DWord;
  pData: Pointer;
begin
  if ((d3ddev = nil) or (texture = nil)) then
  begin
    Result := E_POINTER;
    Exit;
  end;

  if( FvertexBuffer = nil) then
  begin
    Result := D3DERR_INVALIDCALL;
    Exit;
  end;

  // get the difference in time
  dwCurrentTime := GetTickCount;
  difference := Ftime - dwCurrentTime;

  // figure out the rotation of the plane
  x := -cos(difference / 2000);
  y := cos(difference / 2000);
  z := sin(difference / 2000);

  // update the two rotating vertices with the new position
  Fvertices[0].position := MakePosition(x, y, z); // top left
  Fvertices[3].position := MakePosition(-x, -y, -z); // bottom right

  // Adjust the color so the blue is always on the bottom.
  // As the corner approaches the bottom, get rid of all the other
  // colors besides blue
  mask0 := Trunc((255 * (( y + 1) / 2)));
  mask3 := Trunc((255 * ((-y + 1) / 2)));
  Fvertices[0].color := $ff0000ff or (mask0 shl 16) or (mask0 shl 8);
  Fvertices[3].color := $ff0000ff or (mask3 shl 16) or (mask3 shl 8);

  // write the new vertex information into the buffer
  if FailRet(FvertexBuffer.Lock(0, sizeof(pData), pData, 0)) then exit;
  move(Fvertices, pData^ , sizeof(Fvertices));
  if FailRet(FvertexBuffer.Unlock) then exit;

  // clear the scene so we don't have any articats left
  d3ddev.Clear(0, nil, D3DCLEAR_TARGET, D3DCOLOR_XRGB(255,255,255), 1.0, 0);

  if FailRet(d3ddev.BeginScene) then exit;
  if FailRet(d3ddev.SetTexture(0, texture)) then exit;

  if FailRet(d3ddev.SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE)) then exit;
  if FailRet(d3ddev.SetTextureStageState(0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE)) then exit;
  if FailRet(d3ddev.SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE)) then exit;
  if FailRet(d3ddev.SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE)) then exit;

  if FailRet(d3ddev.SetStreamSource(0, FvertexBuffer, 0, sizeof(TCustomVertex))) then exit; //set next source ( NEW )
  if FailRet(d3ddev.SetFVF(D3DFVF_CUSTOMVERTEX)) then exit;
  if FailRet(d3ddev.DrawPrimitive(D3DPT_TRIANGLESTRIP, 0, 2)) then exit; //draw quad
  if FailRet(d3ddev.SetTexture(0, nil)) then exit;
  if FailRet(d3ddev.EndScene) then exit;
end;
Hier endet leider mein mathematisches & delphianotisches Knoff-Hoff.
  Mit Zitat antworten Zitat
TiGü

Registriert seit: 6. Apr 2011
Ort: Berlin
3.070 Beiträge
 
Delphi 10.4 Sydney
 
#7

AW: VMR9 custom allocator-presenter

  Alt 18. Jan 2018, 14:43
Zitat:
Direct3D und DirectShow
Direct3D hat damit weniger bis gar nichts zu tun.
https://msdn.microsoft.com/en-us/lib...(v=vs.85).aspx
Einfach mal zählen, wie oft der Begriff "Direct3D" vorkommt, danke!
Ja und was hat das mit Videos zu tun ?
Ich benötige es nicht einmal. Einfach mal zählen wie oft das in Zusammenhang mit Videos zum tragen kommt. danke

gruss
Emil, wenn du nichts beizutragen hast, dann lass es doch einfach.
Es geht hier nicht darum was du willst oder kannst oder brauchst!
Ist doch völlig egal, ob irgendwelche ABC- oder XYZ-Filter in deinen Player dir die Details vorenthalten.
Mit irgendeiner API werden die ja auf die Grafikkarte zugreifen (GDI, GDI+, Direct3D9, Direct3D10/11/12, DirectDraw, Direct2D, OpenGL, Vulkan).

Es geht hier um DirectShow und die Implementierung eines eigenen Allocator-Presenter für einen Video Mixing Renderer 9 (VMR-9) Filter.
Der verwendet nun mal halt ein D3D9-Device und entsprechende D3D9-Surface nebst D3D9-Texturen.
Siehe entsprechend den Codeauszügen von Terwi (Variablen: FD3DDev, FD3D, surface, texture, ...).
  Mit Zitat antworten Zitat
TiGü

Registriert seit: 6. Apr 2011
Ort: Berlin
3.070 Beiträge
 
Delphi 10.4 Sydney
 
#8

AW: VMR9 custom allocator-presenter

  Alt 18. Jan 2018, 14:48
Delphi-Quellcode:
function TPlaneScene.DrawScene(d3ddev: IDirect3DDevice9;
  texture: IDirect3DTexture9): HRESULT;
  function FailRet(hr: HResult): boolean;
  begin
    DrawScene := hr;
    Result := Failed(hr);
  end;
var
  dwCurrentTime: DWord;
  difference: Int64;
  x, y, z: Single;
  mask0, mask3: DWord;
  pData: Pointer;
begin
  if ((d3ddev = nil) or (texture = nil)) then
  begin
    Result := E_POINTER;
    Exit;
  end;

  if( FvertexBuffer = nil) then
  begin
    Result := D3DERR_INVALIDCALL;
    Exit;
  end;

  // get the difference in time
  dwCurrentTime := GetTickCount;
  difference := Ftime - dwCurrentTime;

  // figure out the rotation of the plane
  x := -cos(difference / 2000);
  y := cos(difference / 2000);
  z := sin(difference / 2000);

  // update the two rotating vertices with the new position
  Fvertices[0].position := MakePosition(x, y, z); // top left
  Fvertices[3].position := MakePosition(-x, -y, -z); // bottom right

  // Adjust the color so the blue is always on the bottom.
  // As the corner approaches the bottom, get rid of all the other
  // colors besides blue
  mask0 := Trunc((255 * (( y + 1) / 2)));
  mask3 := Trunc((255 * ((-y + 1) / 2)));
  Fvertices[0].color := $ff0000ff or (mask0 shl 16) or (mask0 shl 8);
  Fvertices[3].color := $ff0000ff or (mask3 shl 16) or (mask3 shl 8);

  // write the new vertex information into the buffer
  if FailRet(FvertexBuffer.Lock(0, sizeof(pData), pData, 0)) then exit;
  move(Fvertices, pData^ , sizeof(Fvertices));
  if FailRet(FvertexBuffer.Unlock) then exit;

  // clear the scene so we don't have any articats left
  d3ddev.Clear(0, nil, D3DCLEAR_TARGET, D3DCOLOR_XRGB(255,255,255), 1.0, 0);

  if FailRet(d3ddev.BeginScene) then exit;
  if FailRet(d3ddev.SetTexture(0, texture)) then exit;

  if FailRet(d3ddev.SetTextureStageState(0, D3DTSS_ALPHAOP, D3DTOP_MODULATE)) then exit;
  if FailRet(d3ddev.SetTextureStageState(0, D3DTSS_ALPHAARG1, D3DTA_TEXTURE)) then exit;
  if FailRet(d3ddev.SetTextureStageState(0, D3DTSS_ALPHAARG2, D3DTA_DIFFUSE)) then exit;
  if FailRet(d3ddev.SetTextureStageState(0, D3DTSS_COLORARG1, D3DTA_TEXTURE)) then exit;

  if FailRet(d3ddev.SetStreamSource(0, FvertexBuffer, 0, sizeof(TCustomVertex))) then exit; //set next source ( NEW )
  if FailRet(d3ddev.SetFVF(D3DFVF_CUSTOMVERTEX)) then exit;
  if FailRet(d3ddev.DrawPrimitive(D3DPT_TRIANGLESTRIP, 0, 2)) then exit; //draw quad
  if FailRet(d3ddev.SetTexture(0, nil)) then exit;
  if FailRet(d3ddev.EndScene) then exit;
end;
Hier endet leider mein mathematisches & delphianotisches Knoff-Hoff.
Ich dachte eigentlich an ein ZIP-Archiv mit allen benötigten Projektdateien, Quelltexten und Drittanbieter-Units (ja, auch das DSPack).
So das man als Helfender einfach nur das ZIP-Archiv entpackt und das Projekt öffnet und startet.

Nichts desto trotz musst du im oben zitierten Quelltext doch bloß das Drehen verhindern.
Probiere mal testweise diese Zeile difference := Ftime - dwCurrentTime; gegen difference := 0; auszustauschen.

Ansonsten kannst du alles ab der Zeile bis zum d3ddev.Clear auskommentieren und ausprobieren.
  Mit Zitat antworten Zitat
Benutzerbild von TERWI
TERWI

Registriert seit: 29. Mär 2008
Ort: D-49626
381 Beiträge
 
Delphi 11 Alexandria
 
#9

AW: VMR9 custom allocator-presenter

  Alt 18. Jan 2018, 15:12
Download DSPack 2.3.4
Das ist die letzte offizielle Version - es gib auch noch 'überarbeitungen'.
Auspacken, Anweisungen zur Installation in der README.HTM lesen, VCL-Komponenten installieren, notwendige Verzeichnisse zuweisen und die Demo im Unterverzeichnis starten: '\DEMOS\D6-D7\VMR\VMR9ALLOCATOR\PlayFile'
Sonst braucht es nix.

Zitat:
Nichts desto trotz musst du im oben zitierten Quelltext doch bloß das Drehen verhindern. Probiere mal testweise diese Zeile difference := Ftime - dwCurrentTime; gegen difference := 0; auszustauschen.
Das war das erste, was ich getestet habe. Ergebnis siehe 1. Post:
Zitat:
... der Inhalt "hängt irgendwie auf halb-acht" im Raum/Fenster .... Nett, aber so unbrauchbar.
  Mit Zitat antworten Zitat
Benutzerbild von TERWI
TERWI

Registriert seit: 29. Mär 2008
Ort: D-49626
381 Beiträge
 
Delphi 11 Alexandria
 
#10

AW: VMR9 custom allocator-presenter

  Alt 18. Jan 2018, 15:36
Noch eine nachträgliche Info zum kompilieren und DirextX:
Vor etwa 1/2 Jahr hab ich noch mit XP (32bit) und Win7 (auch 32bit, testweise x64) "rumgemacht". Damit ließ sich das DSPack immer einwandfrei kompilieren.
Verwendet wurde derzeit schon D2009.

Nach "Zusammenstellung" meines neuen Power-Schleppi's ist nun Win8.1 x64 auf dem Trapez. (10.x ++ gönne ich mir wahrscheinlich erst viel später ....)

Hier meckert mir Delphi das fehlen der Datei "d3dx9d_33.dll" an.
(.... HALLO, EWeiss ! )
Zur Abhilfe muss man in der DSPack-Datei "D3DX9.pas" die Zeile 95 (je nach Version !?)
// d3dx9MicrosoftDebugDLL = 'd3dx9d_33.dll';
auskommentieren.
  Mit Zitat antworten Zitat
Antwort Antwort
Seite 1 von 2  1 2      

 

Forumregeln

Es ist dir nicht erlaubt, neue Themen zu verfassen.
Es ist dir nicht erlaubt, auf Beiträge zu antworten.
Es ist dir nicht erlaubt, Anhänge hochzuladen.
Es ist dir nicht erlaubt, deine Beiträge zu bearbeiten.

BB-Code ist an.
Smileys sind an.
[IMG] Code ist an.
HTML-Code ist aus.
Trackbacks are an
Pingbacks are an
Refbacks are aus

Gehe zu:

Impressum · AGB · Datenschutz · Nach oben
Alle Zeitangaben in WEZ +1. Es ist jetzt 20:04 Uhr.
Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz