Merge branch 'develop' into task/JAL-3141_JAL-3247_merge
authorBen Soares <bsoares@dundee.ac.uk>
Tue, 28 May 2019 11:14:51 +0000 (12:14 +0100)
committerBen Soares <bsoares@dundee.ac.uk>
Tue, 28 May 2019 11:14:51 +0000 (12:14 +0100)
updating merge

43 files changed:
build.gradle
getdown/lib/getdown-core-1.8.3-SNAPSHOT.jar
getdown/lib/getdown-launcher.jar
getdown/src/getdown/core/src/main/java/com/threerings/getdown/data/Application.java
getdown/src/getdown/core/src/main/java/jalview/bin/MemorySetting.java [new file with mode: 0644]
gradle.properties
j11lib/getdown-core.jar
j8lib/getdown-core.jar
resources/lang/Messages.properties
resources/lang/Messages_es.properties
src/jalview/bin/Jalview.java
src/jalview/bin/JalviewTaskbar.java
src/jalview/bin/Launcher.java
src/jalview/bin/MemorySetting.java [new file with mode: 0644]
src/jalview/gui/APQHandlers.java
src/jalview/gui/Desktop.java
src/jalview/gui/FeatureTypeSettings.java
src/jalview/gui/JvSwingUtils.java
src/jalview/gui/Preferences.java
src/jalview/io/BackupFilenameParts.java
src/jalview/io/BackupFiles.java
src/jalview/io/BackupFilesPresetEntry.java [new file with mode: 0644]
src/jalview/io/IntKeyStringValueEntry.java [new file with mode: 0644]
src/jalview/jbgui/GDesktop.java
src/jalview/jbgui/GPreferences.java
test/jalview/io/BackupFilesTest.java
test/jalview/io/backupfilestest.fa [moved from examples/backupfilestest.fa with 100% similarity]
test/jalview/io/testProps.jvprops
utils/install4j/DS_Store
utils/install4j/DS_Store_1 [new file with mode: 0644]
utils/install4j/DS_Store_2 [new file with mode: 0644]
utils/install4j/Uninstall Old Jalview.app/Contents/Info.plist [new file with mode: 0644]
utils/install4j/Uninstall Old Jalview.app/Contents/MacOS/applet [new file with mode: 0755]
utils/install4j/Uninstall Old Jalview.app/Contents/PkgInfo [new file with mode: 0644]
utils/install4j/Uninstall Old Jalview.app/Contents/Resources/Scripts/main.scpt [new file with mode: 0644]
utils/install4j/Uninstall Old Jalview.app/Contents/Resources/applet.icns [new file with mode: 0644]
utils/install4j/Uninstall Old Jalview.app/Contents/Resources/applet.rsrc [new file with mode: 0644]
utils/install4j/Uninstall Old Jalview.app/Contents/Resources/description.rtfd/TXT.rtf [new file with mode: 0644]
utils/install4j/Uninstall Old Jalview.scpt [new file with mode: 0644]
utils/install4j/install4j_template.install4j
utils/install4j/uninstall_app_dmg_file_inclusions.sh [new file with mode: 0644]
utils/install4j/uninstall_old_jalview.icns [new file with mode: 0644]
utils/install4j/uninstall_old_jalview_files.xml [new file with mode: 0644]

index 07a4095..fb311a4 100644 (file)
@@ -846,15 +846,26 @@ task copyInstall4jTemplate(type: Copy) {
   outputs.files(install4jConf)
 
   doLast {
+    // include file associations in installer
     def installerFileAssociationsXml = file("$install4jDir/$install4jInstallerFileAssociations").text
     ant.replaceregexp(
       byline: false,
       flags: "s",
       match: '<action name="EXTENSIONS_REPLACED_BY_GRADLE".*?</action>',
-      //match: '<action.*?EXTENSIONS_REPLACED_BY_GRADLE.*?</action>',
       replace: installerFileAssociationsXml,
       file: install4jConf
     )
+    /*
+    // include uninstaller applescript app files in dmg
+    def installerDMGUninstallerXml = file("$install4jDir/$install4jDMGUninstallerAppFiles").text
+    ant.replaceregexp(
+      byline: false,
+      flags: "s",
+      match: '<file name="UNINSTALL_OLD_JALVIEW_APP_REPLACED_IN_GRADLE" file=.*?>',
+      replace: installerDMGUninstallerXml,
+      file: install4jConf
+    )
+    */
   }
 }
 
index 7230883..c09d3e4 100644 (file)
Binary files a/getdown/lib/getdown-core-1.8.3-SNAPSHOT.jar and b/getdown/lib/getdown-core-1.8.3-SNAPSHOT.jar differ
index cb5f670..321b5ce 100644 (file)
Binary files a/getdown/lib/getdown-launcher.jar and b/getdown/lib/getdown-launcher.jar differ
index 25cd109..0de5c8a 100644 (file)
@@ -26,6 +26,7 @@ import java.util.zip.GZIPInputStream;
 import com.sun.management.OperatingSystemMXBean;
 import java.lang.management.ManagementFactory;
 
+import jalview.bin.MemorySetting;
 
 import com.threerings.getdown.util.*;
 // avoid ambiguity with java.util.Base64 which we can't use as it's 1.8+
@@ -753,28 +754,34 @@ public class Application
             jvmmempc = config.getInt(appPrefix + "jvmmempc", jvmmempc);
         }
         if (0 <= jvmmempc && jvmmempc <= 100) {
-            final Object o = ManagementFactory.getOperatingSystemMXBean();
-
-            try {
-                if (o instanceof OperatingSystemMXBean) {
-                    final OperatingSystemMXBean osb = (OperatingSystemMXBean) o;
-                    long physicalMem = osb.getTotalPhysicalMemorySize();
-                    long requestedMem = physicalMem*jvmmempc/100;
-                    String[] maxMemHeapArg = new String[]{"-Xmx"+Long.toString(requestedMem)};
-                    // remove other max heap size arg
-                    ARG: for (int i = 0; i < _jvmargs.size(); i++) {
-                           if (_jvmargs.get(i) instanceof java.lang.String && _jvmargs.get(i).startsWith("-Xmx")) {
-                                _jvmargs.remove(i);
-                           }
-                    }
-                    addAll(maxMemHeapArg, _jvmargs);
+          
+          long maxMemLong = -1;
+
+          try
+          {
+            maxMemLong = MemorySetting.memPercent(jvmmempc);
+          } catch (Exception e)
+          {
+            e.printStackTrace();
+          } catch (Throwable t)
+          {
+            t.printStackTrace();
+          }
 
-                }
-            }
-            catch (NoClassDefFoundError e) {
-                // com.sun.management.OperatingSystemMXBean doesn't exist in this JVM
-                System.out.println("No com.sun.management.OperatingSystemMXBean. Cannot use 'jvmmempc'.");
+          if (maxMemLong > 0)
+          {
+            
+            String[] maxMemHeapArg = new String[]{"-Xmx"+Long.toString(maxMemLong)};
+            // remove other max heap size arg
+            ARG: for (int i = 0; i < _jvmargs.size(); i++) {
+              if (_jvmargs.get(i) instanceof java.lang.String && _jvmargs.get(i).startsWith("-Xmx")) {
+                _jvmargs.remove(i);
+              }
             }
+            addAll(maxMemHeapArg, _jvmargs);
+            
+          }
+
         } else if (jvmmempc != -1) {
           System.out.println("'jvmmempc' value must be in range 0 to 100 (read as '"+Integer.toString(jvmmempc)+"')");
         }
diff --git a/getdown/src/getdown/core/src/main/java/jalview/bin/MemorySetting.java b/getdown/src/getdown/core/src/main/java/jalview/bin/MemorySetting.java
new file mode 100644 (file)
index 0000000..b3bae2d
--- /dev/null
@@ -0,0 +1,51 @@
+package jalview.bin;
+
+import java.lang.management.ManagementFactory;
+import java.lang.management.OperatingSystemMXBean;
+
+public class MemorySetting
+{
+  public static final long leaveFreeMinMemory = 536870912; // 0.5 GB
+
+  public static final long applicationMinMemory = 536870912; // 0.5 GB
+
+  protected static long getPhysicalMemory()
+  {
+    final OperatingSystemMXBean o = ManagementFactory
+            .getOperatingSystemMXBean();
+
+    try
+    {
+      if (o instanceof com.sun.management.OperatingSystemMXBean)
+      {
+        final com.sun.management.OperatingSystemMXBean osb = (com.sun.management.OperatingSystemMXBean) o;
+        return osb.getTotalPhysicalMemorySize();
+      }
+    } catch (NoClassDefFoundError e)
+    {
+      // com.sun.management.OperatingSystemMXBean doesn't exist in this JVM
+      System.out.println("No com.sun.management.OperatingSystemMXBean");
+    }
+
+    // We didn't get a com.sun.management.OperatingSystemMXBean.
+    return -1;
+  }
+
+  public static long memPercent(int percent)
+  {
+    long memPercent = -1;
+
+    long physicalMem = getPhysicalMemory();
+    if (physicalMem > applicationMinMemory)
+    {
+      // try and set at least applicationMinMemory and thereafter ensure
+      // leaveFreeMinMemory is left for the OS
+      memPercent = Math.max(applicationMinMemory,
+              physicalMem - Math.max(physicalMem * (100 - percent) / 100,
+                      leaveFreeMinMemory));
+    }
+
+    return memPercent;
+  }
+
+}
index e49c3ab..57119cb 100644 (file)
@@ -59,7 +59,7 @@ getdown_txt_title = Jalview
 getdown_channel_base = http://www.jalview.org/getdown/jalview
 getdown_channel_name = TEST
 getdown_txt_allow_offline = true
-getdown_txt_jvmmempc = 95
+getdown_txt_jalview.jvmmempc = 90
 getdown_txt_multi_jvmarg = -Dgetdownappdir="%APPDIR%"
 getdown_txt_strict_comments = true
 getdown_txt_title = Jalview
@@ -100,8 +100,8 @@ install4jResourceDir = utils/install4j
 install4jTemplate = install4j_template.install4j
 install4jInfoPlistFileAssociations = file_associations_auto-Info_plist.xml
 install4jInstallerFileAssociations = file_associations_auto-install4j.xml
+install4jDMGUninstallerAppFiles = uninstall_old_jalview_files.xml
 install4jBuildDir = build/install4j
-install4jMediaTypes = windows,macosArchive,linuxRPM,linuxDeb,unixArchive
 install4jMediaTypes = windows,macosArchive,linuxRPM,linuxDeb,unixArchive,unixInstaller
 install4jFaster = false
 
index 7230883..c09d3e4 100644 (file)
Binary files a/j11lib/getdown-core.jar and b/j11lib/getdown-core.jar differ
index 7230883..c09d3e4 100644 (file)
Binary files a/j8lib/getdown-core.jar and b/j8lib/getdown-core.jar differ
index 04e8982..f095290 100644 (file)
@@ -1354,12 +1354,13 @@ label.append_to_filename = Append to filename (%n is replaced by the backup numb
 label.append_to_filename_tooltip = %n in the text will be replaced by the backup number. The text will appear after the filename. See the summary box above.
 label.index_digits = Number of digits to use for the backup number (%n)
 label.summary_of_backups_scheme = Summary of backup scheme
+label.scheme_examples = Scheme examples
 label.increment_index = Increase appended text numbers - newest file has largest number.
 label.reverse_roll = "Roll" appended text numbers - newest backup file is always number 1.
 label.keep_files = Deleting old backup files
 label.keep_all_backup_files = Do not delete old backup files
 label.keep_only_this_number_of_backup_files = Keep only this number of most recent backup files
-label.autodelete_old_backup_files = Autodelete old backup files:
+label.autodelete_old_backup_files = Auto-delete old backup files:
 label.always_ask = Always ask
 label.auto_delete = Automatically delete
 label.filename = filename
@@ -1369,10 +1370,18 @@ label.configuration = Configuration
 label.configure_feature_tooltip = Click to configure variable colour or filters
 label.schemes = Schemes
 label.customise = Customise
+label.custom = Custom
 label.default = Default
 label.single_file = Single backup
 label.keep_all_versions = Keep all versions
 label.rolled_backups = Rolled backup files
+label.customise_description = Select Customise, make changes, and click on OK to save your own custom scheme
+label.custom_description = Your own saved scheme
+label.default_description = Keep the last three versions of the file
+label.single_file_description = Keep the last version of the file
+label.keep_all_versions_description = Keep all previous versions of the file
+label.rolled_backups_description = Keep the last nine versions of the file from _bak.1 (newest) to _bak.9 (oldest)
+label.cancel_changes_description = Cancel changes made to your last saved Custom scheme
 label.previously_saved_scheme = Previously saved scheme
 label.no_backup_files = NO BACKUP FILES
 label.include_backup_files = Include backup files
index d7267f6..51a6d1e 100644 (file)
@@ -1355,6 +1355,7 @@ label.append_to_filename = Adjuntar texto (%n es reemplazado por el n
 label.append_to_filename_tooltip = %n en el texto será reemplazado por el número de respaldo. El texto será después del nombre del archivo. Vea el cuadro de resumen arriba.
 label.index_digits = Número de dígitos a utilizar para el número de respaldo.
 label.summary_of_backups_scheme = Resumen del esquema de copias de seguridad
+label.scheme_examples = Ejemplos de esquema
 label.increment_index = Aumente los números de texto adjuntos: el archivo más nuevo tiene el número más grande
 label.reverse_roll = Ciclos de texto adjuntos: el respaldo más reciente es siempre el número 1
 label.keep_files = Borrando los respaldos antiguos
@@ -1369,11 +1370,20 @@ label.braced_newest = (mas nuevo)
 label.configuration = Configuración
 label.configure_feature_tooltip = Haga clic para configurar el color o los filtros
 label.schemes = Esquemas
-label.customise = Personalizado
+label.customise = Personalizar
+label.custom = Personal
 label.default = Defecto
 label.single_file = Solo uno respaldo
 label.keep_all_versions = Mantener todas las versiones
 label.rolled_backups = Ciclos respaldos
+# TODO: Translate these _description s
+label.customise_description = Seleccione Personalizar, haga cambios y haga clic en OK para guardar su propio esquema personalizado
+label.custom_description = Tu propio esquema guardado
+label.default_description = Conserve las Ãºltimas tres versiones del archivo
+label.single_file_description = Conserve la Ãºltima versión del archivo
+label.keep_all_versions_description = Mantener todas las versiones anteriores del archivo
+label.rolled_backups_description = Mantenga las Ãºltimas nueve versiones del archivo desde _bak.1 (más reciente) a _bak.9 (más antigua)
+label.cancel_changes_description = Cancelar los cambios realizados en su Ãºltimo esquema personalizado guardado
 label.previously_saved_scheme = Esquema previamente guardado
 label.no_backup_files = NO ARCHIVOS DE RESPALDOS
 label.include_backup_files = Incluir archivos de respaldos
index c66e63e..449c1fb 100755 (executable)
@@ -360,10 +360,12 @@ public class Jalview
         JalviewTaskbar.setTaskbar(this);
       } catch (Exception e)
       {
-        e.printStackTrace();
+        System.out.println("Cannot set Taskbar");
+        // e.printStackTrace();
       } catch (Throwable t)
       {
-        t.printStackTrace();
+        System.out.println("Cannot set Taskbar");
+        // t.printStackTrace();
       }
 
       desktop.setVisible(true);
index 5747263..7dd0382 100644 (file)
@@ -29,7 +29,7 @@ public class JalviewTaskbar
           }
         } catch (Exception e)
         {
-          e.printStackTrace();
+          System.out.println("Unable to setIconImage()");
         }
       }
     }
