/* * The Unified Mapping Platform (JUMP) is an extensible, interactive GUI for * visualizing and manipulating spatial features with geometry and attributes. * * Copyright (C) 2003 Vivid Solutions * * This program is free software; you can redistribute it and/or modify it under * the terms of the GNU General Public License as published by the Free Software * Foundation; either version 2 of the License, or (at your option) any later * version. * * This program is distributed in the hope that it will be useful, but WITHOUT * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS * FOR A PARTICULAR PURPOSE. See the GNU General Public License for more * details. * * You should have received a copy of the GNU General Public License along with * this program; if not, write to the Free Software Foundation, Inc., 59 Temple * Place - Suite 330, Boston, MA 02111-1307, USA. * * For more information, contact: * * Vivid Solutions Suite #1A 2328 Government Street Victoria BC V8T 5G5 Canada * * (250)385-6040 www.vividsolutions.com */ package com.vividsolutions.jump.workbench.ui.plugin; import java.io.File; import java.io.FileReader; import java.util.ArrayList; import java.util.Collections; import java.util.Iterator; import java.util.Vector; import java.io.FileNotFoundException; import javax.swing.JFileChooser; import javax.swing.filechooser.FileFilter; import java.util.Map; import javax.swing.JOptionPane; import com.vividsolutions.jump.I18N; import com.vividsolutions.jump.coordsys.CoordinateSystemRegistry; import com.vividsolutions.jump.feature.FeatureCollection; import com.vividsolutions.jump.io.datasource.Connection; import com.vividsolutions.jump.io.datasource.DataSource; import com.vividsolutions.jump.task.TaskMonitor; import com.vividsolutions.jump.util.Blackboard; import com.vividsolutions.jump.util.java2xml.XML2Java; import com.vividsolutions.jump.workbench.WorkbenchContext; import com.vividsolutions.jump.workbench.model.Category; import com.vividsolutions.jump.workbench.model.Layer; import com.vividsolutions.jump.workbench.model.LayerManager; import com.vividsolutions.jump.workbench.model.Layerable; import com.vividsolutions.jump.workbench.model.Task; import com.vividsolutions.jump.workbench.model.UndoableEditReceiver; import com.vividsolutions.jump.workbench.plugin.PlugInContext; import com.vividsolutions.jump.workbench.plugin.ThreadedBasePlugIn; import com.vividsolutions.jump.workbench.ui.GUIUtil; import com.vividsolutions.jump.workbench.ui.WorkbenchFrame; /** * @deprecated replaced by org.openjump.core.ui.plugin.file.OpenProjectPlugIn */ public class OpenProjectPlugIn extends ThreadedBasePlugIn { private final static String RECENT_MENU_LIST_KEY = OpenProjectPlugIn.class.getName() + " - RECENT_MENU_LIST"; //LDB: probably shouldn't internationalize keys public final static int RECENT_MENU_LIST_MAX = 8; private JFileChooser fileChooser; private Task newTask; private Task sourceTask; public OpenProjectPlugIn() { } public String getName() { return I18N.get("ui.plugin.OpenProjectPlugIn.open-project"); } public void initialize(PlugInContext context) throws Exception { } private void initFileChooser() { if (fileChooser != null) return; //Don't initialize fileChooser in field declaration -- seems too early // because //we sometimes get a WindowsFileChooserUI NullPointerException [Jon // Aquino 12/10/2003] fileChooser = GUIUtil.createJFileChooserWithExistenceChecking(); fileChooser.setDialogTitle(I18N.get("ui.plugin.OpenProjectPlugIn.open-project")); fileChooser.setDialogType(JFileChooser.OPEN_DIALOG); fileChooser.setFileSelectionMode(JFileChooser.FILES_ONLY); fileChooser.setMultiSelectionEnabled(false); GUIUtil.removeChoosableFileFilters(fileChooser); fileChooser .addChoosableFileFilter(SaveProjectAsPlugIn.JUMP_PROJECT_FILE_FILTER); fileChooser.addChoosableFileFilter(GUIUtil.ALL_FILES_FILTER); fileChooser.setFileFilter(SaveProjectAsPlugIn.JUMP_PROJECT_FILE_FILTER); } public boolean execute(PlugInContext context) throws Exception { initFileChooser(); reportNothingToUndoYet(context); if (JFileChooser.APPROVE_OPTION != fileChooser.showOpenDialog(context .getWorkbenchFrame())) { return false; } open(fileChooser.getSelectedFile(), context.getWorkbenchFrame()); return true; } public void run(TaskMonitor monitor, PlugInContext context) throws Exception { loadLayers(context, sourceTask.getLayerManager(), newTask.getLayerManager(), CoordinateSystemRegistry.instance(context.getWorkbenchContext() .getBlackboard()), monitor); } public void open(File file, WorkbenchFrame workbenchFrame) throws Exception { FileReader reader = new FileReader(file); try { sourceTask = (Task) new XML2Java(workbenchFrame.getContext() .getWorkbench().getPlugInManager().getClassLoader()).read( reader, Task.class); //I can't remember why I'm creating a new Task instead of using //sourceTask. There must be a good reason. [Jon Aquino] // Probably to reverse the order of the layerables. See comments. // Probably also to set the LayerManager coordinate system. // [Jon Aquino 2005-03-16] initializeDataSources(sourceTask, workbenchFrame.getContext()); newTask = new Task(); newTask.setName(GUIUtil.nameWithoutExtension(file)); newTask.setProjectFile(file); newTask.setProperties(sourceTask.getProperties()); workbenchFrame.addTaskFrame(newTask); } finally { reader.close(); putRecentList(workbenchFrame.getContext(), file.getAbsolutePath()); //ArrayList recentList = getRecentList(blackboard); //retrieve list of recent tasks } } public static ArrayList getRecentList(WorkbenchContext context) { Blackboard blackboard = PersistentBlackboardPlugIn.get(context); if (blackboard.get(RECENT_MENU_LIST_KEY) == null) { blackboard.put(RECENT_MENU_LIST_KEY, new ArrayList(RECENT_MENU_LIST_MAX)); } ArrayList list = (ArrayList) blackboard.get(RECENT_MENU_LIST_KEY); return list; } public static void putRecentList(WorkbenchContext context, String path) { Blackboard blackboard = PersistentBlackboardPlugIn.get(context); if (blackboard.get(RECENT_MENU_LIST_KEY) == null) { blackboard.put(RECENT_MENU_LIST_KEY, new ArrayList(RECENT_MENU_LIST_MAX)); } ArrayList list = (ArrayList) blackboard.get(RECENT_MENU_LIST_KEY); if (list.contains(path)) return; if (list.size() >= RECENT_MENU_LIST_MAX){ list.remove(list.size()-1); //remove last element } list.add(0,path); //push rest of list down } private void initializeDataSources(Task task, WorkbenchContext context) { for (Iterator i = task.getLayerManager().getLayers().iterator(); i .hasNext();) { Layer layer = (Layer) i.next(); if (layer.getDataSourceQuery().getDataSource() instanceof WorkbenchContextReference) { ((WorkbenchContextReference) layer.getDataSourceQuery() .getDataSource()).setWorkbenchContext(context); } } } private void loadLayers(PlugInContext context, LayerManager sourceLayerManager, LayerManager newLayerManager, CoordinateSystemRegistry registry, TaskMonitor monitor) throws Exception { FindFile findFile = new FindFile(context); boolean displayDialog = true; for (Iterator i = sourceLayerManager.getCategories().iterator(); i .hasNext();) { Category sourceLayerCategory = (Category) i.next(); // Explicitly add categories. Can't rely on // LayerManager#addLayerable to add the categories, because a // category might not have any layers. [Jon Aquino] newLayerManager.addCategory(sourceLayerCategory.getName()); // LayerManager#addLayerable adds layerables to the top. So reverse // the order. [Jon Aquino] ArrayList layerables = new ArrayList(sourceLayerCategory .getLayerables()); Collections.reverse(layerables); for (Iterator j = layerables.iterator(); j.hasNext();) { Layerable layerable = (Layerable) j.next(); if ( monitor != null ){ monitor.report(I18N.get("ui.plugin.OpenProjectPlugIn.loading") + " " + layerable.getName()); } layerable.setLayerManager(newLayerManager); if (layerable instanceof Layer) { Layer layer = (Layer) layerable; try { load(layer, registry, monitor); } catch (FileNotFoundException ex) { if (displayDialog) { displayDialog = false; int response = JOptionPane.showConfirmDialog(context.getWorkbenchFrame(), I18N.get("ui.plugin.OpenProjectPlugIn.At-least-one-file-in-the-task-could-not-be-found") + "\n" + I18N.get("ui.plugin.OpenProjectPlugIn.Do-you-want-to-locate-it-and-continue-loading-the-task"), "JUMP", JOptionPane.YES_NO_OPTION); if (response != JOptionPane.YES_OPTION) { break; } } String fname = layer.getDataSourceQuery().getDataSource().getProperties().get("File").toString(); String filename = findFile.getFileName(fname); if (filename.length() > 0) { //set the new source for this layer Map properties = layer.getDataSourceQuery().getDataSource().getProperties(); properties.put(DataSource.FILE_KEY, filename); layer.getDataSourceQuery().getDataSource().setProperties(properties); load(layer, registry, monitor); } else { break; } } } newLayerManager.addLayerable(sourceLayerCategory.getName(), layerable); } } } public static void load(Layer layer, CoordinateSystemRegistry registry, TaskMonitor monitor) throws Exception { layer.setFeatureCollection(executeQuery(layer .getDataSourceQuery().getQuery(), layer .getDataSourceQuery().getDataSource(), registry, monitor)); layer.setFeatureCollectionModified(false); } private static FeatureCollection executeQuery(String query, DataSource dataSource, CoordinateSystemRegistry registry, TaskMonitor monitor) throws Exception { Connection connection = dataSource.getConnection(); try { return dataSource.installCoordinateSystem(connection.executeQuery( query, monitor), registry); } finally { connection.close(); } } public class FindFile { private Vector prefixList = new Vector(5, 5); private JFileChooser fileChooser; private PlugInContext context; public FindFile(PlugInContext context) { this.context = context; fileChooser = new JFileChooser(); fileChooser = GUIUtil.createJFileChooserWithExistenceChecking(); fileChooser.setDialogTitle("Choose current location of: "); fileChooser.setDialogType(JFileChooser.OPEN_DIALOG); fileChooser.setFileSelectionMode(JFileChooser.FILES_ONLY); fileChooser.setMultiSelectionEnabled(false); } public FindFile(PlugInContext context, JFileChooser fileChooser) { this(context); this.fileChooser = fileChooser; } public String getFileName(String filenamepath) throws Exception { //strip off file name File oldFile = new File(filenamepath); String oldPath = oldFile.getPath(); //see if something in the prefixList matches all or part of oldPath for (Iterator i = prefixList.iterator(); i.hasNext();) { PathPrefixes prefix = (PathPrefixes) i.next(); if (oldPath.toLowerCase().indexOf(prefix.getOldPrefix().toLowerCase()) > -1) //found match { //replace matching portion with new prefix String newFileNamePath = filenamepath.substring(prefix.getOldPrefix().length()); newFileNamePath = prefix.getNewPrefix() + newFileNamePath; File newFile = new File(newFileNamePath); if (newFile.exists()) return newFileNamePath; //else continue to look through list } } //at this point didn't find a match //ask user to find file fileChooser.setDialogTitle("Choose current location of: " + filenamepath); GUIUtil.removeChoosableFileFilters(fileChooser); fileChooser.addChoosableFileFilter(GUIUtil.ALL_FILES_FILTER); String ext = ""; int k = filenamepath.lastIndexOf('.'); if ((k > 0) && (k < (filenamepath.length() - 1))) { ext = filenamepath.substring(k + 1); FileFilter fileFilter = GUIUtil.createFileFilter(ext.toUpperCase() + " Files", new String[]{ext.toLowerCase()}); fileChooser.addChoosableFileFilter(fileFilter); fileChooser.setFileFilter(fileFilter); } if (JFileChooser.APPROVE_OPTION == fileChooser.showOpenDialog(context.getWorkbenchFrame())) { String newParent = fileChooser.getSelectedFile().getParent() + File.separator; String oldParent = new File(filenamepath).getParent() + File.separator; //find where they differ int i = newParent.length(); int j = oldParent.length(); while (newParent.substring(i).equalsIgnoreCase(oldParent.substring(j))) { i--; j--; } while (newParent.charAt(i) != File.separatorChar) { i++; } while (oldParent.charAt(j) != File.separatorChar) { j++; } String newPrefix = newParent.substring(0, ++i); String oldPrefix = oldParent.substring(0, ++j); PathPrefixes pathPrefix = new PathPrefixes(oldPrefix, newPrefix); prefixList.add(pathPrefix); return fileChooser.getSelectedFile().getPath(); } return ""; //user canceled find file } } public class PathPrefixes { private String oldPrefix = ""; private String newPrefix = ""; public PathPrefixes(String oldPrefix, String newPrefix) { this.oldPrefix = oldPrefix; this.newPrefix = newPrefix; } public String getOldPrefix() { return oldPrefix; } public String getNewPrefix() { return newPrefix; } } }