diff --git a/ChangeLog b/ChangeLog index b03e793..2e0ce84 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,3 +1,10 @@ +2004-07-09 Pierre-Luc Paour (1.4-b17) + + * When the session expires, GR now attempts to login again. + * Fixed duplicate extra field + * Added a warning when EXIF data is about to be dumped by Java resize + * Enabled silent install in the ZeroG installer. + 2004-06-24 Pierre-Luc Paour (1.4-b16) * New Album dialog now prevents user from attempting to create diff --git a/com/gallery/GalleryRemote/GRApplet.java b/com/gallery/GalleryRemote/GRApplet.java index 254edce..5b75abd 100644 --- a/com/gallery/GalleryRemote/GRApplet.java +++ b/com/gallery/GalleryRemote/GRApplet.java @@ -179,7 +179,9 @@ protected AppletInfo getGRAppletInfo() { info.gallery.cookieLogin = true; CookieModule.discardAllCookies(); - CookieModule.addCookie(new Cookie(cookieName, cookieValue, cookieDomain, cookiePath, null, false)); + Cookie cookie = new Cookie(cookieName, cookieValue, cookieDomain, cookiePath, null, false); + Log.log(Log.LEVEL_TRACE, MODULE, "Adding cookie: " + cookie); + CookieModule.addCookie(cookie); return info; } diff --git a/com/gallery/GalleryRemote/GRAppletMini.java b/com/gallery/GalleryRemote/GRAppletMini.java index 848e0be..7ab08a9 100644 --- a/com/gallery/GalleryRemote/GRAppletMini.java +++ b/com/gallery/GalleryRemote/GRAppletMini.java @@ -14,8 +14,6 @@ import javax.swing.event.ListSelectionListener; import javax.swing.event.ListSelectionEvent; import javax.swing.border.TitledBorder; -import java.applet.Applet; -import java.io.FilePermission; import java.io.File; import java.util.Iterator; import java.util.Arrays; @@ -27,9 +25,6 @@ import java.net.URL; import java.net.MalformedURLException; -import HTTPClient.CookieModule; -import HTTPClient.Cookie; - /** * Created by IntelliJ IDEA. * User: paour diff --git a/com/gallery/GalleryRemote/GRAppletSlideshow.java b/com/gallery/GalleryRemote/GRAppletSlideshow.java index 1213152..bb0014c 100644 --- a/com/gallery/GalleryRemote/GRAppletSlideshow.java +++ b/com/gallery/GalleryRemote/GRAppletSlideshow.java @@ -1,10 +1,8 @@ package com.gallery.GalleryRemote; -import com.gallery.GalleryRemote.util.DialogUtil; import com.gallery.GalleryRemote.util.GRI18n; import com.gallery.GalleryRemote.util.ImageUtils; import com.gallery.GalleryRemote.model.Album; -import com.gallery.GalleryRemote.model.Gallery; import com.gallery.GalleryRemote.model.Picture; import com.gallery.GalleryRemote.prefs.SlideshowPanel; import com.gallery.GalleryRemote.prefs.PreferenceNames; @@ -12,21 +10,9 @@ import javax.swing.*; import javax.swing.event.ListDataListener; import javax.swing.event.ListDataEvent; -import javax.swing.border.TitledBorder; -import java.applet.Applet; -import java.io.FilePermission; -import java.io.File; -import java.util.Iterator; -import java.util.Arrays; import java.awt.*; -import java.awt.event.KeyAdapter; -import java.awt.event.KeyEvent; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; -import java.net.URL; - -import HTTPClient.CookieModule; -import HTTPClient.Cookie; /** * Created by IntelliJ IDEA. diff --git a/com/gallery/GalleryRemote/GalleryComm.java b/com/gallery/GalleryRemote/GalleryComm.java index c61e35c..ab2ecdd 100644 --- a/com/gallery/GalleryRemote/GalleryComm.java +++ b/com/gallery/GalleryRemote/GalleryComm.java @@ -135,6 +135,7 @@ public void login(StatusUpdate su) { } public void logOut() { + Log.log(Log.LEVEL_INFO, MODULE, "Logging out and clearing cookies"); isLoggedIn = false; CookieModule.discardAllCookies(); } diff --git a/com/gallery/GalleryRemote/GalleryComm2.java b/com/gallery/GalleryRemote/GalleryComm2.java index 36f9485..9e653e5 100644 --- a/com/gallery/GalleryRemote/GalleryComm2.java +++ b/com/gallery/GalleryRemote/GalleryComm2.java @@ -310,7 +310,7 @@ private boolean login() { if (g.getType() != Gallery.TYPE_STANDALONE && g.getType() != Gallery.TYPE_APPLET) { try { - requestResponse(null, null, g.getLoginUrl(scriptName), false, su); + requestResponse(null, null, g.getLoginUrl(scriptName), false, su, this); } catch (IOException ioe) { Log.logException(Log.LEVEL_ERROR, MODULE, ioe); Object[] params2 = {ioe.toString()}; @@ -377,7 +377,7 @@ private boolean login() { triedLogin = true; // load and validate the response - Properties p = requestResponse(form_data, g.getGalleryUrl(scriptName), su); + Properties p = requestResponse(form_data, null, g.getGalleryUrl(scriptName), true, su, this, true); if (GR_STAT_SUCCESS.equals(p.getProperty("status")) || GR_STAT_LOGIN_MISSING.equals(p.getProperty("status"))) { status(su, StatusUpdate.LEVEL_GENERIC, GRI18n.getString(MODULE, "loggedIn")); @@ -579,7 +579,7 @@ boolean uploadPicture(Picture p) { byte[] data = Codecs.mpFormDataEncode(fudgeFormParameters(opts), fudgeParameters(afile), hdrs); // load and validate the response - Properties props = requestResponse(hdrs, data, g.getGalleryUrl(scriptName), true, su); + Properties props = requestResponse(hdrs, data, g.getGalleryUrl(scriptName), true, su, this); if (props.getProperty("status").equals(GR_STAT_SUCCESS)) { status(su, StatusUpdate.LEVEL_UPLOAD_ONE, GRI18n.getString(MODULE, "upSucc")); return true; @@ -663,7 +663,7 @@ private void list20() throws IOException, ModuleException { form_data = fudgeFormParameters(form_data); // load and validate the response - Properties p = requestResponse(form_data, su); + Properties p = requestResponse(form_data, su, this); if (p.getProperty("status").equals(GR_STAT_SUCCESS)) { ArrayList mAlbumList = new ArrayList(); @@ -747,7 +747,7 @@ private void list22() throws IOException, ModuleException { form_data = fudgeFormParameters(form_data); // load and validate the response - Properties p = requestResponse(form_data, su); + Properties p = requestResponse(form_data, su, this); if (p.getProperty("status").equals(GR_STAT_SUCCESS)) { ArrayList albums = new ArrayList(); @@ -886,6 +886,10 @@ private void list22() throws IOException, ModuleException { depth++; } + if ("no".equals(p.getProperty("can_create_root"))) { + rootAlbum.setCanCreateSubAlbum(false); + } + Log.log(Log.LEVEL_TRACE, MODULE, "Ordered " + orderedAlbums.size() + " albums"); status(su, StatusUpdate.LEVEL_BACKGROUND, GRI18n.getString(MODULE, "ftchdAlbms")); @@ -924,7 +928,7 @@ void runTask() { form_data = fudgeFormParameters(form_data); // load and validate the response - Properties p = requestResponse(form_data, su); + Properties p = requestResponse(form_data, su, this); if (p.getProperty("status").equals(GR_STAT_SUCCESS)) { // parse and store the data int autoResize = Integer.parseInt(p.getProperty("auto_resize")); @@ -999,7 +1003,7 @@ void runTask() { form_data = fudgeFormParameters(form_data); // load and validate the response - Properties p = requestResponse(form_data, su); + Properties p = requestResponse(form_data, su, this); if (p.getProperty("status").equals(GR_STAT_SUCCESS)) { status(su, StatusUpdate.LEVEL_GENERIC, GRI18n.getString(MODULE, "crateAlbmOk")); newAlbumName = p.getProperty("album_name"); @@ -1085,7 +1089,7 @@ private void fetch(Album a, String albumName, ArrayList newPictures) form_data = fudgeFormParameters(form_data); // load and validate the response - GalleryProperties p = requestResponse(form_data, su); + GalleryProperties p = requestResponse(form_data, su, this); if (p.getProperty("status").equals(GR_STAT_SUCCESS)) { // parse and store the data int numImages = p.getIntProperty("image_count"); @@ -1095,6 +1099,7 @@ private void fetch(Album a, String albumName, ArrayList newPictures) if (baseUrl == null) { Log.log(Log.LEVEL_TRACE, MODULE, "Gallery root, baseurl is null"); } else { + // verify that baseUrl is a valid URL (don't remove) URL tmpUrl = new URL(baseUrl); } } catch (MalformedURLException e) { @@ -1230,7 +1235,7 @@ void runTask() { form_data = fudgeFormParameters(form_data); // load and validate the response - GalleryProperties p = requestResponse(form_data, su); + GalleryProperties p = requestResponse(form_data, su, this); if (p.getProperty("status").equals(GR_STAT_SUCCESS)) { status(su, StatusUpdate.LEVEL_GENERIC, GRI18n.getString(MODULE, "moveAlbumDone")); @@ -1267,19 +1272,23 @@ boolean isTrue(String s) { /** * POSTSs a request to the Gallery server with the given form data. */ - GalleryProperties requestResponse(NVPair form_data[], StatusUpdate su) throws GR2Exception, ModuleException, IOException { - return requestResponse(form_data, null, g.getGalleryUrl(scriptName), true, su); + GalleryProperties requestResponse(NVPair form_data[], StatusUpdate su, GalleryTask task) throws GR2Exception, ModuleException, IOException { + return requestResponse(form_data, null, g.getGalleryUrl(scriptName), true, su, task); } - GalleryProperties requestResponse(NVPair form_data[], URL galUrl, StatusUpdate su) throws GR2Exception, ModuleException, IOException { - return requestResponse(form_data, null, galUrl, true, su); + GalleryProperties requestResponse(NVPair form_data[], URL galUrl, StatusUpdate su, GalleryTask task) throws GR2Exception, ModuleException, IOException { + return requestResponse(form_data, null, galUrl, true, su, task); + } + + GalleryProperties requestResponse(NVPair form_data[], byte[] data, URL galUrl, boolean checkResult, StatusUpdate su, GalleryTask task) throws GR2Exception, ModuleException, IOException { + return requestResponse(form_data, data, galUrl, checkResult, su, task, false); } /** * POSTSs a request to the Gallery server with the given form data. If data is * not null, a multipart MIME post is performed. */ - GalleryProperties requestResponse(NVPair form_data[], byte[] data, URL galUrl, boolean checkResult, StatusUpdate su) throws GR2Exception, ModuleException, IOException { + GalleryProperties requestResponse(NVPair form_data[], byte[] data, URL galUrl, boolean checkResult, StatusUpdate su, GalleryComm2.GalleryTask task, boolean alreadyRetried) throws GR2Exception, ModuleException, IOException { // assemble the URL String urlPath = galUrl.getFile(); Log.log(Log.LEVEL_TRACE, MODULE, "Url: " + urlPath); @@ -1344,6 +1353,18 @@ GalleryProperties requestResponse(NVPair form_data[], byte[] data, URL galUrl, b GalleryProperties p = new GalleryProperties(); p.load(new StringBufferInputStream(response)); + // catch session expiration problems + if (!alreadyRetried && !g.cookieLogin && g.getUsername() != null + && ! "1".equals(p.getProperty("debug_user_already_logged_in"))) { + Log.log(Log.LEVEL_INFO, MODULE, "The session seems to have expired: trying to login and retry..."); + + if (task.login()) { + return requestResponse(form_data, data, galUrl, checkResult, su, task, true); + } else { + Log.log(Log.LEVEL_INFO, MODULE, "Login attempt unsuccessful"); + } + } + //mConnection.stop(); su.stopProgress(StatusUpdate.LEVEL_UPLOAD_ONE, GRI18n.getString(MODULE, "addImgOk")); diff --git a/com/gallery/GalleryRemote/MainFrame.java b/com/gallery/GalleryRemote/MainFrame.java index 17a471a..69d9c05 100644 --- a/com/gallery/GalleryRemote/MainFrame.java +++ b/com/gallery/GalleryRemote/MainFrame.java @@ -178,24 +178,6 @@ public void initMainFrame() { } else { //Gallery g = new Gallery(jStatusBar); Applet applet = GalleryRemote._().getApplet(); - /*String url = applet.getParameter("gr_url"); - String cookieName = applet.getParameter("gr_cookie_name"); - String cookieValue = applet.getParameter("gr_cookie_value"); - String cookieDomain = applet.getParameter("gr_cookie_domain"); - String cookiePath = applet.getParameter("gr_cookie_path"); - - if (cookieDomain == null || cookieDomain.length() < 1) { - try { - cookieDomain = new URL(url).getHost(); - } catch (Exception e) { - Log.logException(Log.LEVEL_ERROR, MODULE, e); - } - } - - g.setType(Gallery.TYPE_STANDALONE); - g.setStUrlString(url); - g.addListDataListener(this); - g.cookieLogin = true;*/ GRApplet.AppletInfo info = ((GRApplet) applet).getGRAppletInfo(); @@ -1156,19 +1138,27 @@ public void keyPressed(KeyEvent e) { * we should display to prompt the user * before we do the dangerous thing. * - * @return one of CANCEL_OPTION, OK_OPTION (from the JOptionPane + * @param gallery + * @return one of CANCEL_OPTION, OK_OPTION (from the JOptionPane * class). On CANCEL_OPTION you should stop the current * process. OK_OPTION means that either we are not dirty) * or that we just saved for the user. */ - private int saveOnPermission(String promptMessageID) { + private int saveOnPermission(String promptMessageID, Gallery gallery) { if (!m_isDirty) { return (JOptionPane.OK_OPTION); } - int response = JOptionPane.showConfirmDialog( + String prompt; + if (gallery != null) { + prompt = GRI18n.getString(MODULE, promptMessageID, new Object[] {gallery.toString() }); + } else { + prompt = GRI18n.getString(MODULE, promptMessageID); + } + + int response = JOptionPane.showConfirmDialog( this, - GRI18n.getString(MODULE, promptMessageID), + prompt, lastOpenedFile == null ? GRI18n.getString(MODULE, "noTitleHeader") : lastOpenedFile.getName(), JOptionPane.YES_NO_CANCEL_OPTION); @@ -1262,7 +1252,7 @@ public void actionPerformed(ActionEvent e) { // We're currently logged in, but we might be dirty // so ask the user if it's OK to log out. - int response = saveOnPermission("logoutQuestion"); + int response = saveOnPermission("logoutQuestion", getCurrentGallery()); if (JOptionPane.CANCEL_OPTION == response) { return; @@ -1552,7 +1542,7 @@ private void openState(String fileToOpen) { } // Before we change galleries, ask them if they want to save. - int response = saveOnPermission("OK_toSaveBeforeClose"); + int response = saveOnPermission("OK_toSaveBeforeClose", null); if (JOptionPane.CANCEL_OPTION == response) { return; diff --git a/com/gallery/GalleryRemote/PictureInspector.java b/com/gallery/GalleryRemote/PictureInspector.java index 010f272..af21e60 100644 --- a/com/gallery/GalleryRemote/PictureInspector.java +++ b/com/gallery/GalleryRemote/PictureInspector.java @@ -212,9 +212,9 @@ private void jbInit() { , GridBagConstraints.WEST, GridBagConstraints.NONE, new Insets(0, 0, 0, 0), 0, 0)); add(jDeleteButton, new GridBagConstraints(1, 6, 1, 1, 0.0, 0.0 , GridBagConstraints.WEST, GridBagConstraints.NONE, new Insets(2, 0, 0, 0), 0, 0)); - this.add(jScrollPane1, new GridBagConstraints(1, 1, 1, 1, 1.0, 0.0 + add(jScrollPane1, new GridBagConstraints(1, 1, 1, 1, 1.0, 0.0 , GridBagConstraints.CENTER, GridBagConstraints.BOTH, new Insets(0, 0, 0, 0), 0, 0)); - this.add(jScrollPane2, new GridBagConstraints(1, 7, 1, 1, 1.0, 1.0 + add(jScrollPane2, new GridBagConstraints(1, 7, 1, 1, 1.0, 1.0 , GridBagConstraints.NORTH, GridBagConstraints.BOTH, new Insets(5, 0, 0, 0), 0, 0)); jScrollPane1.getViewport().add(jPath, null); jScrollPane2.getViewport().add(jCaption, null); diff --git a/com/gallery/GalleryRemote/model/Album.java b/com/gallery/GalleryRemote/model/Album.java index ffd4f67..a6a26ce 100644 --- a/com/gallery/GalleryRemote/model/Album.java +++ b/com/gallery/GalleryRemote/model/Album.java @@ -92,7 +92,7 @@ public class Album extends GalleryItem implements ListModel, Serializable, Prefe transient private Integer albumDepth; transient private boolean suppressEvents = false; - public static List extraFieldsNoShow = Arrays.asList(new String[]{GRI18n.getString(MODULE, "upDate"), GRI18n.getString(MODULE, "captDate")}); + public static List extraFieldsNoShow = Arrays.asList(new String[]{"Capture date", "Upload date", "Description"}); public Album(Gallery gallery) { @@ -627,7 +627,7 @@ public void setExtraFieldsString(String extraFieldsString) { while (st.hasMoreTokens()) { String name = st.nextToken(); - if (!extraFieldsNoShow.contains(name)) { + if (!extraFieldsNoShow.contains(name) && !extraFields.contains(name)) { extraFields.add(name); } } diff --git a/com/gallery/GalleryRemote/model/Gallery.java b/com/gallery/GalleryRemote/model/Gallery.java index d2a66ea..b35e6cb 100644 --- a/com/gallery/GalleryRemote/model/Gallery.java +++ b/com/gallery/GalleryRemote/model/Gallery.java @@ -28,10 +28,7 @@ import javax.swing.*; import javax.swing.event.*; -import javax.swing.tree.TreeModel; -import javax.swing.tree.TreePath; import javax.swing.tree.DefaultTreeModel; -import javax.swing.tree.DefaultMutableTreeNode; import java.io.File; import java.io.Serializable; import java.net.MalformedURLException; @@ -59,11 +56,7 @@ public class Gallery extends DefaultTreeModel implements Serializable, Preferenc String username; String password; String alias; - //ArrayList albumList = null; - //Album selectedAlbum = null; int type = TYPE_STANDALONE; - //Album root = null; - //ArrayList rootAlbums = new ArrayList(); transient GalleryComm comm = null; @@ -151,147 +144,18 @@ public String doNewAlbum(Album a, StatusUpdate su) { } public void logOut() { - boolean logout = true; - - //albumList = null; - //selectedAlbum = null; if (comm != null) { comm.logOut(); } comm = null; - if (logout) { - //albumList = null; - //rootAlbums.clear(); - //selectedAlbum = null; - setRoot(null); - - if (comm != null) { - comm.logOut(); - } - comm = null; - - //reload(); - } + setRoot(null); } /* * **** Gallery contents handling **** */ - /*public void setAlbumList(ArrayList albumList) { - if (albumList == null) { - throw new IllegalArgumentException("Must supply non-null album list."); - } - - ArrayList oldList = this.albumList; - this.albumList = albumList; - if (albumList.size() > 0) { - selectedAlbum = (Album) this.albumList.get(0); - } - - if (oldList != null) { - for (Iterator i = oldList.iterator(); i.hasNext();) { - Album a = (Album) i.next(); - - //Log.log(Log.LEVEL_TRACE, MODULE, a.toString()); - if (!a.getPicturesList().isEmpty()) { - Log.log(Log.LEVEL_TRACE, MODULE, "Album " + a + " had pictures"); - int j = albumList.indexOf(a); - - if (j != -1) { - Album newAlbum = (Album) albumList.get(j); - newAlbum.setPicturesList(a.getPicturesList()); - } - } - } - } - - refreshRootAlbums(); - - reload(); - }*/ - - /*public void refreshRootAlbums() { - rootAlbums.clear(); - - for (Iterator it = albumList.iterator(); it.hasNext();) { - Album album = (Album) it.next(); - - if (album.getParentAlbum() == null) { - rootAlbums.add(album); - } - } - }*/ - - /** - * Adds an album to the gallery and selects the first one added. - */ - /*public synchronized void addAlbum(Album a) { - if (a == null) { - throw new IllegalArgumentException("Must supply non-null album."); - } - - // when the first album becomes available, make sure to select - // it in the list - boolean firstAlbum = false; - - // lazy allocation - if (this.albumList == null) { - this.albumList = new ArrayList(); - firstAlbum = true; - } - - albumList.add(a); - - if (firstAlbum) { - selectedAlbum = (Album) this.albumList.get(0); - } - - //notifyListeners(); - if (a.getParentAlbum() == null) { - fireTreeNodesInserted(this, getObjectArrayForAlbum(root), - new int[] { rootAlbums.indexOf(a) }, - new Object[] { a }); - } else { - fireTreeNodesInserted(this, getObjectArrayForAlbum(a.getParentAlbum()), - new int[] { a.getParentAlbum().subAlbums.indexOf(a) }, - new Object[] { a }); - } - }*/ - - /*public void addRootAlbum(Album a) { - rootAlbums.add(a); - - //fireTreeNodesInserted(this, new Object[] { root }, - // new int[] { rootAlbums.indexOf(a) }, - // new Object[] { a }); - fireTreeStructureChanged(this, new TreePath(root)); - }*/ - - /*public void removeRootAlbum(Album a) { - int index = rootAlbums.indexOf(a); - if (index != -1) { - rootAlbums.remove(a); - - //fireTreeNodesRemoved(this, new Object[] { root }, - // new int[] { index }, - // new Object[] { a }); - //fireTreeStructureChanged(this, getPathForAlbum(a)); - fireTreeStructureChanged(this, new TreePath(root)); - } - }*/ - - /*public ArrayList getAlbumList() { - return albumList; - } - - public void clearAlbumList() { - albumList.clear(); - - reload(); - }*/ - public File getGalleryDefaultFile() { StringBuffer defaultFilePath = new StringBuffer(); @@ -927,62 +791,6 @@ public static void uncacheAmbiguousUrl() { } } - /** - * this no longer works: the JTree is the only object that - * knows what the selected album is. This only works in - * JList context... - * - * @return - */ - /*public Album getSelectedAlbum() { - return selectedAlbum; - }*/ - - - /*public void setSelectedItem(Object anObject) { - if ((selectedAlbum != null && !selectedAlbum.equals(anObject)) || - selectedAlbum == null && anObject != null) { - selectedAlbum = (Album) anObject; - fireContentsChanged(this, -1, -1); - } - } - - public void fireContentsChanged(Object source, int index0, int index1) { - if (listenerList == null) listenerList = new EventListenerList(); - Object[] listeners = listenerList.getListenerList(); - ListDataEvent e = null; - - for (int i = listeners.length - 2; i >= 0; i -= 2) { - if (listeners[i] == ListDataListener.class) { - if (e == null) { - e = new ListDataEvent(source, ListDataEvent.CONTENTS_CHANGED, index0, index1); - } - ((ListDataListener) listeners[i + 1]).contentsChanged(e); - } - } - } - - public Object getSelectedItem() { - return selectedAlbum; - }*/ - - /*public void albumChanged(Album a) { - if (a == null) { - fireTreeNodesChanged(this, getObjectArrayForAlbum(root), null, null); - } else { - fireTreeNodesChanged(this, getObjectArrayForAlbum(a), null, null); - } - } - - public void albumStructureChanged(Album a) { - if (a == null) { - fireTreeStructureChanged(this, getPathForAlbum(root)); - } else { - fireTreeStructureChanged(this, getPathForAlbum(a)); - } - }*/ - - /* * Miscellaneous */ @@ -1012,46 +820,6 @@ public boolean hasComm() { return comm != null; } - /*void notifyListeners() { - //ListDataEvent lde; - if (albumList != null) { - //lde = new ListDataEvent( this, ListDataEvent.CONTENTS_CHANGED, 0, albumList.size() ); - fireContentsChanged(this, 0, albumList.size()); - } else { - //lde = new ListDataEvent( this, ListDataEvent.CONTENTS_CHANGED, 0, 0 ); - fireContentsChanged(this, 0, 0); - } - fireTreeStructureChanged(this, new TreePath(root)); - - //notifyListeners(lde); - }*/ - - /* - * ListModel Implementation - */ - /*public int getSize() { - if (albumList != null) { - return albumList.size(); - } else { - return 0; - } - } - - public Object getElementAt(int index) { - return albumList.get(index); - }*/ - - /*public void addListDataListener(ListDataListener l) { - if (listenerList == null) listenerList = new EventListenerList(); - listenerList.add(ListDataListener.class, l); - } - - - public void removeListDataListener(ListDataListener l) { - if (listenerList == null) listenerList = new EventListenerList(); - listenerList.remove(ListDataListener.class, l); - }*/ - public Album getAlbumByName(String name) { ArrayList albumList = getFlatAlbumList(); if (albumList == null || name == null) { diff --git a/com/gallery/GalleryRemote/prefs/PreferenceNames.java b/com/gallery/GalleryRemote/prefs/PreferenceNames.java index 1f84841..60f9012 100644 --- a/com/gallery/GalleryRemote/prefs/PreferenceNames.java +++ b/com/gallery/GalleryRemote/prefs/PreferenceNames.java @@ -76,6 +76,8 @@ public interface PreferenceNames { public static final String SUPPRESS_WARNING_JPEGTRAN = "suppressWarningJpegtran"; public static final String SUPPRESS_WARNING_JPEGTRAN_CROP = "suppressWarningJpegtranCrop"; public static final String SUPPRESS_WARNING_CORRUPTED = "suppressWarningCorrupted"; + public static final String SUPPRESS_WARNING_JAVA = "suppressWarningJava"; + public static final String USE_JAVA_RESIZE = "useJavaResize"; public static final String FONT_OVERRIDE_NAME = "fontOverrideName"; public static final String FONT_OVERRIDE_STYLE = "fontOverrideStyle"; public static final String FONT_OVERRIDE_SIZE = "fontOverrideSize"; diff --git a/com/gallery/GalleryRemote/resources/GRResources.properties b/com/gallery/GalleryRemote/resources/GRResources.properties index 2480606..68c6ee6 100644 --- a/com/gallery/GalleryRemote/resources/GRResources.properties +++ b/com/gallery/GalleryRemote/resources/GRResources.properties @@ -54,8 +54,6 @@ MainFrame.quitQuestion.title = Warning #Album module Album.title = Not yet connected to Gallery -Album.upDate = Upload Date -Album.captDate = Capture Date Album.ro = (read-only) @@ -462,12 +460,6 @@ UploadProgress.shutDownTip = Shut down the computer when the transfer completes UploadProgress.shutDown = Shutdown computer when done UploadProgress.Error = Error - -# Gallery model -Gallery.logoutQuestion = Logging out will lose all the work you have performed on this Gallery. You may want to save first.\n\nLog out anyway? -Gallery.logoutQuestion.title = Warning - - # ImageUtils ImageUtils.down.start = Downloading {0} from server... ImageUtils.down.end = Finished downloading {0} @@ -493,7 +485,10 @@ ImageUtils.warningTextJpegtranCrop=An optional part of Gallery Remote, You can find out how to fix this by going to this page: ImageUtils.warningUrlJpegtranCrop=http://gallery.menalto.com/modules.php?op=modload&name=GalleryDocs&file=index&page=gallery-remote.problems.php ImageUtils.warningUrlTextJpegtranCrop=Gallery Remote Known Problems - +ImageUtils.warningTextJava=Using Java as a fallback to resize pictures will cause them to lose their EXIF data.
\ + Do you want to resize with Gallery Remote anyway, or let the server perform the resize (longer upload time). +ImageUtils.useJava=Resize in GR +ImageUtils.dontUseJava=Don't resize in GR # AppletMini AppletMini.Upload = Upload diff --git a/com/gallery/GalleryRemote/resources/GRResources_ca.properties b/com/gallery/GalleryRemote/resources/GRResources_ca.properties index 70f3e72..88d82a8 100644 --- a/com/gallery/GalleryRemote/resources/GRResources_ca.properties +++ b/com/gallery/GalleryRemote/resources/GRResources_ca.properties @@ -45,8 +45,6 @@ MainFrame.quitQuestion.title = Atenci #Album module Album.title = Encara no connectat a la Galeria -Album.upDate = Data d'enviament -Album.captDate = Data de captura Album.ro = (només lectura) @@ -355,11 +353,6 @@ UploadProgress.shutDownTip = Tanca l'ordinador quan la transfer UploadProgress.shutDown = Tanca l'ordinador quan acabi UploadProgress.Error = Error - -# Gallery model -Gallery.logoutQuestion = Desautenticant-se es perdrŕ tota la feina realitzada en aquesta Gallery. S'hauria potser de guardar abans.\n\nDesautenticar-se igualment? -Gallery.logoutQuestion.title = Atenció - # ImageUtils ImageUtils.warningTitle=Atenció ImageUtils.warningOK=OK diff --git a/com/gallery/GalleryRemote/resources/GRResources_de.properties b/com/gallery/GalleryRemote/resources/GRResources_de.properties index 9a120e0..f04c3b7 100644 --- a/com/gallery/GalleryRemote/resources/GRResources_de.properties +++ b/com/gallery/GalleryRemote/resources/GRResources_de.properties @@ -24,10 +24,8 @@ AlbmInspec.res2H=Gr\u00F6\u00DFen\u00E4nderung auf H\u00F6he AlbmInspec.res2W=Gr\u00F6\u00DFen\u00E4nderung auf Breite AlbmInspec.resBfrUpld=Vor dem Hochladen die Gr\u00F6\u00DFe \u00E4ndern AlbmInspec.resBfrUpldTip=Weist Gallery Remote an, die Bilder vor dem Hochladen auf die richtige Gr\u00F6\u00DFe zu verkleinern. Dies spart Bandbreite, ist aber nur dann m\u00F6glich, wenn ImageMagick installiert ist. -Album.captDate=Datum holen Album.ro=(nur-lesen) Album.title=Noch nicht mit Gallery verbunden -Album.upDate=\u00DCbertragungsdatum AppletMini.Add=Bilder hinzuf\u00FCgen... AppletMini.DefMessage=Bilder zur Liste hinzuf\u00FCgen... AppletMini.Upload=Hochladen @@ -49,7 +47,6 @@ GEdiDlog.typeTip=Verwende Standalone wenn deine Gallery in kein Content Manageme GalComm2.passwd=Kennwort GalComm2.passwdLbl=Kennwort GalComm2.rootAlbum=Stammalbum -Gallery.logoutQuestion.title=Warnung GeneralPa.icon=General GeneralPa.label2=x GeneralPa.lang=Sprache diff --git a/com/gallery/GalleryRemote/resources/GRResources_fr.properties b/com/gallery/GalleryRemote/resources/GRResources_fr.properties index 00aed72..2c96b05 100644 --- a/com/gallery/GalleryRemote/resources/GRResources_fr.properties +++ b/com/gallery/GalleryRemote/resources/GRResources_fr.properties @@ -26,10 +26,8 @@ AlbmInspec.res2H=Redimensionner \u00E0 la hauteur AlbmInspec.res2W=Redimensionner \u00E0 la largeur AlbmInspec.resBfrUpld=Redimensionner avant l'envoi AlbmInspec.resBfrUpldTip=Demande \u00E0 Gallery Remote de redimensionner les images avant l'envoi au serveur, ce qui \u00E9conomise de la bande passante. Possible uniquement si ImageMagick est install\u00E9. -Album.captDate=Date de capture Album.ro=(Lecture seule) Album.title=Pas encore connect\u00E9 \u00E0 Gallery -Album.upDate=Date d'envoi AppletMini.Add=Ajouter des images... AppletMini.DefMessage=Ajouter des images \u00E0 la liste... AppletMini.Upload=Envoyer @@ -127,8 +125,6 @@ GalComm2.upSucc=L'envoi s'est termin\u00E9 avec succ\u00E8s GalComm2.username=Identifiant GalComm2.usernameLbl=Identifiant \: GalComm2.usrpwdErr=Mauvais identifiant/mot de passe. Si votre Gallery est int\u00E9gr\u00E9 dans un CMS comme PostNuke, vous devez utiliser l'URL "native" de Gallery pour vous connecter, ainsi que l'identifiant et le mot de passe "natifs" de Gallery. Vous pouvez les tester en allant sur l'URL "native" et en essayant de vous connecter. -Gallery.logoutQuestion=Vous d\u00E9connecter sans avoir sauvegard\u00E9 auparavant entra\u00EEnera la perte de toutes vos modifications effectu\u00E9es sur cette Gallery. Voulez-vous quand m\u00EAme vous d\u00E9connecter ? -Gallery.logoutQuestion.title=Attention GeneralPa.icon=G\u00E9n\u00E9rales GeneralPa.label2=x GeneralPa.lang=Langue @@ -182,7 +178,7 @@ MainFrame.cbmenuThumb=Afficher les miniatures MainFrame.gllryCombo=S\u00E9lectionnez une Gallery \u00E0 laquelle vous souhaitez vous connecter MainFrame.inspDvdr=Images et albums de la Gallery courante MainFrame.loginButtonTip=Se connecter ou se d\u00E9connecter de la Gallery s\u00E9lectionn\u00E9e. Vous pouvez vous connecter \u00E0 plusieurs Gallery simultan\u00E9ment. -MainFrame.logoutQuestion=Vous d\u00E9connecter entra\u00EEnera la perte de toutes les modifications effectu\u00E9es sur la Gallery {0} que vous n'avez pas encore envoy\u00E9es. Voulez-vous quand m\u00EAme vous d\u00E9connecter ? +MainFrame.logoutQuestion=Vous d\u00E9connecter entra\u00EEnera la perte de toutes les modifications effectu\u00E9es sur la Gallery {0} que vous n'avez pas encore envoy\u00E9es. Voulez-vous enregistrer avant de vous d\u00E9connecter ? MainFrame.manySel=Images MainFrame.menuAbout=A propos de Gallery Remote... MainFrame.menuClearCache=Vider la cache diff --git a/com/gallery/GalleryRemote/util/GRI18n.java b/com/gallery/GalleryRemote/util/GRI18n.java index 4ec8911..065aeb6 100644 --- a/com/gallery/GalleryRemote/util/GRI18n.java +++ b/com/gallery/GalleryRemote/util/GRI18n.java @@ -214,8 +214,13 @@ private static List initAvailableLocales() { // perf optimization: don't go through all the regions if the main language was not found if (!loc.startsWith(prefix)) { prefix = loc; + if (devMode) { + Log.log(Log.LEVEL_TRACE, MODULE, "Trying locale: " + loc); + } + locPath = (devMode?RESNAME_DEV:RESPATH) + "_" + loc + ".properties"; if (ClassLoader.getSystemClassLoader().getResource(locPath) != null) { + Log.log(Log.LEVEL_INFO, MODULE, "Found locale: " + loc); aList.add(list[i]); prefix = "##DUMMY"; } diff --git a/com/gallery/GalleryRemote/util/ImageUtils.java b/com/gallery/GalleryRemote/util/ImageUtils.java index 060e561..d57d0df 100644 --- a/com/gallery/GalleryRemote/util/ImageUtils.java +++ b/com/gallery/GalleryRemote/util/ImageUtils.java @@ -286,7 +286,11 @@ public static File resize(String filename, Dimension d, Rectangle cropTo) { if (!useIM && r == null) { r = resizeJava(filename, d); - //throw new UnsupportedOperationException("IM must be installed for this operation"); + + if (r == null) { + Log.log(Log.LEVEL_TRACE, MODULE, "All methods of resize failed: sending original file"); + r = new File(filename); + } } long time = System.currentTimeMillis() - start; @@ -300,6 +304,16 @@ public static File resize(String filename, Dimension d, Rectangle cropTo) { public static File resizeJava(String filename, Dimension d) { File r = null; + if (!GalleryRemote._().properties.getBooleanProperty(PreferenceNames.USE_JAVA_RESIZE)) { + return null; + } + + if (!GalleryRemote._().properties.getBooleanProperty(PreferenceNames.SUPPRESS_WARNING_JAVA)) { + if (stopUsingJavaResize()) { + return null; + } + } + try { // read the image ImageInputStream iis = ImageIO.createImageInputStream(new File(filename)); @@ -445,8 +459,6 @@ public static File rotate(String filename, int angle, boolean flip, boolean rese resetExifOrientation(filename); }*/ - } catch (IOException e1) { - Log.logException(Log.LEVEL_ERROR, MODULE, e1); } finally { if (orig != null && dest != null) { dest.renameTo(orig); @@ -483,8 +495,6 @@ public static File losslessCrop(String filename, Rectangle cropTo) { r = jpegtranExec(filename, "-crop", cropTo.width + "x" + cropTo.height + "+" + cropTo.x + "+" + cropTo.y, true); - } catch (IOException e1) { - Log.logException(Log.LEVEL_ERROR, MODULE, e1); } finally { if (orig != null && dest != null) { dest.renameTo(orig); @@ -499,7 +509,7 @@ public static File losslessCrop(String filename, Rectangle cropTo) { return r; } - private static File jpegtranExec(String filename, String arg1, String arg2, boolean crop) throws IOException { + private static File jpegtranExec(String filename, String arg1, String arg2, boolean crop) { File r; ArrayList cmd = new ArrayList(); cmd.add(jpegtranPath); @@ -1134,6 +1144,25 @@ static void stopUsingIM() { } } + static boolean stopUsingJavaResize() { + UrlMessageDialog md = new UrlMessageDialog( + GRI18n.getString(MODULE, "warningTextJava"), + null, + null, + GRI18n.getString(MODULE, "useJava"), + GRI18n.getString(MODULE, "dontUseJava") + ); + + boolean useJavaResize = (md.getButtonChosen() == 1); + + if (md.dontShow()) { + GalleryRemote._().properties.setBooleanProperty(PreferenceNames.SUPPRESS_WARNING_JAVA, true); + GalleryRemote._().properties.setBooleanProperty(PreferenceNames.USE_JAVA_RESIZE, useJavaResize); + } + + return !useJavaResize; + } + static void stopUsingJpegtran() { useJpegtran = false; diff --git a/com/gallery/GalleryRemote/util/UrlMessageDialog.java b/com/gallery/GalleryRemote/util/UrlMessageDialog.java index 6b3c1bf..a1889db 100644 --- a/com/gallery/GalleryRemote/util/UrlMessageDialog.java +++ b/com/gallery/GalleryRemote/util/UrlMessageDialog.java @@ -12,15 +12,24 @@ * User: paour * Date: Jan 13, 2004 */ -public class UrlMessageDialog extends JDialog { +public class UrlMessageDialog extends JDialog implements ActionListener { public static final String MODULE = "ImageUtils"; + JLabel jIcon = new JLabel(); JLabel jMessage = new JLabel(); BrowserLink jURL = new BrowserLink(); JCheckBox jDontShow = new JCheckBox(); - JButton jOk = new JButton(); + JButton jButton1 = new JButton(); + JButton jButton2 = new JButton(); + JPanel jButtons = new JPanel(new GridLayout(1, 0, 5, 0)); + + int buttonChosen = 0; public UrlMessageDialog(String message, String url, String urlText) { + this(message, url, urlText, null, null); + } + + public UrlMessageDialog(String message, String url, String urlText, String button1Label, String button2Label) { super(GalleryRemote._().getMainFrame(), GRI18n.getString(MODULE, "warningTitle"), true); @@ -30,33 +39,48 @@ public UrlMessageDialog(String message, String url, String urlText) { getContentPane().setLayout(new GridBagLayout()); jMessage.setText(message); - if (urlText != null) { - jURL.setText(urlText); - } else { - jURL.setText(url); + if (url != null) { + if (urlText != null) { + jURL.setText(urlText); + } else { + jURL.setText(url); + } + + jURL.setUrl(url); } - - jURL.setUrl(url); + jDontShow.setText(GRI18n.getString(MODULE, "warningDontShow")); - jOk.setText(GRI18n.getString("Common", "OK")); - jOk.addActionListener(new ActionListener() { - public void actionPerformed(ActionEvent e) { - setVisible(false); - } - }); + + if (button1Label != null) { + jButton1.setText(button1Label); + } else { + jButton1.setText(GRI18n.getString("Common", "OK")); + } + jButton1.addActionListener(this); + + if (button2Label != null) { + jButton2.setText(button2Label); + jButton2.addActionListener(this); + } getContentPane().add(jIcon, new GridBagConstraints(0, 0, 1, 1, 0.0, 0.0 , GridBagConstraints.NORTH, GridBagConstraints.NONE, new Insets(5, 5, 0, 10), 0, 0)); getContentPane().add(jMessage, new GridBagConstraints(1, 0, 2, 1, 1.0, 1.0 , GridBagConstraints.CENTER, GridBagConstraints.NONE, new Insets(5, 0, 0, 5), 0, 0)); - getContentPane().add(jURL, new GridBagConstraints(1, 1, 2, 1, 0.0, 0.0 - , GridBagConstraints.WEST, GridBagConstraints.NONE, new Insets(5, 0, 0, 5), 0, 0)); + if (url != null) { + getContentPane().add(jURL, new GridBagConstraints(1, 1, 2, 1, 0.0, 0.0 + , GridBagConstraints.WEST, GridBagConstraints.NONE, new Insets(5, 0, 0, 5), 0, 0)); + } getContentPane().add(jDontShow, new GridBagConstraints(1, 2, 1, 1, 0.0, 0.0 , GridBagConstraints.CENTER, GridBagConstraints.NONE, new Insets(5, 0, 0, 5), 0, 0)); - getContentPane().add(jOk, new GridBagConstraints(2, 2, 1, 2, 0.0, 0.0 + getContentPane().add(jButtons, new GridBagConstraints(2, 2, 1, 2, 0.0, 0.0 , GridBagConstraints.EAST, GridBagConstraints.NONE, new Insets(5, 0, 5, 5), 0, 0)); + jButtons.add(jButton1); + if (button2Label != null) { + jButtons.add(jButton2); + } - getRootPane().setDefaultButton(jOk); + getRootPane().setDefaultButton(jButton1); pack(); @@ -65,7 +89,21 @@ public void actionPerformed(ActionEvent e) { setVisible(true); } + public void actionPerformed(ActionEvent e) { + if (e.getSource() == jButton1) { + buttonChosen = 1; + } else { + buttonChosen = 2; + } + + setVisible(false); + } + public boolean dontShow() { return jDontShow.isSelected(); } + + public int getButtonChosen() { + return buttonChosen; + } } diff --git a/defaults.properties b/defaults.properties index e22e627..86039e5 100644 --- a/defaults.properties +++ b/defaults.properties @@ -44,6 +44,11 @@ htmlEscapeCaptions=false # after a drag-and-drop or a Add images... Disable it for greater speed. exifAutorotate=true +# if jpegtran is not found, GR can resize images in Java code, but that loses +# the exif data. Set to false to prevent Java resize fallback (the Gallery +# will perform the resize to its default if needed +useJavaResize=true + # # --- Proxy --- # @@ -110,9 +115,12 @@ uiLocale= suppressWarningIM=false suppressWarningJpegtran=false -# Warning windows for corruped galleries +# Warning window for corrupted galleries suppressWarningCorrupted=false +# Warning window for EXIF loss when using Java resize +suppressWarningJava=false + # # --- File Menu --- # @@ -222,6 +230,6 @@ updateUrlBeta=http://gallery.sourceforge.net/gallery_remote_version_check_beta.p # # --- Do not edit below this line --- # -version=1.4-b16 -releaseDate=2004/06/24 +version=1.4-b17 +releaseDate=2004/07/09 aboutText=Gallery Remote\n \n \nA part of the Gallery Open-Source Project\nhttp://gallery.sourceforge.net\n \n \nMaintained by:\n \nPierre-Luc Paour\n \n \nInitial version by Chris Smith\n \n \nContributors:\n \nTim Miller\nDolan Halbrook\nMarkus Cozowicz\nScott Gartner\nAmedeo Paglione\nChris Schwerdt\n \n \nArtwork by Ross A. Reyman\n \n \nBundled software:\n \nImageMagick\nJSX\nJava look and feel Graphics Repository icons\njpegtran, Guido Vollbeding's version\nMetadataExtractor diff --git a/gallery_remote.iap_xml b/gallery_remote.iap_xml index 3ccdaae..ca37c2f 100644 --- a/gallery_remote.iap_xml +++ b/gallery_remote.iap_xml @@ -1,18 +1,18 @@ - - + DATE: Fri Jul 09 15:18:04 PDT 2004 --> + - - 54,46,48,32,69,110,116,101,114,112,114,105,115,101,32,66,117,105,108,100,32,50,50,54,50 + + 54,46,49,32,69,110,116,101,114,112,114,105,115,101,32,66,117,105,108,100,32,50,51,50,53 12,42,11,90,81,52,54,53,54,68,86,83,81,54,80,74 3,13,71,87,105,110,100,111,119,115,32,88,80,44,32,53,46,49,44,32,120,56,54,59,32,74,97,118,97,32,49,46,51,46,49,95,48,56,44,32,83,117,110,32,77,105,99,114,111,115,121,115,116,101,109,115,32,73,110,99,46,44,32,104,116,116,112,58,47,47,106,97,118,97,46,115,117,110,46,99,111,109,47,59,32,101,110,44,32,85,83,59,32,67,112,49,50,53,50 - 1,0,0,-16,-61,-17,48,-16,80,112,116,103,88,98,113,97,113,65,65,88,74,65,72,71,70,69,64,69,66,69,48,79,87,5,2,2,14,88,101,10,0,0,0 + 1,0,0,-16,-93,-13,0,-128,80,112,116,103,88,98,113,97,113,65,65,88,74,65,72,71,70,69,64,69,66,69,48,79,87,5,2,2,11,108,101,13,0,0,0 - + @@ -179,7 +179,7 @@ it will search for ones in this list]]> - + @@ -263,7 +263,7 @@ and any path to a file to read from that file]]> - 532681 + 566800 false @@ -328,12 +328,41 @@ and any path to a file to read from that file]]> false - 0 + 1 false + + + + + + + + + false + + + + + + true + + + + + + 24555 + + + false + + + 0 + + @@ -1013,10 +1042,10 @@ and any path to a file to read from that file]]> true - false + true - false + true @@ -1637,7 +1666,7 @@ If the commands above do not work, you should download and install these package - + @@ -1685,7 +1714,7 @@ If the commands above do not work, you should download and install these package - + @@ -1816,6 +1845,9 @@ If the commands above do not work, you should download and install these package + + 0 + @@ -1897,10 +1929,10 @@ If the commands above do not work, you should download and install these package 1 - 3 + 4 - 2 + 0 0 @@ -2397,7 +2429,7 @@ and any path to a file to read from that file]]> false - 0 + 1 false @@ -2427,7 +2459,7 @@ and any path to a file to read from that file]]> - 31509 + 41350 false @@ -2456,7 +2488,7 @@ and any path to a file to read from that file]]> - 5080 + 6436 false @@ -2596,7 +2628,7 @@ and any path to a file to read from that file]]> - 330 + 395 false @@ -2626,9 +2658,6 @@ and any path to a file to read from that file]]> - - - @@ -2672,6 +2701,9 @@ and any path to a file to read from that file]]> + + + @@ -2726,7 +2758,7 @@ and any path to a file to read from that file]]> - 317 + 382 false @@ -2756,6 +2788,9 @@ and any path to a file to read from that file]]> + + + @@ -2831,7 +2866,7 @@ and any path to a file to read from that file]]> false - 0 + 1 false @@ -2858,6 +2893,9 @@ and any path to a file to read from that file]]> + + + @@ -2912,40 +2950,6 @@ and any path to a file to read from that file]]> - - - - - - - - - false - - - - - - true - - - - - - false - - - 0 - - - false - - - - - - - @@ -2966,7 +2970,7 @@ and any path to a file to read from that file]]> - 7922 + 8137 false @@ -2995,7 +2999,7 @@ and any path to a file to read from that file]]> - 6726 + 7710 false @@ -3082,7 +3086,7 @@ and any path to a file to read from that file]]> - 45916 + 46226 false @@ -3111,7 +3115,7 @@ and any path to a file to read from that file]]> - 5825 + 5910 false @@ -3140,7 +3144,7 @@ and any path to a file to read from that file]]> - 10760 + 10820 false @@ -3198,7 +3202,7 @@ and any path to a file to read from that file]]> - 7505 + 8499 false @@ -3309,7 +3313,7 @@ and any path to a file to read from that file]]> false - 0 + 1 false @@ -3324,79 +3328,6 @@ and any path to a file to read from that file]]> - - - - - - - - - - false - - - - - - true - - - - - - false - - - 0 - - - false - - - - - - - - - - - false - - - - - - true - - - - - - false - - - 0 - - - false - - - - - - - - - - - - - - - - @@ -3561,7 +3492,7 @@ it will search for ones in this list]]> - + @@ -3621,76 +3552,56 @@ and any path to a file to read from that file]]> - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + + + + + + + + + false + + + + + + true + + + + + + false + + + 16162 + + + false + - - - 1 - - - 0 - - - 0 - - - 0 - - - + - + false - + true - + - 1041 + 11032 false @@ -3699,46 +3610,455 @@ and any path to a file to read from that file]]> 0 - - - - + - + - + false - + true - + - - 1033 + + false + + + 1 false - - 0 - - - - - - - - - - + + + + + + + + + + + + + + + + + + + + + + + + + false + + + + + + true + + + + + + 105684 + + + false + + + 0 + + + + + + + + + + + false + + + + + + true + + + + + + 378 + + + false + + + 0 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + false + + + + + + true + + + + + + false + + + 1 + + + false + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + false + + + + + + true + + + + + + false + + + 1 + + + false + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + 1 + + + 0 + + + 0 + + + 0 + + + + + + + + + + + false + + + + + + true + + + + + + 1041 + + + false + + + 0 + + + + + + + + + + + + + + false + + + + + + true + + + + + + 1048 + + + false + + + 0 + + + + + + + @@ -3798,6 +4118,9 @@ and any path to a file to read from that file]]> + + + @@ -3831,6 +4154,87 @@ and any path to a file to read from that file]]> 0 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + @@ -4055,7 +4459,7 @@ and any path to a file to read from that file]]> - 1056 + 1071 false @@ -4085,6 +4489,9 @@ and any path to a file to read from that file]]> + + + @@ -4391,7 +4798,7 @@ and any path to a file to read from that file]]> false - 0 + 1 false @@ -4423,7 +4830,7 @@ and any path to a file to read from that file]]> false - 0 + 1 false @@ -4777,13 +5184,13 @@ and any path to a file to read from that file]]> false - 0 + 1 false - + @@ -4804,13 +5211,13 @@ and any path to a file to read from that file]]> + + + - - - @@ -4847,6 +5254,15 @@ and any path to a file to read from that file]]> + + + + + + + + + @@ -4868,6 +5284,116 @@ and any path to a file to read from that file]]> + + + + + + + + + false + + + + + + true + + + + + + 1064 + + + false + + + 0 + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + @@ -4891,7 +5417,7 @@ and any path to a file to read from that file]]> false - 0 + 1 false @@ -4903,6 +5429,7 @@ and any path to a file to read from that file]]> +