index aec3acd..412f119 100644 (file)
@@ -1,8 +1,8 @@
 package jalview.bin;
 
 import java.io.File;
+import java.io.IOException;
 import java.lang.management.ManagementFactory;
-import java.lang.management.OperatingSystemMXBean;
 import java.util.ArrayList;
 
 public class Launcher
@@ -10,7 +10,9 @@ public class Launcher
 
   private final static String startClass = "jalview.bin.Jalview";
 
-  private final static int maxHeapSizePerCent = 95;
+  private final static int maxHeapSizePerCent = 90;
+
+  private final static String maxHeapSizePerCentProperty = "jvmmempc";
 
   private final static String dockIconPath = "JalviewLogo_Huge.png";
 
@@ -22,6 +24,8 @@ public class Launcher
     ArrayList<String> command = new ArrayList<>();
     command.add(javaBin);
 
+    String memSetting = null;
+
     boolean isAMac = System.getProperty("os.name").indexOf("Mac") > -1;
 
     for (String jvmArg : ManagementFactory.getRuntimeMXBean()
@@ -40,39 +44,81 @@ public class Launcher
     // add memory setting if not specified
     boolean memSet = false;
     boolean dockIcon = false;
+    boolean dockName = false;
     ARG: for (int i = 0; i < command.size(); i++)
     {
       String arg = command.get(i);
       if (arg.startsWith("-Xmx"))
       {
+        memSetting = arg;
         memSet = true;
       }
       else if (arg.startsWith("-Xdock:icon"))
       {
         dockIcon = true;
       }
+      else if (arg.startsWith("-Xdock:name"))
+      {
+        dockName = true;
+      }
     }
 
     if (!memSet)
     {
       long maxMemLong = -1;
-      long physicalMem = getPhysicalMemory();
-      if (physicalMem > 0)
+      int percent = maxHeapSizePerCent;
+      String jvmmempc = System.getProperty(maxHeapSizePerCentProperty);
+      try
+      {
+        if (jvmmempc != null)
+        {
+          int trypercent = Integer.parseInt(jvmmempc);
+          if (0 < trypercent && trypercent <= 100)
+          {
+            percent = trypercent;
+          }
+          else
+          {
+            System.out.println("Property '" + maxHeapSizePerCentProperty
+                    + "' should be in range 1..100");
+          }
+        }
+      } catch (Exception e)
+      {
+        System.out.println("Error parsing " + maxHeapSizePerCentProperty
+                + " '" + jvmmempc + "'");
+      }
+
+      try
       {
-        maxMemLong = physicalMem * maxHeapSizePerCent / 100;
+        maxMemLong = MemorySetting.memPercent(percent);
+      } catch (Exception e)
+      {
+        e.printStackTrace();
+      } catch (Throwable t)
+      {
+        t.printStackTrace();
       }
+
       if (maxMemLong > 0)
       {
-        command.add("-Xmx" + Long.toString(maxMemLong));
+        memSetting = "-Xmx" + Long.toString(maxMemLong);
+        command.add(memSetting);
       }
     }
 
-    if (!dockIcon && isAMac)
+    if (isAMac)
     {
-      command.add("-Xdock:icon=" + dockIconPath);
-      // -Xdock:name=... doesn't actually work :(
-      // Leaving it in in case it gets fixed
-      command.add("-Xdock:name=" + "Jalview");
+      if (!dockIcon)
+      {
+        command.add("-Xdock:icon=" + dockIconPath);
+      }
+      if (!dockName)
+      {
+        // -Xdock:name=... doesn't actually work :(
+        // Leaving it in in case it gets fixed
+        command.add("-Xdock:name=" + "Jalview");
+      }
     }
 
     command.add(startClass);
@@ -80,41 +126,53 @@ public class Launcher
 
     final ProcessBuilder builder = new ProcessBuilder(command);
 
-    System.out.println("COMMAND: " + String.join(" ", builder.command()));
+    // System.out.println("COMMAND: " + String.join(" ", builder.command()));
+    System.out.println("Running " + startClass + " with "
+            + (memSetting == null ? "no memSetting" : memSetting));
 
     try
     {
       builder.inheritIO();
       Process process = builder.start();
       process.waitFor();
-    } catch (Exception e)
+    } catch (IOException e)
     {
-      e.printStackTrace();
-    }
-    // System.exit(0);
-
-  }
-
-  public static long getPhysicalMemory()
-  {
-    final OperatingSystemMXBean o = ManagementFactory
-            .getOperatingSystemMXBean();
-
-    try
-    {
-      if (o instanceof com.sun.management.OperatingSystemMXBean)
+      if (e.getMessage().toLowerCase().contains("memory"))
+      {
+        System.out.println("Caught a memory exception: " + e.getMessage());
+        // Probably the "Cannot allocate memory" error, try without the memory setting
+        ArrayList<String> commandNoMem = new ArrayList<>();
+        for (int i = 0; i < command.size(); i++)
+        {
+          if (!command.get(i).startsWith("-Xmx"))
+          {
+            commandNoMem.add(command.get(i));
+          }
+        }
+        final ProcessBuilder builderNoMem = new ProcessBuilder(
+                commandNoMem);
+        System.out.println("NO MEM COMMAND: "
+                + String.join(" ", builderNoMem.command()));
+        try
+        {
+          builderNoMem.inheritIO();
+          Process processNoMem = builderNoMem.start();
+          processNoMem.waitFor();
+        } catch (Exception ex)
+        {
+          ex.printStackTrace();
+        }
+      }
+      else
       {
-        final com.sun.management.OperatingSystemMXBean osb = (com.sun.management.OperatingSystemMXBean) o;
-        return osb.getTotalPhysicalMemorySize();
+        e.printStackTrace();
       }
-    } catch (NoClassDefFoundError e)
+    } catch (Exception e)
     {
-      // com.sun.management.OperatingSystemMXBean doesn't exist in this JVM
-      System.out.println("No com.sun.management.OperatingSystemMXBean");
+      e.printStackTrace();
     }
+    // System.exit(0);
 
-    // We didn't get a com.sun.management.OperatingSystemMXBean.
-    return -1;
   }
 
 }
diff --git a/src/jalview/bin/MemorySetting.java b/src/jalview/bin/MemorySetting.java
new file mode 100644 (file)
index 0000000..b3bae2d
--- /dev/null
@@ -0,0 +1,51 @@
+package jalview.bin;
+
+import java.lang.management.ManagementFactory;
+import java.lang.management.OperatingSystemMXBean;
+
+public class MemorySetting
+{
+  public static final long leaveFreeMinMemory = 536870912; // 0.5 GB
+
+  public static final long applicationMinMemory = 536870912; // 0.5 GB
+
+  protected static long getPhysicalMemory()
+  {
+    final OperatingSystemMXBean o = ManagementFactory
+            .getOperatingSystemMXBean();
+
+    try
+    {
+      if (o instanceof com.sun.management.OperatingSystemMXBean)
+      {
+        final com.sun.management.OperatingSystemMXBean osb = (com.sun.management.OperatingSystemMXBean) o;
+        return osb.getTotalPhysicalMemorySize();
+      }
+    } catch (NoClassDefFoundError e)
+    {
+      // com.sun.management.OperatingSystemMXBean doesn't exist in this JVM
+      System.out.println("No com.sun.management.OperatingSystemMXBean");
+    }
+
+    // We didn't get a com.sun.management.OperatingSystemMXBean.
+    return -1;
+  }
+
+  public static long memPercent(int percent)
+  {
+    long memPercent = -1;
+
+    long physicalMem = getPhysicalMemory();
+    if (physicalMem > applicationMinMemory)
+    {
+      // try and set at least applicationMinMemory and thereafter ensure
+      // leaveFreeMinMemory is left for the OS
+      memPercent = Math.max(applicationMinMemory,
+              physicalMem - Math.max(physicalMem * (100 - percent) / 100,
+                      leaveFreeMinMemory));
+    }
+
+    return memPercent;
+  }
+
+}
index 31f7a6d..05f5e08 100644 (file)
@@ -86,7 +86,8 @@ public class APQHandlers
                         QuitEvent e, QuitResponse r)
                 {
                   boolean confirmQuit = jalview.bin.Cache
-                          .getDefault(jalviewDesktop.CONFIRM_KEYBOARD_QUIT,
+                          .getDefault(
+                                  jalview.gui.Desktop.CONFIRM_KEYBOARD_QUIT,
                                   true);
                   int n;
                   if (confirmQuit)
@@ -134,12 +135,12 @@ public class APQHandlers
       {
         System.out.println(
                 "Exception when looking for About, Preferences, Quit Handlers");
-        e.printStackTrace();
+        // e.printStackTrace();
       } catch (Throwable t)
       {
         System.out.println(
                 "Throwable when looking for About, Preferences, Quit Handlers");
-        t.printStackTrace();
+        // t.printStackTrace();
       }
 
     }
index 41cbad8..0523d41 100644 (file)
@@ -366,12 +366,12 @@ public class Desktop extends jalview.jbgui.GDesktop
       APQHandlers.setAPQHandlers(this);
     } catch (Exception e)
     {
-      System.out.println("Exception when trying to set APQHandlers");
-      e.printStackTrace();
+      System.out.println("Cannot set APQHandlers");
+      // e.printStackTrace();
     } catch (Throwable t)
     {
-      System.out.println("Throwable when trying to set APQHandlers");
-      t.printStackTrace();
+      System.out.println("Cannot set APQHandlers");
+      // t.printStackTrace();
     }
 
 
