001: /*
002: * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
003: *
004: * Copyright 1997-2007 Sun Microsystems, Inc. All rights reserved.
005: *
006: * The contents of this file are subject to the terms of either the GNU
007: * General Public License Version 2 only ("GPL") or the Common
008: * Development and Distribution License("CDDL") (collectively, the
009: * "License"). You may not use this file except in compliance with the
010: * License. You can obtain a copy of the License at
011: * http://www.netbeans.org/cddl-gplv2.html
012: * or nbbuild/licenses/CDDL-GPL-2-CP. See the License for the
013: * specific language governing permissions and limitations under the
014: * License. When distributing the software, include this License Header
015: * Notice in each file and include the License file at
016: * nbbuild/licenses/CDDL-GPL-2-CP. Sun designates this
017: * particular file as subject to the "Classpath" exception as provided
018: * by Sun in the GPL Version 2 section of the License file that
019: * accompanied this code. If applicable, add the following below the
020: * License Header, with the fields enclosed by brackets [] replaced by
021: * your own identifying information:
022: * "Portions Copyrighted [year] [name of copyright owner]"
023: *
024: * Contributor(s):
025: *
026: * The Original Software is NetBeans. The Initial Developer of the Original
027: * Software is Sun Microsystems, Inc. Portions Copyright 1997-2007 Sun
028: * Microsystems, Inc. All Rights Reserved.
029: *
030: * If you wish your version of this file to be governed by only the CDDL
031: * or only the GPL Version 2, indicate your decision by adding
032: * "[Contributor] elects to include this software in this distribution
033: * under the [CDDL or GPL Version 2] license." If you do not indicate a
034: * single choice of license, a recipient has the option to distribute
035: * your version of this file under either the CDDL, the GPL Version 2 or
036: * to extend the choice of license to its licensees as provided above.
037: * However, if you add GPL Version 2 code and therefore, elected the GPL
038: * Version 2 license, then the option applies only if the new code is
039: * made subject to such option by the copyright holder.
040: */
041:
042: package org.netbeans.modules.visualweb.project.jsf.actions;
043:
044: import org.netbeans.modules.visualweb.project.jsf.api.JsfProjectUtils;
045:
046: import java.awt.event.ActionEvent;
047: import java.io.BufferedReader;
048: import java.io.File;
049: import java.io.FileInputStream;
050: import java.io.InputStream;
051: import java.io.InputStreamReader;
052: import java.io.IOException;
053: import java.io.UnsupportedEncodingException;
054: import java.util.Enumeration;
055: import java.util.StringTokenizer;
056: import javax.swing.Action;
057: import javax.swing.filechooser.FileFilter;
058: import javax.swing.JFileChooser;
059:
060: import org.openide.DialogDisplayer;
061: import org.openide.NotifyDescriptor;
062: import org.openide.ErrorManager;
063: import org.openide.filesystems.*;
064: import org.openide.loaders.*;
065: import org.openide.nodes.*;
066: import org.openide.NotifyDescriptor;
067: import org.openide.util.NbBundle;
068: import org.openide.util.WeakListeners;
069:
070: import org.netbeans.api.project.FileOwnerQuery;
071: import org.netbeans.api.project.Project;
072: import org.netbeans.api.project.ProjectInformation;
073: import org.netbeans.api.project.ProjectUtils;
074: import org.netbeans.spi.project.ui.support.MainProjectSensitiveActions;
075: import org.netbeans.spi.project.ui.support.ProjectActionPerformer;
076:
077: /**
078: * Action appearing in sub menu.. for importing file (java, jsp sources, images... etc.).
079: *
080: * @author Peter Zavadsky
081: */
082: public class ImportFileAction implements ProjectActionPerformer {
083:
084: /** Extension for .jsp files (including the dot) */
085: private static final String JSP_EXT = ".jsp"; //NOI18N
086: /** Extension for .jpg files (including the dot) */
087: private static final String JPG_EXT = ".jpg"; //NOI18N
088: /** Extension for .jpe files (including the dot) */
089: private static final String JPE_EXT = ".jpe"; //NOI18N
090: /** Extension for .gif files (including the dot) */
091: private static final String GIF_EXT = ".gif"; //NOI18N
092: /** Extension for .png files (including the dot) */
093: private static final String PNG_EXT = ".png"; //NOI18N
094: /** Extension for .jpeg files (including the dot) */
095: private static final String JPEG_EXT = ".jpeg"; //NOI18N
096: /** Extension for .css files (including the dot) */
097: private static final String CSS_EXT = ".css"; //NOI18N
098: /** Extension for .html files (including the dot) */
099: private static final String HTML_EXT = ".html"; //NOI18N
100: /** Extension for .java files (including the dot) */
101: private static final String XML_EXT = ".xml"; //NOI18N
102: /** Extension for .java files (including the dot) */
103: private static final String JAVA_EXT = ".java"; //NOI18N
104: /** Extension for .jar files (including the dot) */
105: private static final String JAR_EXT = ".jar"; //NOI18N
106: /** Extension for .properties files (including the dot) */
107: private static final String PROPERTIES_EXT = ".properties"; //NOI18N
108:
109: // private final static ProjectStateListener projectListener;
110: //
111: // private static Project currentProject;
112:
113: /** stores the last current directory of the file chooser */
114: private static File currDir;
115:
116: // static {
117: // projectListener = new ProjectStateAdapter() {
118: // public void projectCreated(ProjectStateEvent evt) {}
119: // public void projectOpened(ProjectStateEvent evt) {
120: // currentProject = evt.getProject();
121: //// javax.swing.SwingUtilities.invokeLater(new Runnable() {
122: //// public void run() {
123: //// ImportFileAction.this.setEnabled(true);
124: //// }
125: //// });
126: // }
127: // public void projectRenamed(ProjectRenameEvent evt) {}
128: // public void projectClosing(ProjectStateEvent evt) {
129: // currentProject = null;
130: //// javax.swing.SwingUtilities.invokeLater(new Runnable() {
131: //// public void run() {
132: //// ImportFileAction.this.setEnabled(false);
133: //// }
134: //// });
135: // }
136: // public void projectClosed(ProjectStateEvent evt) {
137: // }
138: // };
139: //
140: // Portfolio.addProjectStateListener(projectListener);
141: //
142: // // PENDING
143: // Portfolio portfolio = ProjectManager.getDefault().getPortfolio();
144: // if(portfolio != null) {
145: // Project[] projects = portfolio.getProjects();
146: // if(projects != null && projects.length > 0) {
147: // currentProject = projects[0];
148: // }
149: // }
150: // }
151:
152: static final int TYPE_JSP = 0;
153: static final int TYPE_IMAGE = 1;
154: static final int TYPE_STYLESHEET = 2;
155: static final int TYPE_JAVA = 3;
156: static final int TYPE_OTHER = 4;
157:
158: private final int type;
159:
160: /** Creates a new instance of ImportFileAction */
161: private ImportFileAction(int type) {
162: this .type = type;
163: }
164:
165: static Action createAction(int type) {
166: // setEnabled(currentProject != null);
167: String displayName;
168: if (type == TYPE_JSP) {
169: displayName = NbBundle.getMessage(ImportFileAction.class,
170: "LBL_ImportJspFileAction");
171: } else if (type == TYPE_IMAGE) {
172: displayName = NbBundle.getMessage(ImportFileAction.class,
173: "LBL_ImportImageFileAction");
174: } else if (type == TYPE_STYLESHEET) {
175: displayName = NbBundle.getMessage(ImportFileAction.class,
176: "LBL_ImportStylesheetFileAction");
177: } else if (type == TYPE_JAVA) {
178: displayName = NbBundle.getMessage(ImportFileAction.class,
179: "LBL_ImportJavaFileAction");
180: } else if (type == TYPE_OTHER) {
181: displayName = NbBundle.getMessage(ImportFileAction.class,
182: "LBL_ImportOtherFileAction");
183: } else {
184: throw new IllegalArgumentException("Unknown type=" + type);
185: }
186:
187: return MainProjectSensitiveActions.mainProjectSensitiveAction(
188: new ImportFileAction(type), displayName, null);
189: }
190:
191: // public void actionPerformed(ActionEvent evt) {
192: // // TODO
193: //// System.err.println("Performing File.. action in " + Thread.currentThread());
194: // JFileChooser chooser = prepareFileChooser();
195: // File file = chooseFile(chooser);
196: // if(file == null) {
197: // return;
198: // }
199: //// Project proj = currentProject;
200: // if(proj == null) {
201: // return;
202: // }
203: //// System.err.println("chosen file=" + file);
204: // importFile(proj, file);
205: //// for (int i = 0; i < files.length; i++) {
206: //// OpenFile.openFile(files[i], -1, null);
207: //// }
208: // currDir = chooser.getCurrentDirectory();
209: // }
210:
211: //////////////////////////////////////////////////////
212: // Implements ProjectActionPerformer
213: public boolean enable(Project project) {
214: return project != null;
215: }
216:
217: public void perform(Project project) {
218: // TODO
219: // System.err.println("Performing File.. action in " + Thread.currentThread());
220: JFileChooser chooser = null;
221: File file = null;
222: while (true) {
223: chooser = prepareFileChooser();
224: file = chooseFile(chooser);
225: if (file == null) {
226: return;
227: }
228: if (file.exists()) {
229: break;
230: }
231: DialogDisplayer.getDefault().notify(
232: new NotifyDescriptor.Message(NbBundle.getMessage(
233: ImportFileAction.class,
234: "TXT_FileDoesntExist", file.getName())));
235: }
236:
237: importFile(project, file);
238: // for (int i = 0; i < files.length; i++) {
239: // OpenFile.openFile(files[i], -1, null);
240: // }
241: currDir = chooser.getCurrentDirectory();
242: }
243:
244: //
245: /////////////////////////////////////////////////////////
246:
247: private JFileChooser prepareFileChooser() {
248: JFileChooser chooser = JsfProjectUtils
249: .getJFileChooser(currDir/*resolveInitialDirectory()*/);
250: // HelpCtx.setHelpIDString(chooser, getHelpCtx().getHelpID());
251: chooser.setDialogTitle(NbBundle.getMessage(
252: ImportFileAction.class, "LBL_DialogTitle"));
253:
254: chooser.setFileSelectionMode(JFileChooser.FILES_ONLY);
255: chooser.setMultiSelectionEnabled(false);
256:
257: /* initialize file filters */
258: FileFilter currentFilter = chooser.getFileFilter();
259: if (type == TYPE_JSP) {
260: FileFilter filter = new Filter(new String[] { JSP_EXT },
261: NbBundle.getMessage(ImportFileAction.class,
262: "TXT_JspFilter"));
263: chooser.addChoosableFileFilter(filter);
264: chooser.setFileFilter(filter);
265: } else if (type == TYPE_IMAGE) {
266: FileFilter filter = new Filter(new String[] { JPG_EXT,
267: GIF_EXT, PNG_EXT, JPEG_EXT, JPE_EXT }, NbBundle
268: .getMessage(ImportFileAction.class,
269: "TXT_ImageFilter"));
270: chooser.addChoosableFileFilter(filter);
271: chooser.setFileFilter(filter);
272: } else if (type == TYPE_STYLESHEET) {
273: FileFilter filter = new Filter(new String[] { CSS_EXT },
274: NbBundle.getMessage(ImportFileAction.class,
275: "TXT_CssFilter"));
276: chooser.addChoosableFileFilter(filter);
277: chooser.setFileFilter(filter);
278: } else if (type == TYPE_JAVA) {
279: FileFilter filter = new Filter(new String[] { JAVA_EXT },
280: NbBundle.getMessage(ImportFileAction.class,
281: "TXT_JavaFilter"));
282: chooser.addChoosableFileFilter(filter);
283: chooser.setFileFilter(filter);
284: } else {
285: FileFilter filter = new Filter(new String[] { JAR_EXT },
286: NbBundle.getMessage(ImportFileAction.class,
287: "TXT_JarFilter"));
288: chooser.addChoosableFileFilter(filter);
289: chooser.setFileFilter(currentFilter);
290: }
291:
292: return chooser;
293: }
294:
295: // /**
296: // * Resolves directory to be set as a current directory for the file chooser.
297: // * If the file chooser has already been displayed since the beginning
298: // * of the current NetBeans session, the last used current directory
299: // * is returned. Otherwise, the root of the first visible valid non-JAR
300: // * filesystem, having a non-empty system name, is returned.
301: // * <p>
302: // * <em>Warning:</em> The returned directory may not exist -
303: // * <code>JFileChooser</code> should handle such situations.
304: // *
305: // * @return directory to be used as a current directory,
306: // * or <code>null</code> if the resolution failed
307: // */
308: // private File resolveInitialDirectory() {
309: // if (currDir != null) {
310: // return currDir;
311: // }
312: // try {
313: // Enumeration enu = Repository.getDefault().getFileSystems();
314: // while (enu.hasMoreElements()) {
315: // FileSystem fs = (FileSystem) enu.nextElement();
316: // if (fs != null && fs.isValid() && fs.isHidden() == false
317: // && fs instanceof JarFileSystem == false
318: // && fs.getSystemName() != null) {
319: // return new File(fs.getSystemName());
320: // }
321: // }
322: // } catch (Exception e) {
323: // ErrorManager.getDefault().notify(ErrorManager.INFORMATIONAL, e);
324: // }
325: //
326: // return null;
327: // }
328:
329: public static File chooseFile(JFileChooser chooser) {
330: File file;
331: do {
332: int selectedOption = chooser
333: .showDialog(org.openide.windows.WindowManager
334: .getDefault().getMainWindow(), NbBundle
335: .getMessage(ImportFileAction.class,
336: "LBL_ImportButton"));
337:
338: if (selectedOption != JFileChooser.APPROVE_OPTION) {
339: return null;
340: }
341:
342: // In jdk.1.2 is in fact not supported multi selection -> bug.
343: // Try to get the first file and open.
344: file = chooser.getSelectedFile();
345:
346: if (file != null) {
347: return file;
348: } else {
349: // Selected file doesn't exist.
350: DialogDisplayer.getDefault().notify(
351: new NotifyDescriptor.Message(NbBundle
352: .getMessage(ImportFileAction.class,
353: "MSG_noFileSelected"),
354: NotifyDescriptor.WARNING_MESSAGE));
355: }
356: } while (file == null);
357:
358: return file;
359: }
360:
361: /** File chooser filter that filters files by their names' suffixes. */
362: private static class Filter extends FileFilter {
363:
364: /** suffixes accepted by this filter */
365: private String[] extensions;
366:
367: /** localized description of this filter */
368: private String description;
369:
370: /**
371: * Creates a new filter that accepts files having specified suffixes.
372: * The filter is case-insensitive.
373: * <p>
374: * The filter does not use file <em>extensions</em> but it just
375: * tests whether the file name ends with the specified string.
376: * So it is recommended to pass a file name extension including the
377: * preceding dot rather than just the extension.
378: *
379: * @param extensions list of accepted suffixes
380: * @param description name of the filter
381: */
382: public Filter(String[] extensions, String description) {
383:
384: this .extensions = new String[extensions.length];
385: for (int i = 0; i < extensions.length; i++) {
386: this .extensions[i] = extensions[i].toLowerCase();
387: }
388: this .description = description;
389: }
390:
391: /**
392: * @return <code>true</code> if the file's name ends with one of the
393: * strings specified by the constructor or if the file
394: * is a directory, <code>false</code> otherwise
395: */
396: public boolean accept(File file) {
397: if (file.isDirectory()) {
398: return true;
399: }
400: for (int i = 0; i < extensions.length; i++) {
401: if (file.getName().toLowerCase()
402: .endsWith(extensions[i])) {
403: return true;
404: }
405: }
406:
407: return false;
408: }
409:
410: /** */
411: public String getDescription() {
412: return description;
413: }
414: } // End of Filter class.
415:
416: /** */
417: public static void importFile(final Project project, File file) {
418: FileObject fileObject = FileUtil.toFileObject(file);
419: if (FileOwnerQuery.getOwner(fileObject) == project) {
420: NotifyDescriptor nd = new NotifyDescriptor.Message(NbBundle
421: .getMessage(ImportFileAction.class,
422: "MSG_FileIsInProject", file.getName(),
423: ProjectUtils.getInformation(project)
424: .getDisplayName()));
425: DialogDisplayer.getDefault().notify(nd);
426: return;
427: }
428:
429: // Based on the type of the file, copy it to the target directory.
430: String fileName = file.getName().toLowerCase();
431: FileObject targetFolder;
432: if (fileName.endsWith(JSP_EXT) || fileName.endsWith(HTML_EXT)
433: || fileName.endsWith(XML_EXT)) {
434: targetFolder = JsfProjectUtils.getDocumentRoot(project);
435: } else if (fileName.endsWith(JAVA_EXT)) {
436: FileObject beanRoot = JsfProjectUtils
437: .getPageBeanRoot(project);
438: // XXX
439: String pkg = findJavaPackage(file);
440: if (pkg != null && pkg.length() > 0) {
441: String path = pkg.replace('.', '/'); // NOI18N
442: try {
443: targetFolder = FileUtil
444: .createFolder(beanRoot, path);
445: } catch (IOException ioe) {
446: ErrorManager.getDefault().notify(
447: ErrorManager.INFORMATIONAL, ioe);
448: targetFolder = null;
449: }
450: } else {
451: targetFolder = beanRoot;
452: }
453: } else if (fileName.endsWith(PROPERTIES_EXT)) {
454: targetFolder = JsfProjectUtils.getPageBeanRoot(project);
455: } else if (fileName.endsWith(CSS_EXT)
456: || fileName.endsWith(JPG_EXT)
457: || fileName.endsWith(GIF_EXT)
458: || fileName.endsWith(PNG_EXT)
459: || fileName.endsWith(JPEG_EXT)
460: || fileName.endsWith(JPE_EXT)) {
461: try {
462: targetFolder = JsfProjectUtils
463: .getResourcesDirectory(project);
464: } catch (IOException ioe) {
465: ErrorManager.getDefault().notify(
466: ErrorManager.INFORMATIONAL, ioe);
467: targetFolder = JsfProjectUtils.getDocumentRoot(project);
468: }
469: } else if (fileName.endsWith(JAR_EXT)) {
470: targetFolder = JsfProjectUtils.getPageBeanRoot(project);
471: } else {
472: targetFolder = JsfProjectUtils.getPageBeanRoot(project);
473: }
474:
475: // System.err.println("\ntargetFolder=" + targetFolder);
476: if (targetFolder != null) {
477: FileObject newFileObject = copyFileToFolder(targetFolder,
478: file);
479: if (newFileObject != null) {
480: JsfProjectUtils.selectResourceInWindow(newFileObject);
481: // java.util.Set s = org.netbeans.modules.visualweb.project.ProjectFileSystem.getInstance().getFileSystems();
482: // for(java.util.Iterator it = s.iterator(); it.hasNext(); ) {
483: // FileSystem fs = (FileSystem)it.next();
484: // fs.refresh(false);
485: // }
486: // expandNodeForPath(newFileObject.getPath());
487: }
488: } else {
489: ErrorManager.getDefault().notify(
490: ErrorManager.INFORMATIONAL,
491: new NullPointerException(
492: "Cannot find import folder for file "
493: + file.getName())); // NOI18N
494: }
495: }
496:
497: // private static FileObject getProjectFolder(Project proj, String path) {
498: // // Create the folder path if needed..
499: // File f = new File(proj.getAbsolutePath()
500: // + File.separator + path.replace('/', File.separatorChar)); // NOI18N
501: // if(!f.exists()) {
502: // f.mkdirs();
503: // }
504: //
505: // FileSystem fs = getProjectFileSystem(proj);
506: // return fs == null ? null : fs.findResource(path);
507: // }
508: //
509: // private static FileSystem getProjectFileSystem(Project proj) {
510: // File root = new File(proj.getAbsolutePath());
511: // LocalFileSystem lfs = new LocalFileSystem();
512: // try {
513: //// System.err.println("root fs=" + root);
514: // lfs.setRootDirectory(root);
515: // } catch(java.beans.PropertyVetoException pve) { // PropertyVeto??
516: // ErrorManager.getDefault().notify(ErrorManager.INFORMATIONAL, pve);
517: // return null;
518: // } catch(java.io.IOException ioe) {
519: // ErrorManager.getDefault().notify(ErrorManager.INFORMATIONAL, ioe);
520: // return null;
521: // }
522: // return lfs;
523: // }
524:
525: private static FileObject copyFileToFolder(FileObject folder,
526: File file) {
527: try {
528: DataFolder dataFolder = DataFolder.findFolder(folder);
529: DataObject dataSource = DataObject
530: .find(getFileObjectFromFile(file));
531: return dataSource.copy(dataFolder).getPrimaryFile();
532: } catch (java.io.IOException ioe) {
533: ErrorManager.getDefault().notify(
534: ErrorManager.INFORMATIONAL, ioe);
535: return null;
536: }
537: }
538:
539: private static FileObject getFileObjectFromFile(File file) {
540: File parent = file.getParentFile();
541: LocalFileSystem lfs = new LocalFileSystem();
542: try {
543: lfs.setRootDirectory(parent);
544: } catch (java.beans.PropertyVetoException pve) { // ??
545: ErrorManager.getDefault().notify(
546: ErrorManager.INFORMATIONAL, pve);
547: return null;
548: } catch (java.io.IOException ioe) {
549: ErrorManager.getDefault().notify(
550: ErrorManager.INFORMATIONAL, ioe);
551: return null;
552: }
553: return lfs.findResource(file.getName());
554: }
555:
556: // private static void expandNodeForPath(final String path) {
557: // org.netbeans.modules.visualweb.project.ProjectExplorer pe = org.netbeans.modules.visualweb.project.ProjectExplorer.getInstance();
558: // pe.requestActive();
559: // javax.swing.SwingUtilities.invokeLater(new Runnable() {
560: // public void run() {
561: // findNode(org.netbeans.modules.visualweb.project.ProjectExplorer.getInstance()
562: // .getExplorerManager().getRootContext(), path);
563: // }
564: // });
565: // }
566: //
567: // private static void findNode(org.openide.nodes.Node node, final String path) {
568: // DataObject dob = (DataObject)node.getCookie(DataObject.class);
569: // if(dob == null) {
570: // // Must be DataObject
571: //// System.err.println("1");
572: // return;
573: // }
574: //
575: // String p = dob.getPrimaryFile().getPath();
576: // if(p != null && p.length() > 0 && path.endsWith(p)) {
577: // // TODO Expand the node for the newly created file.. and select it.
578: // expandNode(node);
579: //
580: // return;
581: // }
582: //
583: // if(node.getCookie(DataFolder.class) == null) {
584: // // Must be a folder.
585: //// System.err.println("2");
586: // return;
587: // }
588: //
589: // // Force to get the children.
590: // Node[] children = node.getChildren().getNodes(true);
591: // for(int i = 0; i < children.length; i++) {
592: // final Node ch = children[i];
593: // javax.swing.SwingUtilities.invokeLater(new Runnable() {
594: // public void run() {
595: // findNode(ch, path);
596: // }
597: // });
598: // }
599: // }
600: //
601: // private static void expandNode(Node node) {
602: // org.netbeans.modules.visualweb.project.ProjectExplorer.getInstance().expandNode(node);
603: //
604: // // Select node
605: // selectNode(node);
606: // }
607: //
608: // private static void selectNode(Node node) {
609: // try {
610: // org.netbeans.modules.visualweb.project.ProjectExplorer.getInstance().getExplorerManager()
611: // .setSelectedNodes(new Node[] {node});
612: // } catch(java.beans.PropertyVetoException pve) { // ??
613: // ErrorManager.getDefault().notify(ErrorManager.INFORMATIONAL, pve);
614: // }
615: // }
616: //
617: // private static void expandAllNodes(javax.swing.JTree tree,
618: // Object node, javax.swing.tree.TreePath tPath) {
619: // System.err.println("\nexpanding all nodes for->" + node);
620: // System.err.println("getClass->" + node.getClass());
621: // tree.expandPath(tPath);
622: //
623: // final org.openide.nodes.Node n = org.openide.explorer.view.Visualizer.findNode(node);
624: // System.err.println("real..node=" + n);
625: //
626: // if(n != null) {
627: // javax.swing.SwingUtilities.invokeLater(new Runnable() {
628: // public void run() {
629: // expandFolderNode(n);
630: // }
631: // });
632: // }
633: //
634: //// javax.swing.tree.TreeModel model = tree.getModel();
635: ////
636: //// // XXX Reload model.
637: //// System.err.println("model=" + model);
638: //// if(model instanceof javax.swing.tree.DefaultTreeModel) {
639: //// System.err.println("reloading model");
640: //// ((javax.swing.tree.DefaultTreeModel)model).reload();
641: //// }
642: ////
643: //// int childCount = model.getChildCount(node);
644: //// System.err.println("child count = " + childCount);
645: //// for(int i = 0; i < childCount; i++) {
646: //// Object ch = model.getChild(node, i);
647: //// System.err.println("at " + i + " is " + ch);
648: //// if(ch != null) {
649: //// java.util.List pathList = new java.util.ArrayList(java.util.Arrays.asList(tPath.getPath()));
650: //// pathList.add(ch);
651: //// javax.swing.tree.TreePath chPath = new javax.swing.tree.TreePath(pathList.toArray());
652: ////
653: //// expandAllNodes(tree, ch, chPath);
654: //// }
655: //// }
656: // }
657:
658: // private static void expandFolderNode(org.openide.nodes.Node n) {
659: // if(n.getCookie(org.openide.loaders.DataFolder.class) == null) {
660: // // It is not a folder.
661: // System.err.println("it is not a folder=" + n);
662: // return;
663: // }
664: //
665: // System.err.println("children false=" + java.util.Arrays.asList(n.getChildren().getNodes(false)));
666: // org.openide.nodes.Node[] nodes = n.getChildren().getNodes(true);
667: // System.err.println("children nodes=" + java.util.Arrays.asList(nodes));
668: // for(int i = 0; i < nodes.length; i++) {
669: // final org.openide.nodes.Node ch = nodes[i];
670: // System.err.println("expanding->"+ch);
671: // org.netbeans.modules.visualweb.project.ProjectExplorer.getInstance().getTreeView().expandNode(ch);
672: // javax.swing.SwingUtilities.invokeLater(new Runnable() {
673: // public void run() {
674: // expandFolderNode(ch);
675: // }
676: // });
677: // }
678: // }
679:
680: // XXX Copied from utilities/openfile/../DefaultOpenFileImpl
681: /** Name of package keyword. */
682: private static final String PACKAGE = "package"; // NOI18N
683:
684: /**
685: * Find java package in side .java file.
686: *
687: * @return package or null if not found
688: */
689: private static String findJavaPackage(File file) {
690: String pkg = ""; // NOI18N
691: boolean packageKnown = false;
692:
693: // Try to find the package name and then infer a directory to mount.
694: BufferedReader rd = null;
695:
696: try {
697: int pckgPos; // found package position
698:
699: rd = new BufferedReader(new SourceReader(
700: new FileInputStream(file)));
701:
702: // Check for unicode byte watermarks.
703: rd.mark(2);
704: char[] cbuf = new char[2];
705: rd.read(cbuf, 0, 2);
706:
707: if (cbuf[0] == 255 && cbuf[1] == 254) {
708: rd.close();
709: rd = new BufferedReader(new SourceReader(
710: new FileInputStream(file), "Unicode")); // NOI18N
711: } else {
712: rd.reset();
713: }
714:
715: while (!packageKnown) {
716: String line = rd.readLine();
717: if (line == null) {
718: packageKnown = true; // i.e. valid termination of search, default pkg
719: //break;
720: return pkg;
721: }
722:
723: pckgPos = line.indexOf(PACKAGE);
724: if (pckgPos == -1) {
725: continue;
726: }
727: StringTokenizer tok = new StringTokenizer(line, " \t;"); // NOI18N
728: boolean gotPackage = false;
729: while (tok.hasMoreTokens()) {
730: String theTok = tok.nextToken();
731: if (gotPackage) {
732: // Hopefully the package name, but first a sanity check...
733: StringTokenizer ptok = new StringTokenizer(
734: theTok, "."); // NOI18N
735: boolean ok = ptok.hasMoreTokens();
736: while (ptok.hasMoreTokens()) {
737: String component = ptok.nextToken();
738: if (component.length() == 0) {
739: ok = false;
740: break;
741: }
742: if (!Character
743: .isJavaIdentifierStart(component
744: .charAt(0))) {
745: ok = false;
746: break;
747: }
748: for (int pos = 1; pos < component.length(); pos++) {
749: if (!Character
750: .isJavaIdentifierPart(component
751: .charAt(pos))) {
752: ok = false;
753: break;
754: }
755: }
756: }
757: if (ok) {
758: pkg = theTok;
759: packageKnown = true;
760: //break;
761: return pkg;
762: } else {
763: // Keep on looking for valid package statement.
764: gotPackage = false;
765: continue;
766: }
767: } else if (theTok.equals(PACKAGE)) {
768: gotPackage = true;
769: } else if (theTok.equals("{")) { // NOI18N
770: // Most likely we can stop if hit opening brace of class def.
771: // Usually people leave spaces around it.
772: packageKnown = true; // valid end of search, default pkg
773: // break;
774: return pkg;
775: }
776: }
777: }
778: } catch (IOException e1) {
779: ErrorManager.getDefault().notify(e1);
780: } finally {
781: try {
782: if (rd != null) {
783: rd.close();
784: }
785: } catch (IOException e2) {
786: ErrorManager.getDefault().notify(e2);
787: }
788: }
789:
790: return null;
791: }
792:
793: /**
794: * Filtered reader for Java sources - it simply excludes
795: * comments and some useless whitespaces from the original stream.
796: */
797: public static class SourceReader extends InputStreamReader {
798: private int preRead = -1;
799: private boolean inString = false;
800: private boolean backslashLast = false;
801: private boolean separatorLast = false;
802: static private final char separators[] = { '.' }; // dot is enough here...
803: static private final char whitespaces[] = { ' ', '\t', '\r',
804: '\n' };
805:
806: public SourceReader(InputStream in) {
807: super (in);
808: }
809:
810: public SourceReader(InputStream in, String encoding)
811: throws UnsupportedEncodingException {
812: super (in, encoding);
813: }
814:
815: /** Reads chars from input reader and filters them. */
816: public int read(char[] data, int pos, int len)
817: throws IOException {
818: int numRead = 0;
819: int c;
820: char[] onechar = new char[1];
821:
822: while (numRead < len) {
823: if (preRead != -1) {
824: c = preRead;
825: preRead = -1;
826: } else {
827: c = super .read(onechar, 0, 1);
828: if (c == -1) { // end of stream reached
829: return (numRead > 0) ? numRead : -1;
830: }
831: c = onechar[0];
832: }
833:
834: if (c == '/' && !inString) { // a comment could start here
835: preRead = super .read(onechar, 0, 1);
836: if (preRead == 1) {
837: preRead = onechar[0];
838: }
839: if (preRead != '*' && preRead != '/') { // it's not a comment
840: data[pos++] = (char) c;
841: numRead++;
842: if (preRead == -1) { // end of stream reached
843: return numRead;
844: }
845: } else { // we have run into the comment - skip it
846: if (preRead == '*') { // comment started with /*
847: preRead = -1;
848: do {
849: c = moveToChar('*');
850: if (c == 0) {
851: c = super .read(onechar, 0, 1);
852: if (c == 1) {
853: c = onechar[0];
854: }
855: if (c == '*') {
856: preRead = c;
857: }
858: }
859: } while (c != '/' && c != -1);
860: } else { // comment started with //
861: preRead = -1;
862: c = moveToChar('\n');
863: if (c == 0) {
864: preRead = '\n';
865: }
866: }
867: if (c == -1) { // end of stream reached
868: return -1;
869: }
870: }
871: } else { // normal valid character
872: if (!inString) { // not inside a string " ... "
873: if (isWhitespace(c)) { // reduce some whitespaces
874: while (true) {
875: preRead = super .read(onechar, 0, 1);
876: if (preRead == -1) { // end of stream reached
877: return (numRead > 0) ? numRead : -1;
878: }
879: preRead = onechar[0];
880:
881: if (isSeparator(preRead)) {
882: c = preRead;
883: preRead = -1;
884: break;
885: } else if (!isWhitespace(preRead)) {
886: if (separatorLast) {
887: c = preRead;
888: preRead = -1;
889: }
890: break;
891: }
892: }
893: }
894:
895: if (c == '\"' || c == '\'') {
896: inString = true;
897: separatorLast = false;
898: } else {
899: separatorLast = isSeparator(c);
900: }
901: } else { // we are just in a string
902: if (c == '\"' || c == '\'') {
903: if (!backslashLast) {
904: inString = false;
905: } else {
906: backslashLast = false;
907: }
908: } else {
909: backslashLast = (c == '\\');
910: }
911: }
912:
913: data[pos++] = (char) c;
914: numRead++;
915: }
916: }
917: return numRead;
918: }
919:
920: private int moveToChar(int c) throws IOException {
921: int cc;
922: char[] onechar = new char[1];
923:
924: if (preRead != -1) {
925: cc = preRead;
926: preRead = -1;
927: } else {
928: cc = super .read(onechar, 0, 1);
929: if (cc == 1) {
930: cc = onechar[0];
931: }
932: }
933:
934: while (cc != -1 && cc != c) {
935: cc = super .read(onechar, 0, 1);
936: if (cc == 1) {
937: cc = onechar[0];
938: }
939: }
940:
941: return (cc == -1) ? -1 : 0;
942: }
943:
944: static private boolean isSeparator(int c) {
945: for (int i = 0; i < separators.length; i++) {
946: if (c == separators[i]) {
947: return true;
948: }
949: }
950: return false;
951: }
952:
953: static private boolean isWhitespace(int c) {
954: for (int i = 0; i < whitespaces.length; i++) {
955: if (c == whitespaces[i]) {
956: return true;
957: }
958: }
959: return false;
960: }
961: } // End of class SourceReader.
962: // End of copy.
963: }
|