none
WPF - Performanceprobleme beim XPS rendern RRS feed

  • Frage

  • Hallo,

    ich verwende folgenden Code, um für eine XPS-Datei ein Array aus Vorschaubildern zu erstellen:

    DocumentPage aktPage = null;
    XpsDocument xpd = null;
    FixedDocumentSequence document = null;
    RenderTargetBitmap[] xpsThumbnails;
    
    xpd = new XpsDocument("c:\\test.xps", FileAccess.Read, CompressionOption.Fast);
    document = xpd.GetFixedDocumentSequence();
    xpsThumbnails = new RenderTargetBitmap[document.DocumentPaginator.PageCount];
    
    for (int i = 0; i < document.DocumentPaginator.PageCount; i++)
    {
    	aktPage = document.DocumentPaginator.GetPage(i);
    	xpsThumbnails[i] = new RenderTargetBitmap(420, 240, 32, 32, System.Windows.Media.PixelFormats.Default);
    	xpsThumbnails[i].Render(aktPage.Visual);
    	xpsThumbnails[i].Freeze();
    	aktPage.Dispose();
    }

    Letztens habe ich eine Powerpointpräsentation mit 86 Folien als XPS exportiert, Vorschaubilder erstellt und mir diese in einer Image Komponente anzeigen lassen. Der Arbeitsspeicherverbrauch betrug ca 1 GB. Das ist einfach unverhältnismäßig viel. Wenn ich 86 Bilder (z.B. JPEG, PNG) in derselben Größe in ein BitmapImage-Array lade, brauche ich keine 150 MB.

    Weiß jemand, wo mein Performanceproblem liegt?

    Ich habe bereits probiert, statt eines RenderTargetBitmap-Arrays ein BitmapImage-Array zu verwenden (mit ensprechender Konvertierung nach dem Rendern). Das hatte auf den Arbeitsspeicherverbrauch keine positiven Auswirkungen.

    Und ja, ich möchte stetig für alle Seiten kleine Vorschaubilder im Arbeitsspeicher halten. Die XPS Dateien haben max. 100 Folien und 200 MB Arbeitsspeicherverbrauch wären für mich kein Problem.

    Samstag, 15. April 2017 11:19

Alle Antworten

  • Hallo User95,

    Die statische PixelFormats-Klasse hat andere Eigenschaften, bei denen weniger Bits pro Pixel in Anspruch genommen werden. Ändert sich etwas, wenn Du es mit Bgr565 oder Bgr24 versuchst?

    Gruß,
    Dimitar


    Bitte haben Sie Verständnis dafür, dass im Rahmen dieses Forums, welches auf dem Community-Prinzip „IT-Pros helfen IT-Pros“ beruht, kein technischer Support geleistet werden kann oder sonst welche garantierten Maßnahmen seitens Microsoft zugesichert werden können.

    Dienstag, 18. April 2017 09:43
    Administrator
  • Hallo,

    leider funktioniert das bei mir nicht. Ich erhalte folgende Exceptions, wenn ich die beiden vorgeschlagenen Pixelformate verwende:

    • "PixelFormat 'Bgr565'" wird für diesen Vorgang nicht unterstützt.
    • "PixelFormat 'Bgr24'" wird für diesen Vorgang nicht unterstützt.
    Dienstag, 18. April 2017 13:52
  • Hi User95,

    RenderTargetBitmap funktioniert nur mit PixelFormats.Pbgra32.

    Bist Du Dir sicher, dass der große Speicherbedarf durch die thumbnails kommt?

    Schließt Du das xpsDocument mittels Close() methode nach gebrauch?

    https://msdn.microsoft.com/de-de/library/system.windows.xps.packaging.xpsdocument.close(v=vs.110).aspx

    Viele Grüße,

      Thorsten


    Mittwoch, 19. April 2017 02:31
  • Hallo Thorsten,

    Ja, ich schließe das XPS-Dokument auch mit Close(). Das fehlt leider oben im Codesnippet, sorry. Ich habe heute auch nochmal überprüft, ob das Speicherleck tatsächlich von den Vorschaubildern kommt und es hat sich bestätigt.

    Das einzige was mir noch zur Lösung des Problems einfallen würde: Ein kleines Programm schreiben, dass die Seiten als JPG rendert und in einem temporären Ordner abspeichert. Dieses Programm dann immer nach dem Rendern schließen, so dass alle Ressourcen freigegeben werden. Im Anschluss die Seiten als JPG in meine WPF Anwendung laden. Dann würde ich im Endeffekt max. 150 MB RAM dauerhaft belegen (siehe die Infos aus meiner Fragestellung). Die Lösung wäre aber so unschön, dass ich mich dafür schämen würde. Deshalb frage ich hier nach, vielleicht gibt es eine elegantere und Speicher sparende Lösung.

    Mittwoch, 19. April 2017 15:37