@@ -1134,7 +1134,7 @@ public class Desktop extends jalview.jbgui.GDesktop
   {
     String fileFormat = Cache.getProperty("DEFAULT_FILE_FORMAT");
     JalviewFileChooser chooser = JalviewFileChooser
-            .forRead(Cache.getProperty("LAST_DIRECTORY"), fileFormat, true);
+            .forRead(Cache.getProperty("LAST_DIRECTORY"), fileFormat, BackupFiles.getEnabled());
 
     chooser.setFileView(new JalviewFileView());
     chooser.setDialogTitle(
@@ -1299,8 +1299,6 @@ public class Desktop extends jalview.jbgui.GDesktop
   @Override
   public void quit()
   {
-    //System.out.println("********** Desktop.quit()");
-    //System.out.println(savingFiles.toString());
     Dimension screen = Toolkit.getDefaultToolkit().getScreenSize();
     jalview.bin.Cache.setProperty("SCREENGEOMETRY_WIDTH",
             screen.width + "");
@@ -1763,7 +1761,7 @@ public class Desktop extends jalview.jbgui.GDesktop
         "Jalview Project (old)" };
     JalviewFileChooser chooser = new JalviewFileChooser(
             Cache.getProperty("LAST_DIRECTORY"), suffix, desc,
-            "Jalview Project", true, true); // last two booleans: allFiles,
+            "Jalview Project", true, BackupFiles.getEnabled()); // last two booleans: allFiles,
                                             // allowBackupFiles
     chooser.setFileView(new JalviewFileView());
     chooser.setDialogTitle(MessageManager.getString("label.restore_state"));
index a2194f4..7456e18 100644 (file)
@@ -22,6 +22,7 @@ package jalview.gui;
 
 import jalview.api.AlignmentViewPanel;
 import jalview.api.FeatureColourI;
+import jalview.bin.Cache;
 import jalview.datamodel.GraphLine;
 import jalview.datamodel.features.FeatureAttributes;
 import jalview.datamodel.features.FeatureAttributes.Datatype;
@@ -165,7 +166,7 @@ public class FeatureTypeSettings extends JalviewDialog
 
   private JPanel maxColour = new JPanel();
 
-  private JComboBox<String> threshold = new JComboBox<>();
+  private JComboBox<Object> threshold = new JComboBox<>();
 
   private JSlider slider = new JSlider();
 
@@ -182,17 +183,17 @@ public class FeatureTypeSettings extends JalviewDialog
   /*
    * choice of option for 'colour for no value'
    */
-  private JComboBox<String> noValueCombo;
+  private JComboBox<Object> noValueCombo;
 
   /*
    * choice of what to colour by text (Label or attribute)
    */
-  private JComboBox<String> colourByTextCombo;
+  private JComboBox<Object> colourByTextCombo;
 
   /*
    * choice of what to colour by range (Score or attribute)
    */
-  private JComboBox<String> colourByRangeCombo;
+  private JComboBox<Object> colourByRangeCombo;
 
   private JRadioButton andFilters;
 
@@ -1104,7 +1105,7 @@ public class FeatureTypeSettings extends JalviewDialog
    * @param withRange
    * @param withText
    */
-  protected JComboBox<String> populateAttributesDropdown(
+  protected JComboBox<Object> populateAttributesDropdown(
           List<String[]> attNames, boolean withRange, boolean withText)
   {
     List<String> displayAtts = new ArrayList<>();
@@ -1143,9 +1144,11 @@ public class FeatureTypeSettings extends JalviewDialog
       tooltips.add(desc == null ? "" : desc);
     }
 
-    JComboBox<String> attCombo = JvSwingUtils
-            .buildComboWithTooltips(displayAtts, tooltips);
-
+    // now convert String List to Object List for buildComboWithTooltips
+    List<Object> displayAttsObjects = new ArrayList<>(displayAtts);
+    JComboBox<Object> attCombo = JvSwingUtils
+            .buildComboWithTooltips(displayAttsObjects, tooltips);
+    
     return attCombo;
   }
 
@@ -1316,7 +1319,7 @@ public class FeatureTypeSettings extends JalviewDialog
      * drop-down choice of attribute, with description as a tooltip 
      * if we can obtain it
      */
-    final JComboBox<String> attCombo = populateAttributesDropdown(attNames,
+    final JComboBox<Object> attCombo = populateAttributesDropdown(attNames,
             true, true);
     String filterBy = setSelectedAttribute(attCombo, filter);
 
@@ -1444,7 +1447,7 @@ public class FeatureTypeSettings extends JalviewDialog
    * @param attCombo
    * @param filter
    */
-  private String setSelectedAttribute(JComboBox<String> attCombo,
+  private String setSelectedAttribute(JComboBox<Object> attCombo,
           FeatureMatcherI filter)
   {
     String item = null;
@@ -1661,11 +1664,19 @@ public class FeatureTypeSettings extends JalviewDialog
    * @param valueField
    * @param filterIndex
    */
-  protected boolean updateFilter(JComboBox<String> attCombo,
+  protected boolean updateFilter(JComboBox<Object> attCombo,
           JComboBox<Condition> condCombo, JTextField valueField,
           int filterIndex)
   {
-    String attName = (String) attCombo.getSelectedItem();
+    String attName;
+    try
+    {
+      attName = (String) attCombo.getSelectedItem();
+    } catch (Exception e)
+    {
+      Cache.log.error("Problem casting Combo box entry to String");
+      attName = attCombo.getSelectedItem().toString();
+    }
     Condition cond = (Condition) condCombo.getSelectedItem();
     String pattern = valueField.getText().trim();
 
index 4658668..d6090e2 100644 (file)
@@ -319,13 +319,13 @@ public final class JvSwingUtils
    * @param entries
    * @param tooltips
    */
-  public static JComboBox<String> buildComboWithTooltips(
-          List<String> entries, List<String> tooltips)
+  public static JComboBox<Object> buildComboWithTooltips(
+          List<Object> entries, List<String> tooltips)
   {
-    JComboBox<String> combo = new JComboBox<>();
+    JComboBox<Object> combo = new JComboBox<>();
     final ComboBoxTooltipRenderer renderer = new ComboBoxTooltipRenderer();
     combo.setRenderer(renderer);
-    for (String attName : entries)
+    for (Object attName : entries)
     {
       combo.addItem(attName);
     }
index ab09f74..9754e0d 100755 (executable)
@@ -25,6 +25,7 @@ import jalview.bin.Cache;
 import jalview.gui.Help.HelpId;
 import jalview.gui.StructureViewer.ViewerType;
 import jalview.io.BackupFiles;
+import jalview.io.BackupFilesPresetEntry;
 import jalview.io.FileFormatI;
 import jalview.io.JalviewFileChooser;
 import jalview.io.JalviewFileView;
@@ -805,22 +806,25 @@ public class Preferences extends GPreferences
     /*
      * Save Backups settings
      */
-    Cache.applicationProperties.setProperty(BackupFiles.CONFIRM_DELETE_OLD,
-            Boolean.toString(backupfilesConfirmDelete.isSelected()));
     Cache.applicationProperties.setProperty(BackupFiles.ENABLED,
             Boolean.toString(enableBackupFiles.isSelected()));
-    Cache.applicationProperties.setProperty(BackupFiles.NO_MAX,
-            Boolean.toString(backupfilesKeepAll.isSelected()));
-    Cache.applicationProperties.setProperty(BackupFiles.REVERSE_ORDER,
-            Boolean.toString(suffixReverse.isSelected()));
-    Cache.applicationProperties.setProperty(BackupFiles.SUFFIX,
-            suffixTemplate.getText());
-    Cache.applicationProperties.setProperty(BackupFiles.ROLL_MAX,
-            Integer.toString(getSpinnerInt(backupfilesRollMaxSpinner, 4)));
-    Cache.applicationProperties.setProperty(BackupFiles.SUFFIX_DIGITS,
-            Integer.toString(getSpinnerInt(suffixDigitsSpinner, 3)));
-    Cache.applicationProperties.setProperty(BackupFiles.NS+"_PRESET",
-            Integer.toString(getComboIntStringKey(backupfilesPresetsCombo)));
+    int preset = getComboIntStringKey(backupfilesPresetsCombo);
+    Cache.applicationProperties.setProperty(BackupFiles.NS + "_PRESET", Integer.toString(preset));
+
+    if (preset == BackupFilesPresetEntry.BACKUPFILESSCHEMECUSTOM)
+    {
+      BackupFilesPresetEntry customBFPE = getBackupfilesCurrentEntry();
+      BackupFilesPresetEntry.backupfilesPresetEntriesValues.put(
+              BackupFilesPresetEntry.BACKUPFILESSCHEMECUSTOM, customBFPE);
+      Cache.applicationProperties
+              .setProperty(BackupFilesPresetEntry.CUSTOMCONFIG,
+                      customBFPE.toString());
+    }
+
+    BackupFilesPresetEntry savedBFPE = BackupFilesPresetEntry.backupfilesPresetEntriesValues
+            .get(preset);
+    Cache.applicationProperties.setProperty(
+            BackupFilesPresetEntry.SAVEDCONFIG, savedBFPE.toString());
 
     Cache.saveProperties();
     Desktop.instance.doConfigureStructurePrefs();
index 4f93ece..1504404 100644 (file)
@@ -1,7 +1,5 @@
 package jalview.io;
 
-import jalview.bin.Cache;
-
 import java.io.File;
 
 public class BackupFilenameParts
@@ -113,7 +111,9 @@ public class BackupFilenameParts
           String filename, String base, boolean extensionMatch)
   {
     BackupFilenameParts bfp = new BackupFilenameParts();
-    String template = Cache.getDefault(BackupFiles.SUFFIX, null);
+    BackupFilesPresetEntry bfpe = BackupFilesPresetEntry
+            .getSavedBackupEntry();
+    String template = bfpe.suffix;
     if (template == null)
     {
       return bfp;
@@ -121,8 +121,7 @@ public class BackupFilenameParts
     int digits;
     try
     {
-      digits = Integer
-              .parseInt(Cache.getDefault(BackupFiles.SUFFIX_DIGITS, null));
+      digits = bfpe.digits;
     } catch (Exception e)
     {
       return bfp;
index dbda022..7bb5d31 100644 (file)
@@ -17,12 +17,8 @@ import java.util.TreeMap;
  * BackupFiles used for manipulating (naming rolling/deleting) backup/version files when an alignment or project file is saved.
  * User configurable options are:
  * BACKUPFILES_ENABLED - boolean flag as to whether to use this mechanism or act as before, including overwriting files as saved.
- * BACKUPFILES_SUFFIX - a template to insert after the file extension.  Use '%n' to be replaced by a 0-led SUFFIX_DIGITS long integer.
- * BACKUPFILES_NO_MAX - flag to turn off setting a maximum number of backup files to keep.
- * BACKUPFILES_ROLL_MAX - the maximum number of backupfiles to keep for any one alignment or project file.
- * BACKUPFILES_SUFFIX_DIGITS - the number of digits to insert replace %n with (e.g. BACKUPFILES_SUFFIX_DIGITS = 3 would make "001", "002", etc)
- * BACKUPFILES_REVERSE_ORDER - if true then "logfile" style numbering and file rolling will occur. If false then ever-increasing version numbering will occur, but old files will still be deleted if there are more than ROLL_MAX backup files. 
- * BACKUPFILES_CONFIRM_DELETE_OLD - if true then prompt/confirm with the user when deleting older backup/version files.
+ * The rest of the options are now saved as BACKUPFILES_PRESET, BACKUPFILES_SAVED and BACKUPFILES_CUSTOM
+ * (see BackupFilesPresetEntry)
  */
 
 public class BackupFiles
@@ -33,21 +29,8 @@ public class BackupFiles
 
   public static final String ENABLED = NS + "_ENABLED";
 
-  public static final String SUFFIX = NS + "_SUFFIX";
-
-  public static final String NO_MAX = NS + "_NO_MAX";
-
-  public static final String ROLL_MAX = NS + "_ROLL_MAX";
-
-  public static final String SUFFIX_DIGITS = NS + "_SUFFIX_DIGITS";
-
   public static final String NUM_PLACEHOLDER = "%n";
 
-  public static final String REVERSE_ORDER = NS + "_REVERSE_ORDER";
-
-  public static final String CONFIRM_DELETE_OLD = NS
-          + "_CONFIRM_DELETE_OLD";
-
   private static final String DEFAULT_TEMP_FILE = "jalview_temp_file_" + NS;
 
   private static final String TEMP_FILE_EXT = ".tmp";
@@ -101,20 +84,14 @@ public class BackupFiles
   // REVERSE_ORDER
   public BackupFiles(File file)
   {
-    this(file, ".bak" + NUM_PLACEHOLDER, false, 3, 3, false);
-  }
-
-  public BackupFiles(File file, String defaultSuffix, boolean defaultNoMax,
-          int defaultMax, int defaultDigits, boolean defaultReverseOrder)
-  {
     classInit();
     this.file = file;
-    this.suffix = Cache.getDefault(SUFFIX, defaultSuffix);
-    this.noMax = Cache.getDefault(NO_MAX, defaultNoMax);
-    this.max = Cache.getDefault(ROLL_MAX, defaultMax);
-    this.digits = Cache.getDefault(SUFFIX_DIGITS, defaultDigits);
-    this.reverseOrder = Cache.getDefault(REVERSE_ORDER,
-            defaultReverseOrder);
+    BackupFilesPresetEntry bfpe = BackupFilesPresetEntry.getSavedBackupEntry();
+    this.suffix = bfpe.suffix;
+    this.noMax = bfpe.keepAll;
+    this.max = bfpe.rollMax;
+    this.digits = bfpe.digits;
+    this.reverseOrder = bfpe.reverse;
 
     // create a temp file to save new data in
     File temp = null;
@@ -145,7 +122,9 @@ public class BackupFiles
   public static void classInit()
   {
     setEnabled(Cache.getDefault(ENABLED, true));
-    setConfirmDelete(Cache.getDefault(CONFIRM_DELETE_OLD, true));
+    BackupFilesPresetEntry bfpe = BackupFilesPresetEntry
+            .getSavedBackupEntry();
+    setConfirmDelete(bfpe.confirmDelete);
   }
 
   public static void setEnabled(boolean flag)
diff --git a/src/jalview/io/BackupFilesPresetEntry.java b/src/jalview/io/BackupFilesPresetEntry.java
new file mode 100644 (file)
index 0000000..4face29
--- /dev/null
@@ -0,0 +1,173 @@
+package jalview.io;
+
+import jalview.bin.Cache;
+import jalview.util.MessageManager;
+
+import java.util.HashMap;
+import java.util.Map;
+import java.util.StringTokenizer;
+
+public class BackupFilesPresetEntry
+{
+
+  public String suffix;
+
+  public static final int DIGITSMIN = 1;
+
+  public static final int DIGITSMAX = 6;
+
+  public int digits;
+
+  public boolean reverse;
+
+  public boolean keepAll;
+
+  public static final int ROLLMAXMIN = 1;
+
+  public static final int ROLLMAXMAX = 999;
+
+  public int rollMax;
+
+  public boolean confirmDelete;
+
+  public static final String SAVEDCONFIG = BackupFiles.NS + "_SAVED";
+
+  public static final String CUSTOMCONFIG = BackupFiles.NS + "_CUSTOM";
+
+  private static final String stringDelim = "\t";
+
+  public static final int BACKUPFILESSCHEMECUSTOM = 0;
+
+  public static final int BACKUPFILESSCHEMEDEFAULT = 1;
+
+  public BackupFilesPresetEntry(String suffix, int digits, boolean reverse,
+          boolean keepAll, int rollMax, boolean confirmDelete)
+  {
+    this.suffix = suffix == null ? "" : suffix;
+    this.digits = digits < DIGITSMIN ? DIGITSMIN
+            : (digits > DIGITSMAX ? DIGITSMAX : digits);
+    this.reverse = reverse;
+    this.keepAll = keepAll;
+    this.rollMax = rollMax < ROLLMAXMIN ? ROLLMAXMIN
+            : (rollMax > ROLLMAXMAX ? ROLLMAXMAX : rollMax);
+    this.confirmDelete = confirmDelete;
+  }
+
+  public boolean equals(BackupFilesPresetEntry compare)
+  {
+    return suffix.equals(compare.suffix) && digits == compare.digits
+            && reverse == compare.reverse && keepAll == compare.keepAll
+            && rollMax == compare.rollMax
+            && confirmDelete == compare.confirmDelete;
+  }
+
+  @Override
+  public String toString()
+  {
+    StringBuilder sb = new StringBuilder();
+    sb.append(suffix);
+    sb.append(stringDelim);
+    sb.append(digits);
+    sb.append(stringDelim);
+    sb.append(reverse);
+    sb.append(stringDelim);
+    sb.append(keepAll);
+    sb.append(stringDelim);
+    sb.append(rollMax);
+    sb.append(stringDelim);
+    sb.append(confirmDelete);
+    return sb.toString();
+  }
+
+  public static BackupFilesPresetEntry createBackupFilesPresetEntry(
+          String line)
+  {
+    if (line == null)
+    {
+      return null;
+    }
+    StringTokenizer st = new StringTokenizer(line, stringDelim);
+    String suffix = null;
+    int digits = 0;
+    boolean reverse = false;
+    boolean keepAll = false;
+    int rollMax = 0;
+    boolean confirmDelete = false;
+
+    try
+    {
+      suffix = st.nextToken();
+      digits = Integer.valueOf(st.nextToken());
+      reverse = Boolean.valueOf(st.nextToken());
+      keepAll = Boolean.valueOf(st.nextToken());
+      rollMax = Integer.valueOf(st.nextToken());
+      confirmDelete = Boolean.valueOf(st.nextToken());
+    } catch (Exception e)
+    {
+      Cache.log.error("Error parsing backupfiles scheme '" + line + "'");
+    }
+
+    return new BackupFilesPresetEntry(suffix, digits, reverse, keepAll,
+            rollMax, confirmDelete);
+  }
+
+  public static BackupFilesPresetEntry getSavedBackupEntry()
+  {
+    String savedPresetString = Cache
+            .getDefault(BackupFilesPresetEntry.SAVEDCONFIG, null);
+    BackupFilesPresetEntry savedPreset = BackupFilesPresetEntry
+            .createBackupFilesPresetEntry(savedPresetString);
+    if (savedPreset == null)
+    {
+      savedPreset = backupfilesPresetEntriesValues
+              .get(BACKUPFILESSCHEMEDEFAULT);
+    }
+    return savedPreset;
+  }
+
+  public static final IntKeyStringValueEntry[] backupfilesPresetEntries = {
+      new IntKeyStringValueEntry(BACKUPFILESSCHEMEDEFAULT,
+              MessageManager.getString("label.default")),
+      new IntKeyStringValueEntry(2,
+              MessageManager.getString("label.single_file")),
+      new IntKeyStringValueEntry(3,
+              MessageManager.getString("label.keep_all_versions")),
+      new IntKeyStringValueEntry(4,
+              MessageManager.getString("label.rolled_backups")),
+      // ...
+      // IMPORTANT, keep "Custom" entry with key 0 (even though it appears last)
+      new IntKeyStringValueEntry(BACKUPFILESSCHEMECUSTOM,
+              MessageManager.getString("label.custom")) };
+
+  public static final String[] backupfilesPresetEntryDescriptions = {
+      MessageManager.getString("label.default_description"),
+      MessageManager.getString("label.single_file_description"),
+      MessageManager.getString("label.keep_all_versions_description"),
+      MessageManager.getString("label.rolled_backups_description"),
+      MessageManager.getString("label.custom_description") };
+
+  public static final Map<Integer, BackupFilesPresetEntry> backupfilesPresetEntriesValues = new HashMap<Integer, BackupFilesPresetEntry>()
+  {
+    /**
+     * 
+     */
+    private static final long serialVersionUID = 125L;
+
+    {
+      put(1, new BackupFilesPresetEntry(
+              ".bak" + BackupFiles.NUM_PLACEHOLDER, 3, false, false, 3,
+              false));
+      put(2, new BackupFilesPresetEntry("~", 1, false, false, 1, false));
+      put(3, new BackupFilesPresetEntry(".v" + BackupFiles.NUM_PLACEHOLDER,
+              3, false, true, 10, true));
+      put(4, new BackupFilesPresetEntry(
+              "_bak." + BackupFiles.NUM_PLACEHOLDER, 1, true, false, 9,
+              false));
+
+      // This gets replaced by GPreferences
+      put(BACKUPFILESSCHEMECUSTOM,
+              new BackupFilesPresetEntry("", 0, false, false, 0, false));
+    }
+  };
+
+}
diff --git a/src/jalview/io/IntKeyStringValueEntry.java b/src/jalview/io/IntKeyStringValueEntry.java
new file mode 100644 (file)
index 0000000..084dbc5
--- /dev/null
@@ -0,0 +1,21 @@
+package jalview.io;
+
+public class IntKeyStringValueEntry
+{
+  public final int k;
+
+  public final String v;
+
+  public IntKeyStringValueEntry(int k, String v)
+  {
+    this.k = k;
+    this.v = v;
+  }
+
+  @Override
+  public String toString()
+  {
+    return v;
+  }
+
+}
index fe85043..f30fa9b 100755 (executable)
@@ -435,7 +435,7 @@ public class GDesktop extends JFrame
     FileMenu.add(inputMenu);
     FileMenu.add(inputSequence);
     FileMenu.addSeparator();
-    FileMenu.add(saveState);
+    //FileMenu.add(saveState);
     FileMenu.add(saveAsState);
     FileMenu.add(loadState);
     FileMenu.addSeparator();
index 87cc87b..60bf1b7 100755 (executable)
@@ -31,6 +31,8 @@ import jalview.gui.JvSwingUtils;
 import jalview.gui.StructureViewer.ViewerType;
 import jalview.io.BackupFilenameParts;
 import jalview.io.BackupFiles;
+import jalview.io.BackupFilesPresetEntry;
+import jalview.io.IntKeyStringValueEntry;
 import jalview.util.MessageManager;
 
 import java.awt.BorderLayout;
@@ -51,8 +53,8 @@ import java.awt.event.KeyEvent;
 import java.awt.event.KeyListener;
 import java.awt.event.MouseAdapter;
 import java.awt.event.MouseEvent;
-import java.util.HashMap;
-import java.util.Map;
+import java.util.Arrays;
+import java.util.List;
 
 import javax.swing.AbstractCellEditor;
 import javax.swing.BorderFactory;
@@ -63,7 +65,6 @@ import javax.swing.JCheckBox;
 import javax.swing.JComboBox;
 import javax.swing.JFileChooser;
 import javax.swing.JLabel;
-import javax.swing.JList;
 import javax.swing.JPanel;
 import javax.swing.JRadioButton;
 import javax.swing.JScrollPane;
@@ -296,9 +297,15 @@ public class GPreferences extends JPanel
 
   protected JPanel presetsPanel = new JPanel();
 
+  protected JLabel presetsComboLabel = new JLabel();
+
+  protected JCheckBox customiseCheckbox = new JCheckBox();
+
   protected JButton revertButton = new JButton();
 
-  protected JComboBox<IntKeyStringValueEntry> backupfilesPresetsCombo = new JComboBox<>();
+  protected JComboBox<Object> backupfilesPresetsCombo = new JComboBox<>();
+
+  private int backupfilesPresetsComboLastSelected = 0;
 
   protected JPanel suffixPanel = new JPanel();
 
@@ -1695,22 +1702,28 @@ public class GPreferences extends JPanel
 
   protected void loadLastSavedBackupsOptions()
   {
+    BackupFilesPresetEntry savedPreset = BackupFilesPresetEntry
+            .getSavedBackupEntry();
     enableBackupFiles
             .setSelected(Cache.getDefault(BackupFiles.ENABLED, true));
+
+    BackupFilesPresetEntry backupfilesCustomEntry = BackupFilesPresetEntry
+            .createBackupFilesPresetEntry(Cache
+                    .getDefault(BackupFilesPresetEntry.CUSTOMCONFIG, null));
+    if (backupfilesCustomEntry == null)
+    {
+      backupfilesCustomEntry = BackupFilesPresetEntry.backupfilesPresetEntriesValues
+              .get(BackupFilesPresetEntry.BACKUPFILESSCHEMEDEFAULT);
+    }
+    BackupFilesPresetEntry.backupfilesPresetEntriesValues.put(
+            BackupFilesPresetEntry.BACKUPFILESSCHEMECUSTOM,
+            backupfilesCustomEntry);
+
     setComboIntStringKey(backupfilesPresetsCombo,
-            Cache.getDefault(BackupFiles.NS + "_PRESET", 1));
-    suffixTemplate.setText(Cache.getDefault(BackupFiles.SUFFIX,
-            ".bak" + BackupFiles.NUM_PLACEHOLDER));
-    suffixDigitsSpinner
-            .setValue(Cache.getDefault(BackupFiles.SUFFIX_DIGITS, 3));
-    suffixReverse.setSelected(
-            Cache.getDefault(BackupFiles.REVERSE_ORDER, false));
-    backupfilesKeepAll
-            .setSelected(Cache.getDefault(BackupFiles.NO_MAX, false));
-    backupfilesRollMaxSpinner
-            .setValue(Cache.getDefault(BackupFiles.ROLL_MAX, 3));
-    backupfilesConfirmDelete.setSelected(
-            Cache.getDefault(BackupFiles.CONFIRM_DELETE_OLD, true));
+            Cache.getDefault(BackupFiles.NS + "_PRESET",
+                    BackupFilesPresetEntry.BACKUPFILESSCHEMEDEFAULT));
+
+    backupsSetOptions(savedPreset);
 
     backupsOptionsSetEnabled();
     updateBackupFilesExampleLabel();
@@ -1718,11 +1731,11 @@ public class GPreferences extends JPanel
 
   private boolean warnAboutSuffixReverseChange()
   {
-    boolean savedSuffixReverse = Cache.getDefault(BackupFiles.REVERSE_ORDER,
-            false);
-    int savedSuffixDigits = Cache.getDefault(BackupFiles.SUFFIX_DIGITS, 3);
-    String savedSuffixTemplate = Cache.getDefault(BackupFiles.SUFFIX,
-            ".bak" + BackupFiles.NUM_PLACEHOLDER);
+    BackupFilesPresetEntry bfpe = BackupFilesPresetEntry
+            .getSavedBackupEntry();
+    boolean savedSuffixReverse = bfpe.reverse;
+    int savedSuffixDigits = bfpe.digits;
+    String savedSuffixTemplate = bfpe.suffix;
 
     boolean nowSuffixReverse = suffixReverse.isSelected();
     int nowSuffixDigits = getSpinnerInt(suffixDigitsSpinner, 3);
@@ -1799,7 +1812,6 @@ public class GPreferences extends JPanel
     gbc.gridy++; // row 1
     backupsTab.add(presetsPanel, gbc);
 
-    // gbc.anchor = GridBagConstraints.NORTHWEST;
     // now using whole row
     gbc.gridwidth = 2;
     gbc.gridheight = 1;
@@ -1821,50 +1833,10 @@ public class GPreferences extends JPanel
     return backupsTab;
   }
 
-  protected static final int BACKUPFILESSCHEMECUSTOMISE = 0;
-
-  private static final IntKeyStringValueEntry[] backupfilesPresetEntries = {
-      new IntKeyStringValueEntry(1,
-              MessageManager.getString("label.default")),
-      new IntKeyStringValueEntry(2,
-              MessageManager.getString("label.single_file")),
-      new IntKeyStringValueEntry(3,
-              MessageManager.getString("label.keep_all_versions")),
-      new IntKeyStringValueEntry(4,
-              MessageManager.getString("label.rolled_backups")),
-      // ...
-      // IMPORTANT, keep "Custom" entry with key 0 (even though it appears last)
-      new IntKeyStringValueEntry(BACKUPFILESSCHEMECUSTOMISE,
-              MessageManager.getString("label.customise")) };
-
-  private static final Map<Integer, BackupFilesPresetEntry> backupfilesPresetEntriesValues = new HashMap<Integer, BackupFilesPresetEntry>()
-  {
-    /**
-     * 
-     */
-    private static final long serialVersionUID = 125L;
-
-    {
-      put(1, new BackupFilesPresetEntry(
-              ".bak" + BackupFiles.NUM_PLACEHOLDER, 3, false, false, 3,
-              false));
-      put(2, new BackupFilesPresetEntry("~", 1, false, false, 1, false));
-      put(3, new BackupFilesPresetEntry(".v" + BackupFiles.NUM_PLACEHOLDER,
-              3, false, true, 10, true));
-      put(4, new BackupFilesPresetEntry(
-              "_bak." + BackupFiles.NUM_PLACEHOLDER, 1, true, false, 9,
-              false));
-    }
-  };
-
   private JPanel initBackupsTabPresetsPanel()
   {
 
     String title = MessageManager.getString("label.schemes");
-    // TitledBorder tb = new TitledBorder(new EmptyBorder(0, 0, 0, 0), title);
-    // TitledBorder tb = new TitledBorder(title);
-    // tb.setTitleFont(LABEL_FONT);
-    // presetsPanel.setBorder(tb);
 
     presetsPanel.setLayout(new GridBagLayout());
 
@@ -1879,24 +1851,53 @@ public class GPreferences extends JPanel
     // "Scheme: "
     gbc.gridx = 0;
     gbc.gridy = 0;
-    presetsPanel.add(new JLabel(title + ":"), gbc);
 
-    for (int i = 0; i < backupfilesPresetEntries.length; i++)
+    presetsComboLabel = new JLabel(title + ":");
+    presetsPanel.add(presetsComboLabel, gbc);
+
+    List<Object> entries = Arrays
+            .asList((Object[]) BackupFilesPresetEntry.backupfilesPresetEntries);
+    List<String> tooltips = Arrays.asList(
+            BackupFilesPresetEntry.backupfilesPresetEntryDescriptions);
+    backupfilesPresetsCombo = JvSwingUtils.buildComboWithTooltips(entries,
+            tooltips);
+    /*
+    for (int i = 0; i < BackupFilesPresetEntry.backupfilesPresetEntries.length; i++)
     {
-      backupfilesPresetsCombo.addItem(backupfilesPresetEntries[i]);
+      backupfilesPresetsCombo
+              .addItem(BackupFilesPresetEntry.backupfilesPresetEntries[i]);
     }
+    */
 
-    // put "Previously saved scheme" item in italics (it's not really
-    // selectable, as such -- it deselects itself when selected) and
-    // "Customise" in bold
-    backupfilesPresetsCombo
-            .setRenderer(new BackupFilesPresetsComboBoxRenderer());
     backupfilesPresetsCombo.addActionListener(new ActionListener()
     {
       @Override
       public void actionPerformed(ActionEvent e)
       {
-        backupsTabUpdatePresets();
+        int key = getComboIntStringKey(backupfilesPresetsCombo);
+        if (!customiseCheckbox.isSelected())
+        {
+          backupfilesPresetsComboLastSelected = key;
+        }
+        if (key == BackupFilesPresetEntry.BACKUPFILESSCHEMECUSTOM)
+        {
+          if (customiseCheckbox.isSelected())
+          {
+            // got here by clicking on customiseCheckbox so don't change the values
+            backupfilesCustomOptionsSetEnabled();
+          }
+          else
+          {
+            backupsTabUpdatePresets();
+            backupfilesCustomOptionsSetEnabled();
+          }
+        }
+        else
+        {
+          customiseCheckbox.setSelected(false);
+          backupsTabUpdatePresets();
+          backupfilesCustomOptionsSetEnabled();
+        }
       }
     });
 
@@ -1905,20 +1906,55 @@ public class GPreferences extends JPanel
     presetsPanel.add(backupfilesPresetsCombo, gbc);
 
     revertButton.setText(MessageManager.getString("label.cancel_changes"));
+    revertButton.setToolTipText(
+            MessageManager.getString("label.cancel_changes_description"));
     revertButton.addActionListener(new ActionListener()
     {
       @Override
       public void actionPerformed(ActionEvent e)
       {
-        loadLastSavedBackupsOptions();
+        backupsSetOptions(
+                BackupFilesPresetEntry.backupfilesPresetEntriesValues.get(
+                        BackupFilesPresetEntry.BACKUPFILESSCHEMECUSTOM));
+        backupfilesCustomOptionsSetEnabled();
       }
 
     });
     revertButton.setFont(LABEL_FONT);
 
+    customiseCheckbox.setFont(LABEL_FONT);
+    customiseCheckbox.setText(MessageManager.getString("label.customise"));
+    customiseCheckbox.addActionListener(new ActionListener()
+    {
+      @Override
+      public void actionPerformed(ActionEvent e)
+      {
+        int currently = getComboIntStringKey(backupfilesPresetsCombo);
+        if (customiseCheckbox.isSelected())
+        {
+          backupfilesPresetsComboLastSelected = currently;
+          setComboIntStringKey(backupfilesPresetsCombo,
+                  BackupFilesPresetEntry.BACKUPFILESSCHEMECUSTOM);
+        }
+        else
+        {
+          setComboIntStringKey(backupfilesPresetsCombo,
+                  backupfilesPresetsComboLastSelected);
+
+        }
+        backupfilesCustomOptionsSetEnabled();
+      }
+    });
+    customiseCheckbox.setToolTipText(
+            MessageManager.getString("label.customise_description"));
+
+    // customise checkbox
+    gbc.gridx = 0;
+    gbc.gridy++;
+    presetsPanel.add(customiseCheckbox, gbc);
+
     // "Cancel changes" button (aligned with combo box above)
     gbc.gridx = 1;
-    gbc.gridy++;
     presetsPanel.add(revertButton, gbc);
 
     return presetsPanel;
@@ -1927,7 +1963,7 @@ public class GPreferences extends JPanel
   private JPanel initBackupsTabFilenameExamplesPanel()
   {
     String title = MessageManager
-            .getString("label.summary_of_backups_scheme");
+            .getString("label.scheme_examples");
     TitledBorder tb = new TitledBorder(title);
     exampleFilesPanel.setBorder(tb);
     exampleFilesPanel.setLayout(new GridBagLayout());
@@ -1953,45 +1989,68 @@ public class GPreferences extends JPanel
   {
     IntKeyStringValueEntry entry = (IntKeyStringValueEntry) backupfilesPresetsCombo
             .getSelectedItem();
-    int key = entry.getKey();
-    String value = entry.getValue();
+    int key = entry.k;
+    String value = entry.v;
 
-    // BACKUPFILESSCHEMECUSTOMISE (==0) reserved for "Custom"
-    if (key != BACKUPFILESSCHEMECUSTOMISE)
+    if (BackupFilesPresetEntry.backupfilesPresetEntriesValues
+            .containsKey(key))
     {
-      if (backupfilesPresetEntriesValues.containsKey(key))
-      {
-        backupsSetOptions(backupfilesPresetEntriesValues.get(key));
-      }
-      else
-      {
-        System.out.println("Preset '" + value + "' not implemented");
-      }
+      backupsSetOptions(
+              BackupFilesPresetEntry.backupfilesPresetEntriesValues
+                      .get(key));
+    }
+    else
+    {
+      Cache.log.error(
+              "Preset '" + value + "' [key:" + key + "] not implemented");
     }
 
-    backupfilesCustomOptionsSetEnabled();
+    // Custom options will now be enabled when the customiseCheckbox is checked
+    // (performed above)
+    // backupfilesCustomOptionsSetEnabled();
     updateBackupFilesExampleLabel();
   }
 
-  protected int getComboIntStringKey(JComboBox<IntKeyStringValueEntry> c)
+  protected int getComboIntStringKey(
+          JComboBox<Object> backupfilesPresetsCombo2)
   {
-    IntKeyStringValueEntry e = (IntKeyStringValueEntry) c.getSelectedItem();
-    return e != null ? e.getKey() : 0;
+    IntKeyStringValueEntry e;
+    try
+    {
+      e = (IntKeyStringValueEntry) backupfilesPresetsCombo2
+              .getSelectedItem();
+    } catch (Exception ex)
+    {
+      Cache.log.error(
+              "Problem casting Combo entry to IntKeyStringValueEntry.");
+      e = null;
+    }
+    return e != null ? e.k : 0;
   }
 
-  protected void setComboIntStringKey(JComboBox<IntKeyStringValueEntry> c,
+  protected void setComboIntStringKey(
+          JComboBox<Object> backupfilesPresetsCombo2,
           int key)
   {
-    for (int i = 0; i < c.getItemCount(); i++)
+    for (int i = 0; i < backupfilesPresetsCombo2.getItemCount(); i++)
     {
-      IntKeyStringValueEntry e = c.getItemAt(i);
-      if (e.getKey() == key)
+      IntKeyStringValueEntry e;
+      try
       {
-        c.setSelectedIndex(i);
+        e = (IntKeyStringValueEntry) backupfilesPresetsCombo2.getItemAt(i);
+      } catch (Exception ex)
+      {
+        Cache.log.error(
+                "Problem casting Combo entry to IntKeyStringValueEntry. Skipping item. ");
+        continue;
+      }
+      if (e.k == key)
+      {
+        backupfilesPresetsCombo2.setSelectedIndex(i);
         break;
       }
     }
-    backupsTabUpdatePresets();
+    // backupsTabUpdatePresets();
   }
 
   private JPanel initBackupsTabSuffixPanel()
@@ -2015,16 +2074,18 @@ public class GPreferences extends JPanel
       {
         updateBackupFilesExampleLabel();
         backupfilesCustomOptionsSetEnabled();
+        backupfilesRevertButtonSetEnabled(true);
       }
 
     });
-    KeyListener kl = new KeyListener()
+    suffixTemplate.addKeyListener(new KeyListener()
     {
       @Override
       public void keyReleased(KeyEvent e)
       {
         updateBackupFilesExampleLabel();
         backupfilesCustomOptionsSetEnabled();
+        backupfilesRevertButtonSetEnabled(true);
       }
 
       @Override
@@ -2044,26 +2105,25 @@ public class GPreferences extends JPanel
         }
       }
 
-    };
-    suffixTemplate.addKeyListener(kl);
+    });
 
     // digits spinner
     suffixDigitsLabel
             .setText(MessageManager.getString("label.index_digits"));
     suffixDigitsLabel.setHorizontalAlignment(SwingConstants.LEFT);
     suffixDigitsLabel.setFont(LABEL_FONT);
-    int defaultmin = 1;
-    int defaultmax = 6;
     ChangeListener c = new ChangeListener()
     {
       @Override
       public void stateChanged(ChangeEvent e)
       {
+        backupfilesRevertButtonSetEnabled(true);
         updateBackupFilesExampleLabel();
       }
 
     };
-    setIntegerSpinner(suffixDigitsSpinner, defaultmin, defaultmax, 3, c);
+    setIntegerSpinner(suffixDigitsSpinner, BackupFilesPresetEntry.DIGITSMIN,
+            BackupFilesPresetEntry.DIGITSMAX, 3, c);
 
     suffixReverse.setLabels(MessageManager.getString("label.reverse_roll"),
             MessageManager.getString("label.increment_index"));
@@ -2080,12 +2140,13 @@ public class GPreferences extends JPanel
         }
         if (okay)
         {
+          backupfilesRevertButtonSetEnabled(true);
           updateBackupFilesExampleLabel();
         }
         else
         {
-          boolean savedSuffixReverse = Cache
-                  .getDefault(BackupFiles.REVERSE_ORDER, false);
+          boolean savedSuffixReverse = BackupFilesPresetEntry
+                  .getSavedBackupEntry().reverse;
           suffixReverse.setSelected(savedSuffixReverse);
         }
       }
@@ -2161,6 +2222,7 @@ public class GPreferences extends JPanel
       @Override
       public void actionPerformed(ActionEvent e)
       {
+        backupfilesRevertButtonSetEnabled(true);
         updateBackupFilesExampleLabel();
       }
     });
@@ -2169,6 +2231,7 @@ public class GPreferences extends JPanel
       @Override
       public void actionPerformed(ActionEvent e)
       {
+        backupfilesRevertButtonSetEnabled(true);
         keepRollMaxOptionsEnabled();
         updateBackupFilesExampleLabel();
       }
@@ -2179,15 +2242,26 @@ public class GPreferences extends JPanel
       @Override
       public void stateChanged(ChangeEvent e)
       {
+        backupfilesRevertButtonSetEnabled(true);
         updateBackupFilesExampleLabel();
       }
 
     };
-    setIntegerSpinner(backupfilesRollMaxSpinner, 1, 999, 4, true, c);
+    setIntegerSpinner(backupfilesRollMaxSpinner,
+            BackupFilesPresetEntry.ROLLMAXMIN,
+            BackupFilesPresetEntry.ROLLMAXMAX, 4, true, c);
 
     backupfilesConfirmDelete.setLabels(
             MessageManager.getString("label.always_ask"),
             MessageManager.getString("label.auto_delete"));
+    backupfilesConfirmDelete.addActionListener(new ActionListener()
+    {
+      @Override
+      public void actionPerformed(ActionEvent e)
+      {
+        backupfilesRevertButtonSetEnabled(true);
+      }
+    });
     // update the enabled section
     keepRollMaxOptionsEnabled();
 
@@ -2223,13 +2297,6 @@ public class GPreferences extends JPanel
     kgbc.gridwidth = GridBagConstraints.REMAINDER;
     kgbc.fill = GridBagConstraints.HORIZONTAL;
     kgbc.weightx = 1.0;
-    /*
-    keepfilesPanel.add(backupfilesConfirmDelete.getTrueButton(), kgbc);
-    
-    // fourth row (indented)
-    kgbc.gridy = 3;
-    keepfilesPanel.add(backupfilesConfirmDelete.getFalseButton(), kgbc);
-    */
 
     JPanel jp = new JPanel();
     jp.setLayout(new FlowLayout());
@@ -2285,6 +2352,7 @@ public class GPreferences extends JPanel
     int uppersurround = 0;
     StringBuilder exampleSB = new StringBuilder();
     boolean firstLine = true;
+    int lineNumber = 0;
     if (reverse)
     {
 
@@ -2295,6 +2363,7 @@ public class GPreferences extends JPanel
         if (index == min + lowersurround && index < max - uppersurround - 1)
         {
           exampleSB.append("\n...");
+          lineNumber++;
         }
         else if (index > min + lowersurround && index < max - uppersurround)
         {
@@ -2309,6 +2378,7 @@ public class GPreferences extends JPanel
           else
           {
             exampleSB.append("\n");
+            lineNumber++;
           }
           exampleSB.append(BackupFilenameParts.getBackupFilename(index,
                   base, suffix, digits));
@@ -2348,6 +2418,7 @@ public class GPreferences extends JPanel
         if (index == min + lowersurround && index < max - uppersurround - 1)
         {
           exampleSB.append("\n...");
+          lineNumber++;
         }
         else if (index > min + lowersurround && index < max - uppersurround)
         {
@@ -2362,6 +2433,7 @@ public class GPreferences extends JPanel
           else
           {
             exampleSB.append("\n");
+            lineNumber++;
           }
           exampleSB.append(BackupFilenameParts.getBackupFilename(index,
                   base, suffix, digits));
@@ -2390,6 +2462,18 @@ public class GPreferences extends JPanel
 
     }
 
+    // add some extra empty lines to pad out the example files box. ugh, please tell
+    // me how to do this better
+    int remainingLines = lowersurround + uppersurround + 1 - lineNumber;
+    if (remainingLines > 0)
+    {
+      for (int i = 0; i < remainingLines; i++)
+      {
+        exampleSB.append("\n ");
+        lineNumber++;
+      }
+    }
+
     backupfilesExampleLabel.setText(exampleSB.toString());
   }
 
@@ -2404,7 +2488,7 @@ public class GPreferences extends JPanel
         i = Integer.parseInt((String) s.getValue());
       } catch (Exception e)
       {
-        System.out.println(
+        Cache.log.error(
                 "Exception casting the initial value of s.getValue()");
       }
     }
@@ -2436,7 +2520,7 @@ public class GPreferences extends JPanel
       i = (Integer) s.getValue();
     } catch (Exception e)
     {
-      System.out.println("Failed casting (Integer) JSpinner s.getValue()");
+      Cache.log.error("Failed casting (Integer) JSpinner s.getValue()");
     }
     return i;
   }
@@ -2453,7 +2537,7 @@ public class GPreferences extends JPanel
   private void backupfilesKeepAllSetEnabled(boolean tryEnabled)
   {
     boolean enabled = tryEnabled && enableBackupFiles.isSelected()
-            && getComboIntStringKey(backupfilesPresetsCombo) == 0
+            && customiseCheckbox.isSelected()
             && suffixTemplate.getText()
                     .indexOf(BackupFiles.NUM_PLACEHOLDER) > -1;
     keepfilesPanel.setEnabled(enabled);
@@ -2474,18 +2558,48 @@ public class GPreferences extends JPanel
   private void backupfilesSuffixTemplateSetEnabled(boolean tryEnabled)
   {
     boolean enabled = tryEnabled && enableBackupFiles.isSelected()
-            && getComboIntStringKey(backupfilesPresetsCombo) == 0;
+            && customiseCheckbox.isSelected();
     suffixPanel.setEnabled(enabled);
     suffixTemplateLabel.setEnabled(enabled);
     suffixTemplate.setEnabled(enabled);
     backupfilesSuffixTemplateDigitsSetEnabled();
   }
 
+  private void backupfilesRevertButtonSetEnabled(boolean tryEnabled)
+  {
+    boolean enabled = tryEnabled && enableBackupFiles.isSelected()
+            && customiseCheckbox.isSelected() && backupfilesCustomChanged();
+    revertButton.setEnabled(enabled);
+  }
+
+  private boolean backupfilesCustomChanged()
+  {
+    BackupFilesPresetEntry custom = BackupFilesPresetEntry.backupfilesPresetEntriesValues
+            .get(BackupFilesPresetEntry.BACKUPFILESSCHEMECUSTOM);
+    BackupFilesPresetEntry current = getBackupfilesCurrentEntry();
+    return !custom.equals(current);
+  }
+
+  protected BackupFilesPresetEntry getBackupfilesCurrentEntry()
+  {
+    String suffix = suffixTemplate.getText();
+    int digits = getSpinnerInt(suffixDigitsSpinner, 3);
+    boolean reverse = suffixReverse.isSelected();
+    boolean keepAll = backupfilesKeepAll.isSelected();
+    int rollMax = getSpinnerInt(backupfilesRollMaxSpinner, 3);
+    boolean confirmDelete = backupfilesConfirmDelete.isSelected();
+
+    BackupFilesPresetEntry bfpe = new BackupFilesPresetEntry(suffix, digits,
+            reverse, keepAll, rollMax, confirmDelete);
+
+    return bfpe;
+  }
+
   protected void backupfilesCustomOptionsSetEnabled()
   {
-    int scheme = getComboIntStringKey(backupfilesPresetsCombo);
-    boolean enabled = scheme == 0 && enableBackupFiles.isSelected();
+    boolean enabled = customiseCheckbox.isSelected();
 
+    backupfilesRevertButtonSetEnabled(enabled);
     backupfilesSuffixTemplateSetEnabled(enabled);
     backupfilesKeepAllSetEnabled(enabled);
   }
@@ -2501,7 +2615,10 @@ public class GPreferences extends JPanel
   {
     boolean enabled = enableBackupFiles.isSelected();
     presetsPanel.setEnabled(enabled);
+    presetsComboLabel.setEnabled(enabled);
     backupfilesPresetsCombo.setEnabled(enabled);
+    customiseCheckbox.setEnabled(enabled);
+    revertButton.setEnabled(enabled);
   }
 
   protected void backupsOptionsSetEnabled()
@@ -2715,85 +2832,3 @@ public class GPreferences extends JPanel
   }
 }
 
