Suite

Petit GeoTiff du monde très lent lorsqu'il est zoomé au niveau de la ville

Petit GeoTiff du monde très lent lorsqu'il est zoomé au niveau de la ville


Je suis nouveau sur GeoTools et pour commencer, j'essaie d'afficher un petit fichier GeoTiff sur une carte.

Les fichiers GeoTiff que j'utilise font moins de 10 Mo (par exemple un fichier de 1 Mo à 720x360 pixels) et couvrent le monde entier (il indique la température moyenne). Les points de données que je souhaite afficher sur la carte sont à un niveau beaucoup plus bas (par exemple, l'emplacement des arbres dans un parc de la ville), je dois donc zoomer beaucoup.

j'utiliseGeoTiffReaderlire le tif fichier que j'ajoute ensuite à unGridReaderLayer. La carte s'affiche à l'aideJMapFrame.showMap(carte).

public class QuickStart { public static void main(String[] args) lève une exception { File file = new File("C: emp.tif"); Lecteur GeoTiffReader = new GeoTiffReader(fichier); MapContent map = new MapContent(); map.setTitle("Test GeoTiff"); Layer layer = new GridReaderLayer(reader, createRGBStyle(reader)); map.addLayer(calque); JMapFrame.showMap(carte); } Style statique privé createRGBStyle (lecteur AbstractGridCoverage2DReader) { GridCoverage2D cov = null; try { cov = reader.read(null); } catch (IOException giveUp) { throw new RuntimeException(giveUp); } int numBands = cov.getNumSampleDimensions(); if (numBands < 3) { return null; } String[] sampleDimensionNames = new String[numBands]; for (int i = 0; i < numBands; i++) { GridSampleDimension dim = cov.getSampleDimension(i); sampleDimensionNames[i] = dim.getDescription().toString(); } int final ROUGE = 0, VERT = 1, BLEU = 2; int[] channelNum = { -1, -1, -1 }; for (int i = 0; i < numBands; i++) { String name = sampleDimensionNames[i].toLowerCase(); if (nom != null) { if (nom.matches("red.*")) { channelNum[RED] = i + 1; } else if (name.matches("green.*")) { channelNum[GREEN] = i + 1; } else if (name.matches("blue.*")) { channelNum[BLUE] = i + 1; } } } if (numérocanal[RED] < 0 ||numérocanal[VERT] < 0 ||numérocanal[BLEU] < 0) {numérocanal[RED] = 1; Numcanal[VERT] = 2 ; ChannelNum[BLEU] = 3; } SelectedChannelType[] sct = new SelectedChannelType[cov.getNumSampleDimensions()] ; StyleFactory sf = CommonFactoryFinder.getStyleFactory(); FilterFactory2 ff = CommonFactoryFinder.getFilterFactory2(); ContrastEnhancement ce = sf.contrastEnhancement(ff.literal(1.0), ContrastMethod.NORMALIZE); for (int i = 0; i < 3; i++) { sct[i] = sf.createSelectedChannelType(String.valueOf(channelNum[i]), ce); } RasterSymbolizer sym = sf.getDefaultRasterSymbolizer(); ChannelSelection sel = sf.channelSelection(sct[RED], sct[GREEN], sct[BLUE]); sym.setChannelSelection(sel); renvoie SLD.wrapSymbolizers(sym); } }

Lorsque l'application Swing s'ouvre, je peux voir la carte et interagir avec elle sans retard majeur. Cependant, à mesure que je zoome de plus en plus, la carte devient de plus en plus lente, jusqu'à ce qu'elle devienne inutilisable (éventuellement, la JVM commencera à utiliser beaucoup de CPU et de mémoire et plantera), mais lorsque je dézoome à nouveau, la carte redevient rapide.

Je m'attendais à ce que les performances s'améliorent lorsque je travaille avec des parties de plus en plus petites de l'image, car le système n'a besoin de fonctionner qu'avec un petit sous-ensemble de données / pixels. Pourtant, il semble que la bibliothèque GeoTools redimensionne l'image entière avant de la recadrer pour l'adapter à la zone affichée, plutôt que d'obtenir d'abord un "recadrage" de la zone affichée (par lat/lon), puis la redimensionner pour l'adapter à l'affichage de la carte .

