Skip to content

Commit f9bd2a4

Browse files
author
rcartwright
committed
This revision reduces the overhead of the insertUpdate and caretUpdate
operations performed every time a character is inserted in a document. It also fixes some bugs in the management of "find all panels". The panels in the _findResults list in MainFrame were never deleted from this list even after they were closed. In addition, this revision contains some minor reactoring of some unit tests that have been intermittently failing on Windows. The followoing documents were modified or deleted. M src/edu/rice/cs/drjava/DrJavaTestCase.java M src/edu/rice/cs/drjava/model/definitions/indent/Indenter.java D src/edu/rice/cs/drjava/model/definitions/indent/ActionStartPrevLinePlusMultilineTest.java M src/edu/rice/cs/drjava/model/definitions/indent/IndentRulesTestCase.java D src/edu/rice/cs/drjava/model/definitions/indent/ActionStartPrevLinePlusBackup.java D src/edu/rice/cs/drjava/model/definitions/indent/ActionStartPrevLinePlusBackupTest.java M src/edu/rice/cs/drjava/model/definitions/IndentTest.java M src/edu/rice/cs/drjava/model/repl/InteractionsModelTest.java M src/edu/rice/cs/drjava/model/repl/InteractionsModel.java M src/edu/rice/cs/drjava/model/repl/DefaultInteractionsModel.java M src/edu/rice/cs/drjava/model/AbstractDJDocument.java M src/edu/rice/cs/drjava/model/AbstractGlobalModel.java M src/edu/rice/cs/drjava/ui/MainFrame.java M src/edu/rice/cs/drjava/ui/DefinitionsPane.java M src/edu/rice/cs/drjava/ui/ErrorCaretListener.java M src/edu/rice/cs/drjava/ui/AbstractDJPane.java M src/edu/rice/cs/drjava/ui/MainFrameTest.java M src/edu/rice/cs/drjava/ui/FindResultsPanel.java M src/edu/rice/cs/drjava/ui/FindReplacePanel.java M src/edu/rice/cs/util/XMLConfigTest.java M src/edu/rice/cs/util/Pair.java git-svn-id: file:///tmp/test-svn/trunk@4576 fe72c1cf-3628-48e9-8b72-1c46755d3cff
1 parent b43f29e commit f9bd2a4

21 files changed

Lines changed: 1533 additions & 1758 deletions

drjava/src/edu/rice/cs/drjava/DrJavaTestCase.java

Lines changed: 25 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -36,7 +36,13 @@
3636

3737
package edu.rice.cs.drjava;
3838

39+
import javax.swing.text.BadLocationException;
40+
3941
import junit.framework.TestCase;
42+
43+
import edu.rice.cs.drjava.config.Option;
44+
import edu.rice.cs.drjava.model.AbstractDJDocument;
45+
import edu.rice.cs.util.UnexpectedException;
4046
import edu.rice.cs.util.swing.Utilities;
4147

4248
/** Test case class for all DrJava test cases. DrJava test cases should extend this class, potentially override setUp()
@@ -65,15 +71,13 @@ protected void setUp() throws Exception {
6571
assert newName != null;
6672
// if (newName != null) {
6773
// Utilities.show("Setting '" + newName + "' as DrJava configuration file");
68-
Utilities.invokeLater(new Runnable() {
74+
Utilities.invokeAndWait(new Runnable() {
6975
public void run() {
7076
DrJava.setPropertiesFile(newName); // spawns change updates which should run in event thread
7177
// Utilities.clearEventQueue();
7278
DrJava._initConfig(); // spawns change updates which should run in event thread
73-
// Utilities.clearEventQueue();
7479
}
7580
});
76-
// }
7781
}
7882

7983
/** Clean up for every test case. Only used in unit tests. Added because Windows would intermittently throw
@@ -84,4 +88,22 @@ protected void tearDown() throws Exception {
8488
DrJava.cleanUp();
8589
super.tearDown();
8690
}
91+
92+
protected <T> void setConfigSetting(final Option<T> op, final T value) {
93+
Utilities.invokeAndWait(new Runnable() { public void run() { DrJava.getConfig().setSetting(op, value); } });
94+
}
95+
96+
/** Clears the text of the _doc field and sets it to the given string. */
97+
protected static final void setDocText(final AbstractDJDocument doc, final String text) {
98+
Utilities.invokeAndWait(new Runnable() {
99+
public void run() {
100+
try {
101+
doc.clear();
102+
doc._insertString(0, text, null);
103+
}
104+
catch(BadLocationException e) { throw new UnexpectedException(e); }
105+
}
106+
});
107+
Utilities.clearEventQueue(); // make sure that all listener actions triggered by this document update have completed
108+
}
87109
}

drjava/src/edu/rice/cs/drjava/model/AbstractDJDocument.java

Lines changed: 41 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -119,16 +119,19 @@ public abstract class AbstractDJDocument extends SwingDocument implements DJDocu
119119
* purposes. */
120120
protected volatile int _currentLocation = 0;
121121