-class IntKeyStringValueEntry
-{
-  int k;
-
-  String v;
-
-  public IntKeyStringValueEntry(int k, String v)
-  {
-    this.k = k;
-    this.v = v;
-  }
-
-  @Override
-  public String toString()
-  {
-    return this.getValue();
-  }
-
-  public int getKey()
-  {
-    return k;
-  }
-
-  public String getValue()
-  {
-    return v;
-  }
-}
-
-class BackupFilesPresetEntry
-{
-  String suffix;
-
-  int digits;
-
-  boolean reverse;
-
-  boolean keepAll;
-
-  int rollMax;
-
-  boolean confirmDelete;
-
-  public BackupFilesPresetEntry(String suffix, int digits, boolean reverse,
-          boolean keepAll, int rollMax, boolean confirmDelete)
-  {
-    this.suffix = suffix;
-    this.digits = digits;
-    this.reverse = reverse;
-    this.keepAll = keepAll;
-    this.rollMax = rollMax;
-    this.confirmDelete = confirmDelete;
-  }
-}
-
-class BackupFilesPresetsComboBoxRenderer extends DefaultListCellRenderer
-{
-  /**
-   * 
-   */
-  private static final long serialVersionUID = 88L;
-
-  @Override
-  public Component getListCellRendererComponent(JList list, Object value,
-          int index, boolean isSelected, boolean cellHasFocus)
-  {
-    super.getListCellRendererComponent(list, value, index, isSelected, cellHasFocus);
-    
-    try {
-      IntKeyStringValueEntry e = (IntKeyStringValueEntry) value;
-      if (e.getKey() == GPreferences.BACKUPFILESSCHEMECUSTOMISE)
-      {
-        // "Customise" item
-        this.setFont(this.getFont().deriveFont(Font.BOLD));
-      }
-    } catch (Exception e) {
-      return this;
-    }
-
-    return this;
-  }
-}
index 723279d..64cf902 100644 (file)
@@ -34,7 +34,8 @@ public class BackupFilesTest
   }
 
   private static boolean actuallyDeleteTmpFiles = true;
