Revision: 18184
          http://sourceforge.net/p/gate/code/18184
Author:   markagreenwood
Date:     2014-07-15 18:42:12 +0000 (Tue, 15 Jul 2014)
Log Message:
-----------
the new document export support and updated the fast infoset plugin to match

Modified Paths:
--------------
    
gate/trunk/plugins/Format_FastInfoset/src/gate/corpora/FastInfosetDocumentFormat.java
    
gate/trunk/plugins/Format_FastInfoset/src/gate/corpora/FastInfosetExporter.java
    gate/trunk/src/main/gate/DocumentFormat.java
    gate/trunk/src/main/gate/gui/NameBearerHandle.java

Added Paths:
-----------
    gate/trunk/src/main/gate/DocumentExporter.java
    gate/trunk/src/main/gate/gui/DocumentExportDialog.java

Modified: 
gate/trunk/plugins/Format_FastInfoset/src/gate/corpora/FastInfosetDocumentFormat.java
===================================================================
--- 
gate/trunk/plugins/Format_FastInfoset/src/gate/corpora/FastInfosetDocumentFormat.java
       2014-07-15 15:38:32 UTC (rev 18183)
+++ 
gate/trunk/plugins/Format_FastInfoset/src/gate/corpora/FastInfosetDocumentFormat.java
       2014-07-15 18:42:12 UTC (rev 18184)
@@ -29,10 +29,8 @@
 import java.io.IOException;
 import java.io.InputStream;
 import java.io.InputStreamReader;
-import java.io.OutputStream;
 import java.io.Reader;
 import java.io.StringReader;
-import java.util.Map;
 
 import javax.xml.stream.XMLStreamException;
 import javax.xml.stream.XMLStreamReader;
@@ -45,7 +43,7 @@
 import com.sun.xml.fastinfoset.stax.StAXDocumentParser;
 import com.sun.xml.fastinfoset.stax.StAXManager;
 
-@CreoleResource(name = "Fast Infoset Document Format", isPrivate = true, 
autoinstances = {@AutoInstance(hidden = true)}, comment = "Format parser for 
GATE XML stored in the binary FastInfoset format", helpURL = 
"http://gate.ac.uk/userguide/sec:creole:fastinfoset";)
+@CreoleResource(name = "Fast Infoset Document Format", isPrivate = true, 
autoinstances = {@AutoInstance(hidden = true)}, comment = "Format parser for 
GATE XML stored in the binary Fast Infoset format", helpURL = 
"http://gate.ac.uk/userguide/sec:creole:fastinfoset";)
 public class FastInfosetDocumentFormat extends TextualDocumentFormat {
 
   private static final long serialVersionUID = -2394353168913311584L;
@@ -55,7 +53,6 @@
   /** Default construction */
   public FastInfosetDocumentFormat() {
     super();
-    supportsExport = true;
   }
 
   /** We could collect repositioning information during XML parsing */
@@ -334,14 +331,4 @@
 
     return this;
   }
-
-  @Override
-  public void export(Document doc, OutputStream out, Map<String,Object> 
options) throws IOException {
-   try {
-     FastInfosetExporter.export(doc, out); 
-   }
-   catch (Exception e) {
-     throw new IOException("Error exporting document",e);
-   }
-  }
 }

Modified: 
gate/trunk/plugins/Format_FastInfoset/src/gate/corpora/FastInfosetExporter.java
===================================================================
--- 
gate/trunk/plugins/Format_FastInfoset/src/gate/corpora/FastInfosetExporter.java 
    2014-07-15 15:38:32 UTC (rev 18183)
+++ 
gate/trunk/plugins/Format_FastInfoset/src/gate/corpora/FastInfosetExporter.java 
    2014-07-15 18:42:12 UTC (rev 18184)
@@ -14,45 +14,49 @@
 
 package gate.corpora;
 
-import gate.Corpus;
 import gate.Document;
+import gate.DocumentExporter;
 import gate.Factory;
+import gate.FeatureMap;
 import gate.Gate;
 import gate.creole.metadata.AutoInstance;
+import gate.creole.metadata.CreoleParameter;
 import gate.creole.metadata.CreoleResource;
-import gate.gui.MainFrame;
-import gate.gui.NameBearerHandle;
+import gate.creole.metadata.RunTime;
 import gate.gui.ResourceHelper;
-import gate.swing.XJFileChooser;
-import gate.util.Err;
-import gate.util.ExtensionFileFilter;
-import gate.util.Files;
-import gate.util.InvalidOffsetException;
 
-import java.awt.event.ActionEvent;
 import java.io.File;
-import java.io.FileOutputStream;
+import java.io.IOException;
 import java.io.OutputStream;
-import java.net.URISyntaxException;
 import java.net.URL;
-import java.util.ArrayList;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Set;
 
-import javax.swing.AbstractAction;
-import javax.swing.Action;
-import javax.swing.JFileChooser;
-import javax.swing.JOptionPane;
+import javax.xml.stream.XMLStreamException;
 
 import com.sun.xml.fastinfoset.stax.StAXDocumentSerializer;
 
 @SuppressWarnings("serial")
