2010-01-11 8 views
9

Chciałbym użyć LibTiff, aby uzyskać dostęp do bardzo dużych plików TIFF. Potrzebuję funkcji, takich jak wiele stron i płytek, a więc LibTiff wydaje się być właściwą drogą. Czy ktoś może mi pomóc, jak korzystać z LibTiff z C#? Znalazłem kilka linków (np. blog.bee-ee, które zawierały częściowy kod, ale nie mogłem wyjść poza otrzymanie wersji.) Spojrzałem na FreeImage, ale uznałem, że nie jest to odpowiednie (zdjęcia mają około 800 MPixel 8 lub 16-bitową skalę szarości - > 800-1600 MB) i nie mogę załadować go do pamięci w środowisku 32-bitowym)Używanie LibTiff z C# (aby uzyskać dostęp do kafelkowych obrazów TIFF)

Jestem bardzo doświadczony w C/C++, ale jeszcze nie w C#. Czy ktoś może mi pomóc w otworze lub niektórych podpowiedziach?

Uwaga: Potrzebuję stron, aby uzyskać dostęp do płaszczyzn piramidowych (wielu rozdzielczości) w tiff, a kafelków o wymiarach 256x256, aby uzyskać szybki dostęp do różnych części obrazu bez ładowania go na raz.

[Edytuj] Rozwiązanie LibTIFF.NET wydawało mi się najbardziej praktyczne. Teraz integruję go w rozwój produktu i prawdopodobnie uratuje mnie wiele bólów głowy z wchodzenia/wychodzenia z zarządzanej pamięci. Jeszcze nie próbowałem funkcji "oddzwaniania", która wydaje się być rozwiązana ładnie w sposób .net. Dzięki za pomoc na stackoverflow [/ Edytuj]

Odpowiedz

6

Możesz wypróbować naszą LibTiff.Net. Jest to darmowa i otwarta wersja LibTiff napisana przy użyciu zarządzanego C#. Interfejs API naszej implementacji był bardzo podobny do oryginału.

http://bitmiracle.com/libtiff/

Właśnie wydała go, więc nie może być błędów. Ale pełny kod źródłowy zawiera szereg testów, więc najbardziej oczywiste błędy powinny zostać naprawione.

+0

Dzięki. Moje pierwsze testy wyglądają dobrze. Mimo że znalazłem klasę opakowania, nie miał on znanego autora i wcześniej czy później dostałbym pewne problemy z dostępem do zarządzanych/niezarządzanych zasobów pamięci. Testy porównawcze wykazały równoważną wydajność odczytu nieskompresowanych plików i 50% perfomance na kompresowanych ostrosłupowych tiffach Adobe. Jest to dla mnie do przyjęcia. Mogę zrezygnować z kompresji, a ja będę lepiej, aby moje oprogramowanie było przyjazne dla wielu rdzeni niż rozwiązywanie problemów z pamięcią. – Adriaan

+0

Dzięki, Adriaan nasza implementacja jest zdecydowanie wolniejsza niż oryginalny język wyboru :-) – Bobrovsky

+0

Nie mam nic przeciwko. Dla mojego projektu wydajność oznacza funkcjonalność/euro. A godziny rozwoju to 95% kosztów. Mogę łatwo rzucić quadcore, aby to zrekompensować. Poza tym, kiedy trzymam się z daleka od kompresji, różnica jest niewielka. A moje pliki kompresują tylko około 10%, więc to tylko marne 100 MB na plik ;-) – Adriaan

4

WIC zapewnia wsparcie dla bardzo dużych plików graficznych. W ramce .NET jest dobre opakowanie: TiffBitmapDecoder.

+1

Czy możesz dodać linki? Z tego, co widziałem, TiffBitmapDecoder próbuje załadować obraz w pamięci naraz. Nie mogę tego zrobić. Obrazy> 1 GB zawsze zawiedzie na maszynie 32-bitowej z powodu fragmentacji. czy odnosisz się do specyfiki Windows7 (http://msdn.microsoft.com/en-us/library/ee720061%28VS.85%29.aspx)? – Adriaan

+0

Nie, TBD nie przechowuje obrazu. Zacznij tutaj: http://msdn.microsoft.com/en-us/library/ms748873.aspx –

+0

Dzięki za pomoc. Niestety moje doświadczenie jest inne. Kroki opisane w http://msdn.microsoft.com/en-us/library/ms748873.aspx próbują przydzielić pojedynczy blok pamięci z rozmiarem 1 klatki mapy bitowej. Potrzebuję dostępu do każdego piksela w bitmapa (więc nie można zapisać opcji zapisu na ekranie), niekoniecznie w jednym kawałku pamięci. Kiedy próbuję uruchomić dekoder tiff, jak podano w przykładzie, generalnie kończy się niepowodzeniem w bitmapach> 10k * 10k. A to tylko moje "małe pliki testowe". Mój cel to 800 pikseli x 16 bitów. Dlatego szukam kafelkowych plików TIFF. – Adriaan

1

Moim początkowym rozwiązaniem było użycie otoki C# .NET dla biblioteki DLL LibTIFF. Znalazłem go na libtiff ftp. Wydaje się, że zawiera wszystkie ważne metody biblioteki LIBTiff. Utrzymuje pamięć w niezarządzanej pamięci LibTIFF; oznacza to, że kod C# musi być tego świadomy i kopiować dane, gdy trzeba je przetworzyć w bezpiecznym kodzie.

My „dachówka odczyt kodów”, aby przetestować go czytać jak

if (LibTIFF.IsTiled(tiff)) 
{ 
    if (LibTIFF.GetField(tiff, (int)TIFFTags.TIFFTAG_TILEWIDTH, out tileWidth) && 
     LibTIFF.GetField(tiff, (int)TIFFTags.TIFFTAG_TILELENGTH, out tileLength)) 
    { 
     uint tiles = 0; 
     IntPtr pTile = LibTIFF._malloc((int)(tileLength*tileWidth*bitsPerSample/2)); 
     for (uint y = 0; y < imageLength; y += tileLength) 
     { 
      for (uint x = 0; x < imageWidth; x += tileWidth) 
      { 
       LibTIFF.ReadTile(tiff, pTile, x, y, 0, 0); 
       tiles++; 
      } 
     }       
     LibTIFF._free(pTile); 
    } 
} 

Pójdę do portu .NET libtiff chociaż, ale to rozwiązanie może być odpowiedni dla innych ludzi, więc zostawiam to na StackOverflow.

+0

Czy "LibTiff" jest jedynym sposobem na przetworzenie kafelkowego TIFF? czy możemy zrobić to samo z klasą TiffBitmapDecoder w .Net Framework? –

+0

Z tego co widzę, TiffBitMapDecoder nie zapewnia funkcjonalności do selektywnego ładowania części pliku (tylko do renderowania kompletnych ramek). http://msdn.microsoft.com/en-us/library/system.windows.media.imaging.tiffbitmapdecoder(v=vs.110).aspx – Adriaan

Powiązane problemy