-  private static String testDir = "examples";
+
+  private static String testDir = "test/jalview/io";
 
   private static String testBasename = "backupfilestest";
 
@@ -61,7 +62,7 @@ public class BackupFilesTest
 
   private static String suffix = "_BACKUPTEST-%n";
 
-  private static int digits = 8;
+  private static int digits = 6;
 
   private static int rollMax = 2;
 
@@ -107,28 +108,28 @@ public class BackupFilesTest
     }
 
     // check 10 backup files
-    HashMap correctindexmap = new HashMap();
-    correctindexmap.put(1, "backupfilestestTemp.fa_BACKUPTEST-00000001");
-    correctindexmap.put(2, "backupfilestestTemp.fa_BACKUPTEST-00000002");
-    correctindexmap.put(3, "backupfilestestTemp.fa_BACKUPTEST-00000003");
-    correctindexmap.put(4, "backupfilestestTemp.fa_BACKUPTEST-00000004");
-    correctindexmap.put(5, "backupfilestestTemp.fa_BACKUPTEST-00000005");
-    correctindexmap.put(6, "backupfilestestTemp.fa_BACKUPTEST-00000006");
-    correctindexmap.put(7, "backupfilestestTemp.fa_BACKUPTEST-00000007");
-    correctindexmap.put(8, "backupfilestestTemp.fa_BACKUPTEST-00000008");
-    correctindexmap.put(9, "backupfilestestTemp.fa_BACKUPTEST-00000009");
-    correctindexmap.put(10, "backupfilestestTemp.fa_BACKUPTEST-00000010");
-    HashMap wrongindexmap = new HashMap();
+    HashMap<Integer, String> correctindexmap = new HashMap<>();
+    correctindexmap.put(1, "backupfilestestTemp.fa_BACKUPTEST-000001");
+    correctindexmap.put(2, "backupfilestestTemp.fa_BACKUPTEST-000002");
+    correctindexmap.put(3, "backupfilestestTemp.fa_BACKUPTEST-000003");
+    correctindexmap.put(4, "backupfilestestTemp.fa_BACKUPTEST-000004");
+    correctindexmap.put(5, "backupfilestestTemp.fa_BACKUPTEST-000005");
+    correctindexmap.put(6, "backupfilestestTemp.fa_BACKUPTEST-000006");
+    correctindexmap.put(7, "backupfilestestTemp.fa_BACKUPTEST-000007");
+    correctindexmap.put(8, "backupfilestestTemp.fa_BACKUPTEST-000008");
+    correctindexmap.put(9, "backupfilestestTemp.fa_BACKUPTEST-000009");
+    correctindexmap.put(10, "backupfilestestTemp.fa_BACKUPTEST-000010");
+    HashMap<Integer, String> wrongindexmap = new HashMap<>();
     wrongindexmap.put(1, "backupfilestestTemp.fa_BACKUPTEST-1");
