diff --git a/app/src/processing/app/Base.java b/app/src/processing/app/Base.java index ee8fd5390..4c0974fb7 100644 --- a/app/src/processing/app/Base.java +++ b/app/src/processing/app/Base.java @@ -1298,12 +1298,36 @@ public class Base { protected void rebuildSketchbookMenu() { - try { // System.err.println("sketchbook: " + sketchbookFolder); - sketchbookMenu.removeAll(); - addSketches(sketchbookMenu, sketchbookFolder, false); + sketchbookMenu.removeAll(); + populateSketchbookMenu(sketchbookMenu); +// boolean found = false; +// try { +// found = addSketches(sketchbookMenu, sketchbookFolder, false); +// } catch (IOException e) { +// Base.showWarning("Sketchbook Menu Error", +// "An error occurred while trying to list the sketchbook.", e); +// } +// if (!found) { +// JMenuItem empty = new JMenuItem("(empty)"); +// empty.setEnabled(false); +// sketchbookMenu.add(empty); +// } + } + + + public void populateSketchbookMenu(JMenu menu) { + boolean found = false; + try { + found = addSketches(menu, sketchbookFolder, false); } catch (IOException e) { - e.printStackTrace(); + Base.showWarning("Sketchbook Menu Error", + "An error occurred while trying to list the sketchbook.", e); + } + if (!found) { + JMenuItem empty = new JMenuItem("Empty Sketchbook"); + empty.setEnabled(false); + menu.add(empty); } } @@ -1332,6 +1356,11 @@ public class Base { } + public JMenu getToolbarRecentMenu() { + return recent.getToolbarMenu(); + } + + public void handleRecent(Editor editor) { recent.handle(editor); } diff --git a/app/src/processing/app/Editor.java b/app/src/processing/app/Editor.java index 127893ea5..f29953d5a 100644 --- a/app/src/processing/app/Editor.java +++ b/app/src/processing/app/Editor.java @@ -144,6 +144,7 @@ public abstract class Editor extends JFrame implements RunnerListener { fileMenu.insert(base.getRecentMenu(), 3); // fileMenu.insert(mode.getExamplesMenu(), 3); sketchMenu.insert(mode.getImportMenu(), 4); + mode.insertToolbarRecentMenu(); } // added for 1.0.5 @@ -155,6 +156,7 @@ public abstract class Editor extends JFrame implements RunnerListener { fileMenu.remove(base.getRecentMenu()); // fileMenu.remove(mode.getExamplesMenu()); sketchMenu.remove(mode.getImportMenu()); + mode.removeToolbarRecentMenu(); } }); @@ -592,7 +594,7 @@ public abstract class Editor extends JFrame implements RunnerListener { fileMenu.add(base.getSketchbookMenu()); // fileMenu.add(mode.getExamplesMenu()); - item = new JMenuItem("Examples..."); + item = Base.newJMenuItemShift("Examples...", 'O'); item.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { mode.showExamplesFrame(); diff --git a/app/src/processing/app/FindReplace.java b/app/src/processing/app/FindReplace.java index 721306428..83b9c75a0 100644 --- a/app/src/processing/app/FindReplace.java +++ b/app/src/processing/app/FindReplace.java @@ -3,7 +3,7 @@ /* Part of the Processing project - http://processing.org - Copyright (c) 2004-11 Ben Fry and Casey Reas + Copyright (c) 2004-12 Ben Fry and Casey Reas Copyright (c) 2001-04 Massachusetts Institute of Technology This program is free software; you can redistribute it and/or modify @@ -53,6 +53,9 @@ public class FindReplace extends JFrame implements ActionListener { JCheckBox ignoreCaseBox; static boolean ignoreCase = true; + JCheckBox allTabsBox; + static boolean allTabs = false; + JCheckBox wrapAroundBox; static boolean wrapAround = true; @@ -88,6 +91,16 @@ public class FindReplace extends JFrame implements ActionListener { ignoreCaseBox.setSelected(ignoreCase); pain.add(ignoreCaseBox); + allTabsBox = new JCheckBox("All Tabs"); + allTabsBox.addActionListener(new ActionListener() { + public void actionPerformed(ActionEvent e) { + allTabs = allTabsBox.isSelected(); + } + }); + allTabsBox.setSelected(allTabs); + allTabsBox.setEnabled(false); + pain.add(allTabsBox); + wrapAroundBox = new JCheckBox("Wrap Around"); wrapAroundBox.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { @@ -163,13 +176,19 @@ public class FindReplace extends JFrame implements ActionListener { ypos += fieldHeight + SMALL; + final int third = (fieldWidth - SMALL*2) / 3; ignoreCaseBox.setBounds(EDGE + labelDimension.width + SMALL, ypos, - (fieldWidth-SMALL)/2, fieldHeight); + third, fieldHeight); - wrapAroundBox.setBounds(EDGE + labelDimension.width + SMALL + (fieldWidth-SMALL)/2 + SMALL, + allTabsBox.setBounds(EDGE + labelDimension.width + SMALL + third + SMALL, + ypos, + third, fieldHeight); + + //wrapAroundBox.setBounds(EDGE + labelDimension.width + SMALL + (fieldWidth-SMALL)/2 + SMALL, + wrapAroundBox.setBounds(EDGE + labelDimension.width + SMALL + third*2 + SMALL*2, ypos, - (fieldWidth-SMALL)/2, fieldHeight); + third, fieldHeight); ypos += fieldHeight + SMALL; @@ -272,15 +291,23 @@ public class FindReplace extends JFrame implements ActionListener { // look for the next instance of the find string to be found // once found, select it (and go to that line) private boolean find(boolean wrap, boolean backwards) { - String search = findField.getText(); + String searchTerm = findField.getText(); //System.out.println("finding for " + search + " " + findString); // this will catch "find next" being called when no search yet - if (search.length() == 0) return false; + if (searchTerm.length() == 0) return false; String text = editor.getText(); + // Started work on find/replace across tabs. These two variables store + // the original tab and selection position so that it knew when to stop + // rotating through. +// Sketch sketch = editor.getSketch(); +// int tabIndex = sketch.getCurrentCodeIndex(); +// int selIndex = backwards ? +// editor.getSelectionStart() : editor.getSelectionStop(); + if (ignoreCase) { - search = search.toLowerCase(); + searchTerm = searchTerm.toLowerCase(); text = text.toLowerCase(); } @@ -289,28 +316,28 @@ public class FindReplace extends JFrame implements ActionListener { //int selectionStart = editor.textarea.getSelectionStart(); int selectionEnd = editor.getSelectionStop(); - nextIndex = text.indexOf(search, selectionEnd); - if (wrap && nextIndex == -1) { + nextIndex = text.indexOf(searchTerm, selectionEnd); + if (nextIndex == -1 && wrap) { // if wrapping, a second chance is ok, start from beginning - nextIndex = text.indexOf(search, 0); + nextIndex = text.indexOf(searchTerm, 0); } } else { //int selectionStart = editor.textarea.getSelectionStart(); int selectionStart = editor.getSelectionStart()-1; if (selectionStart >= 0) { - nextIndex = text.lastIndexOf(search, selectionStart); + nextIndex = text.lastIndexOf(searchTerm, selectionStart); } else { nextIndex = -1; } if (wrap && nextIndex == -1) { // if wrapping, a second chance is ok, start from the end - nextIndex = text.lastIndexOf(search); + nextIndex = text.lastIndexOf(searchTerm); } } if (nextIndex != -1) { - editor.setSelection(nextIndex, nextIndex + search.length()); + editor.setSelection(nextIndex, nextIndex + searchTerm.length()); } else { //Toolkit.getDefaultToolkit().beep(); } diff --git a/app/src/processing/app/Mode.java b/app/src/processing/app/Mode.java index 9cba46841..780c67808 100644 --- a/app/src/processing/app/Mode.java +++ b/app/src/processing/app/Mode.java @@ -204,6 +204,20 @@ public abstract class Mode { } + public void insertToolbarRecentMenu() { + if (toolbarMenu == null) { + rebuildToolbarMenu(); + } else { + toolbarMenu.insert(base.getToolbarRecentMenu(), 1); + } + } + + + public void removeToolbarRecentMenu() { + toolbarMenu.remove(base.getToolbarRecentMenu()); + } + + protected void rebuildToolbarMenu() { //JMenu menu) { JMenuItem item; if (toolbarMenu == null) { @@ -222,36 +236,30 @@ public abstract class Mode { }); toolbarMenu.add(item); -// JMenu examplesMenu = new JMenu("Examples"); -// rebuildExamplesMenu(examplesMenu, true); - item = new JMenuItem("Examples..."); + insertToolbarRecentMenu(); + + item = Base.newJMenuItemShift("Examples...", 'O'); item.addActionListener(new ActionListener() { public void actionPerformed(ActionEvent e) { showExamplesFrame(); } }); toolbarMenu.add(item); -// toolbarMenu.add(examplesMenu); - - toolbarMenu.addSeparator(); // Add a list of all sketches and subfolders - try { - base.addSketches(toolbarMenu, base.getSketchbookFolder(), true); -// boolean sketches = base.addSketches(toolbarMenu, base.getSketchbookFolder(), true); -// if (sketches) { -// toolbarMenu.addSeparator(); -// } - } catch (IOException e) { - e.printStackTrace(); - } - - //System.out.println("rebuilding examples menu"); - // Add each of the subfolders of examples directly to the menu + toolbarMenu.addSeparator(); + base.populateSketchbookMenu(toolbarMenu); +// boolean found = false; // try { -// base.addSketches(toolbarMenu, examplesFolder, true); +// found = base.addSketches(toolbarMenu, base.getSketchbookFolder(), true); // } catch (IOException e) { -// e.printStackTrace(); +// Base.showWarning("Sketchbook Toolbar Error", +// "An error occurred while trying to list the sketchbook.", e); +// } +// if (!found) { +// JMenuItem empty = new JMenuItem("(empty)"); +// empty.setEnabled(false); +// toolbarMenu.add(empty); // } } @@ -527,46 +535,13 @@ public abstract class Mode { tree.expandRow(0); // now hide the root tree.setRootVisible(false); - // now expand the other folks - for (int row = tree.getRowCount()-1; row >= 0; --row) { - tree.expandRow(row); - } - /* - tree.addTreeSelectionListener(new TreeSelectionListener() { - public void valueChanged(TreeSelectionEvent e) { - DefaultMutableTreeNode node = (DefaultMutableTreeNode) - tree.getLastSelectedPathComponent(); + // After 2.0a7, no longer expanding each of the categories at Casey's + // request. He felt that the window was too complicated too quickly. +// for (int row = tree.getRowCount()-1; row >= 0; --row) { +// tree.expandRow(row); +// } - if (node != null) { - Object nodeInfo = node.getUserObject(); - if (node.isLeaf()) { - System.out.println(node + " user obj: " + nodeInfo); - // BookInfo book = (BookInfo)nodeInfo; - // displayURL(book.bookURL); - } - } - } - }); - */ - - /* - * MouseListener ml = new MouseAdapter() { - * public void mousePressed(MouseEvent e) { - * int selRow = tree.getRowForLocation(e.getX(), e.getY()); - * TreePath selPath = tree.getPathForLocation(e.getX(), e.getY()); - * if(selRow != -1) { - * if(e.getClickCount() == 1) { - * mySingleClick(selRow, selPath); - * } - * else if(e.getClickCount() == 2) { - * myDoubleClick(selRow, selPath); - * } - * } - * } - * }; - * tree.addMouseListener(ml); - */ tree.addMouseListener(new MouseAdapter() { public void mouseClicked(MouseEvent e) { if (e.getClickCount() == 2) { diff --git a/app/src/processing/app/Recent.java b/app/src/processing/app/Recent.java index a9f944043..edbd72a58 100644 --- a/app/src/processing/app/Recent.java +++ b/app/src/processing/app/Recent.java @@ -43,14 +43,18 @@ public class Recent { /** How many recent sketches to remember. */ int remember; ArrayList records; - JMenu menu; + /** actual menu used in the primary menu bar */ + JMenu mainMenu; + /** copy of the menu to use in the toolbar */ + JMenu toolbarMenu; public Recent(Base base) { this.base = base; remember = Preferences.getInteger("recent.count"); file = Base.getSettingsFile(FILENAME); - menu = new JMenu("Recent Sketches"); + mainMenu = new JMenu("Recent"); + toolbarMenu = new JMenu("Recent"); try { load(); @@ -80,7 +84,8 @@ public class Recent { } } } - updateMenu(); + updateMenu(mainMenu); + updateMenu(toolbarMenu); } @@ -94,17 +99,22 @@ public class Recent { } writer.flush(); writer.close(); -// System.out.println(); - updateMenu(); + updateMenu(mainMenu); + updateMenu(toolbarMenu); } public JMenu getMenu() { - return menu; + return mainMenu; } - private void updateMenu() { + public JMenu getToolbarMenu() { + return toolbarMenu; + } + + + private void updateMenu(JMenu menu) { menu.removeAll(); for (final Record rec : records) { String purtyPath = new File(rec.getPath()).getParent(); diff --git a/app/src/processing/app/Sketch.java b/app/src/processing/app/Sketch.java index 9db56c558..fed66d2ac 100644 --- a/app/src/processing/app/Sketch.java +++ b/app/src/processing/app/Sketch.java @@ -1380,6 +1380,11 @@ public class Sketch { } + public int getCurrentCodeIndex() { + return currentIndex; + } + + public String getMainProgram() { return getCode(0).getProgram(); } diff --git a/todo.txt b/todo.txt index 11b8e61b1..d7c558fa0 100644 --- a/todo.txt +++ b/todo.txt @@ -25,6 +25,11 @@ o make better version of the windows launcher for debugging X add code for setting the L&F from the prefs file for linux o strange window flicker when first opened X not seen since rolling back canvas changes +X added 'all tabs' checkbox, but it's dimmed out +X don't expand the folders in the examples window +X cmd-shift-o for opening examples +X add recent menu to the toolbar +X add 'empty sketchbook' indicator when the sketchbook menus are empty cleaning o switching into present mode in info.plist @@ -53,14 +58,13 @@ o specifically add "eclipse" to integration description o link books and sample chapters from the "getting started" portion of the faq o if export fails (compile error) need to un-highlight the export button o http://dev.processing.org/bugs/show_bug.cgi?id=39 +o [LaunchRunner Error] processing.app.Base.main(String[]) threw an exception +o http://dev.processing.org/bugs/show_bug.cgi?id=821 +o http://code.google.com/p/processing/issues/detail?id=102 +X not seen for a long time, closed - -PDE / Find & Replace - -_ implement find & replace over multiple tabs -_ http://code.google.com/p/processing/issues/detail?id=25 -_ find across all tabs (jer request) -_ http://code.google.com/p/processing/issues/detail?id=25 +_ figure out why modes are not loading classes properly +_ first see if it's something quick 2.0 FINAL / command line @@ -103,7 +107,7 @@ _ blank sketch opened even if another opened by double-click _ http://code.google.com/p/processing/issues/detail?id=179 _ also can have case of opening two of same sketch at once _ if sketch was open, then restart by dragging the .pde to p5.app -_ osx not opening a sketch at all on double-click? (though opening the app) +_ osx not opening a sketch at all on pde double-click? (though opening the app) _ active editor not being set null _ in Base.nextEditorLocation(), changed to "editors.size() == 0" _ instead of (activeEditor == null), but that's papering over a problem @@ -114,14 +118,9 @@ _ restrict more things like "show sketch folder" _ don't allow adding files w/o saving _ others? -_ figure out why modes are not loading classes properly - _ change syntax highlighting so it differentiates keyPressed and keyPressed() _ syntax highlight with parens also helps "String line" vs "line()" -_ undo seems to not be going to the right location (now with example) -_ http://code.google.com/p/processing/issues/detail?id=668 - _ bad tool brings down the environment _ http://code.google.com/p/processing/issues/detail?id=798 @@ -692,15 +691,13 @@ _ http://code.google.com/p/processing/issues/detail?id=8 PDE / Editor -_ cmd-shift-n not creating new tab -_ http://code.google.com/p/processing/issues/detail?id=149 +_ undo seems to not be going to the right location (now with example) +_ http://code.google.com/p/processing/issues/detail?id=668 _ improve update check message "a new release (1.0.1) is available" _ be more descriptive, use a second line in latest.txt _ maybe just include the full text of the update message there? _ go through other sketch-opening menus to check for disappearing sketches _ deal with isManagingFocus() warning in the editor src -_ [LaunchRunner Error] processing.app.Base.main(String[]) threw an exception -_ http://dev.processing.org/bugs/show_bug.cgi?id=821 _ strange NullPointerException problem prevents launch _ some kind of NPE in handleOpenInternal and friends _ appears to be a synchronization problem with the loading @@ -807,6 +804,13 @@ _ exporting application copies .java files _ .java files are copied to the root folder as well as the source folder +PDE / Find & Replace + +_ implement find & replace over multiple tabs +_ http://code.google.com/p/processing/issues/detail?id=25 +_ added to the projects list + + PDE / Examples _ keep examples.zip in a zip file? (5000 files @ 30 MB instead of 15 MB zip)