--- a/jumpto/src/org/netbeans/modules/jumpto/file/FileDescription.java +++ a/jumpto/src/org/netbeans/modules/jumpto/file/FileDescription.java @@ -43,6 +43,7 @@ * made subject to such option by the copyright holder. * * Contributor(s): Petr Hrebejk + * markiewb@netbeans.org */ package org.netbeans.modules.jumpto.file; @@ -55,11 +56,14 @@ import org.netbeans.api.project.ProjectInformation; import org.netbeans.api.project.ProjectUtils; import org.netbeans.spi.jumpto.file.FileDescriptor; +import org.openide.ErrorManager; import org.openide.cookies.EditCookie; +import org.openide.cookies.LineCookie; import org.openide.cookies.OpenCookie; import org.openide.filesystems.FileObject; import org.openide.loaders.DataObject; import org.openide.loaders.DataObjectNotFoundException; +import org.openide.text.Line; import org.openide.util.ImageUtilities; /** Contains interesting information about file found in the search. @@ -83,11 +87,17 @@ private Icon icon; private String projectName; private Icon projectIcon; + private int lineNr; public FileDescription(FileObject file, String ownerPath, Project project) { + this(file, ownerPath, project, -1); + } + + public FileDescription(FileObject file, String ownerPath, Project project, int lineNr) { this.fileObject = file; this.ownerPath = ownerPath; this.project = project; + this.lineNr = lineNr; } @Override @@ -133,20 +143,40 @@ public void open() { DataObject od = getDataObject(); if ( od != null ) { - EditCookie ec = (EditCookie) od.getCookie(EditCookie.class); - if (ec != null) { - ec.edit(); + + // if linenumber is given then try to open file at this line + // code taken from org.netbeans.modules.java.stackanalyzer.StackLineAnalyser.Link.show() + LineCookie lineCookie = od.getLookup().lookup(LineCookie.class); + if (lineCookie != null && lineNr != -1) { + try { + Line l = lineCookie.getLineSet().getCurrent(lineNr - 1); + + if (l != null) { + // open file at the given line + l.show(Line.ShowOpenType.OPEN, Line.ShowVisibilityType.FOCUS, -1); + return; + } + } catch (IndexOutOfBoundsException oob) { + //line number is no more valid + ErrorManager.getDefault().notify(ErrorManager.INFORMATIONAL, oob); + } } - else { - OpenCookie oc = od.getCookie( OpenCookie.class ); - if ( oc != null ) { - oc.open(); + // fallback to default for non-linenumber stuff + { + EditCookie ec = od.getLookup().lookup(EditCookie.class); + if (ec != null) { + ec.edit(); + } else { + OpenCookie oc = od.getLookup().lookup(OpenCookie.class); + if (oc != null) { + oc.open(); + } } } } } - + @Override public FileObject getFileObject() { return fileObject; --- a/jumpto/src/org/netbeans/modules/jumpto/file/FileSearchAction.java +++ a/jumpto/src/org/netbeans/modules/jumpto/file/FileSearchAction.java @@ -44,6 +44,7 @@ * * Contributor(s): Andrei Badea * Petr Hrebejk + * markiewb@netbeans.org */ package org.netbeans.modules.jumpto.file; @@ -70,6 +71,7 @@ import java.util.Set; import java.util.logging.Level; import java.util.logging.Logger; +import java.util.regex.Matcher; import java.util.regex.Pattern; import java.util.regex.PatternSyntaxException; import javax.swing.AbstractAction; @@ -139,12 +141,15 @@ private FileSearchPanel panel; private Dimension initialDimension; private Iterable providers; + private final Pattern patternWithLineNumber; public FileSearchAction() { super( NbBundle.getMessage(FileSearchAction.class, "CTL_FileSearchAction") ); // XXX this should be in initialize()? putValue("PopupMenuText", NbBundle.getBundle(FileSearchAction.class).getString("editor-popup-CTL_FileSearchAction")); // NOI18N putValue("noIconInMenu", Boolean.TRUE); // NOI18N + + this.patternWithLineNumber = Pattern.compile("(.*):(\\d+)"); } @Override @@ -212,11 +217,31 @@ else { nameKind = panel.isCaseSensitive() ? QuerySupport.Kind.PREFIX : QuerySupport.Kind.CASE_INSENSITIVE_PREFIX; } + + + //Extract linenumber from search text + //Pattern is like 'My*Object.java:123' + Matcher matcher = patternWithLineNumber.matcher(text); + boolean endsWithLineNumber = matcher.matches(); + int lineNr; + if (endsWithLineNumber) + { + text = matcher.group(1); + try { + lineNr = Integer.parseInt(matcher.group(2)); + } catch (NumberFormatException numberFormatException) { + //prevent non convertable numbers + lineNr=-1; + } + } + else { + lineNr = -1; + } // Compute in other thread synchronized( this ) { - running = new Worker(text , nameKind, panel.getCurrentProject()); + running = new Worker(text , nameKind, panel.getCurrentProject(), lineNr); task = rp.post( running, 220); if ( panel.time != -1 ) { LOGGER.log( Level.FINE, "Worker posted after {0} ms.", System.currentTimeMillis() - panel.time ); @@ -395,9 +420,11 @@ private final QuerySupport.Kind searchType; private final Project currentProject; private final long createTime; + private final int lineNr; - public Worker(String text, QuerySupport.Kind searchType, Project currentProject) { + public Worker(String text, QuerySupport.Kind searchType, Project currentProject, int lineNr) { this.text = text; + this.lineNr = lineNr; this.searchType = searchType; this.currentProject = currentProject; this.createTime = System.currentTimeMillis(); @@ -516,7 +543,7 @@ FileDescriptor fd = new FileDescription( file, r.getRelativePath().substring(0, Math.max(r.getRelativePath().length() - file.getNameExt().length() - 1, 0)), - project); + project, lineNr); FileProviderAccessor.getInstance().setFromCurrentProject(fd, preferred); files.add(fd); LOGGER.log(Level.FINER, "Found: {0}, project={1}, currentProject={2}, preferred={3}", @@ -599,7 +626,7 @@ FileDescriptor fd = new FileDescription( file, relativePath, - project + project, lineNr ); FileProviderAccessor.getInstance().setFromCurrentProject(fd, preferred); files.add(fd);