Source Code Cross Referenced for PyramidBuilder.java in  » GIS » GeoTools-2.4.1 » it » geosolutions » utils » imagepyramid » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » GIS » GeoTools 2.4.1 » it.geosolutions.utils.imagepyramid 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        package it.geosolutions.utils.imagepyramid;
002:
003:        import it.geosolutions.utils.coveragetiler.CoverageTiler;
004:        import it.geosolutions.utils.imagemosaic.MosaicIndexBuilder;
005:        import it.geosolutions.utils.progress.ExceptionEvent;
006:        import it.geosolutions.utils.progress.ProcessingEvent;
007:        import it.geosolutions.utils.progress.ProcessingEventListener;
008:        import it.geosolutions.utils.progress.ProgressManager;
009:
010:        import java.awt.RenderingHints;
011:        import java.io.BufferedOutputStream;
012:        import java.io.BufferedWriter;
013:        import java.io.File;
014:        import java.io.FileNotFoundException;
015:        import java.io.FileOutputStream;
016:        import java.io.FileWriter;
017:        import java.io.IOException;
018:        import java.util.ArrayList;
019:        import java.util.List;
020:        import java.util.Properties;
021:        import java.util.logging.Level;
022:        import java.util.logging.Logger;
023:
024:        import javax.imageio.ImageIO;
025:        import javax.media.jai.BorderExtender;
026:        import javax.media.jai.Interpolation;
027:        import javax.media.jai.JAI;
028:        import javax.media.jai.RecyclingTileFactory;
029:        import javax.media.jai.TileCache;
030:
031:        import org.apache.commons.cli2.option.DefaultOption;
032:        import org.apache.commons.cli2.option.GroupImpl;
033:        import org.apache.commons.cli2.util.HelpFormatter;
034:        import org.apache.commons.cli2.validation.InvalidArgumentException;
035:        import org.apache.commons.cli2.validation.Validator;
036:        import org.apache.commons.io.FileUtils;
037:        import org.geotools.data.coverage.grid.AbstractGridCoverage2DReader;
038:        import org.geotools.data.coverage.grid.AbstractGridFormat;
039:        import org.geotools.data.coverage.grid.GridFormatFinder;
040:        import org.geotools.geometry.GeneralEnvelope;
041:        import org.opengis.coverage.grid.GridRange;
042:
043:        /**
044:         * Given an original image, builds an image pyramid out of it by combining the
045:         * various tiler, mosaic and pyramid layer builder tools.
046:         * 
047:         * <pre>
048:         * Example of use:
049:         *   PyramidBuilder -s "/usr/home/data/home.tif" -f 2 -n 4 -t "25,25" -w
050:         * </pre>
051:         * 
052:         * @author Andrea Aime
053:         * @since 2.3.x
054:         * 
055:         */
056:        public class PyramidBuilder extends ProgressManager implements 
057:                Runnable, ProcessingEventListener {
058:
059:            /**
060:             * Default tile cache size.
061:             */
062:            public final static long DEFAULT_TILE_CHACHE_SIZE = 32 * 1024 * 1024;
063:
064:            /**
065:             * Default imageio caching behaviour.
066:             */
067:            public final boolean DEFAULT_IMAGEIO_CACHING_BEHAVIOUR = false;
068:
069:            /**
070:             * Default thread priority.
071:             */
072:            public final int DEFAULT_THREAD_PRIORITY = Thread.NORM_PRIORITY;
073:
074:            /**
075:             * Default interpolation.
076:             */
077:            public final static Interpolation DEFAULT_INTERPOLATION = Interpolation
078:                    .getInstance(Interpolation.INTERP_NEAREST);
079:
080:            /** Default filter for subsampling averaged. */
081:            public final static float[] DEFAULT_KERNEL_GAUSSIAN = new float[] {
082:                    0.5F, 1.0F / 3.0F, 0.0F, -1.0F / 12.0F };
083:
084:            /**
085:             * Default border extender.
086:             */
087:            public final static BorderExtender DEFAULT_BORDER_EXTENDER = BorderExtender
088:                    .createInstance(BorderExtender.BORDER_COPY);
089:
090:            /** Static immutable ap for scaling algorithms. */
091:            private static List scalingAlgorithms;
092:            static {
093:                scalingAlgorithms = new ArrayList(4);
094:                scalingAlgorithms.add("nn");
095:                scalingAlgorithms.add("bil");
096:                scalingAlgorithms.add("bic");
097:                scalingAlgorithms.add("avg");
098:                scalingAlgorithms.add("filt");
099:            }
100:
101:            /** Program Version */
102:            private final static String versionNumber = "0.2";
103:
104:            /** Commons-cli option for the input location. */
105:            private DefaultOption locationOpt;
106:
107:            /** Commons-cli option for the output location. */
108:            private DefaultOption outputLocationOpt;
109:
110:            /** Output folder, defaults to the "pyramid" subfolder */
111:            private File outputLocation;
112:
113:            /** Commons-cli option for the tile dimension. */
114:            private DefaultOption tileDimOpt;
115:
116:            /** Commons-cli option for the scale algorithm. */
117:            private DefaultOption scaleAlgorithmOpt;
118:
119:            /** Commons-cli option for the tile cache size to use. */
120:            private DefaultOption tileCacheSizeOpt;
121:
122:            /** Commons-cli option for the tile numbe of subsample step to use. */
123:            private DefaultOption numStepsOpt;
124:
125:            /** Commons-cli option for the scale factor to use. */
126:            private DefaultOption scaleFactorOpt;
127:
128:            /**
129:             * Commons-cli options for overwriting the output layer dirs if already
130:             * available
131:             */
132:            private DefaultOption overwriteOpt;
133:
134:            /** Tile width. */
135:            private int tileW = -1;
136:
137:            /** Tile height. */
138:            private int tileH = -1;
139:
140:            /** Scale algorithm. */
141:            private String scaleAlgorithm;
142:
143:            /** Logger for this class. */
144:            private final static Logger LOGGER = org.geotools.util.logging.Logging
145:                    .getLogger(PyramidBuilder.class.toString());
146:
147:            /** ImageIO caching behvaiour controller. */
148:            private boolean useImageIOCache = DEFAULT_IMAGEIO_CACHING_BEHAVIOUR;
149:
150:            /** Default border extender. */
151:            private BorderExtender borderExtender = DEFAULT_BORDER_EXTENDER;
152:
153:            /** Downsampling step. */
154:            private int scaleFactor;
155:
156:            /** Default tile cache size. */
157:            private long tileCacheSize = DEFAULT_TILE_CHACHE_SIZE;
158:
159:            /**
160:             * The source path.
161:             */
162:            private File inputLocation;
163:
164:            /**
165:             * The name of the output pyramid, will simply be "pyramid" if not set
166:             */
167:            private String name;
168:
169:            /**
170:             * Commons-cli option for the pyramid name
171:             */
172:            private DefaultOption nameOpt;
173:
174:            /**
175:             * 
176:             * Interpolation method used througout all the program.
177:             * 
178:             * @TODO make the interpolation method customizable from the user
179:             *       perpsective.
180:             * 
181:             */
182:            private Interpolation interp = DEFAULT_INTERPOLATION;
183:
184:            private int numSteps;
185:
186:            private boolean exceptionOccurred = false;
187:
188:            private boolean overwriteOutputDirs = false;
189:
190:            private double currStep = 0;
191:
192:            private double totalSteps = 0;
193:
194:            /**
195:             * Relaunches slave tools progress with the appropriate percentage
196:             * corrections
197:             */
198:            private ProcessingEventListener slaveToolsListener = new ProcessingEventListener() {
199:
200:                public void getNotification(ProcessingEvent event) {
201:                    fireEvent(event.getMessage(), (currStep / totalSteps) * 100
202:                            + event.getPercentage() / totalSteps);
203:                }
204:
205:                public void exceptionOccurred(ExceptionEvent event) {
206:                    fireException(event.getMessage(), event.getPercentage(),
207:                            event.getException());
208:                    exceptionOccurred = true;
209:                }
210:
211:            };
212:
213:            private GeneralEnvelope envelope;
214:
215:            private double[][] resolutions;
216:
217:            /**
218:             * Simple constructor for a pyramid generator. Use the input string in order
219:             * to read an image.
220:             * 
221:             * 
222:             */
223:            public PyramidBuilder() {
224:                // /////////////////////////////////////////////////////////////////////
225:                // Options for the command line
226:                // /////////////////////////////////////////////////////////////////////
227:                helpOpt = optionBuilder.withShortName("h").withShortName("?")
228:                        .withLongName("helpOpt").withDescription(
229:                                "print this message.").withRequired(false)
230:                        .create();
231:
232:                versionOpt = optionBuilder.withShortName("v").withLongName(
233:                        "versionOpt").withDescription("print the versionOpt.")
234:                        .withRequired(false).create();
235:
236:                locationOpt = optionBuilder
237:                        .withShortName("s")
238:                        .withLongName("source")
239:                        .withArgument(
240:                                arguments.withName("source").withMinimum(1)
241:                                        .withMaximum(1).withValidator(
242:                                                new Validator() {
243:
244:                                                    public void validate(
245:                                                            List args)
246:                                                            throws InvalidArgumentException {
247:                                                        final int size = args
248:                                                                .size();
249:                                                        if (size > 1)
250:                                                            throw new InvalidArgumentException(
251:                                                                    "Source can be a single file or directory ");
252:                                                        final File source = new File(
253:                                                                (String) args
254:                                                                        .get(0));
255:                                                        if (!source.exists())
256:                                                            throw new InvalidArgumentException(
257:                                                                    new StringBuffer(
258:                                                                            "The provided source is invalid! ")
259:
260:                                                                    .toString());
261:                                                    }
262:
263:                                                }).create()).withDescription(
264:                                "path where files are located").withRequired(
265:                                true)
266:                        .create();
267:
268:                nameOpt = optionBuilder.withShortName("name").withLongName(
269:                        "pyramid_name").withArgument(
270:                        arguments.withName("name").withMinimum(0)
271:                                .withMaximum(1).create()).withDescription(
272:                        "name for the pyramid property file").withRequired(
273:                        false).create();
274:
275:                tileDimOpt = optionBuilder.withShortName("t").withLongName(
276:                        "tiled_dimension").withArgument(
277:                        arguments.withName("t").withMinimum(0).withMaximum(1)
278:                                .create()).withDescription(
279:                        "tile dimensions as a couple width,height in pixels")
280:                        .withRequired(false).create();
281:
282:                scaleFactorOpt = optionBuilder.withShortName("f").withLongName(
283:                        "scale_factor").withArgument(
284:                        arguments.withName("f").withMinimum(1).withMaximum(1)
285:                                .withValidator(new Validator() {
286:
287:                                    public void validate(List args)
288:                                            throws InvalidArgumentException {
289:                                        final int size = args.size();
290:                                        if (size > 1)
291:                                            throw new InvalidArgumentException(
292:                                                    "Only one scaling algorithm at a time can be chosen");
293:                                        int factor = Integer
294:                                                .parseInt((String) args.get(0));
295:                                        if (factor <= 0)
296:                                            throw new InvalidArgumentException(
297:                                                    new StringBuffer(
298:                                                            "The provided scale factor is negative! ")
299:
300:                                                    .toString());
301:                                        if (factor == 1) {
302:                                            LOGGER
303:                                                    .warning("The scale factor is 1, program will exit!");
304:                                            System.exit(0);
305:                                        }
306:                                    }
307:
308:                                }).create()).withDescription(
309:                        "integer scale factor").withRequired(true).create();
310:
311:                numStepsOpt = optionBuilder.withShortName("n").withLongName(
312:                        "num_steps").withArgument(
313:                        arguments.withName("n").withMinimum(1).withMaximum(1)
314:                                .withValidator(new Validator() {
315:
316:                                    public void validate(List args)
317:                                            throws InvalidArgumentException {
318:                                        final int size = args.size();
319:                                        if (size > 1)
320:                                            throw new InvalidArgumentException(
321:                                                    "Only one scaling algorithm at a time can be chosen");
322:                                        int steps = Integer
323:                                                .parseInt((String) args.get(0));
324:                                        if (steps <= 0)
325:                                            throw new InvalidArgumentException(
326:                                                    new StringBuffer(
327:                                                            "The provided scale factor is negative! ")
328:
329:                                                    .toString());
330:
331:                                    }
332:
333:                                }).create()).withDescription(
334:                        "integer scale factor").withRequired(true).create();
335:
336:                scaleAlgorithmOpt = optionBuilder
337:                        .withShortName("a")
338:                        .withLongName("scaling_algorithm")
339:                        .withArgument(
340:                                arguments.withName("a").withMinimum(0)
341:                                        .withMaximum(1).withValidator(
342:                                                new Validator() {
343:
344:                                                    public void validate(
345:                                                            List args)
346:                                                            throws InvalidArgumentException {
347:                                                        final int size = args
348:                                                                .size();
349:                                                        if (size > 1)
350:                                                            throw new InvalidArgumentException(
351:                                                                    "Only one scaling algorithm at a time can be chosen");
352:                                                        if (!scalingAlgorithms
353:                                                                .contains(args
354:                                                                        .get(0)))
355:                                                            throw new InvalidArgumentException(
356:                                                                    new StringBuffer(
357:                                                                            "The output format ")
358:                                                                            .append(
359:                                                                                    args
360:                                                                                            .get(0))
361:                                                                            .append(
362:                                                                                    " is not permitted")
363:                                                                            .toString());
364:
365:                                                    }
366:                                                }).create())
367:                        .withDescription(
368:                                "name of the scaling algorithm, eeither one of average (a), filtered (f), bilinear (bil), nearest neigbhor (nn)")
369:                        .withRequired(false).create();
370:
371:                priorityOpt = optionBuilder.withShortName("p").withLongName(
372:                        "thread_priority").withArgument(
373:                        arguments.withName("thread_priority").withMinimum(0)
374:                                .withMaximum(1).create()).withDescription(
375:                        "priority for the underlying thread").withRequired(
376:                        false).create();
377:
378:                tileCacheSizeOpt = optionBuilder.withShortName("c")
379:                        .withLongName("cache_size").withArgument(
380:                                arguments.withName("c").withMinimum(0)
381:                                        .withMaximum(1).create())
382:                        .withDescription("tile cache sized")
383:                        .withRequired(false).create();
384:
385:                overwriteOpt = optionBuilder
386:                        .withShortName("w")
387:                        .withLongName("overwrite")
388:                        .withDescription(
389:                                "completely wipe out existing layer dirs before proceeding.")
390:                        .withRequired(false).create();
391:
392:                cmdOpts.add(locationOpt);
393:                cmdOpts.add(tileDimOpt);
394:                cmdOpts.add(scaleFactorOpt);
395:                cmdOpts.add(scaleAlgorithmOpt);
396:                cmdOpts.add(numStepsOpt);
397:                cmdOpts.add(priorityOpt);
398:                cmdOpts.add(tileCacheSizeOpt);
399:                cmdOpts.add(versionOpt);
400:                cmdOpts.add(helpOpt);
401:                cmdOpts.add(overwriteOpt);
402:
403:                optionsGroup = new GroupImpl(cmdOpts, "Options",
404:                        "All the options", 0, 9);
405:
406:                // /////////////////////////////////////////////////////////////////////
407:                //
408:                // Help Formatter
409:                //
410:                // /////////////////////////////////////////////////////////////////////
411:                final HelpFormatter cmdHlp = new HelpFormatter("| ", "  ",
412:                        " |", 75);
413:                cmdHlp.setShellCommand("PyramidBuilder");
414:                cmdHlp.setHeader("Help");
415:                cmdHlp.setFooter(new StringBuffer(
416:                        "PyramidBuilder - GeoSolutions S.a.s (C) 2006 - v ")
417:                        .append(PyramidBuilder.versionNumber).toString());
418:                cmdHlp
419:                        .setDivider("|-------------------------------------------------------------------------|");
420:
421:                cmdParser.setGroup(optionsGroup);
422:                cmdParser.setHelpOption(helpOpt);
423:                cmdParser.setHelpFormatter(cmdHlp);
424:            }
425:
426:            /**
427:             * 
428:             * This method is a utlity method for setting various JAi wide hints we will
429:             * use here and afterwards.
430:             * 
431:             * 
432:             */
433:            private void settingJAIHints() {
434:
435:                // //
436:                // Imageio caching behaviour in case it is ever needed.
437:                // //
438:                ImageIO.setUseCache(useImageIOCache);
439:
440:                // //
441:                //
442:                // JAI cache fine tuning
443:                //
444:                // //
445:                final JAI jaiDef = JAI.getDefaultInstance();
446:                // setting the tile cache
447:                final TileCache cache = jaiDef.getTileCache();
448:                cache.setMemoryCapacity(tileCacheSize);
449:                // setting JAI wide hints
450:                jaiDef.setRenderingHint(JAI.KEY_INTERPOLATION, this .interp);
451:                jaiDef.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
452:                        RenderingHints.VALUE_ANTIALIAS_ON);
453:                jaiDef.setRenderingHint(RenderingHints.KEY_RENDERING,
454:                        RenderingHints.VALUE_RENDER_SPEED);
455:                jaiDef.setRenderingHint(JAI.KEY_CACHED_TILE_RECYCLING_ENABLED,
456:                        Boolean.TRUE);
457:                // //
458:                //
459:                // tile factory and recycler
460:                //
461:                // //
462:                RecyclingTileFactory recyclingFactory = new RecyclingTileFactory();
463:                jaiDef.setRenderingHint(JAI.KEY_TILE_FACTORY, recyclingFactory);
464:                jaiDef
465:                        .setRenderingHint(JAI.KEY_TILE_RECYCLER,
466:                                recyclingFactory);
467:
468:                // //
469:                //
470:                // border extender
471:                //
472:                // //
473:                jaiDef
474:                        .setRenderingHint(JAI.KEY_BORDER_EXTENDER,
475:                                borderExtender);
476:
477:            }
478:
479:            public void run() {
480:                // //
481:                //
482:                // setting JAI wide hints
483:                //
484:                // //
485:                settingJAIHints();
486:
487:                // /////////////////////////////////////////////////////////////////////
488:                //
489:                // Gather reader to compute tile x and y from tile size
490:                //
491:                // /////////////////////////////////////////////////////////////////////
492:
493:                AbstractGridFormat format = (AbstractGridFormat) GridFormatFinder
494:                        .findFormat(inputLocation);
495:                if (format == null) {
496:                    String message = "Could not find a format for this coverage";
497:                    fireException(message, 0, new IOException(message));
498:                    return;
499:                }
500:                AbstractGridCoverage2DReader inReader = (AbstractGridCoverage2DReader) format
501:                        .getReader(inputLocation);
502:                if (inReader == null) {
503:                    String message = "Unable to instantiate a reader for this coverage";
504:                    fireException(message, 0, new IOException(message));
505:                    return;
506:                }
507:
508:                envelope = inReader.getOriginalEnvelope();
509:                final GridRange range = inReader.getOriginalGridRange();
510:                final int numTileX = (int) Math
511:                        .ceil(range.getLength(0) / tileW);
512:                final int numtileY = (int) Math
513:                        .ceil(range.getLength(1) / tileH);
514:                inReader.dispose();
515:
516:                // /////////////////////////////////////////////////////////////////////
517:                //
518:                // Create output directory
519:                //
520:                // /////////////////////////////////////////////////////////////////////
521:
522:                if (!outputLocation.exists())
523:                    if (!outputLocation.mkdir()) {
524:                        String message = "Could not create output directory: "
525:                                + outputLocation;
526:                        fireException(message, 0, new IOException(message));
527:                        return;
528:                    }
529:
530:                // /////////////////////////////////////////////////////////////////////
531:                // 
532:                // Compute total steps and set current one so that slave tools progress
533:                // event percentages can be corrected to represent the global progress
534:                //
535:                // //////////////////////////////////////////////////////////////////////
536:
537:                totalSteps = (numSteps + 1) * 2;
538:                currStep = 1;
539:
540:                // /////////////////////////////////////////////////////////////////////
541:                //
542:                // Set up initial level using the coverage tiler
543:                //
544:                // /////////////////////////////////////////////////////////////////////
545:
546:                File outputDir = new File(outputLocation, "0");
547:                if (!checkLayerDir(outputDir))
548:                    return;
549:
550:                // create first tiled set
551:                resolutions = new double[2][numSteps + 1];
552:                tileInput(numTileX, numtileY, outputDir);
553:                if (exceptionOccurred)
554:                    return;
555:                currStep++;
556:
557:                // mosaic it
558:                double[] resolution = mosaicLevel(0);
559:                resolutions[0][0] = resolution[0];
560:                resolutions[1][0] = resolution[1];
561:                if (exceptionOccurred)
562:                    return;
563:                currStep++;
564:
565:                // /////////////////////////////////////////////////////////////////////
566:                //
567:                // Now do create a new level, and mosaic it, up to the final level
568:                //
569:                // /////////////////////////////////////////////////////////////////////
570:                int currLevel = scaleFactor;
571:                int prevLevel = 0;
572:                for (int step = 0; step < numSteps; step++) {
573:                    // check output dir
574:                    File prevLevelDirectory = new File(outputLocation, String
575:                            .valueOf(prevLevel));
576:                    File currLevelDirectory = new File(outputLocation, String
577:                            .valueOf(currLevel));
578:                    if (!checkLayerDir(currLevelDirectory))
579:                        return;
580:
581:                    // create next tiled set
582:                    buildNewLayer(prevLevelDirectory, currLevelDirectory);
583:                    if (exceptionOccurred)
584:                        return;
585:                    currStep++;
586:
587:                    // mosaic it
588:                    resolution = mosaicLevel(currLevel);
589:                    resolutions[0][step + 1] = resolution[0];
590:                    resolutions[1][step + 1] = resolution[1];
591:                    if (exceptionOccurred)
592:                        return;
593:                    currStep++;
594:
595:                    // switch to next resolution level
596:                    prevLevel = currLevel;
597:                    currLevel *= scaleFactor;
598:                }
599:
600:                // /////////////////////////////////////////////////////////////////////
601:                //
602:                // Finally, build the property file
603:                //
604:                // /////////////////////////////////////////////////////////////////////
605:
606:                fireEvent("Creating final properties file ", 99.9);
607:                createPropertiesFiles();
608:                if (!exceptionOccurred)
609:                    fireEvent("Done!!!", 100);
610:            }
611:
612:            private boolean checkLayerDir(File outputDir) {
613:                if (!outputDir.exists())
614:                    return true;
615:                if (!overwriteOutputDirs) {
616:                    fireException(new IOException("Layer directory "
617:                            + outputDir
618:                            + " already exist. Use -w to force its deletion"));
619:                    return false;
620:                }
621:                try {
622:                    FileUtils.deleteDirectory(outputDir);
623:                } catch (IOException e) {
624:                    fireException(e);
625:                    return false;
626:                }
627:                return true;
628:            }
629:
630:            private void tileInput(final int numTileX, final int numtileY,
631:                    File outputDir) {
632:                CoverageTiler tiler = new CoverageTiler();
633:                tiler.addProcessingEventListener(slaveToolsListener);
634:                tiler.setInputLocation(inputLocation);
635:                tiler.setOutputLocation(outputDir);
636:                tiler.setNumTileX(numTileX);
637:                tiler.setNumTileY(numtileY);
638:                tiler.run();
639:                tiler.removeAllProcessingEventListeners();
640:            }
641:
642:            private void buildNewLayer(File prevLevelDirectory,
643:                    File currLevelDirectory) {
644:                PyramidLayerBuilder layerBuilder = new PyramidLayerBuilder();
645:                layerBuilder.addProcessingEventListener(slaveToolsListener);
646:                layerBuilder.setInputLocation(new File(prevLevelDirectory, name
647:                        + ".shp"));
648:                layerBuilder.setOutputLocation(currLevelDirectory);
649:                layerBuilder.setScaleAlgorithm(scaleAlgorithm);
650:                layerBuilder.setScaleFactor(scaleFactor);
651:                layerBuilder.setTileH(tileH);
652:                layerBuilder.setTileW(tileW);
653:                layerBuilder.run();
654:                layerBuilder.removeAllProcessingEventListeners();
655:            }
656:
657:            private double[] mosaicLevel(int level) {
658:                MosaicIndexBuilder builder = new MosaicIndexBuilder();
659:                builder.addProcessingEventListener(slaveToolsListener);
660:                builder.setLocationPath(new File(outputLocation, String
661:                        .valueOf(level)).getAbsolutePath());
662:                builder.setIndexName(name);
663:                builder.run();
664:                builder.removeAllProcessingEventListeners();
665:                return new double[] { builder.getResolutionX(),
666:                        builder.getResolutionY() };
667:            }
668:
669:            /**
670:             * @param envelope
671:             * @param doneSomething
672:             */
673:            private void createPropertiesFiles() {
674:                // envelope
675:                final Properties properties = new Properties();
676:                properties.setProperty("Envelope2D", new StringBuffer(Double
677:                        .toString(envelope.getMinimum(0))).append(",").append(
678:                        Double.toString(envelope.getMinimum(1))).append(" ")
679:                        .append(Double.toString(envelope.getMaximum(0)))
680:                        .append(",").append(
681:                                Double.toString(envelope.getMaximum(1)))
682:                        .toString());
683:                properties.setProperty("LevelsNum", Integer
684:                        .toString(numSteps + 1));
685:                final StringBuffer levels = new StringBuffer();
686:                final StringBuffer levelDirs = new StringBuffer();
687:                for (int i = 0; i < numSteps + 1; i++) {
688:                    levels.append(Double.toString(resolutions[0][i])).append(
689:                            ",").append(Double.toString(resolutions[1][i]));
690:                    levelDirs.append(i == 0 ? "0" : Integer.toString((int) Math
691:                            .pow(scaleFactor, i)));
692:                    if (i < numSteps) {
693:                        levels.append(" ");
694:                        levelDirs.append(" ");
695:                    }
696:                }
697:                properties.setProperty("Levels", levels.toString());
698:                properties.setProperty("LevelsDirs", levelDirs.toString());
699:                properties.setProperty("Name", name);
700:                try {
701:                    properties.store(new BufferedOutputStream(
702:                            new FileOutputStream(new File(outputLocation, name
703:                                    + ".properties"))), "");
704:
705:                    // //
706:                    // Creating PRJ file
707:                    // //
708:                    File prjFile = new File(outputLocation, name + ".prj");
709:                    BufferedWriter out = new BufferedWriter(new FileWriter(
710:                            prjFile));
711:                    out.write(envelope.getCoordinateReferenceSystem().toWKT());
712:                    out.close();
713:                } catch (FileNotFoundException e) {
714:                    fireException(e);
715:                } catch (IOException e) {
716:                    fireException(e);
717:                }
718:            }
719:
720:            public void getNotification(ProcessingEvent event) {
721:                LOGGER.info(new StringBuffer("Progress is at ").append(
722:                        event.getPercentage()).append("\n").append(
723:                        "attached message is: ").append(event.getMessage())
724:                        .toString());
725:            }
726:
727:            public void exceptionOccurred(ExceptionEvent event) {
728:                LOGGER.log(Level.SEVERE, "An error occurred during processing",
729:                        event.getException());
730:            }
731:
732:            private boolean parseArgs(String[] args) {
733:                cmdLine = cmdParser.parseAndHelp(args);
734:                if (cmdLine != null && cmdLine.hasOption(versionOpt)) {
735:                    LOGGER
736:                            .fine(new StringBuffer(
737:                                    "OverviewsEmbedder - GeoSolutions S.a.s (C) 2006 - v")
738:                                    .append(PyramidBuilder.versionNumber)
739:                                    .toString());
740:                    System.exit(1);
741:
742:                } else if (cmdLine != null) {
743:                    // ////////////////////////////////////////////////////////////////
744:                    //
745:                    // parsing command line parameters and setting up
746:                    // Pyramid Builder options
747:                    //
748:                    // ////////////////////////////////////////////////////////////////
749:                    inputLocation = new File((String) cmdLine
750:                            .getValue(locationOpt));
751:
752:                    // output files' directory
753:                    if (cmdLine.hasOption(outputLocationOpt))
754:                        outputLocation = new File((String) cmdLine
755:                                .getValue(outputLocationOpt));
756:                    else
757:                        outputLocation = new File(
758:                                inputLocation.getParentFile(), "pyramid");
759:
760:                    // output file name
761:                    if (cmdLine.hasOption(nameOpt))
762:                        name = (String) cmdLine.getValue(nameOpt);
763:                    else
764:                        name = "pyramid";
765:
766:                    // shall we overwrite the output dirs?
767:                    overwriteOutputDirs = cmdLine.hasOption(overwriteOpt);
768:
769:                    // tile dim
770:                    if (cmdLine.hasOption(tileDimOpt)) {
771:                        final String tileDim = (String) cmdLine
772:                                .getValue(tileDimOpt);
773:                        final String[] pairs = tileDim.split(",");
774:                        tileW = Integer.parseInt(pairs[0]);
775:                        tileH = Integer.parseInt(pairs[1]);
776:                    }
777:                    // //
778:                    //
779:                    // scale factor
780:                    //
781:                    // //
782:                    final String scaleF = (String) cmdLine
783:                            .getValue(scaleFactorOpt);
784:                    scaleFactor = Integer.parseInt(scaleF);
785:
786:                    // //
787:                    //
788:                    // scaling algorithm (default to nearest neighbour)
789:                    //
790:                    // //
791:                    scaleAlgorithm = (String) cmdLine
792:                            .getValue(scaleAlgorithmOpt);
793:                    if (scaleAlgorithm == null)
794:                        scaleAlgorithm = "nn";
795:
796:                    // //
797:                    //
798:                    // number of steps
799:                    //
800:                    // //
801:                    numSteps = Integer.parseInt((String) cmdLine
802:                            .getValue(numStepsOpt));
803:
804:                    // //
805:                    //
806:                    // Thread priority
807:                    //
808:                    // //
809:                    // index name
810:                    if (cmdLine.hasOption(priorityOpt))
811:                        priority = Integer.parseInt((String) cmdLine
812:                                .getValue(priorityOpt));
813:
814:                    // //
815:                    //
816:                    // Tile cache size
817:                    //
818:                    // //
819:                    // index name
820:                    if (cmdLine.hasOption(tileCacheSizeOpt)) {
821:                        tileCacheSize = Integer.parseInt((String) cmdLine
822:                                .getValue(tileCacheSizeOpt));
823:
824:                    }
825:                    return true;
826:
827:                }
828:                return false;
829:
830:            }
831:
832:            /**
833:             * This tool is designed to be used by the command line using this main
834:             * class but it can also be used from an GUI by using the setters and
835:             * getters.
836:             * 
837:             * @param args
838:             * @throws IOException
839:             * @throws IllegalArgumentException
840:             * @throws InterruptedException
841:             */
842:            public static void main(String[] args)
843:                    throws IllegalArgumentException, IOException,
844:                    InterruptedException {
845:
846:                // creating an overviews embedder
847:                final PyramidBuilder builder = new PyramidBuilder();
848:                // adding the embedder itself as a listener
849:                builder.addProcessingEventListener(builder);
850:                // parsing input arguments
851:                if (builder.parseArgs(args)) {
852:                    // creating a thread to execute the request process, with the
853:                    // provided priority
854:                    final Thread t = new Thread(builder, "PyramidBuilder");
855:                    t.setPriority(builder.priority);
856:                    t.start();
857:                    try {
858:                        t.join();
859:                    } catch (InterruptedException e) {
860:                        LOGGER.log(Level.SEVERE, e.getLocalizedMessage(), e);
861:                    }
862:
863:                } else if (LOGGER.isLoggable(Level.FINE))
864:                    LOGGER
865:                            .fine("Unable to parse command line arguments, exiting...");
866:
867:            }
868:        }
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.