2008-08-18 3 views

Antwort

0

Hoffentlich wird jemand mich korrigieren, wenn ich falsch liege, aber ich denke nicht, dass es so etwas in WPF gibt. Aber hoffentlich ist dies einer der vielen Fälle, in denen Fortschritte in der Technologie veraltet sind, so wie wir es gewohnt sind, Dinge zu tun. Wie "wie wickle ich meine Digitaluhr?"

Der Grund, warum ImageCodecInfo.GetImageDecoders() in System.Drawing erforderlich ist, hat mit der kludgy Natur von System.Drawing selbst zu tun: System.Drawing ist ein verwalteter Wrapper um GDI +, das ein nicht verwalteter Wrapper ist um einen Teil der Win32-API. Es könnte also einen Grund geben, warum ein neuer Codec in Windows installiert wird, ohne dass .NET inhärent davon weiß. Und was von GetImageDecoders() zurückgegeben wird, ist nur eine Reihe von Zeichenfolgen, die normalerweise an System.Drawing/GDI + zurückgegeben werden und zum Suchen und Konfigurieren der entsprechenden DLL zum Lesen/Speichern Ihres Abbilds verwendet werden.

Auf der anderen Seite, in WPF, die Standard-Encoder und Decoder sind in das Framework integriert, und, wenn ich mich nicht irre, nicht von etwas abhängen, dass nicht garantiert, dass als Teil von installiert werden der Rahmen. Die folgenden Klassen erben von BitmapEncoder und sind standardmäßig mit WPF verfügbar: BmpBitmapEncoder, GifBitmapEncoder, JpegBitmapEncoder, PngBitmapEncoder, TiffBitmapEncoder, WmpBitmapEncoder. Es gibt BitmapDecoder für alle die gleichen Formate plus IconBitmapDecoder und LateBoundBitmapDecoder.

Sie haben vielleicht mit einem Fall zu tun, den ich mir nicht vorstelle, aber es scheint mir, dass wenn Sie eine Klasse verwenden müssen, die von BitmapEncoder erbt, aber nicht in WPF enthalten war, ist es wahrscheinlich Ihre eigene benutzerdefinierte Klasse dass Sie mit Ihrer Anwendung installieren würden.

Hoffe, das hilft. Wenn ich einen notwendigen Teil des Bildes vermisse, lass es mich wissen.

+1

Ich recherchiere gerade dieses Problem, und Sie irren sich. WPF-Imaging ist genau das gleiche wie System.Drawing: ein managed Wrapper für Win32-Sachen, nämlich WIC (Windows Imaging Component). Kein Encoder/Decoder ist in das Framework integriert, und ich denke, das wird es nie geben (Performance- und Code-Wiederverwendungs-Gründe, sie haben alles in Windows). Sie haben nur vergessen, Funktionalität hinzuzufügen, um die Formate aufzulisten :(. – fejesjoco

+0

re: "Wie wickle ich meine Digitaluhr?" Sie machen jetzt digitale Uhren, die Ihre Bewegung nutzen, um den Akku aufzuladen. Sie könnten also einen mit einem Wickler machen. :) –

4

Sie müssen .NET Reflexion lieben. Ich habe im WPF-Team gearbeitet und kann mir nichts besseres vorstellen. Der folgende Code erzeugt diese Liste auf meiner Maschine:

Bitmap Encoders: 
System.Windows.Media.Imaging.BmpBitmapEncoder 
System.Windows.Media.Imaging.GifBitmapEncoder 
System.Windows.Media.Imaging.JpegBitmapEncoder 
System.Windows.Media.Imaging.PngBitmapEncoder 
System.Windows.Media.Imaging.TiffBitmapEncoder 
System.Windows.Media.Imaging.WmpBitmapEncoder 

Bitmap Decoders: 
System.Windows.Media.Imaging.BmpBitmapDecoder 
System.Windows.Media.Imaging.GifBitmapDecoder 
System.Windows.Media.Imaging.IconBitmapDecoder 
System.Windows.Media.Imaging.LateBoundBitmapDecoder 
System.Windows.Media.Imaging.JpegBitmapDecoder 
System.Windows.Media.Imaging.PngBitmapDecoder 
System.Windows.Media.Imaging.TiffBitmapDecoder 
System.Windows.Media.Imaging.WmpBitmapDecoder 

Es gibt einen Kommentar im Code ist, wo zusätzliche Baugruppen aus (wenn Sie Plugins zum Beispiel unterstützen). Außerdem werden Sie die Decoder Liste filtern zu entfernen:

System.Windows.Media.Imaging.LateBoundBitmapDecoder 

Kompliziertere Filterung Konstruktor Musterabgleich ist möglich, aber ich fühle mich nicht wie es zu schreiben. :-)

Alles, was Sie jetzt tun müssen, ist die Instanziierung der Encoder und Decoder, um sie zu verwenden. Sie können auch bessere Namen erhalten, indem Sie die CodecInfo Eigenschaft der Encoder-Decoder abrufen. Diese Klasse wird Ihnen unter anderen Faktoiden lesbare Namen geben.

using System; 
using System.Linq; 
using System.Collections.Generic; 
using System.Reflection; 
using System.Windows.Media.Imaging; 

namespace Codecs { 
    class Program { 
     static void Main(string[] args) { 
      Console.WriteLine("Bitmap Encoders:"); 
      AllEncoderTypes.ToList().ForEach(t => Console.WriteLine(t.FullName)); 
      Console.WriteLine("\nBitmap Decoders:"); 
      AllDecoderTypes.ToList().ForEach(t => Console.WriteLine(t.FullName)); 
      Console.ReadKey(); 
     } 

     static IEnumerable<Type> AllEncoderTypes { 
      get { 
       return AllSubclassesOf(typeof(BitmapEncoder)); 
      } 
     } 

     static IEnumerable<Type> AllDecoderTypes { 
      get { 
       return AllSubclassesOf(typeof(BitmapDecoder)); 
      } 
     } 

     static IEnumerable<Type> AllSubclassesOf(Type type) { 
      var r = new Reflector(); 
      // Add additional assemblies here 
      return r.AllSubclassesOf(type); 
     } 
    } 

    class Reflector { 
     List<Assembly> assemblies = new List<Assembly> { 
      typeof(BitmapDecoder).Assembly 
     }; 
     public IEnumerable<Type> AllSubclassesOf(Type super) { 
      foreach (var a in assemblies) { 
       foreach (var t in a.GetExportedTypes()) { 
        if (t.IsSubclassOf(super)) { 
         yield return t; 
        } 
       } 
      } 
     } 
    } 
} 
Verwandte Themen