-    wrongindexmap.put(2, "backupfilestestTemp.fa_BACKUPTEST-00000002");
-    wrongindexmap.put(3, "backupfilestestTemp.fa_BACKUPTEST-00000003");
-    wrongindexmap.put(4, "backupfilestestTemp.fa_BACKUPTEST-00000004");
-    wrongindexmap.put(5, "backupfilestestTemp.fa_BACKUPTEST-00000005");
-    wrongindexmap.put(6, "backupfilestestTemp.fa_BACKUPTEST-00000006");
-    wrongindexmap.put(7, "backupfilestestTemp.fa_BACKUPTEST-00000007");
-    wrongindexmap.put(8, "backupfilestestTemp.fa_BACKUPTEST-00000008");
-    wrongindexmap.put(9, "backupfilestestTemp.fa_BACKUPTEST-00000009");
-    wrongindexmap.put(10, "backupfilestestTemp.fa_BACKUPTEST-00000010");
+    wrongindexmap.put(2, "backupfilestestTemp.fa_BACKUPTEST-000002");
+    wrongindexmap.put(3, "backupfilestestTemp.fa_BACKUPTEST-000003");
+    wrongindexmap.put(4, "backupfilestestTemp.fa_BACKUPTEST-000004");
+    wrongindexmap.put(5, "backupfilestestTemp.fa_BACKUPTEST-000005");
+    wrongindexmap.put(6, "backupfilestestTemp.fa_BACKUPTEST-000006");
+    wrongindexmap.put(7, "backupfilestestTemp.fa_BACKUPTEST-000007");
+    wrongindexmap.put(8, "backupfilestestTemp.fa_BACKUPTEST-000008");
+    wrongindexmap.put(9, "backupfilestestTemp.fa_BACKUPTEST-000009");
+    wrongindexmap.put(10, "backupfilestestTemp.fa_BACKUPTEST-000010");
     int[] indexes2 = { 3, 4, 5, 6, 7, 8, 9, 10 };
     int[] indexes3 = { 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11 };
     Assert.assertTrue(checkBackupFiles(correctindexmap));
@@ -158,9 +159,9 @@ public class BackupFilesTest
 
     // check there are "rollMax" backup files and they are all saved correctly
     // check 10 backup files
-    HashMap correctindexmap = new HashMap();
-    correctindexmap.put(9, "backupfilestestTemp.fa_BACKUPTEST-00000009");
-    correctindexmap.put(10, "backupfilestestTemp.fa_BACKUPTEST-00000010");
+    HashMap<Integer, String> correctindexmap = new HashMap<>();
+    correctindexmap.put(9, "backupfilestestTemp.fa_BACKUPTEST-000009");
+    correctindexmap.put(10, "backupfilestestTemp.fa_BACKUPTEST-000010");
     int[] indexes2 = { 10 };
     int[] indexes3 = { 8, 9, 10 };
     Assert.assertTrue(checkBackupFiles(correctindexmap));
@@ -189,9 +190,9 @@ public class BackupFilesTest
 
     // check there are "rollMax" backup files and they are all saved correctly
     // check 10 backup files
-    HashMap correctindexmap = new HashMap();
-    correctindexmap.put(1, "backupfilestestTemp.fa_BACKUPTEST-00000001");
-    correctindexmap.put(2, "backupfilestestTemp.fa_BACKUPTEST-00000002");
+    HashMap<Integer, String> correctindexmap = new HashMap<>();
+    correctindexmap.put(1, "backupfilestestTemp.fa_BACKUPTEST-000001");
+    correctindexmap.put(2, "backupfilestestTemp.fa_BACKUPTEST-000002");
     int[] indexes2 = { 1 };
     int[] indexes3 = { 1, 2, 3 };
     Assert.assertTrue(checkBackupFiles(correctindexmap));
@@ -209,6 +210,14 @@ public class BackupFilesTest
   {
     Cache.loadProperties("test/jalview/io/testProps.jvprops");
 
+    BackupFilesPresetEntry bfpe = new BackupFilesPresetEntry(suffix, digits,
+            reverse, noMax, rollMax, false);
+
+    Cache.applicationProperties.setProperty(BackupFiles.ENABLED,
+            Boolean.toString(enabled));
+    Cache.applicationProperties.setProperty(
+            BackupFilesPresetEntry.SAVEDCONFIG, bfpe.toString());
+    /*
     Cache.applicationProperties.setProperty(BackupFiles.ENABLED,
             Boolean.toString(enabled));
     Cache.applicationProperties.setProperty(BackupFiles.SUFFIX, suffix);
@@ -222,6 +231,7 @@ public class BackupFilesTest
             Integer.toString(rollMax));
     Cache.applicationProperties.setProperty(BackupFiles.CONFIRM_DELETE_OLD,
             "false");
+            */
   }
 
   private void save()
index f180395..94bc5d9 100644 (file)
@@ -1,13 +1,10 @@
 #---JalviewX Properties File---
 #Fri Apr 25 09:54:25 BST 2014
 #
-BACKUPFILES_ROLL_MAX=2
-BACKUPFILES_REVERSE_ORDER=false
-BACKUPFILES_SUFFIX=_BACKUPFILESTESTTMP%n
-BACKUPFILES_CONFIRM_DELETE_OLD=false
-BACKUPFILES_NO_MAX=false
 BACKUPFILES_ENABLED=true
-BACKUPFILES_SUFFIX_DIGITS=8
+BACKUPFILES_PRESET=0
+BACKUPFILES_SAVED=_BACKUPFILESTESTTMP%n\t6\tfalse\tfalse\t2\tfalse
+BACKUPFILES_CUSTOM=_BACKUPFILESTESTTMP%n\t6\tfalse\tfalse\t2\tfalse
 SCREEN_Y=768
 SCREEN_X=936
 SHOW_WSDISCOVERY_ERRORS=true
index 374da46..2eafdbc 100644 (file)
Binary files a/utils/install4j/DS_Store and b/utils/install4j/DS_Store differ
diff --git a/utils/install4j/DS_Store_1 b/utils/install4j/DS_Store_1
new file mode 100644 (file)
index 0000000..374da46
Binary files /dev/null and b/utils/install4j/DS_Store_1 differ
diff --git a/utils/install4j/DS_Store_2 b/utils/install4j/DS_Store_2
new file mode 100644 (file)
index 0000000..2eafdbc
Binary files /dev/null and b/utils/install4j/DS_Store_2 differ
diff --git a/utils/install4j/Uninstall Old Jalview.app/Contents/Info.plist b/utils/install4j/Uninstall Old Jalview.app/Contents/Info.plist
new file mode 100644 (file)
index 0000000..c10a834
--- /dev/null
@@ -0,0 +1,52 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+       <key>CFBundleAllowMixedLocalizations</key>
+       <true/>
+       <key>CFBundleDevelopmentRegion</key>
+       <string>English</string>
+       <key>CFBundleExecutable</key>
+       <string>applet</string>
+       <key>CFBundleIconFile</key>
+       <string>applet</string>
+       <key>CFBundleIdentifier</key>
+       <string>com.apple.ScriptEditor.id.Uninstall-Old-Jalview</string>
+       <key>CFBundleInfoDictionaryVersion</key>
+       <string>6.0</string>
+       <key>CFBundleName</key>
+       <string>Uninstall Old Jalview</string>
+       <key>CFBundlePackageType</key>
+       <string>APPL</string>
+       <key>CFBundleShortVersionString</key>
+       <string>1.0</string>
+       <key>CFBundleSignature</key>
+       <string>aplt</string>
+       <key>LSMinimumSystemVersionByArchitecture</key>
+       <dict>
+               <key>x86_64</key>
+               <string>10.6</string>
+       </dict>
+       <key>LSRequiresCarbon</key>
+       <true/>
+       <key>WindowState</key>
+       <dict>
+               <key>bundleDividerCollapsed</key>
+               <true/>
+               <key>bundlePositionOfDivider</key>
+               <real>0.0</real>
+               <key>dividerCollapsed</key>
+               <false/>
+               <key>eventLogLevel</key>
+               <integer>2</integer>
+               <key>name</key>
+               <string>ScriptWindowState</string>
+               <key>positionOfDivider</key>
+               <real>223</real>
+               <key>savedFrame</key>
+               <string>329 957 700 672 0 0 3360 1867 </string>
+               <key>selectedTab</key>
+               <string>description</string>
+       </dict>
+</dict>
+</plist>
diff --git a/utils/install4j/Uninstall Old Jalview.app/Contents/MacOS/applet b/utils/install4j/Uninstall Old Jalview.app/Contents/MacOS/applet
new file mode 100755 (executable)
index 0000000..171d0cc
Binary files /dev/null and b/utils/install4j/Uninstall Old Jalview.app/Contents/MacOS/applet differ
diff --git a/utils/install4j/Uninstall Old Jalview.app/Contents/PkgInfo b/utils/install4j/Uninstall Old Jalview.app/Contents/PkgInfo
new file mode 100644 (file)
index 0000000..3253614
--- /dev/null
@@ -0,0 +1 @@
+APPLaplt
\ No newline at end of file
diff --git a/utils/install4j/Uninstall Old Jalview.app/Contents/Resources/Scripts/main.scpt b/utils/install4j/Uninstall Old Jalview.app/Contents/Resources/Scripts/main.scpt
new file mode 100644 (file)
index 0000000..1dce96c
Binary files /dev/null and b/utils/install4j/Uninstall Old Jalview.app/Contents/Resources/Scripts/main.scpt differ
diff --git a/utils/install4j/Uninstall Old Jalview.app/Contents/Resources/applet.icns b/utils/install4j/Uninstall Old Jalview.app/Contents/Resources/applet.icns
new file mode 100644 (file)
index 0000000..67a2cbd
Binary files /dev/null and b/utils/install4j/Uninstall Old Jalview.app/Contents/Resources/applet.icns differ
diff --git a/utils/install4j/Uninstall Old Jalview.app/Contents/Resources/applet.rsrc b/utils/install4j/Uninstall Old Jalview.app/Contents/Resources/applet.rsrc
new file mode 100644 (file)
index 0000000..c41bb4e
Binary files /dev/null and b/utils/install4j/Uninstall Old Jalview.app/Contents/Resources/applet.rsrc differ
diff --git a/utils/install4j/Uninstall Old Jalview.app/Contents/Resources/description.rtfd/TXT.rtf b/utils/install4j/Uninstall Old Jalview.app/Contents/Resources/description.rtfd/TXT.rtf
new file mode 100644 (file)
index 0000000..76ac711
--- /dev/null
@@ -0,0 +1,5 @@
+{\rtf1\ansi\ansicpg1252\cocoartf1561\cocoasubrtf600
+{\fonttbl}
+{\colortbl;\red255\green255\blue255;}
+{\*\expandedcolortbl;;}
+}
\ No newline at end of file
diff --git a/utils/install4j/Uninstall Old Jalview.scpt b/utils/install4j/Uninstall Old Jalview.scpt
new file mode 100644 (file)
index 0000000..1692009
Binary files /dev/null and b/utils/install4j/Uninstall Old Jalview.scpt differ
index 7a924e2..2f65f51 100644 (file)
@@ -1,6 +1,6 @@
 <?xml version="1.0" encoding="UTF-8"?>
 <install4j version="7.0.9" transformSequenceNumber="7">
-  <directoryPresets config="../../../../../buildtools/jre/openjdk-java_vm/macos-jdk8u202-b08-jre" />
+  <directoryPresets config="." />
   <application name="Jalview" distributionSourceDir="" applicationId="6595-2347-1923-0725" mediaDir="../../build/install4j" mediaFilePattern="${compiler:sys.shortName}_${compiler:sys.platform}_${compiler:sys.version}" compression="6" lzmaCompression="true" pack200Compression="false" excludeSignedFromPacking="true" commonExternalFiles="false" createMd5Sums="true" shrinkRuntime="true" shortName="Jalview" publisher="University of Dundee" publisherWeb="http://www.jalview.org/" version="$$VERSION$$" allPathsRelative="true" backupOnSave="false" autoSave="false" convertDotsToUnderscores="true" macSignature="????" macVolumeId="5aac4968c304f65" javaMinVersion="9999999999" javaMaxVersion="" allowBetaVM="true" jdkMode="jdk" jdkName="JDK 11.0">
     <languages skipLanguageSelection="false" languageSelectionInPrincipalLanguage="false">
       <principalLanguage id="en" customLocalizationFile="" />
@@ -8,6 +8,8 @@
     </languages>
     <searchSequence>
       <directory location="${compiler:JRE_DIR}" />
