mirror of
https://gitflic.ru/project/openide/openide.git
synced 2026-01-04 17:20:55 +07:00
Project view: support manual oder
This commit is contained in:
@@ -15,19 +15,30 @@
|
||||
*/
|
||||
package com.intellij.projectView;
|
||||
|
||||
import com.intellij.ide.projectView.ProjectView;
|
||||
import com.intellij.ide.projectView.*;
|
||||
import com.intellij.ide.projectView.impl.AbstractProjectViewPSIPane;
|
||||
import com.intellij.ide.projectView.impl.ProjectViewImpl;
|
||||
import com.intellij.ide.util.treeView.AbstractTreeNode;
|
||||
import com.intellij.openapi.project.Project;
|
||||
import com.intellij.openapi.ui.Queryable;
|
||||
import com.intellij.openapi.util.Disposer;
|
||||
import com.intellij.openapi.vfs.VirtualFile;
|
||||
import com.intellij.psi.PsiFileSystemItem;
|
||||
import com.intellij.testFramework.PlatformTestUtil;
|
||||
import com.intellij.util.containers.hash.LinkedHashMap;
|
||||
import com.intellij.util.ui.tree.TreeUtil;
|
||||
import org.jetbrains.annotations.NotNull;
|
||||
import org.jetbrains.annotations.Nullable;
|
||||
|
||||
import javax.swing.tree.DefaultMutableTreeNode;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Collection;
|
||||
import java.util.Map;
|
||||
|
||||
public class ProjectTreeSortingTest extends BaseProjectViewTestCase {
|
||||
private ProjectView myProjectView;
|
||||
private AbstractProjectViewPSIPane myPane;
|
||||
private boolean myOriginalManualOrder;
|
||||
private boolean myOriginalSortByType;
|
||||
private boolean myOriginalFoldersAlwaysOnTop;
|
||||
|
||||
@@ -41,6 +52,7 @@ public class ProjectTreeSortingTest extends BaseProjectViewTestCase {
|
||||
|
||||
myProjectView = ProjectView.getInstance(myProject);
|
||||
myProjectView.addProjectPane(myPane);
|
||||
myOriginalManualOrder = myProjectView.isManualOrder(myPane.getId());
|
||||
myOriginalSortByType = myProjectView.isSortByType(myPane.getId());
|
||||
myOriginalFoldersAlwaysOnTop = ((ProjectViewImpl)myProjectView).isFoldersAlwaysOnTop();
|
||||
|
||||
@@ -49,6 +61,7 @@ public class ProjectTreeSortingTest extends BaseProjectViewTestCase {
|
||||
|
||||
@Override
|
||||
public void tearDown() throws Exception {
|
||||
myProjectView.setManualOrder(myPane.getId(), myOriginalManualOrder);
|
||||
myProjectView.setSortByType(myPane.getId(), myOriginalSortByType);
|
||||
((ProjectViewImpl)myProjectView).setFoldersAlwaysOnTop(myOriginalFoldersAlwaysOnTop);
|
||||
myProjectView.removeProjectPane(myPane);
|
||||
@@ -151,9 +164,195 @@ public class ProjectTreeSortingTest extends BaseProjectViewTestCase {
|
||||
" +b_folder\n");
|
||||
}
|
||||
|
||||
public void testManualOrder() throws Exception {
|
||||
MyOrderProvider provider = new MyOrderProvider(myProject);
|
||||
provider.setOrder("b_ordered.java",
|
||||
"a_folder_ordered",
|
||||
"b_ordered.txt",
|
||||
"a_ordered.txt",
|
||||
"b_folder_ordered",
|
||||
"a_ordered.java");
|
||||
getProjectTreeStructure().setProviders(provider);
|
||||
|
||||
myProjectView.setManualOrder(myPane.getId(), true);
|
||||
|
||||
((ProjectViewImpl)myProjectView).setFoldersAlwaysOnTop(true);
|
||||
|
||||
myProjectView.setSortByType(myPane.getId(), false);
|
||||
assertTree("-manualOrder\n" +
|
||||
" b_ordered.java\n" +
|
||||
" +a_folder_ordered\n" +
|
||||
" b_ordered.txt\n" +
|
||||
" a_ordered.txt\n" +
|
||||
" +b_folder_ordered\n" +
|
||||
" a_ordered.java\n" +
|
||||
|
||||
" +a_folder_unordered\n" +
|
||||
" +b_folder_unordered\n" +
|
||||
" a_unordered.java\n" +
|
||||
" a_unordered.txt\n" +
|
||||
" b_unordered.java\n" +
|
||||
" b_unordered.txt\n");
|
||||
|
||||
myProjectView.setSortByType(myPane.getId(), true);
|
||||
assertTree("-manualOrder\n" +
|
||||
" b_ordered.java\n" +
|
||||
" +a_folder_ordered\n" +
|
||||
" b_ordered.txt\n" +
|
||||
" a_ordered.txt\n" +
|
||||
" +b_folder_ordered\n" +
|
||||
" a_ordered.java\n" +
|
||||
|
||||
" +a_folder_unordered\n" +
|
||||
" +b_folder_unordered\n" +
|
||||
" a_unordered.java\n" +
|
||||
" b_unordered.java\n" +
|
||||
" a_unordered.txt\n" +
|
||||
" b_unordered.txt\n");
|
||||
|
||||
((ProjectViewImpl)myProjectView).setFoldersAlwaysOnTop(false);
|
||||
|
||||
myProjectView.setSortByType(myPane.getId(), false);
|
||||
assertTree("-manualOrder\n" +
|
||||
" b_ordered.java\n" +
|
||||
" +a_folder_ordered\n" +
|
||||
" b_ordered.txt\n" +
|
||||
" a_ordered.txt\n" +
|
||||
" +b_folder_ordered\n" +
|
||||
" a_ordered.java\n" +
|
||||
|
||||
" +a_folder_unordered\n" +
|
||||
" a_unordered.java\n" +
|
||||
" a_unordered.txt\n" +
|
||||
" +b_folder_unordered\n" +
|
||||
" b_unordered.java\n" +
|
||||
" b_unordered.txt\n");
|
||||
|
||||
myProjectView.setSortByType(myPane.getId(), true);
|
||||
assertTree("-manualOrder\n" +
|
||||
" b_ordered.java\n" +
|
||||
" +a_folder_ordered\n" +
|
||||
" b_ordered.txt\n" +
|
||||
" a_ordered.txt\n" +
|
||||
" +b_folder_ordered\n" +
|
||||
" a_ordered.java\n" +
|
||||
|
||||
" a_unordered.java\n" +
|
||||
" b_unordered.java\n" +
|
||||
" a_unordered.txt\n" +
|
||||
" b_unordered.txt\n" +
|
||||
" +a_folder_unordered\n" +
|
||||
" +b_folder_unordered\n");
|
||||
}
|
||||
|
||||
private void assertTree(String expected) {
|
||||
DefaultMutableTreeNode element = myPane.getTreeBuilder().getNodeForElement(getContentDirectory());
|
||||
assertNotNull("Element for " + getContentDirectory() + " not found", element);
|
||||
assertEquals(expected, PlatformTestUtil.print(myPane.getTree(), element, new Queryable.PrintInfo(), false));
|
||||
}
|
||||
|
||||
static class MyOrderProvider implements TreeStructureProvider {
|
||||
private final Project myProject;
|
||||
private final Map<String, Integer> myOrder = new LinkedHashMap<String, Integer>();
|
||||
|
||||
public MyOrderProvider(Project project) {
|
||||
myProject = project;
|
||||
}
|
||||
|
||||
void setOrder(String... fileNames) {
|
||||
int i = 0;
|
||||
for (String each : fileNames) {
|
||||
myOrder.put(each, i++);
|
||||
}
|
||||
}
|
||||
|
||||
@NotNull
|
||||
@Override
|
||||
public Collection<AbstractTreeNode> modify(@NotNull AbstractTreeNode parent,
|
||||
@NotNull Collection<AbstractTreeNode> children,
|
||||
ViewSettings settings) {
|
||||
ArrayList<AbstractTreeNode> result = new ArrayList<AbstractTreeNode>();
|
||||
|
||||
for (final AbstractTreeNode child : children) {
|
||||
ProjectViewNode treeNode = (ProjectViewNode)child;
|
||||
final Object o = treeNode.getValue();
|
||||
if (o instanceof PsiFileSystemItem) {
|
||||
final Integer order = myOrder.get(((PsiFileSystemItem)o).getVirtualFile().getName());
|
||||
|
||||
treeNode = new ProjectViewNode<PsiFileSystemItem>(myProject, (PsiFileSystemItem)o, settings) {
|
||||
@Override
|
||||
@NotNull
|
||||
public Collection<AbstractTreeNode> getChildren() {
|
||||
return child.getChildren();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toTestString(Queryable.PrintInfo printInfo) {
|
||||
return child.toTestString(printInfo);
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getWeight() {
|
||||
return ((ProjectViewNode)child).getWeight();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Comparable getSortKey() {
|
||||
return ((ProjectViewNode)child).getSortKey();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Comparable getManualOrderKey() {
|
||||
return order == null ? null : order;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public String getQualifiedNameSortKey() {
|
||||
return ((ProjectViewNode)child).getQualifiedNameSortKey();
|
||||
}
|
||||
|
||||
@Nullable
|
||||
@Override
|
||||
public Comparable getTypeSortKey() {
|
||||
return ((ProjectViewNode)child).getTypeSortKey();
|
||||
}
|
||||
|
||||
@Override
|
||||
public int getTypeSortWeight(boolean sortByType) {
|
||||
return ((ProjectViewNode)child).getTypeSortWeight(sortByType);
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getTestPresentation() {
|
||||
return child.getTestPresentation();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean contains(@NotNull VirtualFile file) {
|
||||
return ((ProjectViewNode)child).contains(file);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update(PresentationData presentation) {
|
||||
}
|
||||
|
||||
@Override
|
||||
public String toString() {
|
||||
return ((PsiFileSystemItem)o).getName();
|
||||
}
|
||||
};
|
||||
}
|
||||
result.add(treeNode);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
@Override
|
||||
public Object getData(Collection<AbstractTreeNode> selected, String dataName) {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -253,6 +253,11 @@ public abstract class ProjectViewNode <Value> extends AbstractTreeNode<Value> im
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public Comparable getManualOrderKey() {
|
||||
return null;
|
||||
}
|
||||
|
||||
@Nullable
|
||||
public String getQualifiedNameSortKey() {
|
||||
return null;
|
||||
|
||||
@@ -87,6 +87,9 @@ public abstract class ProjectView {
|
||||
|
||||
public abstract void selectPsiElement(PsiElement element, boolean requestFocus);
|
||||
|
||||
public abstract boolean isManualOrder(String paneId);
|
||||
public abstract void setManualOrder(@NotNull String paneId, final boolean enabled);
|
||||
|
||||
public abstract boolean isSortByType(String paneId);
|
||||
public abstract void setSortByType(@NotNull String paneId, final boolean sortByType);
|
||||
|
||||
|
||||
@@ -155,6 +155,10 @@ public abstract class AbstractProjectViewPane implements DataProvider, Disposabl
|
||||
return true;
|
||||
}
|
||||
|
||||
public boolean supportsManualOrder() {
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* @return all supported sub views IDs.
|
||||
* should return empty array if there is no subViews as in Project/Packages view.
|
||||
|
||||
@@ -66,6 +66,18 @@ public class GroupByTypeComparator implements Comparator<NodeDescriptor> {
|
||||
|
||||
ProjectViewNode node1 = (ProjectViewNode)descriptor1;
|
||||
ProjectViewNode node2 = (ProjectViewNode)descriptor2;
|
||||
|
||||
if (isManualOrder()) {
|
||||
final Comparable key1 = node1.getManualOrderKey();
|
||||
final Comparable key2 = node2.getManualOrderKey();
|
||||
if (!(key1 == null && key2 == null)) {
|
||||
if (key1 == null) return 1;
|
||||
if (key2 == null) return -1;
|
||||
//noinspection unchecked
|
||||
final int result = key1.compareTo(key2);
|
||||
if (result != 0) return result;
|
||||
}
|
||||
}
|
||||
|
||||
boolean isFoldersOnTop = !(projectView instanceof ProjectViewImpl && !((ProjectViewImpl)projectView).isFoldersAlwaysOnTop());
|
||||
if (isFoldersOnTop) {
|
||||
@@ -116,6 +128,13 @@ public class GroupByTypeComparator implements Comparator<NodeDescriptor> {
|
||||
return AlphaComparator.INSTANCE.compare(descriptor1, descriptor2);
|
||||
}
|
||||
|
||||
protected boolean isManualOrder() {
|
||||
if (myProjectView != null) {
|
||||
return myProjectView.isManualOrder(myPaneId);
|
||||
}
|
||||
return true;
|
||||
}
|
||||
|
||||
protected boolean isSortByType() {
|
||||
if (myProjectView != null) {
|
||||
return myProjectView.isSortByType(myPaneId);
|
||||
|
||||
@@ -126,6 +126,8 @@ public class ProjectViewImpl extends ProjectView implements PersistentStateCompo
|
||||
private static final boolean ourFlattenPackagesDefaults = false;
|
||||
private final Map<String, Boolean> myShowMembers = new THashMap<String, Boolean>();
|
||||
private static final boolean ourShowMembersDefaults = false;
|
||||
private final Map<String, Boolean> myManualOrder = new THashMap<String, Boolean>();
|
||||
private static final boolean ourManualOrderDefaults = false;
|
||||
private final Map<String, Boolean> mySortByType = new THashMap<String, Boolean>();
|
||||
private static final boolean ourSortByTypeDefaults = false;
|
||||
private final Map<String, Boolean> myShowModules = new THashMap<String, Boolean>();
|
||||
@@ -703,6 +705,7 @@ public class ProjectViewImpl extends ProjectView implements PersistentStateCompo
|
||||
}
|
||||
myActionGroup.addAction(myAutoScrollToSourceHandler.createToggleAction()).setAsSecondary(true);
|
||||
myActionGroup.addAction(myAutoScrollFromSourceHandler.createToggleAction()).setAsSecondary(true);
|
||||
myActionGroup.addAction(new ManualOrderAction()).setAsSecondary(true);
|
||||
myActionGroup.addAction(new SortByTypeAction()).setAsSecondary(true);
|
||||
myActionGroup.addAction(new FoldersAlwaysOnTopAction()).setAsSecondary(true);
|
||||
|
||||
@@ -1783,6 +1786,18 @@ public class ProjectViewImpl extends ProjectView implements PersistentStateCompo
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isManualOrder(String paneId) {
|
||||
return getPaneOptionValue(myManualOrder, paneId, ourManualOrderDefaults);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setManualOrder(@NotNull String paneId, final boolean enabled) {
|
||||
setPaneOption(myManualOrder, enabled, paneId, false);
|
||||
final AbstractProjectViewPane pane = getProjectViewPaneById(paneId);
|
||||
pane.installComparator();
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSortByType(String paneId) {
|
||||
return getPaneOptionValue(mySortByType, paneId, ourSortByTypeDefaults);
|
||||
@@ -1795,6 +1810,30 @@ public class ProjectViewImpl extends ProjectView implements PersistentStateCompo
|
||||
pane.installComparator();
|
||||
}
|
||||
|
||||
private class ManualOrderAction extends ToggleAction {
|
||||
private ManualOrderAction() {
|
||||
super(IdeBundle.message("action.manual.order"), IdeBundle.message("action.manual.order"), AllIcons.ObjectBrowser.Sorted);
|
||||
}
|
||||
|
||||
@Override
|
||||
public boolean isSelected(AnActionEvent event) {
|
||||
return isManualOrder(getCurrentViewId());
|
||||
}
|
||||
|
||||
@Override
|
||||
public void setSelected(AnActionEvent event, boolean flag) {
|
||||
setManualOrder(getCurrentViewId(), flag);
|
||||
}
|
||||
|
||||
@Override
|
||||
public void update(final AnActionEvent e) {
|
||||
super.update(e);
|
||||
final Presentation presentation = e.getPresentation();
|
||||
AbstractProjectViewPane pane = getCurrentProjectViewPane();
|
||||
presentation.setVisible(pane != null && pane.supportsManualOrder());
|
||||
}
|
||||
}
|
||||
|
||||
private class SortByTypeAction extends ToggleAction {
|
||||
private SortByTypeAction() {
|
||||
super(IdeBundle.message("action.sort.by.type"), IdeBundle.message("action.sort.by.type"), AllIcons.ObjectBrowser.SortByType);
|
||||
|
||||
@@ -561,6 +561,7 @@ action.show.libraries.contents=Show Libraries Contents
|
||||
action.show.hide.library.contents=Show/Hide Library Contents
|
||||
action.show.excluded.files=Show Excluded Files
|
||||
action.show.hide.excluded.files=Show/Hide Excluded Files
|
||||
action.manual.order=Manual Order
|
||||
action.sort.by.type=Sort by Type
|
||||
action.show.structure=Show Structure
|
||||
action.description.show.structure=Show structure view
|
||||
|
||||
Reference in New Issue
Block a user