diff --git a/app/Editor.java b/app/Editor.java
index 51e0b5b80..e6f6ae11d 100644
--- a/app/Editor.java
+++ b/app/Editor.java
@@ -581,7 +581,7 @@ public class Editor extends JFrame
JMenuItem item;
JMenu menu = new JMenu("Tools");
- item = new JMenuItem("Auto Format");
+ item = newJMenuItem("Auto Format", 'F', true);
item.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
new AutoFormat(Editor.this).show();
diff --git a/app/tools/AutoFormat.java b/app/tools/AutoFormat.java
index 59579f305..3e1a2f8da 100644
--- a/app/tools/AutoFormat.java
+++ b/app/tools/AutoFormat.java
@@ -3,8 +3,8 @@
/*
Part of the Processing project - http://processing.org
- Copyright (c) 2004-05 Ben Fry and Casey Reas
- Copyright (c) 2001-04 Massachusetts Institute of Technology
+ Copyright (c) 2005 Ben Fry and Casey Reas
+ Copyright (c) 2003 Martin Gomez, Ateneo de Manila University
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,33 +26,13 @@ package processing.app.tools;
import processing.app.*;
import processing.core.*;
-import java.awt.*;
-import java.awt.event.*;
import java.io.*;
-import java.util.*;
-
-import javax.swing.*;
-import javax.swing.border.*;
-import javax.swing.event.*;
+import java.util.StringTokenizer;
/**
- * Basic but buggy handler for cleaning up code.
- *
- * an improved algorithm that would still avoid a full state machine
- * 1. build an array of strings for the lines
- * 2. first remove everything between / * and * / (relentless)
- * 3. next remove anything inside two sets of " "
- * but not if escaped with a \
- * these can't extend beyond a line, so that works well
- * (this will save from "http://blahblah" showing up as a comment)
- * 4. remove from* to the end of a line everywhere
- * 5. run through remaining text to do indents
- * using hokey brace-counting algorithm
- * 6. also add indents for switch statements
- * case blah: { } (colons at end of line isn't a good way)
- * maybe /case \w+\:/
- *
+ * Alternate handler for dealing with auto format,
+ * contributed by Martin Gomez.
*/
public class AutoFormat {
Editor editor;
@@ -63,13 +43,14 @@ public class AutoFormat {
}
+ /*
public void show() {
String prog = editor.textarea.getText();
// TODO re-enable history
//history.record(prog, SketchHistory.BEAUTIFY);
- int tabSize = Preferences.getInteger("editor.tabs.size");
+ //int tabSize = Preferences.getInteger("editor.tabs.size");
char program[] = prog.toCharArray();
StringBuffer buffer = new StringBuffer();
@@ -157,4 +138,876 @@ public class AutoFormat {
editor.sketch.setModified();
//buttons.clear();
}
+ */
+
+
+ StringBuffer strOut;
+ String formattedText;
+ int indentValue;
+ String indentChar;
+ String uhOh = null;
+ String theStuff;
+ int EOF;
+ BufferedInputStream bin = null;
+ int nBytesRead, indexBlock, lineLength, lineNumber;
+ byte bArray[];
+ String strBlock;
+ int s_level[];
+ int c_level;
+ int sp_flg[][];
+ int s_ind[][];
+ int s_if_lev[];
+ int s_if_flg[];
+ int if_lev, if_flg, level;
+ int ind[];
+ int e_flg, paren;
+ static int p_flg[];
+ char l_char, p_char;
+ int a_flg, q_flg, ct;
+ int s_tabs[][];
+ String w_if_, w_else, w_for, w_ds, w_case, w_cpp_comment, w_jdoc;
+ int jdoc, j;
+ int BLOCK_MAXLEN;
+ char string[];
+ byte bstring[];
+ byte bblank;
+ char cc;
+ int s_flg, b_flg;
+ int peek;
+ char peekc;
+ int tabs;
+ char next_char, last_char;
+ char lastc0, lastc1;
+ char c, c0;
+ char w_kptr;
+
+ String line_feed;
+
+ static int outfil; // temporary
+
+
+ public void comment() {
+ int save_s_flg;
+ save_s_flg = s_flg;
+
+ int done = 0;
+ c = string[j++] = getchr(); // extra char
+ while (done == 0) {
+ c = string[j++] = getchr();
+ while(c != '/') {
+ if(c == '\n' || c == '\r') {
+ lineNumber++;
+ putcoms();
+ s_flg = 1;
+ }
+ c = string[j++] = getchr();
+ }
+ String tmpstr = new String(string);
+ if (j>1 && string[j-2] == '*') {
+ done = 1;
+ jdoc = 0;
+ }
+ }
+
+ putcoms();
+ s_flg = save_s_flg;
+ jdoc = 0;
+ return;
+ }
+
+
+ public char get_string() {
+ char ch;
+ ch = '*';
+ while (true) {
+ switch (ch) {
+ default:
+ ch = string[j++] = getchr();
+ if (ch == '\\') {
+ string[j++] = getchr();
+ break;
+ }
+ if (ch == '\'' || ch == '"') {
+ cc = string[j++] = getchr();
+ while (cc != ch) {
+ if (cc == '\\') string[j++] = getchr();
+ cc = string[j++] = getchr();
+ }
+ break;
+ }
+ if (ch == '\n' || ch == '\r') {
+ indent_puts();
+ a_flg = 1;
+ break;
+ } else {
+ return(ch);
+ }
+ }
+ }
+ }
+
+
+ public void indent_puts() {
+ string[j] = '\0';
+ if (j > 0) {
+ if (s_flg != 0) {
+ if((tabs > 0) && (string[0] != '{') && (a_flg == 1)) {
+ tabs++;
+ }
+ p_tabs();
+ s_flg = 0;
+ if ((tabs > 0) && (string[0] != '{') && (a_flg == 1)) {
+ tabs--;
+ }
+ a_flg = 0;
+ }
+ String j_string = new String(string);
+ strOut.append(j_string.substring(0,j));
+ for (int i=0; i 0)string[j++] = c;
+ indent_puts();
+ s_flg = 0;
+ break;
+ }
+ if(s_flg == 0 || j > 0)string[j++] = c;
+ break;
+ case '\r': /* for MS Windows 95 */
+ case '\n':
+ lineNumber++;
+ if (EOF==1)
+ {
+ break;
+ }
+ String j_string = new String(string);
+
+ e_flg = lookup(w_else);
+ if(e_flg == 1) gotelse();
+ if (lookup_com(w_cpp_comment) == 1)
+ {
+ if (string[j] == '\n')
+ {
+ string[j] = '\0';
+ j--;
+ }
+ }
+
+ indent_puts();
+ fprintf(outfil, line_feed);
+ s_flg = 1;
+ if(e_flg == 1)
+ {
+ p_flg[level]++;
+ tabs++;
+ }
+ else
+ if(p_char == l_char)
+ {
+ a_flg = 1;
+ }
+ break;
+ case '{':
+ if(lookup(w_else) == 1)gotelse();
+ s_if_lev[c_level] = if_lev;
+ s_if_flg[c_level] = if_flg;
+ if_lev = if_flg = 0;
+ c_level++;
+ if(s_flg == 1 && p_flg[level] != 0)
+ {
+ p_flg[level]--;
+ tabs--;
+ }
+ string[j++] = c;
+ indent_puts();
+ getnl() ;
+ indent_puts();
+ fprintf(outfil,"\n");
+ tabs++;
+ s_flg = 1;
+ if(p_flg[level] > 0)
+ {
+ ind[level] = 1;
+ level++;
+ s_level[level] = c_level;
+ }
+ break;
+ case '}':
+ c_level--;
+ if (c_level < 0)
+ {
+ EOF = 1;
+ string[j++] = c;
+ indent_puts();
+ break;
+ }
+ if((if_lev = s_if_lev[c_level]-1) < 0)if_lev = 0;
+ if_flg = s_if_flg[c_level];
+ indent_puts();
+ tabs--;
+ p_tabs();
+ peekc = getchr();
+ if( peekc == ';')
+ {
+ onechar = new StringBuffer();
+ onechar.append(c); /* } */
+ onechar.append(';');
+ fprintf(outfil, onechar.toString());
+ peek = -1;
+ peekc = '`';
+ }
+ else
+ {
+ onechar = new StringBuffer();
+ onechar.append(c);
+ fprintf(outfil, onechar.toString());
+ peek = 1;
+ }
+ getnl();
+ indent_puts();
+ fprintf(outfil,"\n");
+ s_flg = 1;
+ if(c_level < s_level[level])
+ if(level > 0) level--;
+ if(ind[level] != 0)
+ {
+ tabs -= p_flg[level];
+ p_flg[level] = 0;
+ ind[level] = 0;
+ }
+ break;
+ case '"':
+ case '\'':
+ string[j++] = c;
+ cc = getchr();
+ while(cc != c)
+ {
+ // max. length of line should be 256
+ string[j++] = cc;
+
+ if(cc == '\\')
+ {
+ cc = string[j++] = getchr();
+ }
+ if(cc == '\n')
+ {
+ lineNumber++;
+ indent_puts();
+ s_flg = 1;
+ }
+ cc = getchr();
+
+ }
+ string[j++] = cc;
+ if(getnl() == 1)
+ {
+ l_char = cc;
+ peek = 1;
+ peekc = '\n';
+ }
+ break;
+ case ';':
+ string[j++] = c;
+ indent_puts();
+ if(p_flg[level] > 0 && ind[level] == 0)
+ {
+ tabs -= p_flg[level];
+ p_flg[level] = 0;
+ }
+ getnl();
+ indent_puts();
+ fprintf(outfil,"\n");
+ s_flg = 1;
+ if(if_lev > 0)
+ if(if_flg == 1)
+ {
+ if_lev--;
+ if_flg = 0;
+ }
+ else if_lev = 0;
+ break;
+ case '\\':
+ string[j++] = c;
+ string[j++] = getchr();
+ break;
+ case '?':
+ q_flg = 1;
+ string[j++] = c;
+ break;
+ case ':':
+ string[j++] = c;
+ peekc = getchr();
+ if(peekc == ':')
+ {
+ indent_puts();
+ fprintf (outfil,":");
+ peek = -1;
+ peekc = '`';
+ break;
+ }
+ else
+ {
+ int double_colon = 0;
+ peek = 1;
+ }
+
+ if(q_flg == 1)
+ {
+ q_flg = 0;
+ break;
+ }
+ if(lookup(w_ds) == 0 && lookup(w_case) == 0)
+ {
+ s_flg = 0;
+ indent_puts();
+ }
+ else
+ {
+ tabs--;
+ indent_puts();
+ tabs++;
+ }
+ peekc = getchr();
+ if(peekc == ';')
+ {
+ fprintf(outfil,";");
+ peek = -1;
+ peekc = '`';
+ }
+ else
+ {
+ peek = 1;
+ }
+ getnl();
+ indent_puts();
+ fprintf(outfil,"\n");
+ s_flg = 1;
+ break;
+
+ case '/':
+ c0 = string[j];
+ string[j++] = c;
+ peekc = getchr();
+
+ if(peekc == '/')
+ {
+ string[j++] = peekc;
+ peekc = '`';
+ peek = -1;
+ cpp_comment();
+ fprintf(outfil,"\n");
+ break;
+ }
+ else
+ {
+ peek = 1;
+ }
+
+ if(peekc != '*') {
+ break;
+ }
+ else
+ {
+ if (j > 0) string[j--] = '\0';
+ if (j > 0) indent_puts();
+ string[j++] = '/';
+ string[j++] = '*';
+ peek = -1;
+ peekc = '`';
+ comment();
+ break;
+ }
+ case '#':
+ string[j++] = c;
+ cc = getchr();
+ while(cc != '\n')
+ {
+ string[j++] = cc;
+ cc = getchr();
+ }
+ string[j++] = cc;
+ s_flg = 0;
+ indent_puts();
+ s_flg = 1;
+ break;
+ case ')':
+ paren--;
+ if (paren < 0)
+ {
+ EOF = 1;
+ }
+ string[j++] = c;
+ indent_puts();
+ if(getnl() == 1)
+ {
+ peekc = '\n';
+ peek = 1;
+ if(paren != 0)
+ {
+ a_flg = 1;
+ }
+ else if(tabs > 0)
+ {
+ p_flg[level]++;
+ tabs++;
+ ind[level] = 0;
+ }
+ }
+ break;
+ case '(':
+ string[j++] = c;
+ paren++;
+ if ((lookup(w_for) == 1))
+ {
+ c = get_string();
+ while(c != ';') c = get_string();
+ ct=0;
+ int for_done = 0;
+ while (for_done==0)
+ {
+ c = get_string();
+ while(c != ')')
+ {
+ if(c == '(') ct++;
+ c = get_string();
+ }
+ if(ct != 0)
+ {
+ ct--;
+ }
+ else for_done = 1;
+ } /* endwhile for_done */
+ paren--;
+ if (paren < 0)
+ {
+ EOF = 1;
+ }
+ indent_puts();
+ if(getnl() == 1)
+ {
+ peekc = '\n';
+ peek = 1;
+ p_flg[level]++;
+ tabs++;
+ ind[level] = 0;
+ }
+ break;
+ }
+
+ if(lookup(w_if_) == 1)
+ {
+ indent_puts();
+ s_tabs[c_level][if_lev] = tabs;
+ sp_flg[c_level][if_lev] = p_flg[level];
+ s_ind[c_level][if_lev] = ind[level];
+ if_lev++;
+ if_flg = 1;
+ }
+ } /* end switch */
+
+ String j_string = new String(string);
+
+ } // end while not EOF
+
+ //formattedText = strOut.toString();
+
+ // save current (rough) selection point
+ int selectionEnd = editor.textarea.getSelectionEnd();
+
+ // replace with new bootiful text
+ editor.setText(strOut.toString(), false);
+
+ // make sure the caret would be past the end of the text
+ if (strOut.length() < selectionEnd - 1) {
+ selectionEnd = strOut.length() - 1;
+ }
+
+ // at least in the neighborhood
+ editor.textarea.select(selectionEnd, selectionEnd);
+
+ editor.sketch.setModified();
+
+ bin.close(); // close buff
+
+ } catch (IOException ioe) {
+ editor.error(ioe);
+ //ioe.printStackTrace();
+ }
+
+
+ // () {} check
+
+ String ck_paren = new String("left");
+ if (paren < 0) ck_paren = "right";
+
+ if (paren != 0) {
+ setUhOh("Uh oh... too many " + ck_paren + " parentheses.");
+
+ } else { // check braces only if parens are ok
+ ck_paren = "left";
+ if (c_level < 0) {
+ ck_paren = "right";
+ } else if (c_level != 0) {
+ setUhOh("Uh oh... too many " + ck_paren + " curled braces.");
+ }
+ }
+ }
+
+
+ /* throw back the stuff to the editor */
+ public String getFormattedText()
+ {
+ return formattedText;
+ }
+
+
+ /* special edition of put string for comment processing */
+ public void putcoms()
+ {
+ int i = 0;
+ int sav_s_flg = s_flg;
+ if(j > 0)
+ {
+ if(s_flg != 0)
+ {
+ p_tabs();
+ s_flg = 0;
+ }
+ string[j] = '\0';
+ i = 0;
+ while (string[i] == ' ') i++;
+ if (lookup_com(w_jdoc) == 1) jdoc = 1;
+ String strBuffer = new String(string,0,j);
+ if (string[i] == '/' && string[i+1]=='*')
+ {
+ if ((last_char != ';') && (sav_s_flg==1) )
+ {
+ fprintf(outfil, strBuffer.substring(i,j));
+ }
+ else
+ {
+ fprintf(outfil, strBuffer);
+ }
+ }
+ else
+ {
+ if (string[i]=='*' || jdoc == 0)
+ fprintf (outfil, " "+strBuffer.substring(i,j));
+ else
+ fprintf (outfil, " * "+strBuffer.substring(i,j));
+ }
+ j = 0;
+ string[0] = '\0';
+ }
+ }
+
+ public void cpp_comment()
+ {
+ c = getchr();
+ while(c != '\n' && c != '\r' && j<133)
+ {
+ string[j++] = c;
+ c = getchr();
+ }
+ lineNumber++;
+ indent_puts();
+ s_flg = 1;
+ }
+
+
+ /* expand indentValue into tabs and spaces */
+ public void p_tabs()
+ {
+ int i,k;
+
+ if (tabs<0) tabs = 0;
+ if (tabs==0) return;
+ i = tabs * indentValue; // calc number of spaces
+ //j = i/8; /* calc number of tab chars */
+
+ for (k=0; k < i; k++) {
+ strOut.append(indentChar);
+ }
+ }
+
+
+ public char getchr()
+ {
+ if((peek < 0) && (last_char != ' ') && (last_char != '\t'))
+ {
+ if((last_char != '\n') && (last_char != '\r'))
+ p_char = last_char;
+ }
+ if(peek > 0) /* char was read previously */
+ {
+ last_char = peekc;
+ peek = -1;
+ }
+ else /* read next char in string */
+ {
+ indexBlock++;
+ if (indexBlock >= lineLength)
+ {
+ for (int ib=0; ib 0)
+ {
+ nBytesRead = bin.read(bArray);
+ lineLength = nBytesRead;
+ strBlock = new String(bArray);
+ indexBlock = 0;
+ last_char = strBlock.charAt(indexBlock);
+ peek = -1;
+ peekc = '`';
+ }
+ else
+ {
+ EOF = 1;
+ peekc = '\0';
+ }
+ }
+ catch(IOException ioe)
+ {
+ System.out.println(ioe.toString());
+ }
+ }
+ else
+ {
+ last_char = strBlock.charAt(indexBlock);
+ }
+ }
+ peek = -1;
+ if (last_char == '\r')
+ {
+ last_char = getchr();
+ }
+
+ return last_char;
+ }
+
+ /* else processing */
+ public void gotelse()
+ {
+ tabs = s_tabs[c_level][if_lev];
+ p_flg[level] = sp_flg[c_level][if_lev];
+ ind[level] = s_ind[c_level][if_lev];
+ if_flg = 1;
+ }
+
+ /* read to new_line */
+ public int getnl()
+ {
+ int save_s_flg;
+ save_s_flg = tabs;
+ peekc = getchr();
+ while(peekc == '\t' || peekc == ' ')
+ {
+ string[j++] = peekc;
+ peek = -1;
+ peekc = '`';
+ peekc = getchr();
+ peek = 1;
+ }
+ peek = 1;
+
+ if (peekc == '/')
+ {
+ peek = -1;
+ peekc = '`';
+ peekc = getchr();
+ if (peekc == '*')
+ {
+ string[j++] = '/';
+ string[j++] = '*';
+ peek = -1;
+ peekc = '`';
+ comment();
+ }
+ else if (peekc == '/')
+ {
+ string[j++] = '/';
+ string[j++] = '/';
+ peek = -1;
+ peekc = '`';
+ cpp_comment();
+ return (1);
+ }
+ else
+ {
+ string[j++] = '/';
+ peek = 1;
+ }
+ }
+ peekc = getchr();
+ if(peekc == '\n')
+ {
+ lineNumber++;
+ peek = -1;
+ peekc = '`';
+ tabs = save_s_flg;
+ return(1);
+ }
+ else
+ {
+ peek = 1;
+ }
+ return 0;
+ }
+
+ public int lookup (String keyword)
+ {
+ char r;
+ int l,kk,k,i;
+ String j_string = new String(string);
+
+ if (j<1) return (0);
+ kk=0;
+ while(string[kk] == ' ')kk++;
+ l=0;
+ l = j_string.indexOf(keyword);
+ if (l<0 || l!=kk)
+ {
+ return 0;
+ }
+ r = string[kk+keyword.length()];
+ if(r >= 'a' && r <= 'z') return(0);
+ if(r >= 'A' && r <= 'Z') return(0);
+ if(r >= '0' && r <= '9') return(0);
+ if(r == '_' || r == '&') return(0);
+ return (1);
+ }
+
+ public int lookup_com (String keyword)
+ {
+ char r;
+ int l,kk,k,i;
+ String j_string = new String(string);
+
+ if (j<1) return (0);
+ kk=0;
+ while(string[kk] == ' ')kk++;
+ l=0;
+ l = j_string.indexOf(keyword);
+ if (l<0 || l!=kk)
+ {
+ return 0;
+ }
+ return (1);
+ }
}
\ No newline at end of file