+ allow simple skipping of conflicting rename operations
This commit is contained in:
parent
029abe25b8
commit
24044a434f
|
@ -100,6 +100,24 @@ public enum StandardRenameAction implements RenameAction {
|
|||
}
|
||||
};
|
||||
|
||||
public String getDisplayName() {
|
||||
switch (this) {
|
||||
case MOVE:
|
||||
return "Rename";
|
||||
case COPY:
|
||||
return "Copy";
|
||||
case KEEPLINK:
|
||||
return "Keeplink";
|
||||
case SYMLINK:
|
||||
return "Symlink";
|
||||
case HARDLINK:
|
||||
return "Hardlink";
|
||||
default:
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
public static StandardRenameAction forName(String action) {
|
||||
for (StandardRenameAction it : values()) {
|
||||
if (it.name().equalsIgnoreCase(action))
|
||||
|
@ -108,4 +126,5 @@ public enum StandardRenameAction implements RenameAction {
|
|||
|
||||
throw new IllegalArgumentException("Illegal rename action: " + action);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
Binary file not shown.
Before Width: | Height: | Size: 883 B After Width: | Height: | Size: 592 B |
|
@ -3,6 +3,7 @@ package net.sourceforge.filebot.ui.rename;
|
|||
|
||||
|
||||
import static java.util.Collections.*;
|
||||
import static javax.swing.JOptionPane.*;
|
||||
import static net.sourceforge.filebot.Settings.*;
|
||||
import static net.sourceforge.filebot.ui.NotificationLogging.*;
|
||||
import static net.sourceforge.tuned.ExceptionUtilities.*;
|
||||
|
@ -10,6 +11,7 @@ import static net.sourceforge.tuned.FileUtilities.*;
|
|||
import static net.sourceforge.tuned.ui.TunedUtilities.*;
|
||||
|
||||
import java.awt.Cursor;
|
||||
import java.awt.Dimension;
|
||||
import java.awt.Window;
|
||||
import java.awt.event.ActionEvent;
|
||||
import java.beans.PropertyChangeEvent;
|
||||
|
@ -34,6 +36,9 @@ import java.util.logging.Logger;
|
|||
|
||||
import javax.swing.AbstractAction;
|
||||
import javax.swing.Icon;
|
||||
import javax.swing.JList;
|
||||
import javax.swing.JOptionPane;
|
||||
import javax.swing.JScrollPane;
|
||||
import javax.swing.SwingWorker;
|
||||
|
||||
import net.sourceforge.filebot.Analytics;
|
||||
|
@ -76,8 +81,11 @@ class RenameAction extends AbstractAction {
|
|||
return;
|
||||
}
|
||||
|
||||
Map<File, File> renameMap = checkRenamePlan(validate(model.getRenameMap(), window));
|
||||
Map<File, File> renameMap = checkRenamePlan(validate(model.getRenameMap(), window), window);
|
||||
StandardRenameAction action = (StandardRenameAction) getValue(RENAME_ACTION);
|
||||
if (renameMap.isEmpty()) {
|
||||
return;
|
||||
}
|
||||
|
||||
// start processing
|
||||
window.setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
|
||||
|
@ -138,10 +146,11 @@ class RenameAction extends AbstractAction {
|
|||
}
|
||||
|
||||
|
||||
private Map<File, File> checkRenamePlan(List<Entry<File, File>> renamePlan) {
|
||||
private Map<File, File> checkRenamePlan(List<Entry<File, File>> renamePlan, Window parent) {
|
||||
// build rename map and perform some sanity checks
|
||||
Map<File, File> renameMap = new HashMap<File, File>();
|
||||
Set<File> destinationSet = new HashSet<File>();
|
||||
List<String> issues = new ArrayList<String>();
|
||||
|
||||
for (Entry<File, File> mapping : renamePlan) {
|
||||
File source = mapping.getKey();
|
||||
|
@ -153,18 +162,44 @@ class RenameAction extends AbstractAction {
|
|||
destination = new File(source.getParentFile(), destination.getPath());
|
||||
}
|
||||
|
||||
if (renameMap.containsKey(source))
|
||||
throw new IllegalArgumentException("Duplicate source file: " + source.getName());
|
||||
try {
|
||||
if (renameMap.containsKey(source))
|
||||
throw new IllegalArgumentException("Duplicate source file: " + source.getPath());
|
||||
|
||||
if (destinationSet.contains(destination))
|
||||
throw new IllegalArgumentException("Conflict detected: " + mapping.getValue().getPath());
|
||||
|
||||
if (destination.exists() && !source.equals(destination))
|
||||
throw new IllegalArgumentException("File already exists: " + mapping.getValue().getPath());
|
||||
|
||||
// use original mapping values
|
||||
renameMap.put(mapping.getKey(), mapping.getValue());
|
||||
destinationSet.add(destination);
|
||||
} catch (Exception e) {
|
||||
issues.add(e.getMessage());
|
||||
}
|
||||
}
|
||||
|
||||
if (issues.size() > 0) {
|
||||
String text = "Unable to rename files:";
|
||||
JList issuesComponent = new JList(issues.toArray()) {
|
||||
|
||||
@Override
|
||||
public Dimension getPreferredScrollableViewportSize() {
|
||||
// adjust component size
|
||||
return new Dimension(80, 80);
|
||||
}
|
||||
};
|
||||
Object[] message = new Object[] { text, new JScrollPane(issuesComponent) };
|
||||
String[] actions = new String[] { "Continue", "Cancel" };
|
||||
JOptionPane pane = new JOptionPane(message, PLAIN_MESSAGE, YES_NO_OPTION, null, actions, actions[1]);
|
||||
|
||||
if (destinationSet.contains(destination))
|
||||
throw new IllegalArgumentException("Conflict detected: " + mapping.getValue());
|
||||
// display option dialog
|
||||
pane.createDialog(getWindow(parent), "Conflicting Files").setVisible(true);
|
||||
|
||||
if (destination.exists() && !source.equals(destination))
|
||||
throw new IllegalArgumentException("File already exists: " + mapping.getValue());
|
||||
|
||||
// use original mapping values
|
||||
renameMap.put(mapping.getKey(), mapping.getValue());
|
||||
destinationSet.add(destination);
|
||||
if (pane.getValue() != actions[0]) {
|
||||
return emptyMap();
|
||||
}
|
||||
}
|
||||
|
||||
return renameMap;
|
||||
|
|
|
@ -110,7 +110,7 @@ class RenameListCellRenderer extends DefaultFancyListCellRenderer {
|
|||
setText(isSelected || matchProbablity < 1 ? formatPath(path) : colorizePath(path, true));
|
||||
|
||||
String ext = getExtension(path);
|
||||
typeRenderer.setText(ext != null ? ext.toLowerCase() : "!");
|
||||
typeRenderer.setText(ext != null ? ext.toLowerCase() : "NO EXTENSION");
|
||||
if (file.isDirectory()) {
|
||||
typeRenderer.setText("Folder");
|
||||
}
|
||||
|
|
|
@ -174,7 +174,8 @@ public class RenamePanel extends JComponent {
|
|||
namesList.getButtonPanel().add(settingsButton, "gap indent");
|
||||
|
||||
// open rename log button
|
||||
filesList.getButtonPanel().add(createImageButton(openHistoryAction), "gap 0");
|
||||
filesList.getButtonPanel().add(createImageButton(clearFilesAction), "gap 0");
|
||||
filesList.getButtonPanel().add(createImageButton(openHistoryAction), "gap indent");
|
||||
|
||||
// reveal file location on double click
|
||||
filesList.getListComponent().addMouseListener(new MouseAdapter() {
|
||||
|
@ -361,12 +362,24 @@ public class RenamePanel extends JComponent {
|
|||
|
||||
actionPopup.addDescription(new JLabel("Action:"));
|
||||
for (StandardRenameAction action : EnumSet.of(StandardRenameAction.MOVE, StandardRenameAction.COPY, StandardRenameAction.KEEPLINK, StandardRenameAction.SYMLINK, StandardRenameAction.HARDLINK)) {
|
||||
actionPopup.add(new SetRenameAction(action, action.toString().toLowerCase(), ResourceManager.getIcon("rename.action." + action.toString().toLowerCase())));
|
||||
actionPopup.add(new SetRenameAction(action, action.getDisplayName(), ResourceManager.getIcon("rename.action." + action.toString().toLowerCase())));
|
||||
}
|
||||
|
||||
return actionPopup;
|
||||
}
|
||||
|
||||
protected final Action clearFilesAction = new AbstractAction("Clear Files", ResourceManager.getIcon("action.clear")) {
|
||||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent evt) {
|
||||
if ((evt.getModifiers() & ActionEvent.SHIFT_MASK) != 0) {
|
||||
renameModel.files().clear();
|
||||
} else {
|
||||
renameModel.clear();
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
protected final Action openHistoryAction = new AbstractAction("Open History", ResourceManager.getIcon("action.report")) {
|
||||
|
||||
@Override
|
||||
|
@ -441,9 +454,13 @@ public class RenamePanel extends JComponent {
|
|||
|
||||
@Override
|
||||
public void actionPerformed(ActionEvent evt) {
|
||||
renameAction.putValue(RenameAction.RENAME_ACTION, action);
|
||||
renameAction.putValue(NAME, this.getValue(NAME));
|
||||
renameAction.putValue(SMALL_ICON, this.getValue(SMALL_ICON));
|
||||
if (action == StandardRenameAction.MOVE) {
|
||||
renameAction.resetValues();
|
||||
} else {
|
||||
renameAction.putValue(RenameAction.RENAME_ACTION, action);
|
||||
renameAction.putValue(NAME, this.getValue(NAME));
|
||||
renameAction.putValue(SMALL_ICON, this.getValue(SMALL_ICON));
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in New Issue