001: /*BEGIN_COPYRIGHT_BLOCK
002: *
003: * Copyright (c) 2001-2007, JavaPLT group at Rice University (javaplt@rice.edu)
004: * All rights reserved.
005: *
006: * Redistribution and use in source and binary forms, with or without
007: * modification, are permitted provided that the following conditions are met:
008: * * Redistributions of source code must retain the above copyright
009: * notice, this list of conditions and the following disclaimer.
010: * * Redistributions in binary form must reproduce the above copyright
011: * notice, this list of conditions and the following disclaimer in the
012: * documentation and/or other materials provided with the distribution.
013: * * Neither the names of DrJava, the JavaPLT group, Rice University, nor the
014: * names of its contributors may be used to endorse or promote products
015: * derived from this software without specific prior written permission.
016: *
017: * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
018: * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
019: * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
020: * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR
021: * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
022: * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
023: * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
024: * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
025: * LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
026: * NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
027: * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
028: *
029: * This software is Open Source Initiative approved Open Source Software.
030: * Open Source Initative Approved is a trademark of the Open Source Initiative.
031: *
032: * This file is part of DrJava. Download the current version of this project
033: * from http://www.drjava.org/ or http://sourceforge.net/projects/drjava/
034: *
035: * END_COPYRIGHT_BLOCK*/
036:
037: package edu.rice.cs.drjava.model;
038:
039: import javax.swing.text.BadLocationException;
040: import java.util.List;
041:
042: import edu.rice.cs.drjava.model.definitions.indent.Indenter;
043: import edu.rice.cs.util.OperationCanceledException;
044:
045: /**
046: * Tests the indenting functionality on the level of the GlobalModel.
047: * Not only are we testing that the document turns out right, but also
048: * that the cursor position in the document is consistent with a standard.
049: * @version $Id: GlobalIndentTest.java 4255 2007-08-28 19:17:37Z mgricken $
050: */
051: public final class GlobalIndentTest extends GlobalModelTestCase {
052: private static final String FOO_EX_1 = "public class Foo {\n";
053: private static final String FOO_EX_2 = "int foo;\n";
054: private static final String BAR_CALL_1 = "bar(monkey,\n";
055: private static final String BAR_CALL_2 = "banana)\n";
056:
057: // private static final String BEAT_1 = "void beat(Horse dead,\n";
058: // private static final String BEAT_2 = " Stick pipe)\n";
059:
060: /** Tests that an indent increases the size of the tab when the cursor is at the start of the line. If the cursor is
061: * in the whitespace before the first word on a line, indent always moves the cursor up to the beginning of the first non-whitespace
062: * character.
063: * @throws BadLocationException
064: */
065: public void testIndentGrowTabAtStart() throws BadLocationException,
066: OperationCanceledException {
067: OpenDefinitionsDocument openDoc = _getOpenDoc();
068:
069: openDoc.insertString(0, FOO_EX_1, null);
070: openDoc.insertString(FOO_EX_1.length(), " " + FOO_EX_2, null);
071: openDoc.setCurrentLocation(FOO_EX_1.length());
072: int loc = openDoc.getCurrentLocation();
073: openDoc
074: .indentLines(loc, loc, Indenter.IndentReason.OTHER,
075: null);
076: _assertContents(FOO_EX_1 + " " + FOO_EX_2, openDoc);
077: _assertLocation(FOO_EX_1.length() + 2, openDoc);
078: }
079:
080: /** Tests indent that increases the size of the tab when the cursor is in the middle of the line.
081: * The cursor stays in the same place.
082: * @throws BadLocationException
083: */
084: public void testIndentGrowTabAtMiddle()
085: throws BadLocationException, OperationCanceledException {
086: OpenDefinitionsDocument openDoc = _getOpenDoc();
087:
088: openDoc.insertString(0, FOO_EX_1, null);
089: openDoc.insertString(FOO_EX_1.length(), " " + FOO_EX_2, null);
090: openDoc.setCurrentLocation(FOO_EX_1.length() + 5);
091: int loc = openDoc.getCurrentLocation();
092: openDoc
093: .indentLines(loc, loc, Indenter.IndentReason.OTHER,
094: null);
095: _assertContents(FOO_EX_1 + " " + FOO_EX_2, openDoc);
096: _assertLocation(FOO_EX_1.length() + 6, openDoc);
097: }
098:
099: /** Tests that an indent increases the size of the tab when the cursor is at the end of the line. The cursor stays
100: * in the same place.
101: * @throws BadLocationException
102: */
103: public void testIndentGrowTabAtEnd() throws BadLocationException,
104: OperationCanceledException {
105: OpenDefinitionsDocument openDoc = _getOpenDoc();
106:
107: openDoc.insertString(0, FOO_EX_1, null);
108: openDoc.insertString(FOO_EX_1.length(), " " + FOO_EX_2, null);
109: openDoc.setCurrentLocation(openDoc.getLength() - 1);
110: int loc = openDoc.getCurrentLocation();
111: openDoc
112: .indentLines(loc, loc, Indenter.IndentReason.OTHER,
113: null);
114: _assertContents(FOO_EX_1 + " " + FOO_EX_2, openDoc);
115: _assertLocation(openDoc.getLength() - 1, openDoc);
116: }
117:
118: /** Tests that an indent increases the size of the tab when the cursor is at the start of the line. If the cursor
119: * is in whitespace before the first word on a line, an indent moves the cursor to the beginning of the first
120: * non-whitespace character.
121: * @throws BadLocationException
122: */
123: public void testIndentShrinkTabAtStart()
124: throws BadLocationException, OperationCanceledException {
125: OpenDefinitionsDocument openDoc = _getOpenDoc();
126:
127: openDoc.insertString(0, FOO_EX_1, null);
128: openDoc.insertString(FOO_EX_1.length(), " " + FOO_EX_2, null);
129: openDoc.setCurrentLocation(FOO_EX_1.length());
130: int loc = openDoc.getCurrentLocation();
131: openDoc
132: .indentLines(loc, loc, Indenter.IndentReason.OTHER,
133: null);
134: _assertContents(FOO_EX_1 + " " + FOO_EX_2, openDoc);
135: _assertLocation(FOO_EX_1.length() + 2, openDoc);
136: }
137:
138: /** Tests that an indent increases the size of the tab when the cursor is in the middle of the line. The cursor stays
139: * in the same place.
140: * @throws BadLocationException
141: */
142: public void testIndentShrinkTabAtMiddle()
143: throws BadLocationException, OperationCanceledException {
144: OpenDefinitionsDocument openDoc = _getOpenDoc();
145:
146: openDoc.insertString(0, FOO_EX_1, null);
147: openDoc.insertString(FOO_EX_1.length(), " " + FOO_EX_2, null);
148: openDoc.setCurrentLocation(FOO_EX_1.length() + 5);
149: int loc = openDoc.getCurrentLocation();
150: openDoc
151: .indentLines(loc, loc, Indenter.IndentReason.OTHER,
152: null);
153: _assertContents(FOO_EX_1 + " " + FOO_EX_2, openDoc);
154: _assertLocation(FOO_EX_1.length() + 4, openDoc);
155: }
156:
157: /** Tests that an indent increases the size of the tab when the cursor is at the end of the line. The cursor stays
158: * in the same place.
159: * @throws BadLocationException
160: */
161: public void testIndentShrinkTabAtEnd() throws BadLocationException,
162: OperationCanceledException {
163: OpenDefinitionsDocument openDoc = _getOpenDoc();
164:
165: openDoc.insertString(0, FOO_EX_1, null);
166: openDoc.insertString(FOO_EX_1.length(), " " + FOO_EX_2, null);
167: openDoc.setCurrentLocation(openDoc.getLength() - 1);
168: int loc = openDoc.getCurrentLocation();
169: openDoc
170: .indentLines(loc, loc, Indenter.IndentReason.OTHER,
171: null);
172: _assertContents(FOO_EX_1 + " " + FOO_EX_2, openDoc);
173: _assertLocation(openDoc.getLength() - 1, openDoc);
174: }
175:
176: /** Tests that an indent matches up with the indent on the line above. The cursor is at the start of the line.
177: * @exception BadLocationException
178: */
179: public void testIndentSameAsLineAboveAtStart()
180: throws BadLocationException, OperationCanceledException {
181: OpenDefinitionsDocument openDoc = _getOpenDoc();
182:
183: openDoc.insertString(0, FOO_EX_2, null);
184: openDoc.insertString(FOO_EX_2.length(), " " + FOO_EX_2, null);
185: openDoc.setCurrentLocation(FOO_EX_2.length());
186: int loc = openDoc.getCurrentLocation();
187: openDoc
188: .indentLines(loc, loc, Indenter.IndentReason.OTHER,
189: null);
190: _assertContents(FOO_EX_2 + FOO_EX_2, openDoc);
191: _assertLocation(FOO_EX_2.length(), openDoc);
192: }
193:
194: /** Tests that an indent matches up with the indent on the line above. The cursor is at the end of the line.
195: * @exception BadLocationException
196: */
197: public void testIndentSameAsLineAboveAtEnd()
198: throws BadLocationException, OperationCanceledException {
199: OpenDefinitionsDocument openDoc = _getOpenDoc();
200:
201: openDoc.insertString(0, FOO_EX_2, null);
202: openDoc.insertString(FOO_EX_2.length(), " " + FOO_EX_2, null);
203: openDoc.setCurrentLocation(openDoc.getLength() - 1);
204: int loc = openDoc.getCurrentLocation();
205: openDoc
206: .indentLines(loc, loc, Indenter.IndentReason.OTHER,
207: null);
208: _assertContents(FOO_EX_2 + FOO_EX_2, openDoc);
209: _assertLocation(openDoc.getLength() - 1, openDoc);
210: }
211:
212: /**
213: * Do an indent that follows the behavior in line with parentheses.
214: * The cursor is at the start of the line.
215: * @exception BadLocationException
216: */
217: public void testIndentInsideParenAtStart()
218: throws BadLocationException, OperationCanceledException {
219: OpenDefinitionsDocument openDoc = _getOpenDoc();
220:
221: openDoc.insertString(0, BAR_CALL_1, null);
222: openDoc.insertString(BAR_CALL_1.length(), BAR_CALL_2, null);
223: openDoc.setCurrentLocation(BAR_CALL_1.length());
224: int loc = openDoc.getCurrentLocation();
225: openDoc
226: .indentLines(loc, loc, Indenter.IndentReason.OTHER,
227: null);
228: _assertContents(BAR_CALL_1 + " " + BAR_CALL_2, openDoc);
229: _assertLocation(BAR_CALL_1.length() + 4, openDoc);
230: }
231:
232: /** Do an indent that follows the behavior in line with parentheses. The cursor is at the end of the line.
233: * @exception BadLocationException
234: */
235: public void testIndentInsideParenAtEnd()
236: throws BadLocationException, OperationCanceledException {
237: OpenDefinitionsDocument openDoc = _getOpenDoc();
238:
239: openDoc.insertString(0, BAR_CALL_1, null);
240: openDoc.insertString(BAR_CALL_1.length(), BAR_CALL_2, null);
241: openDoc.setCurrentLocation(openDoc.getLength() - 1);
242: int loc = openDoc.getCurrentLocation();
243: openDoc
244: .indentLines(loc, loc, Indenter.IndentReason.OTHER,
245: null);
246: _assertContents(BAR_CALL_1 + " " + BAR_CALL_2, openDoc);
247: _assertLocation(openDoc.getLength() - 1, openDoc);
248: }
249:
250: /** Indent does nothing to change the document when everything is in place. */
251: public void testIndentDoesNothing() throws BadLocationException,
252: OperationCanceledException {
253: OpenDefinitionsDocument openDoc = _getOpenDoc();
254:
255: openDoc.insertString(0, FOO_EX_2 + FOO_EX_2, null);
256: openDoc.setCurrentLocation(openDoc.getLength() - 1);
257: int loc = openDoc.getCurrentLocation();
258: openDoc
259: .indentLines(loc, loc, Indenter.IndentReason.OTHER,
260: null);
261: _assertContents(FOO_EX_2 + FOO_EX_2, openDoc);
262: _assertLocation(openDoc.getLength() - 1, openDoc);
263: }
264:
265: /**
266: * The quintessential "make the squiggly go to the start, even though
267: * method arguments extend over two lines" test. This behavior is not
268: * correctly followed yet, so until it is, leave this method commented.
269: * @exception BadLocationException
270: *
271: public void testIndentSquigglyAfterTwoLines()
272: throws BadLocationException, OperationCanceledException {
273: OpenDefinitionsDocument openDoc = _getOpenDoc();
274:
275: openDoc.insertString(0, BEAT_1, null);
276: openDoc.insertString(BEAT_1.length(), BEAT_2, null);
277: openDoc.insertString(openDoc.getLength(), "{", null);
278: int loc = openDoc.getCurrentLocation();
279: openDoc.indentLines(loc, loc);
280: _assertContents(BEAT_1 + BEAT_2 + "{", openDoc);
281: _assertLocation(openDoc.getLength(), openDoc);
282: }
283: */
284:
285: /**
286: * Indents block comments with stars as they should.
287: * Uncomment this method when the correct functionality is implemented.
288: */
289: // public void testIndentBlockCommentStar()
290: // throws BadLocationException, OperationCanceledException {
291: // OpenDefinitionsDocument openDoc = _getOpenDoc();
292: // openDoc.insertString(0, "/*\n*\n*/\n " + FOO_EX_2, null);
293: // int loc = openDoc.getCurrentLocation();
294: // openDoc.indentLines(0, openDoc.getLength());
295: // _assertContents("/*\n *\n */\n" + FOO_EX_2, openDoc);
296: // _assertLocation(openDoc.getLength(), openDoc);
297: // }
298: /** Get the only open definitions document. */
299: private OpenDefinitionsDocument _getOpenDoc() {
300: _assertNumOpenDocs(1);
301: OpenDefinitionsDocument doc = _model.newFile();
302: doc.setIndent(2);
303: List<OpenDefinitionsDocument> docs = _model
304: .getOpenDefinitionsDocuments();
305: _assertNumOpenDocs(2);
306: return docs.get(0);
307: }
308:
309: private void _assertNumOpenDocs(int num) {
310: assertEquals("number of open documents", num, _model
311: .getOpenDefinitionsDocuments().size());
312: }
313:
314: private void _assertContents(String expected,
315: OpenDefinitionsDocument document)
316: throws BadLocationException {
317: assertEquals("document contents", expected, document.getText());
318: }
319:
320: private void _assertLocation(int loc,
321: OpenDefinitionsDocument openDoc) {
322: assertEquals("current def'n loc", loc, openDoc
323: .getCurrentLocation());
324: }
325: }
|