+      <registry />
+      <envVar name="JAVA_HOME" />
     </searchSequence>
     <variables>
       <variable name="OSX_KEYSTORE" value="" description="" category="" />
       <fileset name="Full file set" id="734" customizedId="" />
       <fileset name="Mac OS X JRE" id="880" customizedId="" />
       <fileset name="Windows JRE" id="882" customizedId="" />
+      <fileset name="Jalview application" id="1873" customizedId="" />
+      <fileset name="MacOS Old Jalview Uninstaller" id="2105" customizedId="" />
     </filesets>
     <roots>
       <root id="735" fileset="734" location="" />
       <root id="881" fileset="880" location="" />
       <root id="883" fileset="882" location="" />
+      <root id="1874" fileset="1873" location="" />
+      <root id="2106" fileset="2105" location="" />
     </roots>
     <mountPoints>
       <mountPoint id="454" root="" location="" mode="755" />
       <mountPoint id="736" root="735" location="" mode="755" />
       <mountPoint id="884" root="881" location="" mode="755" />
       <mountPoint id="885" root="883" location="" mode="755" />
+      <mountPoint id="1875" root="1874" location="" mode="755" />
+      <mountPoint id="2107" root="2106" location="" mode="755" />
     </mountPoints>
     <entries>
       <dirEntry mountPoint="454" file="../../getdown/files/$$JAVA_VERSION$$" overwriteMode="4" shared="false" fileMode="644" uninstallMode="2" overrideFileMode="false" overrideOverwriteMode="true" overrideUninstallMode="true" entryMode="direct" subDirectory="files" excludeSuffixes="" dirMode="755" overrideDirMode="false">
       <dirEntry mountPoint="885" file="$$WINDOWS_JAVA_VM_DIR$$" overwriteMode="4" shared="false" fileMode="755" uninstallMode="0" overrideFileMode="true" overrideOverwriteMode="false" overrideUninstallMode="true" entryMode="subdir" subDirectory="${compiler:JRE_DIR}" excludeSuffixes="" dirMode="755" overrideDirMode="false">
         <exclude />
       </dirEntry>
+      <dirEntry mountPoint="1875" file="../../getdown/website/$$JAVA_VERSION$$/dist" overwriteMode="1" shared="false" fileMode="644" uninstallMode="2" overrideFileMode="true" overrideOverwriteMode="true" overrideUninstallMode="true" entryMode="subdir" subDirectory="dist" excludeSuffixes="" dirMode="755" overrideDirMode="true">
+        <exclude />
+      </dirEntry>
+      <dirEntry mountPoint="2107" file="Uninstall Old Jalview.app" overwriteMode="4" shared="false" fileMode="755" uninstallMode="0" overrideFileMode="true" overrideOverwriteMode="false" overrideUninstallMode="false" entryMode="subdir" subDirectory="Uninstall Old Jalview.app" excludeSuffixes="" dirMode="755" overrideDirMode="true">
+        <exclude />
+      </dirEntry>
     </entries>
     <components>
       <component name="jalview_getdown" id="1031" customizedId="" displayDescription="false" hideHelpButton="false" selected="true" changeable="true" downloadable="false" hidden="false">
         </include>
         <dependencies />
       </component>
+      <component name="jalview" id="1881" customizedId="" displayDescription="false" hideHelpButton="false" selected="true" changeable="true" downloadable="false" hidden="false">
+        <description />
+        <include all="false">
+          <entry location=".i4j_fileset_1873" fileType="regular" />
+        </include>
+        <dependencies />
+      </component>
+      <component name="macos_old_jalview_uninstaller" id="2110" customizedId="" displayDescription="false" hideHelpButton="false" selected="true" changeable="true" downloadable="false" hidden="false">
+        <description />
+        <include all="false">
+          <entry location=".i4j_fileset_2105" fileType="regular" />
+        </include>
+        <dependencies />
+      </component>
     </components>
   </files>
   <launchers>
         <file path="../../resources/images/JalviewLogo_Huge.png" />
       </iconImageFiles>
     </launcher>
+    <launcher name="Jalview package" id="1876" customizedId="" external="false" excludeFromMenu="false" unixMode="755" unixAutoStart="true" menuName="${compiler:sys.shortName} $$VERSION$$" icnsFile="" customMacBundleIdentifier="false" macBundleIdentifier="" swtApp="false" fileset="1873" macBundleBinary="JavaApplicationStub" addMacEntitlements="false" macEntitlementsFile="" useCustomMacosExecutableName="false" customMacosExecutableName="" useJavaMinVersionOverride="false" javaMinVersionOverride="" useJavaMaxVersionOverride="false" javaMaxVersionOverride="" checkUpdater="false" updateExecutionMode="unattendedProgress" unattendedUpdateTitle="${i18n:updater.WindowTitle(&quot;${compiler:sys.fullName}&quot;)}">
+      <executable name="${compiler:sys.shortName}" type="1" iconSet="true" iconFile="" executableDir="" redirectStderr="false" stderrFile="error.log" stderrMode="overwrite" redirectStdout="false" stdoutFile="output.log" stdoutMode="overwrite" failOnStderrOutput="false" executableMode="1" changeWorkingDirectory="false" workingDirectory="." singleInstance="true" serviceStartType="2" serviceDependencies="" serviceDescription="" jreLocation="" executionLevel="asInvoker" checkConsoleParameter="false" globalSingleInstance="false" singleInstanceActivate="true" dpiAware="java9+">
+        <versionInfo include="false" fileVersion="" fileDescription="" legalCopyright="" internalName="" productName="" />
+      </executable>
+      <splashScreen show="false" width="0" height="0" bitmapFile="" textOverlay="false">
+        <text>
+          <statusLine x="20" y="20" text="" fontSize="8" fontColor="0,0,0" bold="false" />
+          <versionLine x="20" y="40" text="version ${compiler:sys.version}" fontSize="8" fontColor="0,0,0" bold="false" />
+        </text>
+      </splashScreen>
+      <java mainClass="jalview.bin.Launcher" mainMode="1" vmParameters="" arguments="" allowVMPassthroughParameters="true" preferredVM="" bundleRuntime="true">
+        <classPath>
+          <scanDirectory location="dist" failOnError="false" />
+        </classPath>
+        <modulePath />
+        <nativeLibraryDirectories />
+        <vmOptions />
+      </java>
+      <includedFiles />
+      <unextractableFiles />
+      <vmOptionsFile mode="template" overwriteMode="0" fileMode="644">
+        <content />
+      </vmOptionsFile>
+      <customScript mode="1" file="">
+        <content />
+      </customScript>
+      <infoPlist mode="1" file="">
+        <content />
+      </infoPlist>
+      <iconImageFiles>
+        <file path="../../resources/images/JalviewLogo_Huge.png" />
+      </iconImageFiles>
+    </launcher>
   </launchers>
   <installerGui installerType="1" addOnAppId="" suggestPreviousLocations="true" autoUpdateDescriptorUrl="https://www.jalview.org/install4j/updates.xml" useAutoUpdateBaseUrl="false" autoUpdateBaseUrl="">
     <staticMembers script="" />
@@ -700,6 +761,36 @@ return console.askOkCancel(message, true);
             <preActivation />
             <postActivation />
             <actions>
+              <action name="" id="2012" customizedId="" beanClass="com.install4j.runtime.beans.actions.desktop.CreateStartMenuEntryAction" enabled="true" commentSet="false" comment="" actionElevationType="elevated" rollbackBarrier="false" rollbackBarrierExitCode="0" multiExec="false" failureStrategy="1" errorMessage="">
+                <serializedBean>
+                  <java class="java.beans.XMLDecoder">
+                    <object class="com.install4j.runtime.beans.actions.desktop.CreateStartMenuEntryAction">
+                      <void property="allUsers">
+                        <boolean>false</boolean>
+                      </void>
+                      <void property="entryName">
+                        <string>${compiler:sys.shortName}</string>
+                      </void>
+                      <void property="file">
+                        <object class="java.io.File">
+                          <string>${compiler:sys.shortName}</string>
+                        </object>
+                      </void>
+                      <void property="icon">
+                        <object class="com.install4j.api.beans.ExternalFile">
+                          <string>../../resources/images/jalview_logos.ico</string>
+                        </object>
+                      </void>
+                      <void property="unixIconFile">
+                        <object class="com.install4j.api.beans.ExternalFile">
+                          <string>../../resources/images/JalviewLogo_Huge.png</string>
+                        </object>
+                      </void>
+                    </object>
+                  </java>
+                </serializedBean>
+                <condition>!context.getBooleanVariable("sys.programGroupDisabled")</condition>
+              </action>
               <action name="" id="573" customizedId="" beanClass="com.install4j.runtime.beans.actions.desktop.CreateDesktopLinkAction" enabled="true" commentSet="false" comment="" actionElevationType="elevated" rollbackBarrier="false" rollbackBarrierExitCode="0" multiExec="false" failureStrategy="1" errorMessage="Could not make desktop link">
                 <serializedBean>
                   <java class="java.beans.XMLDecoder">
@@ -1666,20 +1757,24 @@ return console.askYesNo(message, true);
     </styles>
   </installerGui>
   <mediaSets>
-    <linuxDeb name="Linux Deb Archive" id="153" customizedId="" mediaFileName="" installDir="/opt/${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="true" includedJRE="" manualJREEntry="false" overwriteNeverAsConfigFiles="false" dependencies="" bzip="true" description="Jalview Desktop" maintainerEmail="help@jalview.org" architectureSet="false" architecture="">
+    <linuxDeb name="Jalview .deb Package" id="153" customizedId="" mediaFileName="jalview-$$VERSION$$" installDir="/opt/${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="true" includedJRE="" manualJREEntry="false" overwriteNeverAsConfigFiles="false" dependencies="openjdk-8-jre" bzip="true" description="Jalview Desktop" maintainerEmail="help@jalview.org" architectureSet="false" architecture="">
       <excludedComponents>
+        <component id="1031" />
         <component id="1155" />
         <component id="1156" />
         <component id="1276" />
+        <component id="2110" />
       </excludedComponents>
       <includedDownloadableComponents />
       <excludedLaunchers>
+        <launcher id="737" />
         <launcher id="1402" />
       </excludedLaunchers>
       <excludedBeans />
       <overriddenPrincipalLanguage id="en" customLocalizationFile="" />
       <exclude>
         <entry location=".i4j_fileset_" fileType="regular" />
+        <entry location=".i4j_fileset_734" fileType="regular" />
         <entry location=".i4j_fileset_880" fileType="regular" />
         <entry location=".i4j_fileset_882" fileType="regular" />
       </exclude>
@@ -1701,20 +1796,24 @@ return console.askYesNo(message, true);
         <content />
       </postUninstallScript>
     </linuxDeb>
-    <linuxRPM name="Linux RPM" id="570" customizedId="" mediaFileName="" installDir="/opt/${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="true" includedJRE="" manualJREEntry="false" overwriteNeverAsConfigFiles="false" dependencies="" os="linux" arch="i386">
+    <linuxRPM name="Jalview RPM Package" id="570" customizedId="" mediaFileName="jalview-$$VERSION$$" installDir="/opt/${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="true" includedJRE="" manualJREEntry="false" overwriteNeverAsConfigFiles="false" dependencies="java-1.8.0-openjdk" os="linux" arch="noarch">
       <excludedComponents>
+        <component id="1031" />
         <component id="1155" />
         <component id="1156" />
         <component id="1276" />
+        <component id="2110" />
       </excludedComponents>
       <includedDownloadableComponents />
       <excludedLaunchers>
+        <launcher id="737" />
         <launcher id="1402" />
       </excludedLaunchers>
       <excludedBeans />
       <overriddenPrincipalLanguage id="en" customLocalizationFile="" />
       <exclude>
         <entry location=".i4j_fileset_" fileType="regular" />
+        <entry location=".i4j_fileset_734" fileType="regular" />
         <entry location=".i4j_fileset_880" fileType="regular" />
         <entry location=".i4j_fileset_882" fileType="regular" />
       </exclude>
@@ -1736,11 +1835,13 @@ return console.askYesNo(message, true);
         <content />
       </postUninstallScript>
     </linuxRPM>
-    <windows name="Offline Windows" id="743" customizedId="" mediaFileName="${compiler:sys.shortName}-OFFLINE_${compiler:sys.platform}_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="64" runPostProcessor="true" postProcessor="${compiler:JSIGN_SH} $EXECUTABLE" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="false" includedJRE="$$WINDOWS_JAVA_VM_TGZ$$" manualJREEntry="true" bundleType="1" jreURL="" jreShared="false" directDownload="false" installOnlyIfNecessary="false" customInstallBaseDir="~/AppData/Local" contentFilesType="1" verifyIntegrity="true">
+    <windows name="Offline Windows x64 Installer" id="743" customizedId="" mediaFileName="${compiler:sys.shortName}-OFFLINE_${compiler:sys.platform}_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="64" runPostProcessor="true" postProcessor="${compiler:JSIGN_SH} $EXECUTABLE" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="false" includedJRE="$$WINDOWS_JAVA_VM_TGZ$$" manualJREEntry="true" bundleType="1" jreURL="" jreShared="false" directDownload="false" installOnlyIfNecessary="false" customInstallBaseDir="~/AppData/Local" contentFilesType="1" verifyIntegrity="true">
       <excludedComponents>
         <component id="1155" />
         <component id="1156" />
         <component id="1276" />
+        <component id="1881" />
+        <component id="2110" />
       </excludedComponents>
       <includedDownloadableComponents />
       <excludedLaunchers>
@@ -1751,6 +1852,31 @@ return console.askYesNo(message, true);
       <exclude>
         <entry location=".i4j_fileset_" fileType="regular" />
         <entry location=".i4j_fileset_880" fileType="regular" />
+        <entry location=".i4j_fileset_882" fileType="regular" />
+        <entry location=".i4j_fileset_1873" fileType="regular" />
+      </exclude>
+      <variables />
+      <autoUpdate useMinUpdatableVersion="false" minUpdatableVersion="" useMaxUpdatableVersion="false" maxUpdatableVersion="">
+        <commentFiles />
+        <customAttributes />
+      </autoUpdate>
+    </windows>
+    <windows name="Network Windows x64 Installer" id="1862" customizedId="" mediaFileName="${compiler:sys.shortName}-NETWORK_${compiler:sys.platform}_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="64" runPostProcessor="true" postProcessor="${compiler:JSIGN_SH} $EXECUTABLE" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="false" includedJRE="$$WINDOWS_JAVA_VM_TGZ$$" manualJREEntry="true" bundleType="1" jreURL="" jreShared="false" directDownload="false" installOnlyIfNecessary="false" customInstallBaseDir="~/AppData/Local" contentFilesType="1" verifyIntegrity="true">
+      <excludedComponents>
+        <component id="1031" />
+        <component id="1155" />
+        <component id="1156" />
+        <component id="1881" />
+        <component id="2110" />
+      </excludedComponents>
+      <includedDownloadableComponents />
+      <excludedLaunchers />
+      <excludedBeans />
+      <overriddenPrincipalLanguage id="en" customLocalizationFile="" />
+      <exclude>
+        <entry location=".i4j_fileset_734" fileType="regular" />
+        <entry location=".i4j_fileset_880" fileType="regular" />
+        <entry location=".i4j_fileset_1873" fileType="regular" />
       </exclude>
       <variables />
       <autoUpdate useMinUpdatableVersion="false" minUpdatableVersion="" useMaxUpdatableVersion="false" maxUpdatableVersion="">