-@CreoleResource(name = "Fast Infoset Exporter", tool = true, autoinstances = 
@AutoInstance, comment = "Export GATE documents to GATE XML stored in the 
binary FastInfoset format", helpURL = 
"http://gate.ac.uk/userguide/sec:creole:fastinfoset";)
-public class FastInfosetExporter extends ResourceHelper {
+@CreoleResource(name = "Fast Infoset Exporter", tool = true, autoinstances = 
@AutoInstance, comment = "Export GATE documents to GATE XML stored in the 
binary Fast Infoset format", helpURL = 
"http://gate.ac.uk/userguide/sec:creole:fastinfoset";)
+public class FastInfosetExporter extends DocumentExporter {
 
-  @Override
+  public FastInfosetExporter() {
+    super("Fast Infoset","finf");
+  }
+  
+  
+  private URL test;  
+ 
+  @RunTime
+  @CreoleParameter
+  public void setTestParam(URL test) {
+    this.test = test;
+  }
+  
+  public URL getTestParam() {
+    return test;
+  }
+  
+  
+  /*
   protected List<Action> buildActions(final NameBearerHandle handle) {
     List<Action> actions = new ArrayList<Action>();
 
@@ -68,8 +72,8 @@
             public void run() {
               XJFileChooser fileChooser = MainFrame.getFileChooser();
               ExtensionFileFilter filter =
-                  new ExtensionFileFilter("Fast Infoset XML Files (*.finf)",
-                      "finf");
+                new ExtensionFileFilter("Fast Infoset XML Files (*.finf)",
+                  "finf");
               fileChooser.addChoosableFileFilter(filter);
               fileChooser.setMultiSelectionEnabled(false);
               fileChooser.setFileSelectionMode(JFileChooser.FILES_ONLY);
@@ -85,19 +89,19 @@
                 }
                 if(fileName.equals("") || fileName.equals("/")) {
                   if(doc.getNamedAnnotationSets().containsKey(
-                      "Original markups")
-                      && !doc.getAnnotations("Original markups").get("title")
-                          .isEmpty()) {
+                    "Original markups") &&
+                    !doc.getAnnotations("Original markups").get("title")
+                      .isEmpty()) {
                     // use the title annotation if any
                     try {
                       fileName =
-                          doc.getContent()
-                              .getContent(
-                                  doc.getAnnotations("Original markups")
-                                      .get("title").firstNode().getOffset(),
-                                  doc.getAnnotations("Original markups")
-                                      .get("title").lastNode().getOffset())
-                              .toString();
+                        doc
+                          .getContent()
+                          .getContent(
+                            doc.getAnnotations("Original markups").get("title")
+                              .firstNode().getOffset(),
+                            doc.getAnnotations("Original markups").get("title")
+                              .lastNode().getOffset()).toString();
                     } catch(InvalidOffsetException e) {
                       e.printStackTrace();
                     }
@@ -128,8 +132,8 @@
               File selectedFile = fileChooser.getSelectedFile();
               if(selectedFile == null) return;
               long start = System.currentTimeMillis();
-              handle.statusChanged("Saving as Fast Infoset XML to "
-                  + selectedFile.toString() + "...");
+              handle.statusChanged("Saving as Fast Infoset XML to " +
+                selectedFile.toString() + "...");
               try {
                 MainFrame.lockGUI("Exporting...");
 
@@ -137,17 +141,17 @@
               } catch(Exception ex) {
                 MainFrame.unlockGUI();
                 JOptionPane.showMessageDialog(MainFrame.getInstance(),
-                    "Could not create write file:" + ex.toString(), "GATE",
-                    JOptionPane.ERROR_MESSAGE);
+                  "Could not create write file:" + ex.toString(), "GATE",
+                  JOptionPane.ERROR_MESSAGE);
                 ex.printStackTrace(Err.getPrintWriter());
                 return;
               } finally {
                 MainFrame.unlockGUI();
               }
               long time = System.currentTimeMillis() - start;
-              handle.statusChanged("Finished saving as Fast Infoset XML into "
-                  + " the file: " + selectedFile.toString() + " in "
-                  + ((double)time) / 1000 + " s");
+              handle.statusChanged("Finished saving as Fast Infoset XML into " 
+
+                " the file: " + selectedFile.toString() + " in " +
+                ((double)time) / 1000 + " s");
             }
           };
           Thread thread = new Thread(runableAction, "Fast Infoset Exporter");
@@ -169,7 +173,7 @@
                 // we need a directory
                 XJFileChooser fileChooser = MainFrame.getFileChooser();
                 fileChooser
-                    .setDialogTitle("Select the directory that will contain 
the corpus");
+                  .setDialogTitle("Select the directory that will contain the 
corpus");
                 
fileChooser.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);
 
                 if(fileChooser.showDialog(MainFrame.getInstance(), "Select") 
!= JFileChooser.APPROVE_OPTION)
@@ -180,8 +184,8 @@
                 if(!dir.exists()) {
                   if(!dir.mkdirs()) {
                     JOptionPane.showMessageDialog(MainFrame.getInstance(),
-                        "Could not create top directory!", "GATE",
-                        JOptionPane.ERROR_MESSAGE);
+                      "Could not create top directory!", "GATE",
+                      JOptionPane.ERROR_MESSAGE);
                     return;
                   }
                 }
@@ -198,7 +202,7 @@
                 Set<String> usedFileNames = new HashSet<String>();
                 while(docIter.hasNext()) {
                   boolean docWasLoaded =
-                      corpus.isDocumentLoaded(currentDocIndex);
+                    corpus.isDocumentLoaded(currentDocIndex);
                   Document currentDoc = docIter.next();
                   URL sourceURL = currentDoc.getSourceUrl();
                   String fileName = null;
@@ -234,15 +238,14 @@
                     if(docFile.exists() && !overwriteAll) {
                       // ask the user if we can overwrite the file
                       Object[] options =
-                          new Object[]{"Yes", "All", "No", "Cancel"};
+                        new Object[]{"Yes", "All", "No", "Cancel"};
                       MainFrame.unlockGUI();
                       int answer =
-                          JOptionPane.showOptionDialog(MainFrame.getInstance(),
-                              "File " + docFile.getName()
-                                  + " already exists!\n" + "Overwrite?",
-                              "GATE", JOptionPane.DEFAULT_OPTION,
-                              JOptionPane.WARNING_MESSAGE, null, options,
-                              options[2]);
+                        JOptionPane.showOptionDialog(MainFrame.getInstance(),
+                          "File " + docFile.getName() + " already exists!\n" +
+                            "Overwrite?", "GATE", JOptionPane.DEFAULT_OPTION,
+                          JOptionPane.WARNING_MESSAGE, null, options,
+                          options[2]);
                       MainFrame.lockGUI("Saving...");
                       switch(answer){
                         case 0: {
@@ -259,11 +262,11 @@
                           // alternative name;
                           MainFrame.unlockGUI();
                           fileName =
-                              (String)JOptionPane.showInputDialog(
-                                  MainFrame.getInstance(),
-                                  "Please provide an alternative file name",
-                                  "GATE", JOptionPane.QUESTION_MESSAGE, null,
-                                  null, fileName);
+                            (String)JOptionPane.showInputDialog(
+                              MainFrame.getInstance(),
+                              "Please provide an alternative file name",
+                              "GATE", JOptionPane.QUESTION_MESSAGE, null, null,
+                              fileName);
                           if(fileName == null) {
                             handle.processFinished();
                             return;
@@ -289,8 +292,8 @@
                   } catch(Exception ioe) {
                     MainFrame.unlockGUI();
                     JOptionPane.showMessageDialog(MainFrame.getInstance(),
-                        "Could not create write file:" + ioe.toString(),
-                        "GATE", JOptionPane.ERROR_MESSAGE);
+                      "Could not create write file:" + ioe.toString(), "GATE",
+                      JOptionPane.ERROR_MESSAGE);
                     ioe.printStackTrace(Err.getPrintWriter());
                     return;
                   }
@@ -313,8 +316,8 @@
             }
           };
           Thread thread =
-              new Thread(Thread.currentThread().getThreadGroup(), runnable,
-                  "Corpus Fast Infoset XML dumper");
+            new Thread(Thread.currentThread().getThreadGroup(), runnable,
+              "Corpus Fast Infoset XML dumper");
           thread.setPriority(Thread.MIN_PRIORITY);
           thread.start();
 
@@ -324,37 +327,22 @@
     }
 
     return actions;
-  }
+  }*/
 
-  /**
-   * A static utility method that exports the specified GATE document to a Fast
-   * Infoset file.
-   * 
-   * @param doc
-   *          the {@link gate.Document} instance to export
-   * @param file
-   *          the {@link java.io.File}
-   * @throws Exception
-   */
-  public static void export(Document doc, File file) throws Exception {
-    FileOutputStream out = null;
-    try {
-      out = new FileOutputStream(file);
-      export(doc, out);
-    } finally {
-      out.close();
-    }
-  }
+  public void export(Document doc, OutputStream out, FeatureMap options)
+    throws IOException {
 
-  public static void export(Document doc, OutputStream out) throws Exception {
-
     StAXDocumentSerializer xsw = new StAXDocumentSerializer(out);
 
-    xsw.writeStartDocument("1.0");
-    DocumentStaxUtils.writeDocument(doc, xsw, "");
-    xsw.writeEndDocument();
-    xsw.flush();
-    xsw.close();
+    try {
+      xsw.writeStartDocument("1.0");
+      DocumentStaxUtils.writeDocument(doc, xsw, "");
+      xsw.writeEndDocument();
+      xsw.flush();
+      xsw.close();
+    } catch(XMLStreamException e) {
+      throw new IOException(e);
+    }
   }
 
   public static void main(String args[]) throws Exception {
@@ -362,18 +350,17 @@
     // the Resource Helper)
     Gate.init();
     Gate.getCreoleRegister().registerDirectories(
-        (new File(Gate.getGateHome(), "plugins/Format_FastInfoset")).toURI()
-            .toURL());
+      (new File(Gate.getGateHome(), "plugins/Format_FastInfoset")).toURI()
+        .toURL());
 
     // get the auto created instance of the Resource Helper
     ResourceHelper rh =
-        (ResourceHelper)Gate.getCreoleRegister()
-            .getAllInstances("gate.corpora.FastInfosetExporter").iterator()
-            .next();
+      (ResourceHelper)Gate.getCreoleRegister()
+        .getAllInstances("gate.corpora.FastInfosetExporter").iterator().next();
 
     // create a simple test document
     Document doc =
-        Factory.newDocument("A test of the Resource Handler API access");
+      Factory.newDocument("A test of the Resource Handler API access");
 
     // use the Resource Helper to export the document
     rh.call("export", doc, new File("resource-handler-test.finf"));

Added: gate/trunk/src/main/gate/DocumentExporter.java
===================================================================
--- gate/trunk/src/main/gate/DocumentExporter.java                              
(rev 0)
+++ gate/trunk/src/main/gate/DocumentExporter.java      2014-07-15 18:42:12 UTC 
(rev 18184)
@@ -0,0 +1,81 @@
+package gate;
+
+import gate.creole.AbstractResource;
+import gate.util.ExtensionFileFilter;
+
+import java.io.File;
+import java.io.FileOutputStream;
+import java.io.IOException;
+import java.io.OutputStream;
+import java.util.Map;
+
+import javax.swing.filechooser.FileFilter;
+
+import org.apache.commons.io.IOUtils;
+
+public abstract class DocumentExporter extends AbstractResource {
+
+  private static final long serialVersionUID = -4810523902750051704L;
+
+  protected String fileType, defaultExtension;
+  protected FileFilter filter;
+  
+  public DocumentExporter(String fileType, String defaultExtension) {
+    this.fileType = fileType;
+    this.defaultExtension = defaultExtension;
+    filter = new ExtensionFileFilter(fileType+" Files 
(*."+defaultExtension+")",defaultExtension);    
+  }
+  
+  public String getFileType() {
+    return fileType;
+  }
+  
+  public String getDefaultExtension() {
+    return defaultExtension;
+  }
+  
+  public FileFilter getFileFilter() {
+    return filter;
+  }
+    
+  /**
+   * Equivalent to {@link #export(Document,File, Map)} with an empty map
+   * of options.
+   */
+  public void export(Document doc, File file) throws IOException {
+    export(doc, file, Factory.newFeatureMap());
+  }
+
+  /**
+   * Equivalent to {@link #export(Document,OutputStream, Map)} using a
+   * FileOutputStream instance constructed from the File param.
+   */
+  public void export(Document doc, File file, FeatureMap options)
+          throws IOException {
+    FileOutputStream out = null;
+    try {
+      out = new FileOutputStream(file);
+      export(doc, new FileOutputStream(file), options);
+    } finally {
+      IOUtils.closeQuietly(out);
+    }
+  }
+
+  /**
+   * Equivalent to {@link #export(Document,OutputStream)} with an empty
+   * map of options.
+   */
+  public void export(Document doc, OutputStream out) throws IOException {
+    export(doc, out, Factory.newFeatureMap());
+  }
+
+  /**
+   * Exports the provided {@link Document} instance to the specified
+   * {@link OutputStream} using the specified options.
+   * 
+   * @param doc the document to export
+   * @param out the OutputStream to export the document to
+   * @param options DocumentFormat specific export options
+   */
+  public abstract void export(Document doc, OutputStream out, FeatureMap 
options) throws IOException;
+}

Modified: gate/trunk/src/main/gate/DocumentFormat.java
===================================================================
--- gate/trunk/src/main/gate/DocumentFormat.java        2014-07-15 15:38:32 UTC 
(rev 18183)
+++ gate/trunk/src/main/gate/DocumentFormat.java        2014-07-15 18:42:12 UTC 
(rev 18184)
@@ -23,11 +23,8 @@
 import gate.util.BomStrippingInputStreamReader;
 import gate.util.DocumentFormatException;
 
-import java.io.File;
-import java.io.FileOutputStream;
 import java.io.IOException;
 import java.io.InputStream;
-import java.io.OutputStream;
 import java.io.Reader;
 import java.io.UnsupportedEncodingException;
 import java.net.URL;
@@ -107,8 +104,6 @@
 
   /** Flag for enable/disable collecting of repositioning information */
   private Boolean shouldCollectRepositioning = new Boolean(false);
-  
-  protected boolean supportsExport = false;
 
   /** If the document format could collect repositioning information
    *  during the unpack phase this method will return <B>true</B>.
@@ -164,60 +159,6 @@
      doc.setFeatures(fm);
      unpackMarkup(doc);
   }// unpackMarkup();
-  
-  /**
-   * Returns true if this DocumentFormat instance supports exporting
-   * GATE documents, false otherwise.
-   * 
-   * @return true if this DocumentFormat instance supports exporting
-   *         GATE documents, false otherwise.
-   */
-  public boolean isExportSupported() {
-    return supportsExport;
-  }
-  
-  /**
-   * Equivalent to {@link #export(Document,File, Map)} with an
-   * empty map of options.
-   */
-  public void export(Document doc, File file) throws IOException {
-    export(doc,file,new HashMap<String,Object>());
-  }
-  
-  /**
-   * Equivalent to {@link #export(Document,OutputStream, Map)} using a
-   * FileOutputStream instance constructed from the File param.
-   */
-  public void export(Document doc, File file, Map<String,Object> options) 
throws IOException {
-    FileOutputStream out = null;
-    try {
-      out = new FileOutputStream(file);
-      export(doc, new FileOutputStream(file), options);
-    }
-    finally {
-      IOUtils.closeQuietly(out);
-    }
-  }
-  
-  /**
-   * Equivalent to {@link #export(Document,OutputStream)} with an
-   * empty map of options.
-   */
-  public void export(Document doc, OutputStream out) throws IOException {
-    export(doc,out,new HashMap<String,Object>());
-  }
-  
-  /**
-   * Exports the provided {@link Document} instance to the specified
-   * {@link OutputStream} using the specified options.
-   * 
-   * @param doc the document to export
-   * @param out the OutputStream to export the document to
-   * @param options DocumentFormat specific export options
-   */
-  public void export(Document doc, OutputStream out, Map<String, Object> 
options) throws IOException {
-    throw new UnsupportedOperationException("Export Not Supported");
-  }
 
   /**
     * Returns a MimeType having as input a fileSufix.
@@ -623,7 +564,7 @@
                                                                       URL url) 
{
     return getDocumentFormat(aGateDocument, getMimeType(url));
   } // getDocumentFormat(URL)
-
+  
   /** Get the feature set */
   @Override
   public FeatureMap getFeatures() { return features; }

Added: gate/trunk/src/main/gate/gui/DocumentExportDialog.java
===================================================================
--- gate/trunk/src/main/gate/gui/DocumentExportDialog.java                      
        (rev 0)
+++ gate/trunk/src/main/gate/gui/DocumentExportDialog.java      2014-07-15 
18:42:12 UTC (rev 18184)
@@ -0,0 +1,653 @@
+/*
+ *  Copyright (c) 1995-2014, The University of Sheffield. See the file
+ *  COPYRIGHT.txt in the software or at http://gate.ac.uk/gate/COPYRIGHT.txt
+ *
+ *  This file is part of GATE (see http://gate.ac.uk/), and is free
+ *  software, licenced under the GNU Library General Public License,
+ *  Version 2, June 1991 (in the distribution as file licence.html,
+ *  and also available at http://gate.ac.uk/gate/licence.html).
+ *
+ *  Mark A. Greenwood 11/07/2014
+ *
+ */
+
+package gate.gui;
+
+import gate.Corpus;
+import gate.Document;
+import gate.DocumentExporter;
+import gate.Factory;
+import gate.FeatureMap;
+import gate.Gate;
+import gate.Resource;
+import gate.creole.Parameter;
+import gate.creole.ResourceData;
+import gate.event.CreoleEvent;
+import gate.event.CreoleListener;
+import gate.event.StatusListener;
+import gate.swing.XJFileChooser;
+import gate.swing.XJMenu;
+import gate.swing.XJMenuItem;
+import gate.util.Err;
+import gate.util.Files;
+import gate.util.InvalidOffsetException;
+
+import java.awt.Dimension;
+import java.awt.event.ActionEvent;
+import java.awt.event.KeyEvent;
+import java.io.File;
+import java.io.IOException;
+import java.net.URISyntaxException;
+import java.net.URL;
+import java.util.HashSet;
+import java.util.IdentityHashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Set;
+
+import javax.swing.AbstractAction;
+import javax.swing.Action;
+import javax.swing.ActionMap;
+import javax.swing.Box;
+import javax.swing.BoxLayout;
+import javax.swing.InputMap;
+import javax.swing.JButton;
+import javax.swing.JComponent;
+import javax.swing.JDialog;
+import javax.swing.JFileChooser;
+import javax.swing.JLabel;
+import javax.swing.JMenuItem;
+import javax.swing.JOptionPane;
+import javax.swing.JPanel;
+import javax.swing.JScrollPane;
+import javax.swing.JTable;
+import javax.swing.JTextField;
+import javax.swing.KeyStroke;
+import javax.swing.SwingUtilities;
+import javax.swing.table.TableCellEditor;
+
+@SuppressWarnings("serial")
+public class DocumentExportDialog extends JDialog {
+
+  private static DocumentExportDialog dialog = new DocumentExportDialog();
+
+  private DocumentExporter de;
+
+  private JButton okBtn, fileBtn, cancelBtn;
+
+  private JTextField txtFileName;
+
+  private ResourceParametersEditor parametersEditor;
+
+  private boolean isDocument, userCanceled;
+
+  public DocumentExportDialog() {
+    super(MainFrame.getInstance(), "Save As...", true);
+    MainFrame.getGuiRoots().add(this);
+    initGuiComponents();
+    initListeners();
+  }
+
+  protected void initGuiComponents() {
+    this.getContentPane().setLayout(
+            new BoxLayout(this.getContentPane(), BoxLayout.Y_AXIS));
+
+    // name field
+    Box nameBox = Box.createHorizontalBox();
+    nameBox.add(Box.createHorizontalStrut(5));
+    nameBox.add(new JLabel("Save To:"));
+    nameBox.add(Box.createHorizontalStrut(5));
+    txtFileName = new JTextField(30);
+    txtFileName.setMaximumSize(new Dimension(Integer.MAX_VALUE, txtFileName
+            .getPreferredSize().height));
+    txtFileName.setRequestFocusEnabled(true);
+    txtFileName.setVerifyInputWhenFocusTarget(false);
+    nameBox.add(txtFileName);
+    // nameField.setToolTipText("Enter a name for the resource");
+
+    nameBox.add(Box.createHorizontalStrut(5));
+    nameBox.add(fileBtn = new JButton(MainFrame.getIcon("OpenFile")));
+    nameBox.add(Box.createHorizontalGlue());
+    this.getContentPane().add(nameBox);
+    this.getContentPane().add(Box.createVerticalStrut(5));
+
+    // parameters table
+    parametersEditor = new ResourceParametersEditor();
+    this.getContentPane().add(new JScrollPane(parametersEditor));
+    this.getContentPane().add(Box.createVerticalStrut(5));
+    this.getContentPane().add(Box.createVerticalGlue());
+    // buttons box
+    JPanel buttonsBox = new JPanel();
+    buttonsBox.setLayout(new BoxLayout(buttonsBox, BoxLayout.X_AXIS));
+    buttonsBox.add(Box.createHorizontalStrut(10));
+    buttonsBox.add(okBtn = new JButton("OK"));
+    buttonsBox.add(Box.createHorizontalStrut(10));
+    buttonsBox.add(cancelBtn = new JButton("Cancel"));
+    buttonsBox.add(Box.createHorizontalStrut(10));
+    this.getContentPane().add(buttonsBox);
+    this.getContentPane().add(Box.createVerticalStrut(5));
+    setSize(400, 300);
+
+    getRootPane().setDefaultButton(okBtn);
+  }
+
+  protected void initListeners() {
+    Action fileAction = new AbstractAction() {
+
+      @Override
+      public void actionPerformed(ActionEvent ae) {
+        XJFileChooser fileChooser = MainFrame.getFileChooser();
+        fileChooser.resetChoosableFileFilters();
+        fileChooser.setFileFilter(de.getFileFilter());
+        fileChooser.setMultiSelectionEnabled(false);
+        fileChooser.setDialogTitle("Save as " + de.getFileType());
+        fileChooser.setFileSelectionMode(isDocument
+                ? JFileChooser.FILES_ONLY
+                : JFileChooser.DIRECTORIES_ONLY);
+
+        // TODO set the currently selected file
+        try {
+          File f = new File(txtFileName.getText());
+          fileChooser.ensureFileIsVisible(f);
+          fileChooser.setSelectedFile(f);
+        } catch(Exception e) {
+          // swallow and ignore
+        }
+
+        if(fileChooser.showSaveDialog(DocumentExportDialog.this) != 
JFileChooser.APPROVE_OPTION)
+          return;
+
+        File selectedFile = fileChooser.getSelectedFile();
+        if(selectedFile == null) return;
+
+        txtFileName.setText(selectedFile.getAbsolutePath());
+      }
+    };
+
+    Action applyAction = new AbstractAction() {
+      @Override
+      public void actionPerformed(ActionEvent e) {
+        userCanceled = false;
+        TableCellEditor cellEditor = parametersEditor.getCellEditor();
+        if(cellEditor != null) {
+          cellEditor.stopCellEditing();
+        }
+        setVisible(false);
+      }
+    };
+    Action cancelAction = new AbstractAction() {
+      @Override
+      public void actionPerformed(ActionEvent e) {
+        userCanceled = true;
+        setVisible(false);
+      }
+    };
+
+    fileBtn.addActionListener(fileAction);
+    okBtn.addActionListener(applyAction);
+    cancelBtn.addActionListener(cancelAction);
+
+    // disable Enter key in the table so this key will confirm the
+    // dialog
+    InputMap im =
+            parametersEditor
+                    .getInputMap(JTable.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT);
+    KeyStroke enter = KeyStroke.getKeyStroke(KeyEvent.VK_ENTER, 0);
+    im.put(enter, "none");
+
+    // define keystrokes action bindings at the level of the main window
+    InputMap inputMap =
+            ((JComponent)this.getContentPane())
+                    .getInputMap(JComponent.WHEN_IN_FOCUSED_WINDOW);
+    ActionMap actionMap = ((JComponent)this.getContentPane()).getActionMap();
+    inputMap.put(KeyStroke.getKeyStroke("ENTER"), "Apply");
+    actionMap.put("Apply", applyAction);
+    inputMap.put(KeyStroke.getKeyStroke("ESCAPE"), "Cancel");
+    actionMap.put("Cancel", cancelAction);
+  }
+
+  public synchronized boolean show(DocumentExporter de,
+          List<List<Parameter>> params, boolean isDocument, String filePath) {
+
+    this.isDocument = isDocument;
+    this.de = de;
+
+    setTitle("Save as " + de.getFileType());
+
+    txtFileName.setText(filePath);
+    parametersEditor.init(null, params);
+    pack();
+    txtFileName.requestFocusInWindow();
+    userCanceled = true;
+    setModal(true);
+    setLocationRelativeTo(getOwner());
+    super.setVisible(true);
+    dispose();
+    if(userCanceled)
+      return false;
+    else return true;
+  }
+
+  @Override
+  public void dispose() {
+    de = null;
+  }
+
+  /**
+   * Returns the selected params for the resource or null if none was
+   * selected or the user pressed cancel
+   */
+  public FeatureMap getSelectedParameters() {
+    if(parametersEditor != null)
+      return parametersEditor.getParameterValues();
+    else return null;
+  }
+
+  /**
+   * Return the String entered into the resource name field of the
+   * dialog.
+   * 
+   * @param rData
+   */
+  public String getSelectedFileName() {
+    return txtFileName.getText();
+  }
+
+  public static class SaveAsMenu extends XJMenu implements CreoleListener {
+
+    /**
+     * The first position in the menu that can be used by dynamic items.
+     */
+    protected int firstPluginItem = 0;
+
+    protected IdentityHashMap<Resource, JMenuItem> itemByResource =
+            new IdentityHashMap<Resource, JMenuItem>();
+
+    private Document document;
+
+    private Corpus corpus;
+    
+    
+
+    public SaveAsMenu(Document document, XJMenuItem gateXML, StatusListener 
listener) {
+      super("Save as...", "", listener);
+      if(document == null)
+        throw new NullPointerException("Document cannot be null!");
+      this.document = document;
+      add(gateXML);
+      init();
+    }
+
+    public SaveAsMenu(Corpus corpus, XJMenuItem gateXML, StatusListener 
listener) {
+      super("Save as...", "", listener);
+      if(corpus == null)
+        throw new NullPointerException("Corpus cannot be null!");
+      this.corpus = corpus;
+      add(gateXML);
+      init();
+    }
+
+    private void init() {
+      Set<String> toolTypes = Gate.getCreoleRegister().getToolTypes();
+      for(String type : toolTypes) {
+        List<Resource> instances =
+                Gate.getCreoleRegister().get(type).getInstantiations();
+        for(Resource res : instances) {
+          if(res instanceof DocumentExporter) {
+            addExporter((DocumentExporter)res);
+          }
+        }
+      }
+      Gate.getCreoleRegister().addCreoleListener(this);
+    }
+
+    private File getSelectedFile(List<List<Parameter>> params,
+            DocumentExporter de, FeatureMap options) {
+      // TODO suggest the filename
+      File selectedFile = null;
+
+      if(document != null && document.getSourceUrl() != null) {
+        String fileName = "";
+        try {
+          fileName = document.getSourceUrl().toURI().getPath().trim();
+        } catch(URISyntaxException e) {
+          fileName = document.getSourceUrl().getPath().trim();
+        }
+        if(fileName.equals("") || fileName.equals("/")) {
+          if(document.getNamedAnnotationSets().containsKey(
+            "Original markups") &&
+            !document.getAnnotations("Original markups").get("title")
+              .isEmpty()) {
+            // use the title annotation if any
+            try {
+              fileName =
+                      document
+                  .getContent()
+                  .getContent(
+                          document.getAnnotations("Original 
markups").get("title")
+                      .firstNode().getOffset(),
+                      document.getAnnotations("Original markups").get("title")
+                      .lastNode().getOffset()).toString();
+            } catch(InvalidOffsetException e) {
+              e.printStackTrace();
+            }
+          } else {
+            fileName = document.getSourceUrl().toString();
+          }
+          // cleans the file name
+          fileName = fileName.replaceAll("/", "_");
+        } else {
+          // replaces the extension with the default
+          fileName = fileName.replaceAll("\\.[a-zA-Z]{1,4}$", 
"."+de.getDefaultExtension());
+        }
+        // cleans the file name
+        fileName = fileName.replaceAll("[^/a-zA-Z0-9._-]", "_");
+        fileName = fileName.replaceAll("__+", "_");
+        // adds the default extension if not present
+        if(!fileName.endsWith("."+de.getDefaultExtension())) {
+          fileName += "."+de.getDefaultExtension();
+        }
+        
+        selectedFile = new File(fileName);
+      }
+      
+      
+      if(params == null || params.isEmpty()) {
+        XJFileChooser fileChooser = MainFrame.getFileChooser();
+        fileChooser.resetChoosableFileFilters();
+        fileChooser.setFileFilter(de.getFileFilter());
+        fileChooser.setMultiSelectionEnabled(false);
+        fileChooser.setDialogTitle("Save as " + de.getFileType());
+        fileChooser.setFileSelectionMode(document != null
+                ? JFileChooser.FILES_ONLY
+                : JFileChooser.DIRECTORIES_ONLY);
+        
+        if (selectedFile != null) {
+          fileChooser.ensureFileIsVisible(selectedFile);
+          fileChooser.setSelectedFile(selectedFile);
+        }
+
+        if(fileChooser.showSaveDialog(MainFrame.getInstance()) != 
JFileChooser.APPROVE_OPTION)
+          return null;
+        selectedFile = fileChooser.getSelectedFile();
+      } else {
+        if(!dialog.show(de, params, document != null,selectedFile != null ? 
selectedFile.getAbsolutePath() : "")) return null;
+
+        options.putAll(dialog.getSelectedParameters());
+        selectedFile = new File(dialog.getSelectedFileName());
+      }
+
+      return selectedFile;
+    }
+
+    private void addExporter(final DocumentExporter de) {
+      
+      if (itemByResource.containsKey(de)) return;
+      
+      SwingUtilities.invokeLater(new Runnable() {
+        public void run() {
+          final ResourceData rd =
+                  Gate.getCreoleRegister()
+                          .get(de.getClass().getCanonicalName());
+          
+          if (SaveAsMenu.this.getItemCount() == 1) {
+            SaveAsMenu.this.addSeparator();
+          }
+          
+          JMenuItem item = SaveAsMenu.this.add(new 
AbstractAction(de.getFileType() + " (."
+                  + de.getDefaultExtension() + ")") {
+
+            @Override
+            public void actionPerformed(ActionEvent ae) {
+
+              List<List<Parameter>> params =
+                      rd.getParameterList().getRuntimeParameters();
+
+              final FeatureMap options = Factory.newFeatureMap();
+
+              final File selectedFile =
+                      getSelectedFile(params, de, options);
+
+              if(selectedFile == null) return;
+
+              Runnable runnable = new Runnable() {
+                public void run() {
+
+                  if(document != null) {
+
+                    // TODO add the extension if missing?
+
+                    long start = System.currentTimeMillis();
+                    listener.statusChanged("Saving as " + de.getFileType()
+                            + " to " + selectedFile.toString() + "...");
+                    try {
+                      de.export(document, selectedFile, options);
+                    } catch(IOException e) {
+                      // TODO Auto-generated catch block
+                      e.printStackTrace();
+                    }
+
+                    long time = System.currentTimeMillis() - start;
+                    listener.statusChanged("Finished saving as "
+                            + de.getFileType() + " into " + " the file: "
+                            + selectedFile.toString() + " in " + ((double)time)
+                            / 1000 + " s");
+                  } else {
+                    try {
+                      // TODO add corpus support
+                      File dir = selectedFile;
+                      // create the top directory if needed
+                      if(!dir.exists()) {
+                        if(!dir.mkdirs()) {
+                          JOptionPane.showMessageDialog(
+                                  MainFrame.getInstance(),
+                                  "Could not create top directory!", "GATE",
+                                  JOptionPane.ERROR_MESSAGE);
+                          return;
+                        }
+                      }
+
+                      MainFrame.lockGUI("Saving...");
+
+                      // iterate through all the docs and save each of
+                      // them
+                      Iterator<Document> docIter = corpus.iterator();
+                      boolean overwriteAll = false;
+                      int docCnt = corpus.size();
+                      int currentDocIndex = 0;
+                      Set<String> usedFileNames = new HashSet<String>();
+                      while(docIter.hasNext()) {
+                        boolean docWasLoaded =
+                                corpus.isDocumentLoaded(currentDocIndex);
+                        Document currentDoc = docIter.next();
+
+                        URL sourceURL = currentDoc.getSourceUrl();
+                        String fileName = null;
+                        if(sourceURL != null) {
+                          fileName = sourceURL.getPath();
+                          fileName = Files.getLastPathComponent(fileName);
+                        }
+                        if(fileName == null || fileName.length() == 0) {
+                          fileName = currentDoc.getName();
+                        }
+                        // makes sure that the filename does not contain
+                        // any
+                        // forbidden character
+                        fileName =
+                                fileName.replaceAll("[\\/:\\*\\?\"<>|]", "_");
+                        
if(fileName.toLowerCase().endsWith("."+de.getDefaultExtension())) {
+                          fileName =
+                                  fileName.substring(0, fileName.length() - 5);
+                        }
+                        if(usedFileNames.contains(fileName)) {
+                          // name clash -> add unique ID
+                          String fileNameBase = fileName;
+                          int uniqId = 0;
+                          fileName = fileNameBase + "-" + uniqId++;
+                          while(usedFileNames.contains(fileName)) {
+                            fileName = fileNameBase + "-" + uniqId++;
+                          }
+                        }
+                        usedFileNames.add(fileName);
+                        
if(!fileName.toLowerCase().endsWith("."+de.getDefaultExtension()))
+                          fileName += "."+de.getDefaultExtension();
+                        File docFile = null;
+                        boolean nameOK = false;
+                        do {
+                          docFile = new File(dir, fileName);
+                          if(docFile.exists() && !overwriteAll) {
+                            // ask the user if we can overwrite the file
+                            Object[] opts =
+                                    new Object[] {"Yes", "All", "No", 
"Cancel"};
+                            MainFrame.unlockGUI();
+                            int answer =
+                                    JOptionPane.showOptionDialog(
+                                            MainFrame.getInstance(), "File "
+                                                    + docFile.getName()
+                                                    + " already exists!\n"
+                                                    + "Overwrite?", "GATE",
+                                            JOptionPane.DEFAULT_OPTION,
+                                            JOptionPane.WARNING_MESSAGE, null,
+                                            opts, opts[2]);
+                            MainFrame.lockGUI("Saving...");
+                            switch(answer) {
+                              case 0: {
+                                nameOK = true;
+                                break;
+                              }
+                              case 1: {
+                                nameOK = true;
+                                overwriteAll = true;
+                                break;
+                              }
+                              case 2: {
+                                // user said NO, allow them to provide
+                                // an
+                                // alternative name;
+                                MainFrame.unlockGUI();
+                                fileName =
+                                        (String)JOptionPane.showInputDialog(
+                                                MainFrame.getInstance(),
+                                                "Please provide an alternative 
file name",
+                                                "GATE",
+                                                JOptionPane.QUESTION_MESSAGE,
+                                                null, null, fileName);
+                                if(fileName == null) {
+                                  // handle.processFinished();
+                                  return;
+                                }
+                                MainFrame.lockGUI("Saving");
+                                break;
+                              }
+                              case 3: {
+                                // user gave up; return
+                                // handle.processFinished();
+                                return;
+                              }
+                            }
+
+                          } else {
+                            nameOK = true;
+                          }
+                        } while(!nameOK);
+                        // save the file
+                        try {
+                          // do the actual exporting
+                          de.export(currentDoc, docFile, options);
+                        } catch(Exception ioe) {
+                          MainFrame.unlockGUI();
+                          JOptionPane.showMessageDialog(
+                                  MainFrame.getInstance(),
+                                  "Could not create write file:"
+                                          + ioe.toString(), "GATE",
+                                  JOptionPane.ERROR_MESSAGE);
+                          ioe.printStackTrace(Err.getPrintWriter());
+                          return;
+                        }
+
+                        listener.statusChanged(currentDoc.getName() + " 
saved");
+                        // close the doc if it wasn't already loaded
+                        if(!docWasLoaded) {
+                          corpus.unloadDocument(currentDoc);
+                          Factory.deleteResource(currentDoc);
+                        }
+
+                        // handle.progressChanged(100 *
+                        // currentDocIndex++ /
+                        // docCnt);
+                      }// while(docIter.hasNext())
+                      listener.statusChanged("Corpus Saved");
+                      // handle.processFinished();
+
+                    } finally {
+                      MainFrame.unlockGUI();
+                    }
+                  }
+                }
+              };
+
+              Thread thread =
+                      new Thread(Thread.currentThread().getThreadGroup(),
+                              runnable, "Document Exporter Thread");
+              thread.setPriority(Thread.MIN_PRIORITY);
+              thread.start();
+            }
+
+          });
+          
+          itemByResource.put(de,item);
+        }
+      });
+    }
+
+    /**
+     * If the resource just loaded is a tool (according to the creole
+     * register) then see if it publishes any actions and if so, add
+     * them to the menu in the appropriate places.
+     */
+    @Override
+    public void resourceLoaded(CreoleEvent e) {
+      Resource res = e.getResource();
+      
+      if(res instanceof DocumentExporter) {
+        addExporter((DocumentExporter)res);
+      }
+    }
+    
+    @Override
+    public void resourceUnloaded(CreoleEvent e) {
+      Resource res = e.getResource();
+      
+      if (res instanceof DocumentExporter) {
+        JMenuItem item = itemByResource.get(res);
+        
+        if (item != null) {
+          remove(item);
+          itemByResource.remove(res);
+        }
+      }
+      
+      if (getItemCount() == 2) {
+        remove(1);
+      }
+    }
+
+    // remaining CreoleListener methods not used
+    @Override
+    public void datastoreClosed(CreoleEvent e) {
+    }
+
+    @Override
+    public void datastoreCreated(CreoleEvent e) {
+    }
+
+    @Override
+    public void datastoreOpened(CreoleEvent e) {
+    }
+
+    @Override
+    public void resourceRenamed(Resource resource, String oldName,
+            String newName) {
+    }
+  }
+}// class NewResourceDialog

Modified: gate/trunk/src/main/gate/gui/NameBearerHandle.java
===================================================================
--- gate/trunk/src/main/gate/gui/NameBearerHandle.java  2014-07-15 15:38:32 UTC 
(rev 18183)
+++ gate/trunk/src/main/gate/gui/NameBearerHandle.java  2014-07-15 18:42:12 UTC 
(rev 18184)
@@ -82,7 +82,6 @@
 import javax.swing.Icon;
 import javax.swing.JComponent;
 import javax.swing.JFileChooser;
-import javax.swing.JMenuItem;
 import javax.swing.JOptionPane;
 import javax.swing.JPopupMenu;
 import javax.swing.JTabbedPane;
@@ -207,9 +206,9 @@
   public JPopupMenu getPopup() {
     JPopupMenu popup = new XJPopupMenu();
     // first add the static items
-    Iterator<XJMenuItem> itemIter = staticPopupItems.iterator();
+    Iterator<JComponent> itemIter = staticPopupItems.iterator();
     while(itemIter.hasNext()) {
-      JMenuItem anItem = itemIter.next();
+      JComponent anItem = itemIter.next();
       if(anItem == null)
         popup.addSeparator();
       else popup.add(anItem);
@@ -280,7 +279,7 @@
   
   protected void buildStaticPopupItems() {
     // build the static part of the popup
-    staticPopupItems = new ArrayList<XJMenuItem>();
+    staticPopupItems = new ArrayList<JComponent>();
 
     if(target instanceof ProcessingResource && !(target instanceof 
Controller)) {
       // actions for PRs (but not Controllers)
@@ -298,7 +297,8 @@
         XJMenuItem saveAsXmlItem = new XJMenuItem(new SaveAsXmlAction(),
                 sListenerProxy);
         staticPopupItems.add(null);
-        staticPopupItems.add(saveAsXmlItem);
+        //staticPopupItems.add(saveAsXmlItem);
+        staticPopupItems.add(new 
DocumentExportDialog.SaveAsMenu((Document)target, saveAsXmlItem, 
sListenerProxy));
       }
       else if(target instanceof Corpus) {
         corpusFiller = new CorpusFillerComponent();
@@ -309,8 +309,10 @@
                 new PopulateCorpusFromSingleConcatenatedFileAction(),
                 sListenerProxy));
         staticPopupItems.add(null);
-        staticPopupItems.add(new XJMenuItem(new SaveCorpusAsXmlAction(),
-                sListenerProxy));
+        XJMenuItem saveAsXmlItem = new XJMenuItem(new SaveCorpusAsXmlAction(),
+                sListenerProxy);
+        //staticPopupItems.add(saveAsXmlItem);
+        staticPopupItems.add(new 
DocumentExportDialog.SaveAsMenu((Corpus)target, saveAsXmlItem, sListenerProxy));
         // staticPopupItems.add(new XJMenuItem(new
         // SaveCorpusAsXmlAction(true), sListenerProxy));
         
@@ -495,7 +497,7 @@
    * A list of menu items that constitute the static part of the popup.
    * Null values are used for separators.
    */
-  protected List<XJMenuItem> staticPopupItems;
+  protected List<JComponent> staticPopupItems;
 
   /**
    * The top level GUI component this handle belongs to.
@@ -589,7 +591,7 @@
     private static final long serialVersionUID = 1L;
 
     public SaveAsXmlAction() {
-      super("Save as XML...");
+      super("GATE XML (.xml)");
       putValue(SHORT_DESCRIPTION, "Saves this resource in GATE XML format");
       putValue(ACCELERATOR_KEY, KeyStroke.getKeyStroke("control S"));
     }// SaveAsXmlAction()
@@ -716,7 +718,7 @@
     private static final long serialVersionUID = 1L;
 
     public SaveCorpusAsXmlAction() {
-      super("Save as XML...");
+      super("GATE XML (.xml)");
       putValue(SHORT_DESCRIPTION, "Saves each document in GATE XML format");
     }// SaveAsXmlAction()
 

This was sent by the SourceForge.net collaborative development platform, the 
world's largest Open Source development site.


------------------------------------------------------------------------------
Want fast and easy access to all the code in your enterprise? Index and
search up to 200,000 lines of code with a free copy of Black Duck
Code Sight - the same software that powers the world's largest code
search on Ohloh, the Black Duck Open Hub! Try it now.
http://p.sf.net/sfu/bds
_______________________________________________
GATE-cvs mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/gate-cvs

Reply via email to