From d926adab5614b8e39208e45c6c4d3ec296242fb3 Mon Sep 17 00:00:00 2001
From: benfry
Date: Thu, 5 Apr 2012 03:56:23 +0000
Subject: [PATCH] moving forward with recent sketches menu, almost working and
cleaning up other demons
---
app/src/processing/app/Base.java | 228 ++++++++++-----
app/src/processing/app/Editor.java | 258 +++++++++--------
app/src/processing/app/Mode.java | 172 +++++------
app/src/processing/app/Recent.java | 269 +++++++++++-------
app/src/processing/app/SingleInstance.java | 94 +++---
app/src/processing/app/Sketch.java | 27 +-
app/src/processing/app/UpdateCheck.java | 37 ++-
.../processing/app/macosx/ThinkDifferent.java | 48 ++--
app/src/processing/app/tools/Archiver.java | 24 +-
.../mode/android/AndroidToolbar.java | 2 +-
app/src/processing/mode/java/JavaEditor.java | 10 +-
app/src/processing/mode/java/JavaToolbar.java | 2 +-
.../mode/javascript/JavaScriptEditor.java | 130 ++++-----
.../mode/javascript/JavaScriptToolbar.java | 2 +-
build/shared/lib/preferences.txt | 2 +-
core/src/processing/core/PApplet.java | 141 +++++----
core/src/processing/core/PGraphics.java | 1 +
core/src/processing/core/PGraphicsJava2D.java | 41 ++-
core/todo.txt | 32 ++-
todo.txt | 8 +-
20 files changed, 881 insertions(+), 647 deletions(-)
diff --git a/app/src/processing/app/Base.java b/app/src/processing/app/Base.java
index dabbccbca..6405f2615 100644
--- a/app/src/processing/app/Base.java
+++ b/app/src/processing/app/Base.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
@@ -33,13 +33,7 @@ import java.util.zip.*;
import javax.swing.*;
import javax.swing.tree.*;
-import processing.app.contrib.Contribution;
-import processing.app.contrib.ContributionListing;
-import processing.app.contrib.ContributionManager;
-import processing.app.contrib.ContributionManagerDialog;
-import processing.app.contrib.InstalledContribution;
-import processing.app.contrib.ModeContribution;
-import processing.app.contrib.ToolContribution;
+import processing.app.contrib.*;
import processing.core.*;
/**
@@ -116,14 +110,21 @@ public class Base {
// a lone file menu to be used when all sketch windows are closed
static public JMenu defaultFileMenu;
- private Mode defaultMode;
+// private Mode defaultMode;
+
+ /**
+ * Starts with the last mode used with the environment, or the default mode
+ * if not used.
+ */
+ private Mode nextMode;
+
private Mode[] coreModes;
public List contribModes;
private JMenu sketchbookMenu;
-
+
private Recent recent;
- private JMenu recentMenu;
+// private JMenu recentMenu;
protected File sketchbookFolder;
protected File toolsFolder;
@@ -137,6 +138,7 @@ public class Base {
});
}
+
static private void createAndShowGUI(String[] args) {
try {
File versionFile = getContentFile("lib/version.txt");
@@ -164,20 +166,18 @@ public class Base {
// run static initialization that grabs all the prefs
Preferences.init(null);
-
+
// String filename = args.length > 1 ? args[0] : null;
- if (!SingleInstance.exists(args)) {
- SingleInstance.createServer(platform);
+ if (!SingleInstance.alreadyRunning(args)) {
+// SingleInstance.startServer(platform);
// Set the look and feel before opening the window
try {
platform.setLookAndFeel();
} catch (Exception e) {
String mess = e.getMessage();
- if (mess.indexOf("ch.randelshofer.quaqua.QuaquaLookAndFeel") == -1) {
- System.err.println("Non-fatal error while setting the Look & Feel.");
- System.err.println("The error message follows, however Processing should run fine.");
- System.err.println(mess);
+ if (!mess.contains("ch.randelshofer.quaqua.QuaquaLookAndFeel")) {
+ log("Could not set the Look & Feel", e);
}
}
@@ -186,15 +186,16 @@ public class Base {
untitledFolder = Base.createTempFolder("untitled", "sketches");
untitledFolder.deleteOnExit();
} catch (IOException e) {
- //e.printStackTrace();
Base.showError("Trouble without a name",
"Could not create a place to store untitled sketches.\n" +
"That's gonna prevent us from continuing.", e);
}
-// System.out.println("about to create base...");
- new Base(args);
-// System.out.println("done creating base...");
+ log("about to create base...");
+ Base base = new Base(args);
+ // Prevent more than one copy of the PDE from running.
+ SingleInstance.startServer(base);
+ log("done creating base...");
}
}
@@ -242,7 +243,7 @@ public class Base {
private void buildCoreModes() {
- defaultMode =
+ Mode javaMode =
ModeContribution.getCoreMode(this, "processing.mode.java.JavaMode",
getContentFile("modes/java"));
Mode androidMode =
@@ -252,7 +253,7 @@ public class Base {
ModeContribution.getCoreMode(this, "processing.mode.javascript.JavaScriptMode",
getContentFile("modes/javascript"));
- coreModes = new Mode[] { defaultMode, androidMode, javaScriptMode };
+ coreModes = new Mode[] { javaMode, androidMode, javaScriptMode };
}
/** Instantiates and adds new contributed modes to the contribModes list.
@@ -275,7 +276,7 @@ public class Base {
public Base(String[] args) {
recent = new Recent(this);
- recentMenu = recent.createMenu();
+// recentMenu = recent.createMenu();
// Get the sketchbook path, and make sure it's set properly
determineSketchbookFolder();
@@ -294,6 +295,23 @@ public class Base {
buildCoreModes();
rebuildContribModes();
+ String lastModeIdentifier = Preferences.get("last.sketch.mode");
+ if (lastModeIdentifier == null) {
+ nextMode = coreModes[0];
+ log("Nothing set for last.sketch.mode, using coreMode[0].");
+ } else {
+ for (Mode m : getModeList()) {
+ if (m.getIdentifier().equals(lastModeIdentifier)) {
+ log("Setting next mode to " + lastModeIdentifier);
+ nextMode = m;
+ }
+ }
+ if (nextMode == null) {
+ nextMode = coreModes[0];
+ log("Could not find mode " + lastModeIdentifier + ", using default.");
+ }
+ }
+
libraryManagerFrame = new ContributionManagerDialog("Library Manager",
new ContributionListing.Filter() {
public boolean matches(Contribution contrib) {
@@ -325,7 +343,7 @@ public class Base {
});
// Make sure ThinkDifferent has library examples too
- defaultMode.rebuildLibraryList();
+ nextMode.rebuildLibraryList();
// Put this after loading the examples, so that building the default file
// menu works on Mac OS X (since it needs examplesFolder to be set).
@@ -333,12 +351,9 @@ public class Base {
toolsFolder = getContentFile("tools");
-// // Get the sketchbook path, and make sure it's set properly
-// determineSketchbookFolder();
-
// // Check if there were previously opened sketches to be restored
-// boolean opened = restoreSketches();
- boolean opened = false;
+ boolean opened = restoreSketches();
+// boolean opened = false;
// Check if any files were passed in on the command line
for (int i = 0; i < args.length; i++) {
@@ -396,23 +411,24 @@ public class Base {
* The complement to "storePreferences", this is called when the
* application is first launched.
*/
- protected void restoreSketches() {
- String lastMode = Preferences.get("last.sketch.mode");
- log("setting mode to " + lastMode);
- if (lastMode != null) {
- for (Mode m : getModeList()) {
- if (m.getClass().getName().equals(lastMode)) {
- defaultMode = m;
- }
- }
+ protected boolean restoreSketches() {
+// String lastMode = Preferences.get("last.sketch.mode");
+// log("setting mode to " + lastMode);
+// if (lastMode != null) {
+// for (Mode m : getModeList()) {
+// if (m.getClass().getName().equals(lastMode)) {
+// defaultMode = m;
+// }
+// }
+// }
+// log("default mode set to " + defaultMode.getClass().getName());
+
+ if (Preferences.getBoolean("last.sketch.restore")) {
+ return false;
}
- log("default mode set to " + defaultMode.getClass().getName());
+ return true;
-// if (Preferences.getBoolean("last.sketch.restore")) {
-// return false;
-// }
-//
// // figure out window placement
// Dimension screen = Toolkit.getDefaultToolkit().getScreenSize();
// boolean windowPositionValid = true;
@@ -619,7 +635,10 @@ public class Base {
File sketchProps = new File(sketch.getFolder(), "sketch.properties");
try {
Settings props = new Settings(sketchProps);
+ // Include the pretty name for error messages to show the user
props.set("mode", mode.getTitle());
+ // Actual identifier to be used to resurrect the mode
+ props.set("mode.id", mode.getIdentifier());
props.save();
} catch (IOException e) {
e.printStackTrace();
@@ -667,7 +686,8 @@ public class Base {
EditorConsole.setEditor(activeEditor);
// make this the next mode to be loaded
- defaultMode = whichEditor.getMode();
+ nextMode = whichEditor.getMode();
+ Preferences.set("last.sketch.mode", nextMode.getIdentifier());
}
@@ -715,13 +735,13 @@ public class Base {
// }
- /**
- * Return the same mode as the active editor, or the default mode, which
- * begins as Java/Standard, but is updated with the last mode used.
- */
- public Mode nextEditorMode() {
- return (activeEditor == null) ? defaultMode : activeEditor.getMode();
- }
+// /**
+// * Return the same mode as the active editor, or the default mode, which
+// * begins as Java/Standard, but is updated with the last mode used.
+// */
+// public Mode nextEditorMode() {
+// return (activeEditor == null) ? defaultMode : activeEditor.getMode();
+// }
// . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
@@ -795,7 +815,7 @@ public class Base {
// Make an empty pde file
//File newbieFile = new File(newbieDir, newbieName + getExtension());
- File newbieFile = new File(newbieDir, newbieName + "." + defaultMode.getDefaultExtension());
+ File newbieFile = new File(newbieDir, newbieName + "." + nextMode.getDefaultExtension());
new FileOutputStream(newbieFile); // create the file
return newbieFile.getAbsolutePath();
}
@@ -872,7 +892,7 @@ public class Base {
// replace the document without checking if that's ok
handleNewReplaceImpl();
} else {
- recent.handleOpen(activeEditor, recentMenu);
+ recent.handle(activeEditor);
}
}
@@ -953,8 +973,8 @@ public class Base {
for (Editor editor : editors) {
if (editor.getSketch().getMainFilePath().equals(path)) {
editor.toFront();
-// System.err.println(" handleOpen: already opened");
- recent.handleOpen(editor, recentMenu);
+ // move back to the top of the recent list
+ recent.handle(editor);
return editor;
}
}
@@ -973,22 +993,26 @@ public class Base {
// }
// }
- Mode nextMode = nextEditorMode();
+// Mode nextMode = nextEditorMode();
try {
File sketchFolder = new File(path).getParentFile();
File sketchProps = new File(sketchFolder, "sketch.properties");
if (sketchProps.exists()) {
Settings props = new Settings(sketchProps);
String modeTitle = props.get("mode");
- if (modeTitle != null) {
- nextMode = findMode(modeTitle);
- if (nextMode == null) {
+ String modeIdentifier = props.get("mode.id");
+ if (modeTitle != null && modeIdentifier != null) {
+// nextMode = findMode(modeTitle);
+ Mode mode = findMode(modeIdentifier);
+ if (mode != null) {
+ nextMode = mode;
+
+ } else {
final String msg =
"This sketch was last used in “" + modeTitle + "” mode,\n" +
"which does not appear to be installed. The sketch will\n" +
- "be opened in “" + defaultMode.getTitle() + "” mode instead.";
+ "be opened in “" + nextMode.getTitle() + "” mode instead.";
Base.showWarning("Depeche Mode", msg, null);
- nextMode = defaultMode;
}
}
}
@@ -1002,14 +1026,14 @@ public class Base {
// if (editors.size() == 0 && defaultFileMenu == null) {
// if it's not mode[0] already, then don't go into an infinite loop
// trying to recreate a window with the default mode.
- if (nextMode == defaultMode) {
+ if (nextMode == coreModes[0]) {
Base.showError("Editor Problems",
"An error occurred while trying to change modes.\n" +
"We'll have to quit for now because it's an\n" +
"unfortunate bit of indigestion.",
null);
} else {
- editor = defaultMode.createEditor(this, path, state);
+ editor = coreModes[0].createEditor(this, path, state);
}
}
@@ -1020,7 +1044,7 @@ public class Base {
}
editors.add(editor);
- recent.handleOpen(editor, recentMenu);
+ recent.handle(editor);
// now that we're ready, show the window
// (don't do earlier, cuz we might move it based on a window being closed)
@@ -1030,9 +1054,18 @@ public class Base {
}
- protected Mode findMode(String title) {
+// protected Mode findMode(String title) {
+// for (Mode mode : getModeList()) {
+// if (mode.getTitle().equals(title)) {
+// return mode;
+// }
+// }
+// return null;
+// }
+
+ protected Mode findMode(String id) {
for (Mode mode : getModeList()) {
- if (mode.getTitle().equals(title)) {
+ if (mode.getIdentifier().equals(id)) {
return mode;
}
}
@@ -1114,7 +1147,7 @@ public class Base {
editor.setVisible(false);
editor.dispose();
defaultFileMenu.insert(sketchbookMenu, 2);
- defaultFileMenu.insert(recentMenu, 3);
+ defaultFileMenu.insert(getRecentMenu(), 3);
// defaultFileMenu.insert(defaultMode.getExamplesMenu(), 3);
activeEditor = null;
editors.remove(editor);
@@ -1244,15 +1277,39 @@ public class Base {
}
return sketchbookMenu;
}
-
+
+
+// public JMenu getRecentMenu() {
+// if (recentMenu == null) {
+// recentMenu = recent.createMenu();
+// } else {
+// recent.updateMenu(recentMenu);
+// }
+// return recentMenu;
+// }
+
public JMenu getRecentMenu() {
- if (recentMenu == null) {
- recentMenu = recent.createMenu();
- } else {
- recent.updateMenu(recentMenu);
- }
- return recentMenu;
+ return recent.getMenu();
+ }
+
+
+// public void renameRecent(String oldPath, String newPath) {
+// recent.handleRename(oldPath, newPath);
+// }
+
+
+ public void handleRecent(Editor editor) {
+ recent.handle(editor);
+ }
+
+
+ /**
+ * Called before a sketch is renamed so that its old name is
+ * no longer in the menu.
+ */
+ public void removeRecent(Editor editor) {
+ recent.remove(editor);
}
@@ -2808,7 +2865,24 @@ public class Base {
}
+ static public void log(Object from, String message) {
+ if (DEBUG) {
+ System.out.println(from.getClass().getName() + ": " + message);
+ }
+ }
+
+
static public void log(String message) {
- if (DEBUG) System.out.println(message);
+ if (DEBUG) {
+ System.out.println(message);
+ }
+ }
+
+
+ static public void log(String message, Exception e) {
+ if (DEBUG) {
+ System.out.println(message);
+ e.printStackTrace();
+ }
}
}
diff --git a/app/src/processing/app/Editor.java b/app/src/processing/app/Editor.java
index 71390804b..a63af2a74 100644
--- a/app/src/processing/app/Editor.java
+++ b/app/src/processing/app/Editor.java
@@ -105,7 +105,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
private FindReplace find;
JMenu toolsMenu;
- JMenu modeMenu;
+ JMenu modeMenu;
ArrayList coreTools;
public ArrayList contribTools;
@@ -117,7 +117,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
this.base = base;
this.state = state;
this.mode = mode;
-
+
Base.setIcon(this); // TODO should this be per-mode?
// Install default actions for Run, Present, etc.
@@ -159,7 +159,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
});
timer = new Timer();
-
+
buildMenuBar();
Container contentPain = getContentPane();
@@ -198,7 +198,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
consolePanel.add(lineStatus, BorderLayout.SOUTH);
upper.add(textarea);
-
+
// alternate spot for status, but ugly
// status = new EditorStatus(this);
// upper.add(status);
@@ -222,19 +222,19 @@ public abstract class Editor extends JFrame implements RunnerListener {
if (dividerSize != 0) {
splitPane.setDividerSize(dividerSize);
}
-
+
box.add(splitPane);
pain.add(box);
// get shift down/up events so we can show the alt version of toolbar buttons
textarea.addKeyListener(toolbar);
-
+
// end an undo-chunk any time the caret moves unless it's when text is edited
textarea.addCaretListener(new CaretListener() {
-
+
String lastText = textarea.getText();
-
+
public void caretUpdate(CaretEvent e) {
String newText = textarea.getText();
if (lastText.equals(newText) && isDirectEdit()) {
@@ -256,13 +256,13 @@ public abstract class Editor extends JFrame implements RunnerListener {
// Set the minimum size for the editor window
setMinimumSize(new Dimension(Preferences.getInteger("editor.window.width.min"),
Preferences.getInteger("editor.window.height.min")));
-
+
// Bring back the general options for the editor
applyPreferences();
-
+
// Make textField get the focus whenever frame is activated.
// http://download.oracle.com/javase/tutorial/uiswing/misc/focus.html
- // May not be necessary, but helps avoid random situations with
+ // May not be necessary, but helps avoid random situations with
// the editor not being able to request its own focus.
addWindowFocusListener(new WindowAdapter() {
public void windowGainedFocus(WindowEvent e) {
@@ -285,6 +285,16 @@ public abstract class Editor extends JFrame implements RunnerListener {
}
+ public void removeRecent() {
+ base.removeRecent(this);
+ }
+
+
+ public void addRecent() {
+ base.handleRecent(this);
+ }
+
+
/**
* Handles files dragged & dropped from the desktop and into the editor
* window. Dragging files into the editor window is the same as using
@@ -332,7 +342,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
}
}
} catch (Exception e) {
- Base.showWarning("Drag & Drop Problem",
+ Base.showWarning("Drag & Drop Problem",
"An error occurred while trying to add files to the sketch.", e);
return false;
}
@@ -349,18 +359,18 @@ public abstract class Editor extends JFrame implements RunnerListener {
return true;
}
}
-
-
+
+
public Base getBase() {
return base;
}
-
-
+
+
public Mode getMode() {
return mode;
}
-
-
+
+
protected void initModeMenu() {
modeMenu = new JMenu();
for (final Mode m : base.getModeList()) {
@@ -380,7 +390,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
modeMenu.add(item);
}
}
-
+
modeMenu.addSeparator();
JMenuItem addLib = new JMenuItem("Add Mode...");
addLib.addActionListener(new ActionListener() {
@@ -390,22 +400,22 @@ public abstract class Editor extends JFrame implements RunnerListener {
});
modeMenu.add(addLib);
}
-
-
+
+
public JMenu getModeMenu() {
return modeMenu;
}
-
-
+
+
// public Settings getTheme() {
// return mode.getTheme();
// }
-
-
+
+
abstract public EditorToolbar createToolbar();
-
-
+
+
abstract public Formatter createFormatter();
@@ -432,13 +442,13 @@ public abstract class Editor extends JFrame implements RunnerListener {
//
// return location;
// }
-
-
+
+
protected void setDividerLocation(int pos) {
splitPane.setDividerLocation(pos);
}
-
-
+
+
protected int getDividerLocation() {
return splitPane.getDividerLocation();
}
@@ -467,7 +477,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
painter.setBackground(color);
painter.setLineHighlightEnabled(false);
textarea.setCaretVisible(false);
-
+
// new stuff
// splitPane.setDividerLocation(toolbar.getHeight() + header.getHeight());
// splitPane.setResizeWeight(0D);
@@ -478,7 +488,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
boolean highlight = Preferences.getBoolean("editor.linehighlight");
painter.setLineHighlightEnabled(highlight);
textarea.setCaretVisible(true);
-
+
// new stuff
// splitPane.setDividerLocation(-1); // any negative value resets to preferred size
// splitPane.setResizeWeight(1D);
@@ -513,7 +523,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
rebuildToolList();
rebuildToolMenu();
menubar.add(getToolMenu());
-
+
JMenu modeMenu = buildModeMenu();
if (modeMenu != null) {
menubar.add(modeMenu);
@@ -536,11 +546,11 @@ public abstract class Editor extends JFrame implements RunnerListener {
menubar.add(buildHelpMenu());
setJMenuBar(menubar);
}
-
+
abstract public JMenu buildFileMenu();
-
-
+
+
// public JMenu buildFileMenu(Editor editor) {
// return buildFileMenu(editor, null);
// }
@@ -548,8 +558,8 @@ public abstract class Editor extends JFrame implements RunnerListener {
//
// // most of these items are per-mode
// protected JMenu buildFileMenu(Editor editor, JMenuItem[] exportItems) {
-
-
+
+
protected JMenu buildFileMenu(JMenuItem[] exportItems) {
JMenuItem item;
JMenu fileMenu = new JMenu("File");
@@ -592,7 +602,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
item = Base.newJMenuItem("Save", 'S');
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
- handleSaveRequest(false);
+ handleSave(false);
}
});
saveMenuItem = item;
@@ -655,8 +665,8 @@ public abstract class Editor extends JFrame implements RunnerListener {
}
return fileMenu;
}
-
-
+
+
// public void setSaveItem(JMenuItem item) {
// saveMenuItem = item;
// }
@@ -666,7 +676,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
// saveAsMenuItem = item;
// }
-
+
protected JMenu buildEditMenu() {
JMenu menu = new JMenu("Edit");
JMenuItem item;
@@ -732,7 +742,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
/*
menu.addSeparator();
-
+
item = Base.newJMenuItem("Delete Selected Lines", 'D');
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
@@ -740,7 +750,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
}
});
menu.add(item);
-
+
item = new JMenuItem("Move Selected Lines Up");
item.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_UP, Event.ALT_MASK));
item.addActionListener(new ActionListener() {
@@ -749,7 +759,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
}
});
menu.add(item);
-
+
item = new JMenuItem("Move Selected Lines Down");
item.setAccelerator(KeyStroke.getKeyStroke(KeyEvent.VK_DOWN, Event.ALT_MASK));
item.addActionListener(new ActionListener() {
@@ -759,7 +769,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
});
menu.add(item);
*/
-
+
menu.addSeparator();
item = Base.newJMenuItem("Auto Format", 'T');
@@ -847,8 +857,8 @@ public abstract class Editor extends JFrame implements RunnerListener {
abstract public JMenu buildSketchMenu();
-
-
+
+
protected JMenu buildSketchMenu(JMenuItem[] runItems) {
JMenuItem item;
sketchMenu = new JMenu("Sketch");
@@ -880,8 +890,8 @@ public abstract class Editor extends JFrame implements RunnerListener {
return sketchMenu;
}
-
-
+
+
abstract public void handleImportLibrary(String jarPath);
@@ -905,13 +915,13 @@ public abstract class Editor extends JFrame implements RunnerListener {
} else {
toolsMenu.removeAll();
}
-
+
rebuildToolList();
-
+
addInternalTools(toolsMenu);
addTools(toolsMenu, coreTools);
addTools(toolsMenu, contribTools);
-
+
toolsMenu.addSeparator();
JMenuItem item = new JMenuItem("Add Tool...");
item.addActionListener(new ActionListener() {
@@ -944,7 +954,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
//menu.add(item);
toolItems.put(title, item);
}
-
+
ArrayList toolList = new ArrayList(toolItems.keySet());
if (toolList.size() == 0) return;
@@ -1016,8 +1026,8 @@ public abstract class Editor extends JFrame implements RunnerListener {
return menu;
}
-
-
+
+
/*
// testing internal web server to serve up docs from a zip file
item = new JMenuItem("Web Server Test");
@@ -1066,12 +1076,12 @@ public abstract class Editor extends JFrame implements RunnerListener {
Base.openURL(file.getAbsolutePath());
}
-
+
static public void showChanges() {
Base.openURL("http://wiki.processing.org/w/Changes");
- }
+ }
+
-
// . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
@@ -1083,7 +1093,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
public void actionPerformed(ActionEvent e) {
stopCompoundEdit();
-
+
try {
final Integer caret = caretUndoStack.pop();
caretRedoStack.push(caret);
@@ -1134,7 +1144,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
public void actionPerformed(ActionEvent e) {
stopCompoundEdit();
-
+
try {
undo.redo();
} catch (CannotRedoException ex) {
@@ -1428,29 +1438,29 @@ public abstract class Editor extends JFrame implements RunnerListener {
// code.undo = new UndoManager();
document.addDocumentListener(new DocumentListener() {
-
+
public void removeUpdate(DocumentEvent e) {
if (isInserting && isDirectEdit()) {
endTextEditHistory();
}
isInserting = false;
}
-
+
public void insertUpdate(DocumentEvent e) {
if (!isInserting && isDirectEdit()) {
endTextEditHistory();
}
isInserting = true;
}
-
+
public void changedUpdate(DocumentEvent e) {
endTextEditHistory();
}
});
-
+
// connect the undo listener to the editor
document.addUndoableEditListener(new UndoableEditListener() {
-
+
public void undoableEditHappened(UndoableEditEvent e) {
// if an edit is in progress, reset the timer
if (endUndoEvent != null) {
@@ -1458,13 +1468,13 @@ public abstract class Editor extends JFrame implements RunnerListener {
endUndoEvent = null;
startTimerEvent();
}
-
+
// if this edit is just getting started, create a compound edit
if (compoundEdit == null) {
startCompoundEdit();
startTimerEvent();
}
-
+
compoundEdit.addEdit(e.getEdit());
undoAction.updateUndoState();
redoAction.updateRedoState();
@@ -1503,7 +1513,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
// let the gc eat the cancelled events
timer.purge();
}
-
+
void endTextEditHistory() {
if (endUndoEvent != null) {
endUndoEvent.cancel();
@@ -1562,32 +1572,32 @@ public abstract class Editor extends JFrame implements RunnerListener {
/*
public void handleMoveLines(boolean moveUp) {
startCompoundEdit();
-
+
int startLine = textarea.getSelectionStartLine();
int stopLine = textarea.getSelectionStopLine();
-
+
// if more than one line is selected and none of the characters of the end
// line are selected, don't move that line
if (startLine != stopLine
&& textarea.getSelectionStop() == textarea.getLineStartOffset(stopLine))
stopLine--;
-
+
int replacedLine = moveUp ? startLine - 1 : stopLine + 1;
if (replacedLine < 0 || replacedLine >= textarea.getLineCount())
return;
-
+
final String source = getText();
-
+
int replaceStart = textarea.getLineStartOffset(replacedLine);
int replaceEnd = textarea.getLineStopOffset(replacedLine);
if (replaceEnd == source.length() + 1)
replaceEnd--;
-
+
int selectionStart = textarea.getLineStartOffset(startLine);
int selectionEnd = textarea.getLineStopOffset(stopLine);
if (selectionEnd == source.length() + 1)
selectionEnd--;
-
+
String replacedText = source.substring(replaceStart, replaceEnd);
String selectedText = source.substring(selectionStart, selectionEnd);
if (replacedLine == textarea.getLineCount() - 1) {
@@ -1597,51 +1607,51 @@ public abstract class Editor extends JFrame implements RunnerListener {
selectedText += "\n";
replacedText = replacedText.substring(0, replacedText.length() - 1);
}
-
+
int newSelectionStart, newSelectionEnd;
if (moveUp) {
// Change the selection, then change the line above
textarea.select(selectionStart, selectionEnd);
textarea.setSelectedText(replacedText);
-
+
textarea.select(replaceStart, replaceEnd);
textarea.setSelectedText(selectedText);
-
+
newSelectionStart = textarea.getLineStartOffset(startLine - 1);
- newSelectionEnd = textarea.getLineStopOffset(stopLine - 1) - 1;
+ newSelectionEnd = textarea.getLineStopOffset(stopLine - 1) - 1;
} else {
// Change the line beneath, then change the selection
textarea.select(replaceStart, replaceEnd);
textarea.setSelectedText(selectedText);
-
+
textarea.select(selectionStart, selectionEnd);
textarea.setSelectedText(replacedText);
-
+
newSelectionStart = textarea.getLineStartOffset(startLine + 1);
- newSelectionEnd = textarea.getLineStopOffset(stopLine + 1) - 1;
+ newSelectionEnd = textarea.getLineStopOffset(stopLine + 1) - 1;
}
-
+
textarea.select(newSelectionStart, newSelectionEnd);
stopCompoundEdit();
}
*/
-
+
/*
public void handleDeleteLines() {
int startLine = textarea.getSelectionStartLine();
int stopLine = textarea.getSelectionStopLine();
-
+
int start = textarea.getLineStartOffset(startLine);
- int end = textarea.getLineStopOffset(stopLine);
+ int end = textarea.getLineStopOffset(stopLine);
if (end == getText().length() + 1)
end--;
-
+
textarea.select(start, end);
textarea.setSelectedText("");
}
*/
-
+
public void handleAutoFormat() {
final String source = getText();
@@ -1740,13 +1750,13 @@ public abstract class Editor extends JFrame implements RunnerListener {
public void handleIndent() {
handleIndentOutdent(true);
}
-
-
+
+
public void handleOutdent() {
handleIndentOutdent(false);
}
-
-
+
+
public void handleIndentOutdent(boolean indent) {
int tabSize = Preferences.getInteger("editor.tabs.size");
String tabString = Editor.EMPTY.substring(0, tabSize);
@@ -1829,7 +1839,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
return sketchWindowLocation;
}
-
+
// public void internalCloseRunner() {
// mode.internalCloseRunner(this);
// }
@@ -1854,7 +1864,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
JOptionPane.QUESTION_MESSAGE);
if (result == JOptionPane.YES_OPTION) {
- return handleSaveRequest(true);
+ return handleSave(true);
} else if (result == JOptionPane.NO_OPTION) {
return true; // ok to continue
@@ -1906,7 +1916,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
Object result = pane.getValue();
if (result == options[0]) { // save (and close/quit)
- return handleSaveRequest(true);
+ return handleSave(true);
} else if (result == options[2]) { // don't save (still close/quit)
return true;
@@ -2044,10 +2054,10 @@ public abstract class Editor extends JFrame implements RunnerListener {
// return false;
// }
}
-
-
- /**
- * Set the title of the PDE window based on the current sketch, i.e.
+
+
+ /**
+ * Set the title of the PDE window based on the current sketch, i.e.
* something like "sketch_070752a - Processing 0126"
*/
public void setTitle() {
@@ -2064,7 +2074,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
* won't run properly while a quit is happening. This fixes
* Bug 276.
*/
- public boolean handleSaveRequest(boolean immediately) {
+ public boolean handleSave(boolean immediately) {
// handleStop(); // 0136
if (untitled) {
@@ -2072,12 +2082,12 @@ public abstract class Editor extends JFrame implements RunnerListener {
// need to get the name, user might also cancel here
} else if (immediately) {
- handleSave();
+ handleSaveImpl();
} else {
- SwingUtilities.invokeLater(new Runnable() {
+ EventQueue.invokeLater(new Runnable() {
public void run() {
- handleSave();
+ handleSaveImpl();
}
});
}
@@ -2085,7 +2095,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
}
- public void handleSave() {
+ protected void handleSaveImpl() {
statusNotice("Saving...");
try {
if (sketch.save()) {
@@ -2177,8 +2187,8 @@ public abstract class Editor extends JFrame implements RunnerListener {
}
- /**
- * Grab current contents of the sketch window, advance the console,
+ /**
+ * Grab current contents of the sketch window, advance the console,
* stop any other running sketches... not in that order.
*/
public void prepareRun() {
@@ -2192,7 +2202,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
if (Preferences.getBoolean("console.auto_clear")) {
console.clear();
}
-
+
// make sure the user didn't hide the sketch folder
sketch.ensureExistence();
@@ -2208,16 +2218,16 @@ public abstract class Editor extends JFrame implements RunnerListener {
}
- /**
- * Halt the current runner for whatever reason. Might be the VM dying,
- * the window closing, an error...
+ /**
+ * Halt the current runner for whatever reason. Might be the VM dying,
+ * the window closing, an error...
*/
abstract public void internalCloseRunner();
-
-
+
+
abstract public void deactivateRun();
-
+
// . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
@@ -2292,7 +2302,7 @@ public abstract class Editor extends JFrame implements RunnerListener {
public void statusNotice(String msg) {
status.notice(msg);
}
-
+
public void clearNotice(String msg) {
if (status.message.equals(msg)) {
@@ -2307,23 +2317,23 @@ public abstract class Editor extends JFrame implements RunnerListener {
public void statusEmpty() {
statusNotice(EMPTY);
}
-
-
+
+
public void startIndeterminate() {
status.startIndeterminate();
}
-
-
+
+
public void stopIndeterminate() {
status.stopIndeterminate();
}
-
-
+
+
public void statusHalt() {
// stop called by someone else
}
-
-
+
+
public boolean isHalted() {
return false;
}
diff --git a/app/src/processing/app/Mode.java b/app/src/processing/app/Mode.java
index 5d92da41f..6e7b5f3ec 100644
--- a/app/src/processing/app/Mode.java
+++ b/app/src/processing/app/Mode.java
@@ -14,16 +14,16 @@ import processing.app.syntax.*;
public abstract class Mode {
protected Base base;
-
+
protected File folder;
protected HashMap keywordToReference;
-
+
protected PdeKeywords tokenMarker;
protected Settings theme;
// protected Formatter formatter;
// protected Tool formatter;
-
+
// maps imported packages to their library folder
// protected HashMap importToLibraryTable;
protected HashMap> importToLibraryTable;
@@ -32,25 +32,25 @@ public abstract class Mode {
// each time a sketch is created, renamed, or moved.
protected JMenu examplesMenu; // this is for the menubar, not the toolbar
protected JMenu importMenu;
-
+
// protected JTree examplesTree;
protected JFrame examplesFrame;
-
+
// popup menu used for the toolbar
protected JMenu toolbarMenu;
-
+
protected File examplesFolder;
protected File librariesFolder;
protected File referenceFolder;
public ArrayList coreLibraries;
- public ArrayList contribLibraries;
+ public ArrayList contribLibraries;
+
-
public Mode(Base base, File folder) {
this.base = base;
this.folder = folder;
-
+
// Get paths for the libraries and examples in the mode folder
examplesFolder = new File(folder, "examples");
librariesFolder = new File(folder, "libraries");
@@ -65,38 +65,50 @@ public abstract class Mode {
// other things that have to be set explicitly for the defaults
theme.setColor("run.window.bgcolor", SystemColor.control);
-
+
} catch (IOException e) {
- Base.showError("Problem loading theme.txt",
+ Base.showError("Problem loading theme.txt",
"Could not load theme.txt, please re-install Processing", e);
}
}
-
-
+
+
public File getContentFile(String path) {
return new File(folder, path);
}
-
-
+
+
public InputStream getContentStream(String path) throws FileNotFoundException {
return new FileInputStream(getContentFile(path));
}
-
- /**
+
+ /**
* Return the pretty/printable/menu name for this mode. This is separate from
* the single word name of the folder that contains this mode. It could even
- * have spaces, though that might result in sheer madness or total mayhem.
+ * have spaces, though that might result in sheer madness or total mayhem.
*/
abstract public String getTitle();
/**
- * Create a new editor associated with this mode.
+ * Get an identifier that can be used to resurrect this mode and connect it
+ * to a sketch. Using this instead of getTitle() because there might be name
+ * clashes with the titles, but there should not be once the actual package,
+ * et al. is included.
+ * @return full name (package + class name) for this mode.
+ */
+ public String getIdentifier() {
+ return getClass().getCanonicalName();
+ }
+
+
+ /**
+ * Create a new editor associated with this mode.
*/
abstract public Editor createEditor(Base base, String path, EditorState state);
//abstract public Editor createEditor(Base base, String path, int[] location);
-
+
public File getExamplesFolder() {
return examplesFolder;
@@ -106,8 +118,8 @@ public abstract class Mode {
public File getLibrariesFolder() {
return librariesFolder;
}
-
-
+
+
public File getReferenceFolder() {
return referenceFolder;
}
@@ -122,7 +134,7 @@ public abstract class Mode {
coreLibraries = Library.list(librariesFolder);
contribLibraries = Library.list(base.getSketchbookLibrariesFolder());
-
+
for (Library lib : coreLibraries) {
lib.addPackageList(importToLibraryTable);
}
@@ -130,8 +142,8 @@ public abstract class Mode {
lib.addPackageList(importToLibraryTable);
}
}
-
-
+
+
public Library getLibrary(String pkgName) throws SketchException {
ArrayList libraries = importToLibraryTable.get(pkgName);
if (libraries == null) {
@@ -139,7 +151,7 @@ public abstract class Mode {
} else if (libraries.size() > 1) {
String primary = "More than one library is competing for this sketch.";
- String secondary = "The import " + pkgName + " points to multiple libraries:
";
+ String secondary = "The import " + pkgName + " points to multiple libraries:
";
for (Library library : libraries) {
String location = library.getPath();
if (location.startsWith(getLibrariesFolder().getAbsolutePath())) {
@@ -147,22 +159,22 @@ public abstract class Mode {
}
secondary += "" + library.getName() + " (" + location + ")
";
}
- secondary += "Extra libraries need to be removed before this sketch can be used.";
+ secondary += "Extra libraries need to be removed before this sketch can be used.";
Base.showWarningTiered("Duplicate Library Problem", primary, secondary, null);
throw new SketchException("Duplicate libraries found for " + pkgName + ".");
-
+
} else {
return libraries.get(0);
}
}
-
+
// . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
-
+
// abstract public EditorToolbar createToolbar(Editor editor);
-
-
+
+
public JMenu getToolbarMenu() {
if (toolbarMenu == null) {
// toolbarMenu = new JMenu();
@@ -189,7 +201,7 @@ public abstract class Mode {
}
});
toolbarMenu.add(item);
-
+
// JMenu examplesMenu = new JMenu("Examples");
// rebuildExamplesMenu(examplesMenu, true);
item = new JMenuItem("Examples...");
@@ -200,7 +212,7 @@ public abstract class Mode {
});
toolbarMenu.add(item);
// toolbarMenu.add(examplesMenu);
-
+
toolbarMenu.addSeparator();
// Add a list of all sketches and subfolders
@@ -248,9 +260,9 @@ public abstract class Mode {
});
importMenu.add(addLib);
importMenu.addSeparator();
-
+
rebuildLibraryList();
-
+
ActionListener listener = new ActionListener() {
public void actionPerformed(ActionEvent e) {
base.activeEditor.handleImportLibrary(e.getActionCommand());
@@ -283,12 +295,12 @@ public abstract class Mode {
importMenu.add(contrib);
HashMap subfolders = new HashMap();
-
+
for (Library library : contribLibraries) {
JMenuItem item = new JMenuItem(library.getName());
item.addActionListener(listener);
item.setActionCommand(library.getJarPath());
-
+
String group = library.getGroup();
if (group != null) {
JMenu subMenu = subfolders.get(group);
@@ -298,14 +310,14 @@ public abstract class Mode {
subfolders.put(group, subMenu);
}
subMenu.add(item);
- } else {
+ } else {
importMenu.add(item);
}
}
}
}
-
-
+
+
/*
public JMenu getExamplesMenu() {
if (examplesMenu == null) {
@@ -321,13 +333,13 @@ public abstract class Mode {
}
rebuildExamplesMenu(examplesMenu, false);
}
-
-
+
+
public void rebuildExamplesMenu(JMenu menu, boolean replace) {
try {
// break down the examples folder for examples
File[] subfolders = getExampleCategoryFolders();
-
+
for (File sub : subfolders) {
Base.addDisabledItem(menu, sub.getName());
// JMenuItem categoryItem = new JMenuItem(sub.getName());
@@ -340,7 +352,7 @@ public abstract class Mode {
// if (coreLibraries == null) {
// rebuildLibraryList();
// }
-
+
// get library examples
Base.addDisabledItem(menu, "Libraries");
for (Library lib : coreLibraries) {
@@ -387,8 +399,8 @@ public abstract class Mode {
}
});
}
-
-
+
+
public JTree buildExamplesTree() {
DefaultMutableTreeNode node = new DefaultMutableTreeNode("Examples");
@@ -400,7 +412,7 @@ public abstract class Mode {
// TreeCellRenderer tcr = examplesTree.getCellRenderer();
//
-//
+//
// public void rebuildExamplesTree(DefaultMutableTreeNode node) {
try {
// break down the examples folder for examples
@@ -464,8 +476,8 @@ public abstract class Mode {
}
return examplesTree;
}
-
-
+
+
public void resetExamples() {
if (examplesFrame != null) {
boolean visible = examplesFrame.isVisible();
@@ -517,7 +529,7 @@ public abstract class Mode {
}
});
*/
-
+
/*
* MouseListener ml = new MouseAdapter() {
* public void mousePressed(MouseEvent e) {
@@ -538,7 +550,7 @@ public abstract class Mode {
tree.addMouseListener(new MouseAdapter() {
public void mouseClicked(MouseEvent e) {
if (e.getClickCount() == 2) {
- DefaultMutableTreeNode node =
+ DefaultMutableTreeNode node =
(DefaultMutableTreeNode) tree.getLastSelectedPathComponent();
if (node != null && node.isLeaf()) {
SketchReference sketch = (SketchReference) node.getUserObject();
@@ -565,16 +577,16 @@ public abstract class Mode {
}
public void keyTyped(KeyEvent e) {
if (e.getKeyChar() == KeyEvent.VK_ENTER) {
- DefaultMutableTreeNode node =
+ DefaultMutableTreeNode node =
(DefaultMutableTreeNode) tree.getLastSelectedPathComponent();
if (node != null && node.isLeaf()) {
SketchReference sketch = (SketchReference) node.getUserObject();
base.handleOpen(sketch.getPath());
}
- }
+ }
}
});
-
+
tree.setBorder(new EmptyBorder(5, 5, 5, 5));
JScrollPane treePane = new JScrollPane(tree);
treePane.setPreferredSize(new Dimension(250, 450));
@@ -586,13 +598,13 @@ public abstract class Mode {
int roughWidth = examplesFrame.getWidth() + 20;
Point p = null;
// If no window open, or the editor is at the edge of the screen
- if (base.activeEditor == null ||
+ if (base.activeEditor == null ||
(p = base.activeEditor.getLocation()).x < roughWidth) {
// Center the window on the screen
examplesFrame.setLocationRelativeTo(null);
} else {
// Open the window relative to the editor
- examplesFrame.setLocation(p.x - roughWidth, p.y);
+ examplesFrame.setLocation(p.x - roughWidth, p.y);
}
examplesFrame.setVisible(true);
}
@@ -612,10 +624,10 @@ public abstract class Mode {
// sketchMenu.remove(importMenu);
// }
-
-// abstract public void internalCloseRunner(Editor editor);
-
+// abstract public void internalCloseRunner(Editor editor);
+
+
// . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
@@ -626,16 +638,16 @@ public abstract class Mode {
File file = new File(folder, filename);
return new ImageIcon(file.getAbsolutePath()).getImage();
}
-
-
+
+
//public Settings getTheme() {
// return theme;
//}
- /**
- * Returns the HTML filename (including path prefix if necessary)
- * for this keyword, or null if it doesn't exist.
+ /**
+ * Returns the HTML filename (including path prefix if necessary)
+ * for this keyword, or null if it doesn't exist.
*/
public String lookupReference(String keyword) {
return keywordToReference.get(keyword);
@@ -649,24 +661,24 @@ public abstract class Mode {
public TokenMarker getTokenMarker() {
return tokenMarker;
}
-
-
+
+
// abstract public Formatter createFormatter();
// public Formatter getFormatter() {
-// return formatter;
+// return formatter;
// }
-
-
+
+
// public Tool getFormatter() {
-// return formatter;
+// return formatter;
// }
-
+
// . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
-
+
//public String get(String attribute) {
// return theme.get(attribute);
//}
@@ -699,8 +711,8 @@ public abstract class Mode {
// . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
-
-
+
+
// Breaking out extension types in order to clean up the code, and make it
// easier for other environments (like Arduino) to incorporate changes.
@@ -748,7 +760,7 @@ public abstract class Mode {
* Returns the default extension for this editor setup.
*/
abstract public String getDefaultExtension();
-
+
/**
@@ -761,13 +773,13 @@ public abstract class Mode {
* Get array of file/directory names that needn't be copied during "Save As".
*/
abstract public String[] getIgnorable();
-
-
+
+
// . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
/**
- * Create a fresh applet/application folder if the 'delete target folder'
+ * Create a fresh applet/application folder if the 'delete target folder'
* pref has been set in the preferences.
*/
public void prepareExportFolder(File targetFolder) {
@@ -784,7 +796,7 @@ public abstract class Mode {
}
// public void handleNew() {
-// base.handleNew();
+// base.handleNew();
// }
//
//
diff --git a/app/src/processing/app/Recent.java b/app/src/processing/app/Recent.java
index 44aa1853d..e37377817 100644
--- a/app/src/processing/app/Recent.java
+++ b/app/src/processing/app/Recent.java
@@ -32,32 +32,33 @@ import processing.core.PApplet;
// dealing with renaming
// before sketch save/rename, remove it from the recent list
// after sketch save/rename add it to the list
-// need to do this whether or not
+// need to do this whether or not
public class Recent {
-
static final String FILENAME = "recent.txt";
- static final String VERSION = "1";
-
+ static final String VERSION = "2";
+
Base base;
-
File file;
int count;
ArrayList records;
+ JMenu menu;
public Recent(Base base) {
this.base = base;
count = Preferences.getInteger("recent.count");
file = Base.getSettingsFile(FILENAME);
+ menu = new JMenu("Recent Sketches");
+
try {
load();
} catch (IOException e) {
e.printStackTrace();
}
}
-
-
+
+
protected void load() throws IOException {
records = new ArrayList();
if (file.exists()) {
@@ -66,12 +67,19 @@ public class Recent {
if (version != null && version.equals(VERSION)) {
String line = null;
while ((line = reader.readLine()) != null) {
- String[] pieces = PApplet.split(line, '\t');
- Record record = new Record(pieces[0], new EditorState(pieces[1]));
- records.add(record);
+// String[] pieces = PApplet.split(line, '\t');
+// Record record = new Record(pieces[0], new EditorState(pieces[1]));
+// Record record = new Record(pieces[0]); //, new EditorState(pieces[1]));
+// records.add(record);
+ if (new File(line).exists()) { // don't add ghost entries
+ records.add(new Record(line));
+ } else {
+ Base.log(this, "ghost file: " + line);
+ }
}
}
}
+ updateMenu();
}
@@ -80,121 +88,177 @@ public class Recent {
writer.println(VERSION);
for (Record record : records) {
// System.out.println(record.getPath() + "\t" + record.getState());
- writer.println(record.getPath() + "\t" + record.getState());
-// if (record.sketch == null) {
-// writer.println(record.path + "\t" + record.state);
-// } else {
-// writer.println(record.)
-// }
+// writer.println(record.path + "\t" + record.getState());
+ writer.println(record.path); // + "\t" + record.getState());
}
writer.flush();
writer.close();
// System.out.println();
+ updateMenu();
}
-
-
- public JMenu createMenu() {
- JMenu menu = new JMenu("Recent Sketches");
- updateMenu(menu);
+
+
+ public JMenu getMenu() {
return menu;
}
-
-
- public void updateMenu(JMenu menu) {
+
+
+ private void updateMenu() {
menu.removeAll();
for (final Record rec : records) {
JMenuItem item = new JMenuItem(rec.getName());
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
- handleOpen(rec);
+ // Base will call handle() (below) which will cause this entry to
+ // be removed from the list and re-added to the end. If already
+ // opened, Base will bring the window forward, and also call handle()
+ // so that it's re-queued to the newest slot in the Recent menu.
+ base.handleOpen(rec.path);
+// if (rec.sketch == null) {
+// // this will later call 'add' to put it back on the stack
+// base.handleOpen(rec.path); //, rec.state);
+//// int index = findRecord(rec);
+//// if (index != -1) {
+//// records.remove(index); // remove from the list
+//// save(); // write the recent file with the latest
+//// }
+// } else {
+//// System.out.println("sketch not null in handleOpen: " + record.getPath());
+// }
}
});
menu.add(item);
}
}
-
-
- /** Opened from the recent sketches menu. */
- synchronized void handleOpen(Record record) {
- if (record.sketch == null) {
-// Editor editor = base.handleOpen(record.path, record.state);
- base.handleOpen(record.path, record.state);
- int index = findRecord(record);
- if (index != -1) {
- records.remove(index); // remove from the list
-// if (editor != null) {
-// record.sketch = editor.getSketch();
-// records.add(record); // move to the end of the line
-// }
- save(); // write the recent file with the latest
- }
- } else {
-// System.out.println("sketch not null in handleOpen: " + record.getPath());
- }
- // otherwise the other handleOpen() will be called once it opens
- }
-
-
- /** Called by Base when a new sketch is opened. */
- synchronized void handleOpen(Editor editor, JMenu menu) {
-// System.out.println("handleOpen editor " + editor.getSketch().getMainFilePath());
- Record newRec = new Record(editor, editor.getSketch());
- // If this is already in the menu, remove it
- int index = findRecord(newRec);
+
+
+ synchronized void remove(Editor editor) {
+ int index = findRecord(editor.getSketch().getMainFilePath());
if (index != -1) {
records.remove(index);
}
- if (records.size() == count) {
- records.remove(0); // remove the first entry
- }
- records.add(newRec);
- updateMenu(menu);
- save();
}
-
-
- int findRecord(Record rec) {
- int index = records.indexOf(rec);
- if (index != -1) {
- return index;
- }
- index = 0;
- for (Record r : records) {
-// System.out.println("checking " + r + "\n against " + rec);
- if (r.equals(rec)) {
- return index;
+
+
+// synchronized void handleRename(String oldPath, String newPath) {
+// int index = findRecord(oldPath);
+// if (index != -1) {
+// Record rec = records.get(index);
+// rec.path = newPath;
+// save();
+// } else {
+// Base.log(this, "Could not find " + oldPath +
+// " in list of recent sketches to replace with " + newPath);
+// }
+// }
+
+
+// /** Opened from the recent sketches menu. */
+// synchronized void handleOpen(Record record) {
+// if (record.sketch == null) {
+//// Editor editor = base.handleOpen(record.path, record.state);
+// base.handleOpen(record.path, record.state);
+// int index = findRecord(record);
+// if (index != -1) {
+// records.remove(index); // remove from the list
+//// if (editor != null) {
+//// record.sketch = editor.getSketch();
+//// records.add(record); // move to the end of the line
+//// }
+// save(); // write the recent file with the latest
+// }
+// } else {
+//// System.out.println("sketch not null in handleOpen: " + record.getPath());
+// }
+// // otherwise the other handleOpen() will be called once it opens
+// }
+
+
+ /**
+ * Called by Base when a new sketch is opened, to add the sketch to the last
+ * entry on the Recent queue. If the sketch is already in the list, it is
+ * first removed so it doesn't show up multiple times.
+ */
+ synchronized void handle(Editor editor) {
+ if (!editor.getSketch().isUntitled()) {
+ // If this is already in the menu, remove it
+ remove(editor);
+
+ if (records.size() == count) {
+ records.remove(0); // remove the first entry
+ }
+
+// Record newRec = new Record(editor, editor.getSketch());
+// records.add(newRec);
+ records.add(new Record(editor));
+// updateMenu();
+ save();
+ }
+ }
+
+
+ int findRecord(String path) {
+ for (int i = 0; i < records.size(); i++) {
+ if (path.equals(records.get(i).path)) {
+ return i;
}
- index++;
}
return -1;
}
-
-
+
+
+// int findRecord(Record rec) {
+// int index = records.indexOf(rec);
+// if (index != -1) {
+// return index;
+// }
+// return findRecord(rec.path);
+//// index = 0;
+//// for (Record r : records) {
+//// System.out.println("checking " + r + "\n against " + rec);
+//// if (r.equals(rec)) {
+//// return index;
+//// }
+//// index++;
+//// }
+//// return -1;
+// }
+
+
class Record {
String path; // if not loaded, this is non-null
- EditorState state; // if not loaded, this is non-null
+// EditorState state; // if not loaded, this is non-null
/**
- * If currently loaded, this is non-null, and takes precedence over the
+ * If currently loaded, this is non-null, and takes precedence over the
* path and state information, which will instead be stored actively by
* the actual sketch object.
*/
- Sketch sketch;
Editor editor;
+// Sketch sketch;
- Record(String path, EditorState state) {
+// Record(String path, EditorState state) {
+// this.path = path;
+// this.state = state;
+// }
+
+ Record(String path) {
this.path = path;
- this.state = state;
}
-
- Record(Editor editor, Sketch sketch) {
+
+// Record(Editor editor, Sketch sketch) {
+// this.editor = editor;
+// this.sketch = sketch;
+// }
+
+ Record(Editor editor) {
this.editor = editor;
- this.sketch = sketch;
+ this.path = editor.getSketch().getMainFilePath();
}
String getName() {
- if (sketch != null) {
- return sketch.getName();
+ if (editor != null) {
+ return editor.getSketch().getName();
}
// Get the filename of the .pde (or .js or .py...)
String name = path.substring(path.lastIndexOf(File.separatorChar) + 1);
@@ -202,22 +266,25 @@ public class Recent {
return name.substring(0, name.indexOf('.'));
}
- String getPath() {
- if (sketch != null) {
- return sketch.getMainFilePath();
- } else {
- return path;
- }
- }
+// String getPath() {
+// if (sketch != null) {
+// return sketch.getMainFilePath();
+// } else {
+// return path;
+// }
+// }
- EditorState getState() {
- //return sketch != null ? sketch.getEditor() state;
- return sketch == null ? state : editor.getEditorState();
- }
-
- public boolean equals(Object o) {
- Record r = (Record) o;
- return getPath().equals(r.getPath());
- }
+// EditorState getState() {
+//// return sketch == null ? state : editor.getEditorState();
+// if (editor != null) { // update state if editor is open
+// state = editor.getEditorState();
+// }
+// return state;
+// }
+
+// public boolean equals(Object o) {
+// Record r = (Record) o;
+// return getPath().equals(r.getPath());
+// }
}
}
\ No newline at end of file
diff --git a/app/src/processing/app/SingleInstance.java b/app/src/processing/app/SingleInstance.java
index ae359d4ca..cc6a174d2 100644
--- a/app/src/processing/app/SingleInstance.java
+++ b/app/src/processing/app/SingleInstance.java
@@ -3,7 +3,7 @@
/*
Part of the Processing project - http://processing.org
- Copyright (c) 2011 Ben Fry and Casey Reas
+ Copyright (c) 2011-12 Ben Fry and Casey Reas
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License version 2
@@ -33,30 +33,33 @@ import processing.core.PApplet;
/**
- * Class that handles a small server that prevents multiple instances of
- * Processing from running simultaneously. If there's already an instance
+ * Class that handles a small server that prevents multiple instances of
+ * Processing from running simultaneously. If there's already an instance
* running, it'll handle opening a new empty sketch, or any files that had
* been passed in on the command line.
- *
+ *
* @author Peter Kalauskas, Ben Fry
*/
public class SingleInstance {
static final String SERVER_PORT = "instance_server.port";
static final String SERVER_KEY = "instance_server.key";
-
-
+
+
/**
* Returns true if there's an instance of Processing already running.
- * @param filename Path to the PDE file that was opened, null if double-clicked
+ * Will not return true unless this code was able to successfully
+ * contact the already running instance to have it launch sketches.
+ * @param filename Path to the PDE file that was opened, null if double-clicked
* @return true if successfully launched on the other instance
*/
- static boolean exists(String[] args) {
- return (Preferences.get(SERVER_PORT) != null &&
+ static boolean alreadyRunning(String[] args) {
+ return (Preferences.get(SERVER_PORT) != null &&
sendArguments(args, 5000));
}
-
- static void createServer(final Platform platform) {
+
+// static void startServer(final Platform platform) {
+ static void startServer(final Base base) {
try {
final ServerSocket ss = new ServerSocket(0, 0, InetAddress.getByName(null));
Preferences.set(SERVER_PORT, "" + ss.getLocalPort());
@@ -71,54 +74,55 @@ public class SingleInstance {
Socket s = ss.accept(); // blocks (sleeps) until connection
final BufferedReader reader = PApplet.createReader(s.getInputStream());
String receivedKey = reader.readLine();
- if (Base.DEBUG) {
- System.out.println("key is " + key + ", received is " + receivedKey);
- System.out.println("platform base is " + platform.base);
- System.out.flush();
- }
+ Base.log(this, "key is " + key + ", received is " + receivedKey);
+// Base.log(this, "platform base is " + platform.base);
- if (platform.base != null) {
- if (key.equals(receivedKey)) {
- SwingUtilities.invokeLater(new Runnable() {
- public void run() {
- try {
- Base.log("about to read line");
- String filename = reader.readLine();
- if (filename != null) {
- Base.log("calling open with " + filename);
- platform.base.handleOpen(filename);
- // see if there is more than one file that was passed in
- while ((filename = reader.readLine()) != null) {
- Base.log("continuing to call open with " + filename);
- platform.base.handleOpen(filename);
- }
- } else {
- Base.log("opening new empty sketch");
- platform.base.handleNew();
- }
- } catch (IOException e) {
- e.printStackTrace();
+// if (platform.base != null) {
+ if (key.equals(receivedKey)) {
+ SwingUtilities.invokeLater(new Runnable() {
+ public void run() {
+ try {
+ Base.log(this, "about to read line");
+ String path = reader.readLine();
+ if (path == null) {
+ // Because an attempt was made to launch the PDE again,
+ // throw the user a bone by at least opening a new
+ // Untitled window for them.
+ Base.log(this, "opening new empty sketch");
+// platform.base.handleNew();
+ base.handleNew();
+
+ } else {
+ // loop through the sketches that were passed in
+ do {
+ Base.log(this, "calling open with " + path);
+// platform.base.handleOpen(filename);
+ base.handleOpen(path);
+ path = reader.readLine();
+ } while (path != null);
}
+ } catch (IOException e) {
+ e.printStackTrace();
}
- });
- } else {
- Base.log("keys do not match");
- }
+ }
+ });
+ } else {
+ Base.log(this, "keys do not match");
}
+// }
} catch (IOException e) {
- e.printStackTrace();
+ Base.log("SingleInstance error while listening", e);
}
}
}
}).start();
} catch (IOException e) {
- System.err.println("Could not create single instance server.");
- e.printStackTrace();
+ Base.log("Could not create single instance server.", e);
}
}
-
+
static boolean sendArguments(String[] args, long timeout) {
try {
//int port = Integer.parseInt(Preferences.get("server.port"));
diff --git a/app/src/processing/app/Sketch.java b/app/src/processing/app/Sketch.java
index 1265b630e..76c6ba1a5 100644
--- a/app/src/processing/app/Sketch.java
+++ b/app/src/processing/app/Sketch.java
@@ -663,7 +663,9 @@ public class Sketch {
/**
- * Save all code in the current sketch.
+ * Save all code in the current sketch. This just forces the files to save
+ * in place, so if it's an untitled (un-saved) sketch, saveAs() should be
+ * called instead. (This is handled inside Editor.handleSave()).
*/
public boolean save() throws IOException {
// make sure the user didn't hide the sketch folder
@@ -711,7 +713,7 @@ public class Sketch {
if (false) {
// The Swing file chooser has some upside (i.e. fixes an OS X focus
- // traversal bug) bug is super ugly and not OS native.
+ // traversal bug) but is super ugly and not OS native.
JFileChooser fc = new JFileChooser();
fc.setDialogTitle("Save sketch folder as...");
if (isReadOnly() || isUntitled()) {
@@ -793,12 +795,12 @@ public class Sketch {
} catch (IOException e) { }
// if the new folder already exists, then first remove its contents before
- // copying everything over (user will have already been warned)
+ // copying everything over (user will have already been warned).
if (newFolder.exists()) {
Base.removeDir(newFolder);
}
- // in fact, you can't do this on windows because the file dialog
- // will instead put you inside the folder, but it happens on osx a lot.
+ // in fact, you can't do this on Windows because the file dialog
+ // will instead put you inside the folder, but it happens on OS X a lot.
// now make a fresh copy of the folder
newFolder.mkdirs();
@@ -851,6 +853,13 @@ public class Sketch {
code[i].saveAs(newFile);
}
+ // While the old path to the main .pde is still set, remove the entry from
+ // the Recent menu so that it's not sticking around after the rename.
+ // If untitled, it won't be in the menu, so there's no point.
+ if (!isUntitled()) {
+ editor.removeRecent();
+ }
+
// save the main tab with its new name
File newFile = new File(newFolder, newName + ".pde");
code[0].saveAs(newFile);
@@ -860,6 +869,9 @@ public class Sketch {
// Make sure that it's not an untitled sketch
setUntitled(false);
+ // Add this sketch back using the new name
+ editor.addRecent();
+
// let Editor know that the save was successful
return true;
}
@@ -870,7 +882,12 @@ public class Sketch {
*/
protected void updateInternal(String sketchName, File sketchFolder) {
// reset all the state information for the sketch object
+
+// String oldPath = getMainFilePath();
primaryFile = code[0].getFile();
+// String newPath = getMainFilePath();
+// editor.base.renameRecent(oldPath, newPath);
+
name = sketchName;
folder = sketchFolder;
codeFolder = new File(folder, "code");
diff --git a/app/src/processing/app/UpdateCheck.java b/app/src/processing/app/UpdateCheck.java
index a36ff5976..3a352d431 100644
--- a/app/src/processing/app/UpdateCheck.java
+++ b/app/src/processing/app/UpdateCheck.java
@@ -3,7 +3,7 @@
/*
Part of the Processing project - http://processing.org
- Copyright (c) 2005-06 Ben Fry and Casey Reas
+ Copyright (c) 2005-12 Ben Fry and Casey Reas
This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
@@ -26,7 +26,6 @@ import java.io.BufferedReader;
import java.io.InputStream;
import java.io.InputStreamReader;
import java.net.URL;
-import java.net.URLEncoder;
import java.util.Random;
import javax.swing.JOptionPane;
@@ -88,14 +87,13 @@ public class UpdateCheck {
Preferences.set("update.id", String.valueOf(id));
}
- String info;
- info = URLEncoder.encode(id + "\t" +
- PApplet.nf(Base.REVISION, 4) + "\t" +
- System.getProperty("java.version") + "\t" +
- System.getProperty("java.vendor") + "\t" +
- System.getProperty("os.name") + "\t" +
- System.getProperty("os.version") + "\t" +
- System.getProperty("os.arch"), "UTF-8");
+ String info = PApplet.urlEncode(id + "\t" +
+ PApplet.nf(Base.REVISION, 4) + "\t" +
+ System.getProperty("java.version") + "\t" +
+ System.getProperty("java.vendor") + "\t" +
+ System.getProperty("os.name") + "\t" +
+ System.getProperty("os.version") + "\t" +
+ System.getProperty("os.arch"));
int latest = readInt(downloadURL + "?" + info);
@@ -111,14 +109,13 @@ public class UpdateCheck {
Preferences.set("update.last", String.valueOf(now));
if (base.activeEditor != null) {
-
boolean offerToUpdateContributions = true;
-
+
if (latest > Base.REVISION) {
// Assume the person is busy downloading the latest version
offerToUpdateContributions = !promptToVisitDownloadPage();
}
-
+
if (offerToUpdateContributions) {
// Wait for xml file to be downloaded and updates to come in. (this
// should really be handled better).
@@ -133,11 +130,11 @@ public class UpdateCheck {
}
- protected boolean promptToVisitDownloadPage() {
+ protected boolean promptToVisitDownloadPage() {
String prompt =
"A new version of Processing is available,\n" +
"would you like to visit the Processing download page?";
-
+
Object[] options = { "Yes", "No" };
int result = JOptionPane.showOptionDialog(base.activeEditor,
prompt,
@@ -151,16 +148,16 @@ public class UpdateCheck {
Base.openURL("http://processing.org/download/");
return true;
}
-
+
return false;
}
-
-
+
+
protected boolean promptToOpenContributionManager() {
String contributionPrompt =
"There are updates available for some of the installed contributions,\n" +
"would you like to open the the Contribution Manager now?";
-
+
Object[] options = { "Yes", "No" };
int result = JOptionPane.showOptionDialog(base.activeEditor,
contributionPrompt,
@@ -174,7 +171,7 @@ public class UpdateCheck {
base.handleShowUpdates();
return true;
}
-
+
return false;
}
diff --git a/app/src/processing/app/macosx/ThinkDifferent.java b/app/src/processing/app/macosx/ThinkDifferent.java
index 9f1774e40..7b070c54a 100644
--- a/app/src/processing/app/macosx/ThinkDifferent.java
+++ b/app/src/processing/app/macosx/ThinkDifferent.java
@@ -36,14 +36,14 @@ import com.apple.eawt.*;
/**
* Deal with issues related to thinking differently. This handles the basic
* Mac OS X menu commands (and apple events) for open, about, prefs, etc.
- *
+ *
* Based on OSXAdapter.java from Apple DTS.
- *
- * As of 0140, this code need not be built on platforms other than OS X,
+ *
+ * As of 0140, this code need not be built on platforms other than OS X,
* because of the new platform structure which isolates through reflection.
- *
- * This suppresses deprecation warnings because to use the new code, all users
- * would be forced to use Java Update 3 on OS X 10.6, and Java Update 8 on
+ *
+ * This suppresses deprecation warnings because to use the new code, all users
+ * would be forced to use Java Update 3 on OS X 10.6, and Java Update 8 on
* OS X 10.5, which doesn't seem likely at the moment.
*/
@SuppressWarnings("deprecation")
@@ -58,8 +58,8 @@ public class ThinkDifferent implements ApplicationListener {
// reference to the app where the existing quit, about, prefs code is
private Base base;
-
- static protected void init(Base base) {
+
+ static protected void init(Base base) {
if (application == null) {
//application = new com.apple.eawt.Application();
application = Application.getApplication();
@@ -74,12 +74,12 @@ public class ThinkDifferent implements ApplicationListener {
// Set the menubar to be used when nothing else is open. http://j.mp/dkZmka
// http://developer.apple.com/mac/library/documentation/Java/Reference/
// JavaSE6_AppleExtensionsRef/api/com/apple/eawt/Application.html
- // Only available since Java for Mac OS X 10.6 Update 1, and
+ // Only available since Java for Mac OS X 10.6 Update 1, and
// Java for Mac OS X 10.5 Update 6, so need to load this dynamically
try {
- // com.apple.eawt.Application.setDefaultMenuBar(JMenuBar)
+ // com.apple.eawt.Application.setDefaultMenuBar(JMenuBar)
Class> appClass = Application.class;
- Method method =
+ Method method =
appClass.getMethod("setDefaultMenuBar", new Class[] { JMenuBar.class });
if (method != null) {
JMenuBar defaultMenuBar = new JMenuBar();
@@ -93,12 +93,12 @@ public class ThinkDifferent implements ApplicationListener {
e.printStackTrace(); // oh well nevermind
}
}
-
-
+
+
public ThinkDifferent(Base base) {
this.base = base;
}
-
+
/**
* Gimpy file menu to be used on OS X when no sketches are open.
@@ -124,21 +124,21 @@ public class ThinkDifferent implements ApplicationListener {
fileMenu.add(item);
fileMenu.add(base.getSketchbookMenu());
-
+
// fileMenu.add(base.nextEditorMode().getExamplesMenu());
item = new JMenuItem("Examples...");
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
- base.nextEditorMode().showExamplesFrame();
+ base.nextMode.showExamplesFrame();
}
});
fileMenu.add(item);
return fileMenu;
}
-
-
- // implemented handler methods. These are basically hooks into existing
+
+
+ // implemented handler methods. These are basically hooks into existing
// functionality from the main app, as if it came over from another platform.
public void handleAbout(ApplicationEvent ae) {
if (base != null) {
@@ -148,8 +148,8 @@ public class ThinkDifferent implements ApplicationListener {
throw new IllegalStateException("handleAbout: Base instance detached from listener");
}
}
-
-
+
+
public void handlePreferences(ApplicationEvent ae) {
if (base != null) {
base.handlePrefs();
@@ -179,7 +179,7 @@ public class ThinkDifferent implements ApplicationListener {
public void handleQuit(ApplicationEvent ae) {
if (base != null) {
- /*
+ /*
/ You MUST setHandled(false) if you want to delay or cancel the quit.
/ This is important for cross-platform development -- have a universal quit
/ routine that chooses whether or not to quit, so the functionality is identical
@@ -192,8 +192,8 @@ public class ThinkDifferent implements ApplicationListener {
throw new IllegalStateException("handleQuit: Base instance detached from listener");
}
}
-
-
+
+
public void handleReOpenApplication(ApplicationEvent arg0) {
}
}
\ No newline at end of file
diff --git a/app/src/processing/app/tools/Archiver.java b/app/src/processing/app/tools/Archiver.java
index 9eb9655ff..a760dd79f 100755
--- a/app/src/processing/app/tools/Archiver.java
+++ b/app/src/processing/app/tools/Archiver.java
@@ -46,8 +46,8 @@ public class Archiver implements Tool {
public String getMenuTitle() {
return "Archive Sketch";
}
-
-
+
+
public void init(Editor editor) {
this.editor = editor;
@@ -61,18 +61,11 @@ public class Archiver implements Tool {
public void run() {
Sketch sketch = editor.getSketch();
-
- // first save the sketch so that things don't archive strangely
- boolean success = false;
- try {
- success = sketch.save();
- } catch (Exception e) {
- e.printStackTrace();
- }
- if (!success) {
- Base.showWarning("Couldn't archive sketch",
- "Archiving the sketch has been canceled because\n" +
- "the sketch couldn't save properly.", null);
+
+ if (sketch.isModified()) {
+ Base.showWarning("Save",
+ "Please save the sketch before archiving.",
+ null);
return;
}
@@ -80,9 +73,6 @@ public class Archiver implements Tool {
String name = location.getName();
File parent = new File(location.getParent());
- //System.out.println("loc " + location);
- //System.out.println("par " + parent);
-
File newbie = null;
String namely = null;
int index = 0;
diff --git a/app/src/processing/mode/android/AndroidToolbar.java b/app/src/processing/mode/android/AndroidToolbar.java
index 189789a95..d4cda80aa 100644
--- a/app/src/processing/mode/android/AndroidToolbar.java
+++ b/app/src/processing/mode/android/AndroidToolbar.java
@@ -97,7 +97,7 @@ public class AndroidToolbar extends EditorToolbar {
break;
case SAVE:
- aeditor.handleSaveRequest(false);
+ aeditor.handleSave(false);
break;
case EXPORT:
diff --git a/app/src/processing/mode/java/JavaEditor.java b/app/src/processing/mode/java/JavaEditor.java
index 97c8c1ec9..644c59108 100644
--- a/app/src/processing/mode/java/JavaEditor.java
+++ b/app/src/processing/mode/java/JavaEditor.java
@@ -23,7 +23,7 @@ public class JavaEditor extends Editor {
protected JavaEditor(Base base, String path, EditorState state, Mode mode) {
- super(base, path, state, mode);
+ super(base, path, state, mode);
// hopefully these are no longer needed w/ swing
// (har har har.. that was wishful thinking)
@@ -173,7 +173,7 @@ public class JavaEditor extends Editor {
menu.add(item);
return menu;
- }
+ }
// . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . . .
@@ -224,7 +224,7 @@ public class JavaEditor extends Editor {
// statusError(e);
// }
// toolbar.deactivate(Toolbar.EXPORT);
-// }
+// }
/**
@@ -456,7 +456,7 @@ public class JavaEditor extends Editor {
options[0]);
if (result == JOptionPane.OK_OPTION) {
- handleSaveRequest(true);
+ handleSave(true);
} else {
// why it's not CANCEL_OPTION is beyond me (at least on the mac)
@@ -530,7 +530,7 @@ public class JavaEditor extends Editor {
public void handleSave() {
toolbar.activate(JavaToolbar.SAVE);
//handleStop();
- super.handleSave();
+ super.handleSave(true);
toolbar.deactivate(JavaToolbar.SAVE);
}
diff --git a/app/src/processing/mode/java/JavaToolbar.java b/app/src/processing/mode/java/JavaToolbar.java
index c3dce52ae..62cf03dd2 100644
--- a/app/src/processing/mode/java/JavaToolbar.java
+++ b/app/src/processing/mode/java/JavaToolbar.java
@@ -111,7 +111,7 @@ public class JavaToolbar extends EditorToolbar {
break;
case SAVE:
- jeditor.handleSaveRequest(false);
+ jeditor.handleSave(false);
break;
case EXPORT:
diff --git a/app/src/processing/mode/javascript/JavaScriptEditor.java b/app/src/processing/mode/javascript/JavaScriptEditor.java
index 7bf17ca3f..3d9b8d295 100644
--- a/app/src/processing/mode/javascript/JavaScriptEditor.java
+++ b/app/src/processing/mode/javascript/JavaScriptEditor.java
@@ -15,11 +15,11 @@ import processing.mode.java.AutoFormat;
import javax.swing.*;
-public class JavaScriptEditor extends ServingEditor
+public class JavaScriptEditor extends ServingEditor
{
final static String PROP_KEY_MODE = "mode";
final static String PROP_VAL_MODE = "JavaScript";
-
+
private JavaScriptMode jsMode;
private DirectivesEditor directivesEditor;
@@ -27,33 +27,33 @@ public class JavaScriptEditor extends ServingEditor
// tapping into Java mode might not be wanted?
processing.mode.java.PdeKeyListener listener;
- protected JavaScriptEditor ( Base base, String path, EditorState state, Mode mode )
+ protected JavaScriptEditor ( Base base, String path, EditorState state, Mode mode )
{
super(base, path, state, mode);
listener = new processing.mode.java.PdeKeyListener(this,textarea);
-
+
jsMode = (JavaScriptMode) mode;
}
-
- public EditorToolbar createToolbar ()
+
+ public EditorToolbar createToolbar ()
{
return new JavaScriptToolbar(this, base);
}
-
- public Formatter createFormatter ()
- {
+
+ public Formatter createFormatter ()
+ {
return new AutoFormat();
}
-
+
// - - - - - - - - - - - - - - - - - -
// Menu methods
-
- public JMenu buildFileMenu ()
+
+ public JMenu buildFileMenu ()
{
JMenuItem exportItem = Base.newJMenuItem("Export", 'E');
exportItem.addActionListener(new ActionListener() {
@@ -65,7 +65,7 @@ public class JavaScriptEditor extends ServingEditor
}
- public JMenu buildSketchMenu ()
+ public JMenu buildSketchMenu ()
{
JMenuItem startServerItem = Base.newJMenuItem("Start Server", 'R');
startServerItem.addActionListener(new ActionListener() {
@@ -102,7 +102,7 @@ public class JavaScriptEditor extends ServingEditor
// }
// }
// );
-
+
JMenuItem setServerPortItem = new JMenuItem("Set Server Port");
setServerPortItem.addActionListener(new ActionListener(){
public void actionPerformed (ActionEvent e) {
@@ -111,13 +111,13 @@ public class JavaScriptEditor extends ServingEditor
});
return buildSketchMenu(new JMenuItem[] {
- startServerItem, openInBrowserItem, stopServerItem,
+ startServerItem, openInBrowserItem, stopServerItem,
copyServerAddressItem, setServerPortItem
});
}
public JMenu buildModeMenu() {
- JMenu menu = new JMenu("JavaScript");
+ JMenu menu = new JMenu("JavaScript");
JMenuItem item;
item = new JMenuItem("Playback Settings (Directives)");
@@ -148,8 +148,8 @@ public class JavaScriptEditor extends ServingEditor
return menu;
}
-
- public JMenu buildHelpMenu ()
+
+ public JMenu buildHelpMenu ()
{
JMenu menu = new JMenu("Help ");
JMenuItem item;
@@ -195,7 +195,7 @@ public class JavaScriptEditor extends ServingEditor
item = new JMenuItem("Reference");
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
- //TODO get offline reference archive corresponding to the release
+ //TODO get offline reference archive corresponding to the release
// packaged with this mode see: P.js ticket 1146 "Offline Reference"
Base.openURL("http://processingjs.org/reference");
}
@@ -219,7 +219,7 @@ public class JavaScriptEditor extends ServingEditor
});
menu.add(item);
*/
-
+
item = new JMenuItem("Visit Processingjs.org");
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
@@ -227,7 +227,7 @@ public class JavaScriptEditor extends ServingEditor
}
});
menu.add(item);
-
+
// OSX has its own about menu
if (!Base.isMacOS()) {
menu.addSeparator();
@@ -239,12 +239,12 @@ public class JavaScriptEditor extends ServingEditor
});
menu.add(item);
}
-
+
return menu;
}
-
- public String getCommentPrefix ()
- {
+
+ public String getCommentPrefix ()
+ {
return "//";
}
@@ -265,22 +265,22 @@ public class JavaScriptEditor extends ServingEditor
{
// not sure what to do here ..
}
-
+
// - - - - - - - - - - - - - - - - - -
private void handleSetServerPort ()
{
statusEmpty();
-
+
boolean wasRunning = serverRunning();
if ( wasRunning ) {
statusNotice("Server was running, changing the port requires a restart.");
stopServer();
}
-
+
setServerPort();
saveSketchSettings();
-
+
if ( wasRunning ) {
startServer( getExportFolder() );
}
@@ -289,12 +289,12 @@ public class JavaScriptEditor extends ServingEditor
private void handleCreateCustomTemplate ()
{
Sketch sketch = getSketch();
-
+
File ajs = sketch.getMode().
getContentFile( JavaScriptBuild.TEMPLATE_FOLDER_NAME );
-
+
File tjs = getCustomTemplateFolder();
-
+
if ( !tjs.exists() )
{
try {
@@ -302,7 +302,7 @@ public class JavaScriptEditor extends ServingEditor
statusNotice( "Default template copied." );
Base.openFolder( tjs );
} catch ( java.io.IOException ioe ) {
- Base.showWarning("Copy default template folder",
+ Base.showWarning("Copy default template folder",
"Something went wrong when copying the template folder.", ioe);
}
}
@@ -329,12 +329,12 @@ public class JavaScriptEditor extends ServingEditor
private void handleCopyServerAddress ()
{
String address = getServerAddress();
-
+
if ( address != null )
{
- java.awt.datatransfer.StringSelection stringSelection =
+ java.awt.datatransfer.StringSelection stringSelection =
new java.awt.datatransfer.StringSelection( address );
- java.awt.datatransfer.Clipboard clipboard =
+ java.awt.datatransfer.Clipboard clipboard =
java.awt.Toolkit.getDefaultToolkit().getSystemClipboard();
clipboard.setContents( stringSelection, null );
}
@@ -346,7 +346,7 @@ public class JavaScriptEditor extends ServingEditor
{
directivesEditor = new DirectivesEditor(this);
}
-
+
directivesEditor.show();
}
@@ -362,7 +362,7 @@ public class JavaScriptEditor extends ServingEditor
if (textarea.isSelectionActive()) {
Base.openURL(
"http://www.google.com/search?q=" +
- textarea.getSelectedText().trim() +
+ textarea.getSelectedText().trim() +
"+site%3Ahttp%3A%2F%2Fprocessingjs.org%2Freference"
);
}
@@ -372,21 +372,21 @@ public class JavaScriptEditor extends ServingEditor
// {
// startStopServer( getExportFolder() );
// }
-
+
/**
- * Replacement for RUN:
+ * Replacement for RUN:
* export to folder, start server, open in default browser.
*/
public void handleStartServer ()
{
statusEmpty();
-
+
if ( !startServer( getExportFolder() ) )
{
if ( !handleExport( false ) ) return;
toolbar.activate(JavaScriptToolbar.RUN);
}
-
+
// waiting for server to call "serverStarted() below ..."
}
@@ -401,15 +401,15 @@ public class JavaScriptEditor extends ServingEditor
public void handleStopServer ()
{
stopServer();
-
+
toolbar.deactivate(JavaScriptToolbar.RUN);
}
-
+
/**
* Call the export method of the sketch and handle the gui stuff
*/
- public boolean handleExport ( boolean openFolder )
- {
+ public boolean handleExport ( boolean openFolder )
+ {
if ( !handleExportCheckModified() )
{
return false;
@@ -417,17 +417,17 @@ public class JavaScriptEditor extends ServingEditor
else
{
toolbar.activate(JavaScriptToolbar.EXPORT);
- try
+ try
{
boolean success = jsMode.handleExport(sketch);
- if ( success && openFolder )
+ if ( success && openFolder )
{
File exportFolder = new File( sketch.getFolder(),
JavaScriptBuild.EXPORTED_FOLDER_NAME );
Base.openFolder( exportFolder );
statusNotice("Finished exporting.");
- } else if ( !success ) {
+ } else if ( !success ) {
// error message already displayed by handleExport
return false;
}
@@ -440,12 +440,12 @@ public class JavaScriptEditor extends ServingEditor
}
return true;
}
-
+
/**
* Changed from Editor.java to automaticaly export and
* handle the server when it's running. Normal save ops otherwise.
*/
- public boolean handleSaveRequest(boolean immediately)
+ public boolean handleSave(boolean immediately)
{
if (untitled) {
return handleSaveAs();
@@ -466,8 +466,8 @@ public class JavaScriptEditor extends ServingEditor
}
return true;
}
-
- private boolean handleExportCheckModified ()
+
+ private boolean handleExportCheckModified ()
{
if (sketch.isModified()) {
Object[] options = { "OK", "Cancel" };
@@ -481,7 +481,7 @@ public class JavaScriptEditor extends ServingEditor
options[0]);
if (result == JOptionPane.OK_OPTION) {
- handleSaveRequest(true);
+ handleSave(true);
} else {
statusNotice("Export canceled, changes must first be saved.");
@@ -490,18 +490,18 @@ public class JavaScriptEditor extends ServingEditor
}
return true;
}
-
-
- public void handleSave ()
- {
+
+
+ public void handleSave ()
+ {
toolbar.activate(JavaScriptToolbar.SAVE);
- super.handleSave();
+ super.handleSave(true);
toolbar.deactivate(JavaScriptToolbar.SAVE);
}
-
-
- public boolean handleSaveAs ()
- {
+
+
+ public boolean handleSaveAs ()
+ {
toolbar.activate(JavaScriptToolbar.SAVE);
boolean result = super.handleSaveAs();
toolbar.deactivate(JavaScriptToolbar.SAVE);
@@ -509,7 +509,7 @@ public class JavaScriptEditor extends ServingEditor
}
- public void handleImportLibrary (String item)
+ public void handleImportLibrary (String item)
{
Base.showWarning("Processing.js doesn't support libraries",
"Libraries are not supported. Import statements are " +
@@ -537,7 +537,7 @@ public class JavaScriptEditor extends ServingEditor
private File getCustomTemplateFolder ()
{
- return new File( getSketch().getFolder(),
+ return new File( getSketch().getFolder(),
JavaScriptBuild.TEMPLATE_FOLDER_NAME );
}
diff --git a/app/src/processing/mode/javascript/JavaScriptToolbar.java b/app/src/processing/mode/javascript/JavaScriptToolbar.java
index c997fc6f5..4b50e54ae 100644
--- a/app/src/processing/mode/javascript/JavaScriptToolbar.java
+++ b/app/src/processing/mode/javascript/JavaScriptToolbar.java
@@ -79,7 +79,7 @@ public class JavaScriptToolbar extends EditorToolbar {
break;
case SAVE:
- jsEditor.handleSaveRequest(false);
+ jsEditor.handleSave(false);
break;
case EXPORT:
diff --git a/build/shared/lib/preferences.txt b/build/shared/lib/preferences.txt
index 306d7fbf9..919ef8cba 100755
--- a/build/shared/lib/preferences.txt
+++ b/build/shared/lib/preferences.txt
@@ -66,7 +66,7 @@ contribution.backup.on_remove = true
# (for example, from a plb file)
contribution.backup.on_install = true
-recent.count = 5
+recent.count = 10
# !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
diff --git a/core/src/processing/core/PApplet.java b/core/src/processing/core/PApplet.java
index 55ffa14b1..2742fddc6 100644
--- a/core/src/processing/core/PApplet.java
+++ b/core/src/processing/core/PApplet.java
@@ -861,7 +861,22 @@ public class PApplet extends Applet
width = g.width;
height = g.height;
- addListeners();
+// addListeners(); // 2.0a6
+ // moved out of addListeners() in 2.0a6
+ addComponentListener(new ComponentAdapter() {
+ public void componentResized(ComponentEvent e) {
+ Component c = e.getComponent();
+ //System.out.println("componentResized() " + c);
+ Rectangle bounds = c.getBounds();
+ resizeRequest = true;
+ resizeWidth = bounds.width;
+ resizeHeight = bounds.height;
+
+ if (!looping) {
+ redraw();
+ }
+ }
+ });
// this is automatically called in applets
// though it's here for applications anyway
@@ -1666,6 +1681,7 @@ public class PApplet extends Applet
}
}
*/
+
// the 1.2.1 version
if ((g != null) && (g.image != null)) {
// println("inside paint(), screen.drawImage()");
@@ -1674,7 +1690,7 @@ public class PApplet extends Applet
}
- // active paint method
+ // active paint method (also the 1.2.1 version)
protected void paint() {
try {
Graphics screen = this.getGraphics();
@@ -1695,6 +1711,7 @@ public class PApplet extends Applet
}
}
+
protected void paint_1_5_1() {
try {
Graphics screen = getGraphics();
@@ -1748,9 +1765,7 @@ public class PApplet extends Applet
// println("paused...");
try {
Thread.sleep(100L);
- } catch (InterruptedException e) {
- //ignore?
- }
+ } catch (InterruptedException e) { } // ignored
}
// Don't resize the renderer from the EDT (i.e. from a ComponentEvent),
@@ -1765,17 +1780,22 @@ public class PApplet extends Applet
if (g != null) g.requestDraw();
if (frameCount == 1) {
- // Call the request focus event once the image is sure to be on
- // screen and the component is valid. The OpenGL renderer will
- // request focus for its canvas inside beginDraw().
- // http://java.sun.com/j2se/1.4.2/docs/api/java/awt/doc-files/FocusSpec.html
- // Disabling for 0185, because it causes an assertion failure on OS X
- // http://code.google.com/p/processing/issues/detail?id=258
- // requestFocus();
+ // for 2.0a6, moving this request to the EDT
+ EventQueue.invokeLater(new Runnable() {
+ public void run() {
+ // Call the request focus event once the image is sure to be on
+ // screen and the component is valid. The OpenGL renderer will
+ // request focus for its canvas inside beginDraw().
+ // http://java.sun.com/j2se/1.4.2/docs/api/java/awt/doc-files/FocusSpec.html
+ // Disabling for 0185, because it causes an assertion failure on OS X
+ // http://code.google.com/p/processing/issues/detail?id=258
+ // requestFocus();
- // Changing to this version for 0187
- // http://code.google.com/p/processing/issues/detail?id=279
- requestFocusInWindow();
+ // Changing to this version for 0187
+ // http://code.google.com/p/processing/issues/detail?id=279
+ requestFocusInWindow();
+ }
+ });
}
// wait for update & paint to happen before drawing next frame
@@ -1907,9 +1927,12 @@ public class PApplet extends Applet
frameRateLastNanos = now;
frameCount++;
- paint(); // back to active paint
-// repaint();
-// getToolkit().sync(); // force repaint now (proper method)
+ // 1.2.1 version
+// paint();
+
+ // 1.5.1 version
+ repaint();
+ getToolkit().sync(); // force repaint now (proper method)
if (frameCount != 0) {
postMethods.handle();
@@ -2016,36 +2039,12 @@ public class PApplet extends Applet
//////////////////////////////////////////////////////////////
- public void addListeners() {
- addMouseListener(this);
- addMouseMotionListener(this);
- addKeyListener(this);
- addFocusListener(this);
-
- addComponentListener(new ComponentAdapter() {
- public void componentResized(ComponentEvent e) {
- Component c = e.getComponent();
- //System.out.println("componentResized() " + c);
- Rectangle bounds = c.getBounds();
- resizeRequest = true;
- resizeWidth = bounds.width;
- resizeHeight = bounds.height;
-
- if (!looping) {
- redraw();
- }
- }
- });
- }
-
-
- public void removeListeners() {
- removeMouseListener(this);
- removeMouseMotionListener(this);
- removeKeyListener(this);
- removeFocusListener(this);
-
-// removeComponentListener(??);
+// public void addListeners() {
+// addMouseListener(this);
+// addMouseMotionListener(this);
+// addKeyListener(this);
+// addFocusListener(this);
+//
// addComponentListener(new ComponentAdapter() {
// public void componentResized(ComponentEvent e) {
// Component c = e.getComponent();
@@ -2060,14 +2059,38 @@ public class PApplet extends Applet
// }
// }
// });
- }
+// }
+//
+//
+// public void removeListeners() {
+// removeMouseListener(this);
+// removeMouseMotionListener(this);
+// removeKeyListener(this);
+// removeFocusListener(this);
+//
+//// removeComponentListener(??);
+//// addComponentListener(new ComponentAdapter() {
+//// public void componentResized(ComponentEvent e) {
+//// Component c = e.getComponent();
+//// //System.out.println("componentResized() " + c);
+//// Rectangle bounds = c.getBounds();
+//// resizeRequest = true;
+//// resizeWidth = bounds.width;
+//// resizeHeight = bounds.height;
+////
+//// if (!looping) {
+//// redraw();
+//// }
+//// }
+//// });
+// }
- public void addListeners(Canvas canvas) {
- canvas.addMouseListener(this);
- canvas.addMouseMotionListener(this);
- canvas.addKeyListener(this);
- canvas.addFocusListener(this);
+ public void addListeners(Component comp) {
+ comp.addMouseListener(this);
+ comp.addMouseMotionListener(this);
+ comp.addKeyListener(this);
+ comp.addFocusListener(this);
// canvas.addComponentListener(new ComponentAdapter() {
// public void componentResized(ComponentEvent e) {
@@ -2086,11 +2109,11 @@ public class PApplet extends Applet
}
- public void removeListeners(Canvas canvas) {
- canvas.removeMouseListener(this);
- canvas.removeMouseMotionListener(this);
- canvas.removeKeyListener(this);
- canvas.removeFocusListener(this);
+ public void removeListeners(Component comp) {
+ comp.removeMouseListener(this);
+ comp.removeMouseMotionListener(this);
+ comp.removeKeyListener(this);
+ comp.removeFocusListener(this);
}
diff --git a/core/src/processing/core/PGraphics.java b/core/src/processing/core/PGraphics.java
index 181396f28..273f07e6d 100644
--- a/core/src/processing/core/PGraphics.java
+++ b/core/src/processing/core/PGraphics.java
@@ -667,6 +667,7 @@ public class PGraphics extends PImage implements PConstants {
return true;
}
+
/**
* Try to draw, or put a draw request on the queue.
*/
diff --git a/core/src/processing/core/PGraphicsJava2D.java b/core/src/processing/core/PGraphicsJava2D.java
index ef34045f5..a2e27b904 100644
--- a/core/src/processing/core/PGraphicsJava2D.java
+++ b/core/src/processing/core/PGraphicsJava2D.java
@@ -48,6 +48,7 @@ import java.awt.image.*;
* if it breaks."
*/
public class PGraphicsJava2D extends PGraphics /*PGraphics2D*/ {
+ Canvas canvas;
public Graphics2D g2;
protected BufferedImage offscreen;
@@ -128,6 +129,18 @@ public class PGraphicsJava2D extends PGraphics /*PGraphics2D*/ {
// strange things to happen with blending.
// image = new BufferedImage(width, height, BufferedImage.TYPE_INT_ARGB);
if (primarySurface) {
+// if (canvas != null) {
+// parent.removeListeners(canvas);
+// parent.remove(canvas);
+// }
+// canvas = new Canvas();
+// parent.setLayout(new BorderLayout());
+// parent.add(canvas, BorderLayout.CENTER);
+// parent.addListeners(canvas);
+//// canvas.createBufferStrategy(1);
+// g2 = (Graphics2D) canvas.getGraphics();
+ parent.addListeners(parent);
+
// Needs to be RGB otherwise there's a major performance hit [0204]
// http://code.google.com/p/processing/issues/detail?id=729
image = new BufferedImage(width, height, BufferedImage.TYPE_INT_RGB);
@@ -163,6 +176,15 @@ public class PGraphicsJava2D extends PGraphics /*PGraphics2D*/ {
}
+ public void requestDraw() {
+// EventQueue.invokeLater(new Runnable() {
+// public void run() {
+ parent.handleDraw();
+// }
+// });
+ }
+
+
public void beginDraw() {
checkSettings();
@@ -179,12 +201,19 @@ public class PGraphicsJava2D extends PGraphics /*PGraphics2D*/ {
//updatePixels();
if (primarySurface) {
- // don't copy the pixels/data elements of the buffered image directly,
- // since it'll disable the nice speedy pipeline stuff, sending all drawing
- // into a world of suck that's rough 6 trillion times slower.
- synchronized (image) {
- //System.out.println("inside j2d sync");
- image.getGraphics().drawImage(offscreen, 0, 0, null);
+ if (canvas != null) {
+ System.out.println(canvas);
+ canvas.repaint();
+ // ?? what to do for swapping buffers
+
+ } else {
+ // don't copy the pixels/data elements of the buffered image directly,
+ // since it'll disable the nice speedy pipeline stuff, sending all drawing
+ // into a world of suck that's rough 6 trillion times slower.
+ synchronized (image) {
+ //System.out.println("inside j2d sync");
+ image.getGraphics().drawImage(offscreen, 0, 0, null);
+ }
}
} else {
// TODO this is probably overkill for most tasks...
diff --git a/core/todo.txt b/core/todo.txt
index 69e0003a4..8058735e9 100644
--- a/core/todo.txt
+++ b/core/todo.txt
@@ -21,6 +21,20 @@ X CENTER_RADIUS, CENTER_DIAMETER, NORMALIZED
X text(x, y, w, h, z)
X textX/Y/Z variables
_ update changes Wiki
+_ where did hintEnabled() come from?
+
+_ move requestFocusInWindow() to safter EDT place
+_ look into using BufferStrategy again to improve performance
+_ there are more improvements to be made ala issue #729
+_ make sure rendering is happening on the EDT
+_ (hopefully fixes flicker issues)
+_ change PApplet.java javadoc to reflect the change
+_ Update http://wiki.processing.org/w/Troubleshooting#Flicker
+_ http://code.google.com/p/processing/issues/detail?id=775
+_ thread() causes weird flickering
+_ http://code.google.com/p/processing/issues/detail?id=742
+_ Potential race condition when resizing sketches
+_ http://code.google.com/p/processing/issues/detail?id=697
andres
A polygon shapes without fill slowdown render progressively
@@ -29,6 +43,10 @@ o OPENGL broken in 2.0a5 on Linux (upstream issues)
o http://code.google.com/p/processing/issues/detail?id=1026
A these were upstream issues
_ Update JOGL when RC6 arrive: forum.jogamp.org/Road-to-RC6-td3866404.html
+_ why are LINE_SMOOTH et al being enabled if antialias < 2?
+_ why is initPrimarySurface() public?
+_ why is setFramerate() public? (also should be setFrameRate or just frameRate)
+_ remove 'params' from createImage (is it on loadImage too?)
fixed in 2.0a5
A OpenGL noSmooth() does not work
@@ -78,18 +96,6 @@ _ http://code.google.com/p/processing/issues/detail?id=1045
X test what happens with NPE in OpenGL, does the error make sense?
_ nope, it doesn't, need to clean this up
-_ look into using BufferStrategy again to improve performance
-_ there are more improvements to be made ala issue #729
-_ make sure rendering is happening on the EDT
-_ (hopefully fixes flicker issues)
-_ change PApplet.java javadoc to reflect the change
-_ Update http://wiki.processing.org/w/Troubleshooting#Flicker
-_ http://code.google.com/p/processing/issues/detail?id=775
-_ thread() causes weird flickering
-_ http://code.google.com/p/processing/issues/detail?id=742
-_ Potential race condition when resizing sketches
-_ http://code.google.com/p/processing/issues/detail?id=697
-
sort out full screen issues
X make screenWidth and screenHeight work properly with multiple screens
X also set screenX and screenY
@@ -148,6 +154,8 @@ o or background(r, g, b, a) would be the thing
_ clear() with a color doesn't make (verbal) sense
_ provide a way to clear the PGraphics with plain alpha
+_ dispose() method in PApplet should be empty so ppl can override
+_ move that stuff to destroy()
_ pause()/resume() need to work on the desktop side as well
_ stop() not called in 1.5
_ http://code.google.com/p/processing/issues/detail?id=636
diff --git a/todo.txt b/todo.txt
index b679cd8c1..42f4e7c1a 100644
--- a/todo.txt
+++ b/todo.txt
@@ -64,18 +64,19 @@ X nah, take it out. why the complexity...
X if no window color set, then don't apply it
o also add option for FSEM or not
X nope, FSEM too buggy and error-prone
+
+recent/open
X add EditorState class, device-aware placement
X get rid of restore sketch feature
-_ remove pref for restoring sketches
+o remove pref for restoring sketches
+_ make sure this is still around, we want it
_ implement recent sketches menu
_ Opening sketch via editor window open-menu ignores mode
_ http://code.google.com/p/processing/issues/detail?id=1034
-
_ don't pollute the recent menu with un-saved sketches
_ toFront() not working from recent menu
_ don't re-open new window on top of another
_ not properly handling other odd cases
-http://code.google.com/p/processing/issues/list?can=2&q=owner%3Afry%40processing.org+Type%3ADefect&colspec=Stars+ID+Type+Status+Priority+Owner+Summary&cells=tiles
_ save window positions on quit, and restore them (w/ a preference?)
_ new windows use same mode and dimensions as topmost window
_ saved window position problematic with multiple monitors
@@ -108,6 +109,7 @@ _ http://dev.processing.org/bugs/show_bug.cgi?id=72
_ http://code.google.com/p/processing/issues/detail?id=27
Base.restoreSketches() has commented out code that checked for out of bounds windows with the preferences last.window.x and last.window.y. These prefs don't exist anymore, but it would be quick to implement it again using last.sketch.location instead. It would probably result in less code, because it would mean we could get rid of the windowPositionValid stuff.
+http://code.google.com/p/processing/issues/list?can=2&q=owner%3Afry%40processing.org+Type%3ADefect&colspec=Stars+ID+Type+Status+Priority+Owner+Summary&cells=tiles
with casey
_ does editor.bgcolor live in the theme.txt file for the mode?