@@ -1758,10 +1884,11 @@ return console.askYesNo(message, true);
         <customAttributes />
       </autoUpdate>
     </windows>
-    <macosArchive name="Offline macOS Single Bundle Archive" id="878" customizedId="" mediaFileName="${compiler:sys.shortName}-OFFLINE_${compiler:sys.platform}-app_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="true" includedJRE="" manualJREEntry="false" archiveType="dmg" volumeName="${compiler:sys.shortName} Installer" launcherId="737">
+    <macosArchive name="Offline macOS Disk Image" id="878" customizedId="" mediaFileName="${compiler:sys.shortName}-OFFLINE_${compiler:sys.platform}-app_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="true" includedJRE="" manualJREEntry="false" archiveType="dmg" volumeName="${compiler:sys.shortName} Installer" launcherId="737">
       <excludedComponents>
         <component id="1156" />
         <component id="1276" />
+        <component id="1881" />
       </excludedComponents>
       <includedDownloadableComponents />
       <excludedBeans />
@@ -1769,6 +1896,7 @@ return console.askYesNo(message, true);
       <exclude>
         <entry location=".i4j_fileset_" fileType="regular" />
         <entry location=".i4j_fileset_882" fileType="regular" />
+        <entry location=".i4j_fileset_1873" fileType="regular" />
       </exclude>
       <variables />
       <autoUpdate useMinUpdatableVersion="false" minUpdatableVersion="" useMaxUpdatableVersion="false" maxUpdatableVersion="">
@@ -1782,12 +1910,14 @@ return console.askYesNo(message, true);
         <symlink name="Jalview.app/Contents/Resources/app/${compiler:JRE_DIR}/Contents/MacOS/libjli.dylib" target="../Home/lib/jli/libjli.dylib" />
         <file name="Jalview.app/Contents/Resources/Jalview-File.icns" file="./Jalview-File.icns" />
         <file name="Jalview.app/Contents/Resources/Jalview-Version-Locator.icns" file="Jalview-Version-Locator.icns" />
+        <symlink name="Uninstall Old Jalview.app" target="Jalview.app/Contents/Resources/app/Uninstall Old Jalview.app" />
       </topLevelFiles>
     </macosArchive>
-    <macosArchive name="Network macOS Single Bundle Archive" id="1274" customizedId="" mediaFileName="${compiler:sys.shortName}-NETWORK_${compiler:sys.platform}-app_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="true" includedJRE="" manualJREEntry="false" archiveType="dmg" volumeName="${compiler:sys.shortName} Installer" launcherId="1402">
+    <macosArchive name="Network macOS Disk Image" id="1274" customizedId="" mediaFileName="${compiler:sys.shortName}-NETWORK_${compiler:sys.platform}-app_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="true" includedJRE="" manualJREEntry="false" archiveType="dmg" volumeName="${compiler:sys.shortName} Installer" launcherId="1402">
       <excludedComponents>
         <component id="1031" />
         <component id="1156" />
+        <component id="1881" />
       </excludedComponents>
       <includedDownloadableComponents />
       <excludedBeans />
@@ -1795,6 +1925,7 @@ return console.askYesNo(message, true);
       <exclude>
         <entry location=".i4j_fileset_734" fileType="regular" />
         <entry location=".i4j_fileset_882" fileType="regular" />
+        <entry location=".i4j_fileset_1873" fileType="regular" />
       </exclude>
       <variables />
       <autoUpdate useMinUpdatableVersion="false" minUpdatableVersion="" useMaxUpdatableVersion="false" maxUpdatableVersion="">
@@ -1808,10 +1939,17 @@ return console.askYesNo(message, true);
         <symlink name="Jalview.app/Contents/Resources/app/${compiler:JRE_DIR}/Contents/MacOS/libjli.dylib" target="../Home/lib/jli/libjli.dylib" />
         <file name="Jalview.app/Contents/Resources/Jalview-Version-Locator.icns" file="Jalview-Version-Locator.icns" />
         <file name="Jalview.app/Contents/Resources/Jalview-File.icns" file="Jalview-File.icns" />
+        <symlink name="Uninstall Old Jalview.app" target="Jalview.app/Contents/Resources/app/Uninstall Old Jalview.app" />
       </topLevelFiles>
     </macosArchive>
-    <unixInstaller name="Unix Installer" id="1595" customizedId="" mediaFileName="${compiler:sys.shortName}-OFFLINE_${compiler:sys.platform}_installer_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="false" includedJRE="" manualJREEntry="false" bundleType="1" jreURL="" jreShared="false" directDownload="false" installOnlyIfNecessary="false" customInstallBaseDir="" contentFilesType="1">
-      <excludedComponents />
+    <unixInstaller name="Offline Unix Shell Installer" id="1595" customizedId="" mediaFileName="${compiler:sys.shortName}-OFFLINE_${compiler:sys.platform}_installer_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="false" includedJRE="" manualJREEntry="false" bundleType="1" jreURL="" jreShared="false" directDownload="false" installOnlyIfNecessary="false" customInstallBaseDir="~/opt/" contentFilesType="1">
+      <excludedComponents>
+        <component id="1155" />
+        <component id="1156" />
+        <component id="1276" />
+        <component id="1881" />
+        <component id="2110" />
+      </excludedComponents>
       <includedDownloadableComponents />
       <excludedLaunchers>
         <launcher id="1402" />
@@ -1819,9 +1957,10 @@ return console.askYesNo(message, true);
       <excludedBeans />
       <overriddenPrincipalLanguage id="en" customLocalizationFile="" />
       <exclude>
-        <entry location=".i4j_fileset_734" fileType="regular" />
+        <entry location=".i4j_fileset_" fileType="regular" />
         <entry location=".i4j_fileset_880" fileType="regular" />
         <entry location=".i4j_fileset_882" fileType="regular" />
+        <entry location=".i4j_fileset_1873" fileType="regular" />
       </exclude>
       <variables />
       <autoUpdate useMinUpdatableVersion="false" minUpdatableVersion="" useMaxUpdatableVersion="false" maxUpdatableVersion="">
@@ -1832,11 +1971,40 @@ return console.askYesNo(message, true);
         <content />
       </installerScript>
     </unixInstaller>
-    <unixArchive name="Unix Archive" id="1596" customizedId="" mediaFileName="${compiler:sys.shortName}-OFFLINE_${compiler:sys.platform}_archive_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="true" includedJRE="" manualJREEntry="false">
+    <unixInstaller name="Network Unix Shell Installer" id="1867" customizedId="" mediaFileName="${compiler:sys.shortName}-NETWORK_${compiler:sys.platform}_installer_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="false" includedJRE="" manualJREEntry="false" bundleType="1" jreURL="" jreShared="false" directDownload="false" installOnlyIfNecessary="false" customInstallBaseDir="~/opt/" contentFilesType="1">
       <excludedComponents>
         <component id="1031" />
         <component id="1155" />
         <component id="1156" />
+        <component id="1881" />
+        <component id="2110" />
+      </excludedComponents>
+      <includedDownloadableComponents />
+      <excludedLaunchers />
+      <excludedBeans />
+      <overriddenPrincipalLanguage id="en" customLocalizationFile="" />
+      <exclude>
+        <entry location=".i4j_fileset_734" fileType="regular" />
+        <entry location=".i4j_fileset_880" fileType="regular" />
+        <entry location=".i4j_fileset_882" fileType="regular" />
+        <entry location=".i4j_fileset_1873" fileType="regular" />
+      </exclude>
+      <variables />
+      <autoUpdate useMinUpdatableVersion="false" minUpdatableVersion="" useMaxUpdatableVersion="false" maxUpdatableVersion="">
+        <commentFiles />
+        <customAttributes />
+      </autoUpdate>
+      <installerScript mode="1" file="">
+        <content />
+      </installerScript>
+    </unixInstaller>
+    <unixArchive name="Offline Unix .tar.gz Archive" id="1596" customizedId="" mediaFileName="${compiler:sys.shortName}-OFFLINE_${compiler:sys.platform}_archive_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="true" includedJRE="" manualJREEntry="false">
+      <excludedComponents>
+        <component id="1155" />
+        <component id="1156" />
+        <component id="1276" />
+        <component id="1881" />
+        <component id="2110" />
       </excludedComponents>
       <includedDownloadableComponents />
       <excludedLaunchers>
@@ -1844,18 +2012,25 @@ return console.askYesNo(message, true);
       </excludedLaunchers>
       <excludedBeans />
       <overriddenPrincipalLanguage id="en" customLocalizationFile="" />
-      <exclude />
+      <exclude>
+        <entry location=".i4j_fileset_" fileType="regular" />
+        <entry location=".i4j_fileset_880" fileType="regular" />
+        <entry location=".i4j_fileset_882" fileType="regular" />
+        <entry location=".i4j_fileset_1873" fileType="regular" />
+      </exclude>
       <variables />
       <autoUpdate useMinUpdatableVersion="false" minUpdatableVersion="" useMaxUpdatableVersion="false" maxUpdatableVersion="">
         <commentFiles />
         <customAttributes />
       </autoUpdate>
     </unixArchive>
-    <windows name="Network Windows" id="1862" customizedId="" mediaFileName="${compiler:sys.shortName}-NETWORK_${compiler:sys.platform}_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="64" runPostProcessor="true" postProcessor="${compiler:JSIGN_SH} $EXECUTABLE" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="false" includedJRE="$$WINDOWS_JAVA_VM_TGZ$$" manualJREEntry="true" bundleType="1" jreURL="" jreShared="false" directDownload="false" installOnlyIfNecessary="false" customInstallBaseDir="~/AppData/Local" contentFilesType="1" verifyIntegrity="true">
+    <unixArchive name="Network Unix .tar.gz Archive" id="1871" customizedId="" mediaFileName="${compiler:sys.shortName}-NETWORK_${compiler:sys.platform}_archive_${compiler:sys.version}-j$$JAVA_INTEGER_VERSION$$" installDir="${compiler:sys.shortName}" overridePrincipalLanguage="false" jreBitType="all" runPostProcessor="false" postProcessor="" failOnPostProcessorError="false" useLegacyMediaFileIds="false" legacyMediaFileIds="" downloadURL="" includeAllDownloadableComponents="true" includedJRE="" manualJREEntry="false">
       <excludedComponents>
         <component id="1031" />
         <component id="1155" />
         <component id="1156" />
+        <component id="1881" />
+        <component id="2110" />
       </excludedComponents>
       <includedDownloadableComponents />
       <excludedLaunchers />
@@ -1864,13 +2039,15 @@ return console.askYesNo(message, true);
       <exclude>
         <entry location=".i4j_fileset_734" fileType="regular" />
         <entry location=".i4j_fileset_880" fileType="regular" />
+        <entry location=".i4j_fileset_882" fileType="regular" />
+        <entry location=".i4j_fileset_1873" fileType="regular" />
       </exclude>
       <variables />
       <autoUpdate useMinUpdatableVersion="false" minUpdatableVersion="" useMaxUpdatableVersion="false" maxUpdatableVersion="">
         <commentFiles />
         <customAttributes />
       </autoUpdate>
-    </windows>
+    </unixArchive>
   </mediaSets>
   <buildIds buildAll="true">
     <mediaSet refId="153" />
@@ -1881,6 +2058,8 @@ return console.askYesNo(message, true);
     <mediaSet refId="1595" />
     <mediaSet refId="1596" />
     <mediaSet refId="1862" />
+    <mediaSet refId="1867" />
+    <mediaSet refId="1871" />
   </buildIds>
   <buildOptions verbose="false" faster="false" disableSigning="false" disableJreBundling="false" debug="false" />
 </install4j>
diff --git a/utils/install4j/uninstall_app_dmg_file_inclusions.sh b/utils/install4j/uninstall_app_dmg_file_inclusions.sh
new file mode 100644 (file)
index 0000000..f5bed50
--- /dev/null
@@ -0,0 +1,7 @@
+#!/usr/bin/env bash
+
+find Uninstall\ Old\ Jalview.app | perl -p -e 'chomp;$_=qq(            <file name=").$_.qq(" file="./).$_.qq(" />\n);' > uninstall_old_jalview_files.xml
+
+# makes the file used to replace the line
+# <file name="UNINSTALL_OLD_JALVIEW_APP_REPLACED_IN_GRADLE" file="./Uninstall Old Jalview.app" />
+# (replacement happens in gradle)
diff --git a/utils/install4j/uninstall_old_jalview.icns b/utils/install4j/uninstall_old_jalview.icns
new file mode 100644 (file)
index 0000000..67a2cbd
Binary files /dev/null and b/utils/install4j/uninstall_old_jalview.icns differ
diff --git a/utils/install4j/uninstall_old_jalview_files.xml b/utils/install4j/uninstall_old_jalview_files.xml
new file mode 100644 (file)
index 0000000..342fd90
--- /dev/null
@@ -0,0 +1,13 @@
+            <file name="Uninstall Old Jalview.app" file="./Uninstall Old Jalview.app" />
+            <file name="Uninstall Old Jalview.app/Contents" file="./Uninstall Old Jalview.app/Contents" />
+            <file name="Uninstall Old Jalview.app/Contents/MacOS" file="./Uninstall Old Jalview.app/Contents/MacOS" />
+            <file name="Uninstall Old Jalview.app/Contents/MacOS/applet" file="./Uninstall Old Jalview.app/Contents/MacOS/applet" />
+            <file name="Uninstall Old Jalview.app/Contents/Resources" file="./Uninstall Old Jalview.app/Contents/Resources" />
+            <file name="Uninstall Old Jalview.app/Contents/Resources/applet.rsrc" file="./Uninstall Old Jalview.app/Contents/Resources/applet.rsrc" />
+            <file name="Uninstall Old Jalview.app/Contents/Resources/description.rtfd" file="./Uninstall Old Jalview.app/Contents/Resources/description.rtfd" />
+            <file name="Uninstall Old Jalview.app/Contents/Resources/description.rtfd/TXT.rtf" file="./Uninstall Old Jalview.app/Contents/Resources/description.rtfd/TXT.rtf" />
+            <file name="Uninstall Old Jalview.app/Contents/Resources/Scripts" file="./Uninstall Old Jalview.app/Contents/Resources/Scripts" />
+            <file name="Uninstall Old Jalview.app/Contents/Resources/Scripts/main.scpt" file="./Uninstall Old Jalview.app/Contents/Resources/Scripts/main.scpt" />
+            <file name="Uninstall Old Jalview.app/Contents/Resources/applet.icns" file="./Uninstall Old Jalview.app/Contents/Resources/applet.icns" />
+            <file name="Uninstall Old Jalview.app/Contents/Info.plist" file="./Uninstall Old Jalview.app/Contents/Info.plist" />
+            <file name="Uninstall Old Jalview.app/Contents/PkgInfo" file="./Uninstall Old Jalview.app/Contents/PkgInfo" />