001: /*******************************************************************************
002: * Copyright (c) 2000, 2006 IBM Corporation and others.
003: * All rights reserved. This program and the accompanying materials
004: * are made available under the terms of the Eclipse Public License v1.0
005: * which accompanies this distribution, and is available at
006: * http://www.eclipse.org/legal/epl-v10.html
007: *
008: * Contributors:
009: * IBM Corporation - initial API and implementation
010: *******************************************************************************/package org.eclipse.ui.internal.ide.dialogs;
011:
012: import org.eclipse.core.filesystem.IFileStore;
013: import org.eclipse.core.resources.IResource;
014: import org.eclipse.core.runtime.IStatus;
015: import org.eclipse.core.runtime.NullProgressMonitor;
016: import org.eclipse.core.runtime.Status;
017: import org.eclipse.jface.viewers.ITreeContentProvider;
018: import org.eclipse.jface.viewers.LabelProvider;
019: import org.eclipse.jface.viewers.Viewer;
020: import org.eclipse.jface.viewers.ViewerComparator;
021: import org.eclipse.swt.graphics.Image;
022: import org.eclipse.swt.widgets.Shell;
023: import org.eclipse.ui.ISharedImages;
024: import org.eclipse.ui.PlatformUI;
025: import org.eclipse.ui.dialogs.ElementTreeSelectionDialog;
026: import org.eclipse.ui.dialogs.ISelectionStatusValidator;
027: import org.eclipse.ui.internal.ide.IDEWorkbenchPlugin;
028:
029: /**
030: * Selection dialog to select files and/or folders on the file system. Use
031: * setInput to set input to an IFileStore that points to a folder.
032: *
033: * @since 2.1
034: */
035: public class FileFolderSelectionDialog extends
036: ElementTreeSelectionDialog {
037:
038: /**
039: * Label provider for IFileStore objects.
040: */
041: private static class FileLabelProvider extends LabelProvider {
042: private static final Image IMG_FOLDER = PlatformUI
043: .getWorkbench().getSharedImages().getImage(
044: ISharedImages.IMG_OBJ_FOLDER);
045:
046: private static final Image IMG_FILE = PlatformUI.getWorkbench()
047: .getSharedImages().getImage(ISharedImages.IMG_OBJ_FILE);
048:
049: /*
050: * (non-Javadoc)
051: *
052: * @see org.eclipse.jface.viewers.LabelProvider#getImage(java.lang.Object)
053: */
054: public Image getImage(Object element) {
055: if (element instanceof IFileStore) {
056: IFileStore curr = (IFileStore) element;
057: if (curr.fetchInfo().isDirectory()) {
058: return IMG_FOLDER;
059: }
060: return IMG_FILE;
061: }
062: return null;
063: }
064:
065: /*
066: * (non-Javadoc)
067: *
068: * @see org.eclipse.jface.viewers.LabelProvider#getText(java.lang.Object)
069: */
070: public String getText(Object element) {
071: if (element instanceof IFileStore) {
072: return ((IFileStore) element).getName();
073: }
074: return super .getText(element);
075: }
076: }
077:
078: /**
079: * Content provider for IFileStore objects.
080: */
081: private static class FileContentProvider implements
082: ITreeContentProvider {
083: private static final Object[] EMPTY = new Object[0];
084:
085: private IFileStoreFilter fileFilter;
086:
087: /**
088: * Creates a new instance of the receiver.
089: *
090: * @param showFiles
091: * <code>true</code> files and folders are returned by the
092: * receiver. <code>false</code> only folders are returned.
093: */
094: public FileContentProvider(final boolean showFiles) {
095: fileFilter = new IFileStoreFilter() {
096:
097: /*
098: * (non-Javadoc)
099: *
100: * @see org.eclipse.ui.internal.ide.dialogs.IFileStoreFilter#accept(org.eclipse.core.filesystem.IFileStore)
101: */
102: public boolean accept(IFileStore file) {
103: if (!file.fetchInfo().isDirectory()
104: && showFiles == false) {
105: return false;
106: }
107: return true;
108: }
109: };
110: }
111:
112: public Object[] getChildren(Object parentElement) {
113: if (parentElement instanceof IFileStore) {
114: IFileStore[] children = IDEResourceInfoUtils
115: .listFileStores((IFileStore) parentElement,
116: fileFilter, new NullProgressMonitor());
117: if (children != null) {
118: return children;
119: }
120: }
121: return EMPTY;
122: }
123:
124: /*
125: * (non-Javadoc)
126: *
127: * @see org.eclipse.jface.viewers.ITreeContentProvider#getParent(java.lang.Object)
128: */
129: public Object getParent(Object element) {
130: if (element instanceof IFileStore) {
131: return ((IFileStore) element).getParent();
132: }
133: return null;
134: }
135:
136: public boolean hasChildren(Object element) {
137: return getChildren(element).length > 0;
138: }
139:
140: public Object[] getElements(Object element) {
141: return getChildren(element);
142: }
143:
144: public void dispose() {
145: }
146:
147: public void inputChanged(Viewer viewer, Object oldInput,
148: Object newInput) {
149: }
150: }
151:
152: /**
153: * Viewer sorter that places folders first, then files.
154: */
155: private static class FileViewerSorter extends ViewerComparator {
156: /*
157: * (non-Javadoc)
158: *
159: * @see org.eclipse.jface.viewers.ViewerSorter#category(java.lang.Object)
160: */
161: public int category(Object element) {
162: if (element instanceof IFileStore
163: && !((IFileStore) element).fetchInfo()
164: .isDirectory()) {
165: return 1;
166: }
167: return 0;
168: }
169: }
170:
171: /**
172: * Validates the selection based on the multi select and folder setting.
173: */
174: private static class FileSelectionValidator implements
175: ISelectionStatusValidator {
176: private boolean multiSelect;
177:
178: private boolean acceptFolders;
179:
180: /**
181: * Creates a new instance of the receiver.
182: *
183: * @param multiSelect
184: * <code>true</code> if multi selection is allowed.
185: * <code>false</code> if only single selection is allowed.
186: * @param acceptFolders
187: * <code>true</code> if folders can be selected in the
188: * dialog. <code>false</code> only files and be selected.
189: */
190: public FileSelectionValidator(boolean multiSelect,
191: boolean acceptFolders) {
192: this .multiSelect = multiSelect;
193: this .acceptFolders = acceptFolders;
194: }
195:
196: /*
197: * (non-Javadoc)
198: *
199: * @see org.eclipse.ui.dialogs.ISelectionStatusValidator#validate(java.lang.Object[])
200: */
201: public IStatus validate(Object[] selection) {
202: int nSelected = selection.length;
203: String pluginId = IDEWorkbenchPlugin.IDE_WORKBENCH;
204:
205: if (nSelected == 0
206: || (nSelected > 1 && multiSelect == false)) {
207: return new Status(IStatus.ERROR, pluginId,
208: IStatus.ERROR,
209: IDEResourceInfoUtils.EMPTY_STRING, null);
210: }
211: for (int i = 0; i < selection.length; i++) {
212: Object curr = selection[i];
213: if (curr instanceof IFileStore) {
214: IFileStore file = (IFileStore) curr;
215: if (acceptFolders == false
216: && file.fetchInfo().isDirectory()) {
217: return new Status(IStatus.ERROR, pluginId,
218: IStatus.ERROR,
219: IDEResourceInfoUtils.EMPTY_STRING, null);
220: }
221:
222: }
223: }
224: return Status.OK_STATUS;
225: }
226: }
227:
228: /**
229: * Creates a new instance of the receiver.
230: *
231: * @param parent
232: * @param multiSelect
233: * <code>true</code> if multi selection is allowed.
234: * <code>false</code> if only single selection is allowed.
235: * @param type
236: * one or both of <code>IResource.FILE</code> and
237: * <code>IResource.FOLDER</code>, ORed together. If
238: * <code>IResource.FILE</code> is specified files and folders
239: * are displayed in the dialog. Otherwise only folders are
240: * displayed. If <code>IResource.FOLDER</code> is specified
241: * folders can be selected in addition to files.
242: */
243: public FileFolderSelectionDialog(Shell parent, boolean multiSelect,
244: int type) {
245: super (parent, new FileLabelProvider(), new FileContentProvider(
246: (type & IResource.FILE) != 0));
247: setComparator(new FileViewerSorter());
248: setValidator(new FileSelectionValidator(multiSelect,
249: (type & IResource.FOLDER) != 0));
250: }
251: }
|