122-
/* The fields _queryCache and _offsetToQueries function as an extension of the reduced model.
122+
/* The fields _queryCache, _offsetToQueries, and _cacheModified function as an extension of the reduced model.
123123
* Hence _reduced should be the lock object for operations on these two structures.
124124
* This data structure caches calls to the reduced model to speed up indent performance. Must be cleared every time
125125
* the document is changed. Use by calling _checkCache, _storeInCache, and _clearCache.
126126
*/
127127
private final HashMap<Query, Object> _queryCache;
128-
128+
129129
/** Records the set of queries (as a list) for each offset. */
130130
private final SortedMap<Integer, List<Query>> _offsetToQueries = new TreeMap<Integer, List<Query>>();
131131

132+
/** Records whether the cache has been modified since it was last cleared. */
133+
private volatile boolean _cacheModified = false;
134+
132135
/** Initial number of elements in _queryCache. */
133136
private static final int INIT_CACHE_SIZE = 0x10000; // 16**4 = 16384
134137

@@ -160,11 +163,12 @@ protected AbstractDJDocument(int indentLevel) {
160163
}
161164

162165
/** Constructor used to build a new document with an existing indenter. Used in tests and super calls from
163-
* Definitions*/
164-
protected AbstractDJDocument(Indenter indent) {
165-
_indenter = indent;
166+
* DefinitionsDocument and interactions documents. */
167+
protected AbstractDJDocument(Indenter indenter) {
168+
_indenter = indenter;
166169
_queryCache = new HashMap<Query, Object>(INIT_CACHE_SIZE);
167170
_initNewIndenter();
171+
// System.err.println("AbstractDJDocument constructor with indent level " + indenter.getIndentLevel() + " invoked on " + this);
168172
}
169173

170174
//-------- METHODS ---------//
@@ -193,6 +197,7 @@ public void setIndent(final int indent) {
193197
}
194198

195199
protected void _removeIndenter() {
200+
// System.err.println("REMOVE INDENTER called");
196201
DrJava.getConfig().removeOptionListener(INDENT_LEVEL, _listener1);
197202
DrJava.getConfig().removeOptionListener(AUTO_CLOSE_COMMENTS, _listener2);
198203
}
@@ -202,16 +207,18 @@ private void _initNewIndenter() {
202207
// Create the indenter from the config values
203208

204209
final Indenter indenter = _indenter;
205-
210+
// System.err.println("Installing Indent Option Listener for " + this);
206211
_listener1 = new OptionListener<Integer>() {
207212
public void optionChanged(OptionEvent<Integer> oce) {
208-
indenter.buildTree(oce.value.intValue());
213+
// System.err.println("Changing INDENT_LEVEL for " + this + " to " + oce.value);
214+
indenter.buildTree(oce.value);
209215
}
210216
};
211217

212218
_listener2 = new OptionListener<Boolean>() {
213219
public void optionChanged(OptionEvent<Boolean> oce) {
214-
indenter.buildTree(DrJava.getConfig().getSetting(INDENT_LEVEL).intValue());
220+
// System.err.println("Reconfiguring indenter to use AUTO_CLOSE_COMMENTS = " + oce.value);
221+
indenter.buildTree(DrJava.getConfig().getSetting(INDENT_LEVEL));
215222
}
216223
};
217224

@@ -433,27 +440,7 @@ private boolean _isType(String x) {
433440
*/
434441
protected abstract void _styleChanged();
435442

436-
/** Clears the memozing cache of queries with offset >= than specified value. Should be called every time the
437-
* document is modified. */
438-
protected void _clearCache(int offset) {
439-
if (_queryCache == null) return;
440-
// synchronized(_reduced) {
441-
if (offset <= 0) {
442-
_queryCache.clear();
443-
_offsetToQueries.clear();
444-
return;
445-
}
446-
447-
Integer[] deadOffsets = _offsetToQueries.tailMap(offset).keySet().toArray(new Integer[0]);
448-
for (int i: deadOffsets) {
449-
for (Query query: _offsetToQueries.get(i)) {
450-
_queryCache.remove(query); // remove query entry from cache
451-
}
452-
_offsetToQueries.remove(i); // remove query bucket for i from offsetToQueries table
453-
}
454-
// }
455-
}
456-
443+
457444
/** Add a character to the underlying reduced model. ASSUMEs _reduced lock is already held!
458445
* @param curChar the character to be added. */
459446
private void _addCharToReducedModel(char curChar) {
@@ -955,9 +942,34 @@ protected void _storeInCache(final Query query, final Object answer, final int o
955942
// synchronized(_reduced) {
956943
_queryCache.put(query, answer);
957944
_addToOffsetsToQueries(query, offset);
945+
_cacheModified = true;
958946
// }
959947
}
960948

949+
/** Clears the memozing cache of queries with offset >= than specified value. Should be called every time the
950+
* document is modified. */
951+
protected void _clearCache(int offset) {
952+
if (_queryCache == null || ! _cacheModified) return;
953+
_cacheModified = false;
954+
955+
// synchronized(_reduced) {
956+
if (offset <= 0) {
957+
_queryCache.clear();
958+
_offsetToQueries.clear();
959+
return;
960+
}
961+
962+
Integer[] deadOffsets = _offsetToQueries.tailMap(offset).keySet().toArray(new Integer[0]);
963+
for (int i: deadOffsets) {
964+
for (Query query: _offsetToQueries.get(i)) {
965+
_queryCache.remove(query); // remove query entry from cache
966+
}
967+
_offsetToQueries.remove(i); // remove query bucket for i from offsetToQueries table
968+
}
969+
// }
970+
}
971+
972+
961973
/** Add <query,offset> pair to _offsetToQueries map. Assumes lock on _queryCache is already held. */
962974
private void _addToOffsetsToQueries(final Query query, final int offset) {
963975
List<Query> selectedQueries = _offsetToQueries.get(offset);

drjava/src/edu/rice/cs/drjava/model/AbstractGlobalModel.java

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1991,8 +1991,10 @@ public boolean closeAllFilesOnQuit() {
19911991
private void quit(boolean force) {
19921992
// _log.log("quit(" + force + ") called");
19931993
try {
1994-
if (! force && ! closeAllFilesOnQuit()) return;
1995-
1994+
if (! force && ! closeAllFilesOnQuit()) {
1995+
refreshActiveDocument(); // Ensure that DrJava is in a consistent state.
1996+
return;
1997+
}
19961998
/* [ 1478796 ] DrJava Does Not Shut Down With Project Open. On HP tc1100 and Toshiba Portege tablet PCs, there
19971999
* appears to be a problem in a shutdown hook, presumably the RMI shutdown hook. Shutdown hooks get executed in
19982000
* Runtime.exit (to which System.exit delegates), and if a shutdown hook does not complete, the VM does not shut

drjava/src/edu/rice/cs/drjava/model/definitions/IndentTest.java

Lines changed: 16 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -77,9 +77,7 @@ public void setUp() throws Exception {
7777
DrJava.getConfig().resetToDefaults();
7878
_notifier = new GlobalEventNotifier();
7979
_doc = new DefinitionsDocument(_notifier);
80-
Utilities.invokeAndWait(new Runnable() {
81-
public void run() { DrJava.getConfig().setSetting(OptionConstants.INDENT_LEVEL,indentLevel); }
82-
});
80+
setConfigSetting(OptionConstants.INDENT_LEVEL, indentLevel);
8381
}
8482

8583
/** Builds the suite of tests for Indent.class.
@@ -94,7 +92,11 @@ private void safeIndentLine(final Indenter.IndentReason reason) {
9492

9593
/** Convenience method that performs _doc._indentLines in the event thread. */
9694
private void safeIndentLines(final int startSel, final int endSel) {
97-
Utilities.invokeAndWait(new Runnable() { public void run() { _doc.indentLines(startSel, endSel); } });
95+
Utilities.invokeAndWait(new Runnable() {
96+
public void run() {
97+
_doc.indentLines(startSel, endSel);
98+
}
99+
});
98100
}
99101

100102
/** Regression test for comment portion of indent tree. */
@@ -1124,17 +1126,25 @@ public void testLiveUpdateOfIndentLevel() throws BadLocationException {
11241126
" 5}\n" +
11251127
"};\n";
11261128

1127-
_doc.insertString(0, text, null);
1129+
setDocText(_doc, text);
11281130

11291131
_assertContents(text, _doc);
11301132
safeIndentLines(0, _doc.getLength());
1133+
Utilities.clearEventQueue();
1134+
Utilities.clearEventQueue();
11311135
_assertContents(indentedBefore, _doc);
1132-
DrJava.getConfig().setSetting(OptionConstants.INDENT_LEVEL, 8);
1136+
// System.err.println("Changing INDENT_LEVEL option constant to 8");
1137+
setConfigSetting(OptionConstants.INDENT_LEVEL, 8);
11331138

11341139
Utilities.clearEventQueue();
11351140
Utilities.clearEventQueue();
11361141
// System.err.println("level is " + DrJava.getConfig().getSetting(OptionConstants.INDENT_LEVEL));
1142+
// System.err.println("doc = " + _doc);
11371143
safeIndentLines(0, _doc.getLength());
1144+
1145+
Utilities.clearEventQueue();
1146+
Utilities.clearEventQueue();
1147+
// System.err.println("Performing failing assertion");
11381148
_assertContents(indentedAfter, _doc);
11391149
}
11401150

drjava/src/edu/rice/cs/drjava/model/definitions/indent/ActionStartPrevLinePlusBackup.java

Lines changed: 0 additions & 110 deletions
This file was deleted.

0 commit comments

Comments
 (0)