aboutsummaryrefslogtreecommitdiff
path: root/eclipse/plugins/com.android.ide.eclipse.tests/src/com/android/ide/eclipse/adt/internal/editors/AndroidXmlAutoEditStrategyTest.java
diff options
context:
space:
mode:
Diffstat (limited to 'eclipse/plugins/com.android.ide.eclipse.tests/src/com/android/ide/eclipse/adt/internal/editors/AndroidXmlAutoEditStrategyTest.java')
-rw-r--r--eclipse/plugins/com.android.ide.eclipse.tests/src/com/android/ide/eclipse/adt/internal/editors/AndroidXmlAutoEditStrategyTest.java473
1 files changed, 473 insertions, 0 deletions
diff --git a/eclipse/plugins/com.android.ide.eclipse.tests/src/com/android/ide/eclipse/adt/internal/editors/AndroidXmlAutoEditStrategyTest.java b/eclipse/plugins/com.android.ide.eclipse.tests/src/com/android/ide/eclipse/adt/internal/editors/AndroidXmlAutoEditStrategyTest.java
new file mode 100644
index 000000000..27661b3f2
--- /dev/null
+++ b/eclipse/plugins/com.android.ide.eclipse.tests/src/com/android/ide/eclipse/adt/internal/editors/AndroidXmlAutoEditStrategyTest.java
@@ -0,0 +1,473 @@
+/*
+ * Copyright (C) 2011 The Android Open Source Project
+ *
+ * Licensed under the Eclipse Public License, Version 1.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ * http://www.eclipse.org/org/documents/epl-v10.php
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+package com.android.ide.eclipse.adt.internal.editors;
+
+import com.android.ide.eclipse.adt.internal.editors.layout.refactoring.AdtProjectTest;
+
+import org.eclipse.core.resources.IFile;
+import org.eclipse.jface.text.DocumentCommand;
+import org.eclipse.jface.text.IDocument;
+import org.eclipse.jface.text.source.ISourceViewer;
+import org.eclipse.swt.graphics.Point;
+import org.eclipse.ui.IEditorPart;
+import org.eclipse.ui.IWorkbenchPage;
+import org.eclipse.ui.PlatformUI;
+import org.eclipse.ui.ide.IDE;
+
+@SuppressWarnings("javadoc")
+public class AndroidXmlAutoEditStrategyTest extends AdtProjectTest {
+
+ public void checkInsertNewline(String before, String after) throws Exception {
+ AndroidXmlAutoEditStrategy s = new AndroidXmlAutoEditStrategy();
+
+ // All tests just operate on the "edithandling" document; the contents are
+ // ignored and replaced with the before-document passed in
+ IFile file = getLayoutFile(getProject(), "edithandling.xml");
+
+ IWorkbenchPage page = PlatformUI.getWorkbench().getActiveWorkbenchWindow().getActivePage();
+ assertNotNull(page);
+ IEditorPart editor = IDE.openEditor(page, file);
+ assertTrue(editor instanceof AndroidXmlEditor);
+ AndroidXmlEditor layoutEditor = (AndroidXmlEditor) editor;
+ ISourceViewer viewer = layoutEditor.getStructuredSourceViewer();
+
+ String newDocumentContent = stripCaret(before);
+ IDocument document = viewer.getDocument();
+ document.replace(0, document.getLength(), newDocumentContent);
+
+ // Determine the offset, and possibly make text range selections as well
+ int offset = updateCaret(viewer, before);
+
+ DocumentCommand c = new TestDocumentCommand();
+ c.doit = true;
+ c.offset = offset;
+ c.caretOffset = -1;
+ c.length = 0;
+ c.text = "\n";
+
+ s.customizeDocumentCommand(document, c);
+
+ if (c.doit) {
+ if (c.length == 0 && c.text == null) {
+ return;
+ }
+
+ document.replace(c.offset, c.length, c.text);
+
+ int caretOffset = c.offset + c.text.length();
+
+ // The shiftsCaret flag doesn't behave the way it's documented to
+ //if (c.shiftsCaret && c.caretOffset != -1) {
+ if (c.caretOffset != -1) {
+ caretOffset = c.caretOffset;
+ }
+ viewer.setSelectedRange(caretOffset, 0);
+ }
+
+ String text = document.get();
+ Point selectedRange = viewer.getSelectedRange();
+ assert selectedRange.y == 0;
+ String textWithCaret = text;
+ if (selectedRange.x >= 0) {
+ textWithCaret = text.substring(0, selectedRange.x) + "^" +
+ text.substring(selectedRange.x);
+ }
+
+ assertEquals(after, textWithCaret);
+ }
+
+ private static String stripCaret(String s) {
+ int index = s.indexOf('^');
+ assertTrue(index != -1);
+ return s.substring(0, index) + s.substring(index + 1);
+ }
+
+ public void testCornerCase1() throws Exception {
+ checkInsertNewline("^", "\n^");
+ }
+
+ public void testCornerCase2() throws Exception {
+ checkInsertNewline(
+ "\n^",
+
+ "\n\n^");
+ }
+
+ public void testCornerCase3() throws Exception {
+ checkInsertNewline(
+ " ^",
+
+ " \n" +
+ " ^");
+ }
+
+ public void testSimpleIndentation1() throws Exception {
+ checkInsertNewline(
+ " ^ ",
+
+ " \n" +
+ " ^ ");
+ }
+
+ public void testSimpleIndentation2() throws Exception {
+ checkInsertNewline(
+ "\n" +
+ " foo^\n",
+
+ "\n" +
+ " foo\n" +
+ " ^\n");
+ }
+
+ public void testSimpleIndentation3() throws Exception {
+ checkInsertNewline(
+ "\n" +
+ " <newtag>^\n",
+
+ "\n" +
+ " <newtag>\n" +
+ " ^\n");
+ }
+
+ public void testSimpleIndentation4() throws Exception {
+ checkInsertNewline(
+ "\n" +
+ " <newtag/>^\n",
+
+ "\n" +
+ " <newtag/>\n" +
+ " ^\n");
+ }
+
+ public void testSimpleIndentation5() throws Exception {
+ checkInsertNewline(
+ "\n" +
+ " <newtag^\n",
+ "\n" +
+ " <newtag\n" +
+ " ^\n");
+ }
+
+ public void testSplitAttribute() throws Exception {
+ checkInsertNewline(
+ "\n" +
+ " <newtag ^attribute='value'/>\n",
+
+ "\n" +
+ " <newtag \n" +
+ " ^attribute='value'/>\n");
+ }
+
+ public void testIndentationInComments1() throws Exception {
+ // Make sure that inside a comment we ignore tags etc
+ checkInsertNewline(
+ "<!--\n foo^\n--->\n",
+
+ "<!--\n foo\n ^\n--->\n");
+ }
+
+ public void testIndentationInComments2() throws Exception {
+ // Make sure that inside a comment we ignore tags etc
+ checkInsertNewline(
+ "\n" +
+ "<!--\n" +
+ "<foo><^\n" +
+ "-->\n",
+
+ "\n" +
+ "<!--\n" +
+ "<foo><\n" +
+ "^\n" +
+ "-->\n");
+ }
+
+ public void testSurroundCaret() throws Exception {
+ checkInsertNewline(
+ "\n" +
+ " <item>^</item>\n",
+
+ "\n" +
+ " <item>\n" +
+ " ^\n" +
+ " </item>\n");
+ }
+
+ public void testSurroundCaret2() throws Exception {
+ // This test combines both surround with and continuing earlier lines (where
+ // it searches for a matching tag)
+ checkInsertNewline(
+ "\n" +
+ " <foo\n" +
+ " name='value'>^</foo>\n",
+
+ "\n" +
+ " <foo\n" +
+ " name='value'>\n" +
+ " ^\n" +
+ " </foo>\n");
+ }
+
+ public void testContinueEarlierLine1() throws Exception {
+ // Here we need to indent to the exact location of an earlier line
+ checkInsertNewline(
+ "\n" +
+ " <foo\n" +
+ " name='value'/>^\n",
+
+ "\n" +
+ " <foo\n" +
+ " name='value'/>\n" +
+ " ^\n");
+ }
+
+ public void testContinueEarlierLine2() throws Exception {
+ checkInsertNewline(
+ "\n" +
+ " <foo\n" +
+ " name='value'></foo>^\n",
+
+ "\n" +
+ " <foo\n" +
+ " name='value'></foo>\n" +
+ " ^\n");
+ // Note that
+ // <foo
+ // >
+ // </foo>
+ // does not require special handling, this only happens with the closing tag is sharing
+ // a line.
+ }
+
+ public void testContinueEarlierLine3() throws Exception {
+ // Make sure the code to look up the corresponding opening tag works properly
+ checkInsertNewline(
+ "\n" +
+ " <foo\n" +
+ " name='value'><bar></bar><baz/></foo>^\n",
+
+ "\n" +
+ " <foo\n" +
+ " name='value'><bar></bar><baz/></foo>\n" +
+ " ^\n");
+ }
+
+ public void testContinueEarlierLine4() throws Exception {
+ checkInsertNewline(
+ " <Button\n" +
+ " android:id=\"@+id/button1\"\n" +
+ " android:layout_width=\"wrap_content\"\n" +
+ " android:layout_height=\"wrap_content\"\n" +
+ " android:text=\"Button\" >^\n" +
+ " </Button>\n",
+
+ " <Button\n" +
+ " android:id=\"@+id/button1\"\n" +
+ " android:layout_width=\"wrap_content\"\n" +
+ " android:layout_height=\"wrap_content\"\n" +
+ " android:text=\"Button\" >\n" +
+ " ^\n" +
+ " </Button>\n");
+ }
+
+ public void testIndent() throws Exception {
+ checkInsertNewline(
+ " <Button\n" +
+ " attr=\"value\"></Button>^\n",
+
+ " <Button\n" +
+ " attr=\"value\"></Button>\n" +
+ " ^\n" +
+ "");
+ }
+
+ public void testLineBeginning1() throws Exception {
+ // Test that if you insert on a blank line, we just add a newline and indent
+ checkInsertNewline(
+ "<foo>\n" +
+ "^\n" +
+ "</foo>",
+
+ "<foo>\n" +
+ "\n" +
+ " ^\n" +
+ "</foo>");
+ }
+
+ public void testLineBeginning2() throws Exception {
+ // Test that if you insert with the caret on the beginning of a line that has
+ // content, we insert an indent correctly
+ checkInsertNewline(
+ "<foo>\n" +
+ "^ <bar/>\n" +
+ "</foo>",
+
+ "<foo>\n" +
+ "\n" +
+ " ^<bar/>\n" +
+ "</foo>");
+ }
+
+ public void testLineBeginning3() throws Exception {
+ checkInsertNewline(
+ "<foo>\n" +
+ " <bar>\n" +
+ "^\n" +
+ " <baz/>\n" +
+ " </bar>\n" +
+ "</foo>",
+
+ "<foo>\n" +
+ " <bar>\n" +
+ "\n" +
+ " ^\n" +
+ " <baz/>\n" +
+ " </bar>\n" +
+ "</foo>");
+
+ }
+
+ public void testLineBeginning4() throws Exception {
+ // Test that if you insert with the caret on the beginning of a line that has
+ // content, we insert an indent correctly
+ checkInsertNewline(
+ "<foo>\n" +
+ " <bar>\n" +
+ "\n" +
+ "^ <baz/>\n" +
+ " </bar>\n" +
+ "</foo>",
+
+ "<foo>\n" +
+ " <bar>\n" +
+ "\n" +
+ "\n" +
+ " ^<baz/>\n" +
+ " </bar>\n" +
+ "</foo>");
+ }
+
+ public void testLineBeginning5() throws Exception {
+ // Test that if you insert with the caret on the beginning of a line that has
+ // content, we insert an indent correctly
+ checkInsertNewline(
+ "<foo>\n" +
+ " <bar>\n" +
+ "\n" +
+ " ^ <baz/>\n" +
+ " </bar>\n" +
+ "</foo>",
+
+ "<foo>\n" +
+ " <bar>\n" +
+ "\n" +
+ " \n" +
+ " ^<baz/>\n" +
+ " </bar>\n" +
+ "</foo>");
+ }
+
+ public void testLineBeginning6() throws Exception {
+
+ checkInsertNewline(
+ " <foo>\n" +
+ " <bar>\n" +
+ " \n" +
+ " \n" +
+ "^ </bar>\n" +
+ " </foo>\n",
+
+ " <foo>\n" +
+ " <bar>\n" +
+ " \n" +
+ " \n" +
+ "\n" +
+ " ^</bar>\n" +
+ " </foo>\n");
+ }
+
+ public void testBlankContinuation() throws Exception {
+
+ checkInsertNewline(
+ " <foo>\n" +
+ " <bar>\n" +
+ " ^\n" +
+ " </bar>\n" +
+ " </foo>\n" +
+ "",
+
+ " <foo>\n" +
+ " <bar>\n" +
+ " \n" +
+ " ^\n" +
+ " </bar>\n" +
+ " </foo>\n" +
+ "");
+ }
+
+ public void testIssue22332a() throws Exception {
+ checkInsertNewline(
+ "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n" +
+ "<resources>\n" +
+ "\n" +
+ " <string name=\"hello\">Hello World, MainActivity!</string>^\n" +
+ "\n" +
+ "</resources>",
+
+ "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n" +
+ "<resources>\n" +
+ "\n" +
+ " <string name=\"hello\">Hello World, MainActivity!</string>\n" +
+ " ^\n" +
+ "\n" +
+ "</resources>");
+ }
+
+ public void testIssue22332b() throws Exception {
+ checkInsertNewline(
+ "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n" +
+ "<resources>\n" +
+ "\n" +
+ " <string name=\"hello\">Hello World, MainActivity!</string>\n" +
+ " ^\n" +
+ "\n" +
+ "</resources>",
+
+ "<?xml version=\"1.0\" encoding=\"utf-8\"?>\n" +
+ "<resources>\n" +
+ "\n" +
+ " <string name=\"hello\">Hello World, MainActivity!</string>\n" +
+ " \n" +
+ " ^\n" +
+ "\n" +
+ "</resources>");
+ }
+
+ /**
+ * To test
+ * When you press / after < I should reindent the current line. For example,
+ * if you have
+ * <foo>
+ * <bar>
+ * </ the moment you've typed this we should dedent it back out
+ * When you press newline we need to reindent
+ */
+
+ /** Subclassed for test usage since constructor is protected */
+ private class TestDocumentCommand extends DocumentCommand {
+ public TestDocumentCommand() {
+ }
+ }
+}