Pourquoi le zoom dans GeoTiff est-il si lent dans GeoTools et comment puis-je rendre la carte plus réactive ?

PS. Je ne vois aucun impact sur les performances lorsque je charge le même fichier GeoTiff dans plusieurs outils SIG différents QGIS, ArcGIS Explorer, MapWindows, etc.). En utilisant ces autres outils, je peux même zoomer et afficher seulement 4 pixels du GeoTiff d'origine sous forme de 4 énormes cases sur la carte, ce que GeoTools ne peut même pas faire.

Voici un exemple de fichier TIF qui se traduit par unjava.lang.OutOfMemoryError : espace de tas Javalorsque je zoome (par exemple pour n'afficher qu'une seule des îles britanniques). MISE À JOUR : Désolé, il semble que le fichier soit converti en PNG lors du téléchargement, mais il indique la taille du fichier d'origine.

MISE À JOUR : sortie de gdalinfo.

Pilote : GTiff/GeoTIFF Fichiers : temp.tif La taille est 720, 360 Le système de coordonnées est : GEOGCS["WGS 84", DATUM["WGS_1984", SPHEROID["WGS 84",6378137,298.257223563, AUTHORITY["EPSG"," 7030"]], AUTORITE["EPSG","6326"]], PRIMEM["Greenwich",0], UNIT["degré",0.0174532925199433], AUTORITE["EPSG","4326"]] Origine = (- 179.9999999999999970,90.0000000000000000) Taille de pixel = (0,4999999999999950, -0.4999999999999950) Métadonnées : AREA_OR_POINT=Métadonnées de structure d'image de zone : INTERLEAVE=PIXEL Coordonnées d'angle : en haut à gauche (-180.0000000, 90.0000000) (180d 0' 0.00"W, 90d 0' 0.00"N ) En bas à gauche (-180.000000, -90.0000000) (180d 0' 0.00"W, 90d 0' 0.00"S) En haut à droite ( 180.0000000, 90.0000000) (180d 0' 0.00"E, 90d 0' 0.00"N) En bas à droite ( 180.0000000, -90.0000000) (180d 0' 0.00"E, 90d 0' 0.00"S) Centre ( -0.00000000, 0.0000000) ( 0d 0' 0.00"W, 0d 0' 0.00"N) Bande 1 Bloc=720x2 Type=Byte , ColorInterp=Red Mask Flags : PER_DATASET ALPHA Band 2 Block=720x2 Type=Byte, ColorInterp=Green Mask Flags : PER_DATASET ALPHA Band 3 Block=7 20x2 Type=Byte, ColorInterp=Blue Mask Flags : PER_DATASET ALPHA Band 4 Block=720x2 Type=Byte, ColorInterp=Alpha

MISE À JOUR : J'ai profilé l'application et j'ai obtenu les résultats ci-dessous. S'il s'agit d'un problème/bogue avec GeoTools, quelle serait la meilleure façon de le signaler ?


Merci aux utilisateurs qui ont fourni des conseils dans les commentaires ci-dessus. Je vais répondre à ma propre question ici dans l'espoir que cela aidera quelqu'un d'autre à l'avenir. Après avoir lutté beaucoup plus longtemps que prévu, il me semble enfin avoir une configuration qui pourrait fonctionner pour moi à l'avenir.

j'utilise maintenant GeoTools 11.5 (toute version majeure supérieure semble avoir les problèmes de mémoire que je rencontre - malheureusement, je ne sais toujours pas pourquoi, mais je ne vais pas perdre plus de temps là-dessus maintenant).

Pour se débarrasser ducom.sun.media.jai.mlib.MediaLibAccessormessage d'erreur lors de l'exécution sur Java 8, j'ai ajouté le code suivant en haut de la classe.

static { System.setProperty("com.sun.media.jai.disableMediaLib", "true"); }

J'ai aussi dû changer le style à utiliserContrastMethod.NONE, sinon cela changerait les couleurs lorsque je zoome et me déplace.

Après tous ces changements, la carte est désormais rendue à une vitesse acceptable, peut effectuer un panoramique et un zoom à n'importe quel niveau, ne fait pas planter la JVM avec des problèmes de MOO et ne change pas la couleur de la carte de manière aléatoire.


Voir la vidéo: QGIS: Raster conversion. DEM to.tif