| /* |
| * Copyright (C) 2011 The Android Open Source Project |
| * |
| * Licensed under the Apache License, Version 2.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.apache.org/licenses/LICENSE-2.0 |
| * |
| * 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.ex.chips; |
| |
| import android.content.Context; |
| import android.graphics.Bitmap; |
| import android.graphics.drawable.BitmapDrawable; |
| import android.graphics.drawable.Drawable; |
| import android.test.AndroidTestCase; |
| import android.test.suitebuilder.annotation.SmallTest; |
| import android.text.Editable; |
| import android.text.SpannableStringBuilder; |
| import android.text.style.ImageSpan; |
| import android.text.util.Rfc822Tokenizer; |
| import android.widget.TextView; |
| |
| import com.android.ex.chips.BaseRecipientAdapter; |
| import com.android.ex.chips.RecipientEditTextView; |
| import com.android.ex.chips.RecipientEntry; |
| import com.android.ex.chips.recipientchip.DrawableRecipientChip; |
| import com.android.ex.chips.recipientchip.VisibleRecipientChip;; |
| |
| import java.util.regex.Pattern; |
| |
| @SmallTest |
| public class ChipsTest extends AndroidTestCase { |
| private DrawableRecipientChip[] mMockRecips; |
| |
| private RecipientEntry[] mMockEntries; |
| |
| private Rfc822Tokenizer mTokenizer; |
| |
| private Editable mEditable; |
| |
| class BaseMockRecipientEditTextView extends RecipientEditTextView { |
| |
| public BaseMockRecipientEditTextView(Context context) { |
| super(context, null); |
| mTokenizer = new Rfc822Tokenizer(); |
| setTokenizer(mTokenizer); |
| } |
| |
| @Override |
| public DrawableRecipientChip[] getSortedRecipients() { |
| return mMockRecips; |
| } |
| |
| @Override |
| public int getLineHeight() { |
| return 48; |
| } |
| |
| @Override |
| Drawable getChipBackground(RecipientEntry contact) { |
| return createChipBackground(); |
| } |
| |
| @Override |
| public int getViewWidth() { |
| return 100; |
| } |
| } |
| |
| class MockRecipientEditTextView extends BaseMockRecipientEditTextView { |
| |
| public MockRecipientEditTextView(Context context) { |
| super(context); |
| mTokenizer = new Rfc822Tokenizer(); |
| setTokenizer(mTokenizer); |
| } |
| |
| @Override |
| public DrawableRecipientChip[] getSortedRecipients() { |
| return mMockRecips; |
| } |
| |
| @Override |
| public Editable getText() { |
| return mEditable; |
| } |
| |
| @Override |
| public Editable getSpannable() { |
| return mEditable; |
| } |
| |
| @Override |
| public int getLineHeight() { |
| return 48; |
| } |
| |
| @Override |
| Drawable getChipBackground(RecipientEntry contact) { |
| return createChipBackground(); |
| } |
| |
| @Override |
| public int length() { |
| return mEditable != null ? mEditable.length() : 0; |
| } |
| |
| @Override |
| public String toString() { |
| return mEditable != null ? mEditable.toString() : ""; |
| } |
| |
| @Override |
| public int getViewWidth() { |
| return 100; |
| } |
| } |
| |
| private class TestBaseRecipientAdapter extends BaseRecipientAdapter { |
| public TestBaseRecipientAdapter(final Context context) { |
| super(context); |
| } |
| |
| public TestBaseRecipientAdapter(final Context context, final int preferredMaxResultCount, |
| final int queryMode) { |
| super(context, preferredMaxResultCount, queryMode); |
| } |
| } |
| |
| private MockRecipientEditTextView createViewForTesting() { |
| mEditable = new SpannableStringBuilder(); |
| MockRecipientEditTextView view = new MockRecipientEditTextView(getContext()); |
| view.setAdapter(new TestBaseRecipientAdapter(getContext())); |
| return view; |
| } |
| |
| public void testCreateDisplayText() { |
| RecipientEditTextView view = createViewForTesting(); |
| RecipientEntry entry = RecipientEntry.constructGeneratedEntry("User Name, Jr", |
| "user@username.com", true); |
| String testAddress = view.createAddressText(entry); |
| String testDisplay = view.createChipDisplayText(entry); |
| assertEquals("Expected a properly formatted RFC email address", |
| "\"User Name, Jr\" <user@username.com>, ", testAddress); |
| assertEquals("Expected a displayable name", "User Name, Jr", testDisplay); |
| |
| RecipientEntry alreadyFormatted = |
| RecipientEntry.constructFakeEntry("user@username.com, ", true); |
| testAddress = view.createAddressText(alreadyFormatted); |
| testDisplay = view.createChipDisplayText(alreadyFormatted); |
| assertEquals("Expected a properly formatted RFC email address", "<user@username.com>, ", |
| testAddress); |
| assertEquals("Expected a displayable name", "user@username.com", testDisplay); |
| |
| RecipientEntry alreadyFormattedNoSpace = RecipientEntry |
| .constructFakeEntry("user@username.com,", true); |
| testAddress = view.createAddressText(alreadyFormattedNoSpace); |
| assertEquals("Expected a properly formatted RFC email address", "<user@username.com>, ", |
| testAddress); |
| |
| RecipientEntry alreadyNamed = RecipientEntry.constructGeneratedEntry("User Name", |
| "\"User Name, Jr\" <user@username.com>", true); |
| testAddress = view.createAddressText(alreadyNamed); |
| testDisplay = view.createChipDisplayText(alreadyNamed); |
| assertEquals( |
| "Expected address that used the name not the excess address name", |
| "User Name <user@username.com>, ", testAddress); |
| assertEquals("Expected a displayable name", "User Name", testDisplay); |
| } |
| |
| public void testSanitizeBetween() { |
| // First, add 2 chips and then make sure we remove |
| // the extra content between them correctly. |
| populateMocks(2); |
| MockRecipientEditTextView view = createViewForTesting(); |
| String first = (String) mTokenizer.terminateToken("FIRST"); |
| String second = (String) mTokenizer.terminateToken("SECOND"); |
| String extra = "EXTRA"; |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + extra + second); |
| int firstStart = mEditable.toString().indexOf(first); |
| int firstEnd = firstStart + first.trim().length(); |
| int secondStart = mEditable.toString().indexOf(second); |
| int secondEnd = secondStart + second.trim().length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], secondStart, secondEnd, 0); |
| view.sanitizeBetween(); |
| String editableString = mEditable.toString(); |
| assertEquals(editableString.indexOf(extra), -1); |
| assertEquals(editableString.indexOf(first), firstStart); |
| assertEquals(editableString.indexOf(second), secondStart - extra.length()); |
| assertEquals(editableString, (first + second)); |
| |
| // Add 1 chip and make sure that we remove the extra stuff before it correctly. |
| mEditable = new SpannableStringBuilder(); |
| populateMocks(1); |
| mEditable.append(extra); |
| mEditable.append(first); |
| firstStart = mEditable.toString().indexOf(first); |
| firstEnd = firstStart + first.length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], firstStart, firstEnd, 0); |
| view.sanitizeBetween(); |
| assertEquals(mEditable.toString(), first); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), firstStart |
| - extra.length()); |
| } |
| |
| public void testSanitizeEnd() { |
| // First, add 2 chips and then make sure we remove |
| // the extra content between them correctly. |
| populateMocks(2); |
| MockRecipientEditTextView view = createViewForTesting(); |
| String first = (String) mTokenizer.terminateToken("FIRST"); |
| String second = (String) mTokenizer.terminateToken("SECOND"); |
| String extra = "EXTRA"; |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + second); |
| int firstStart = mEditable.toString().indexOf(first); |
| int firstEnd = firstStart + first.trim().length(); |
| int secondStart = mEditable.toString().indexOf(second); |
| int secondEnd = secondStart + second.trim().length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], secondStart, secondEnd, 0); |
| view.sanitizeEnd(); |
| String editableString = mEditable.toString(); |
| assertEquals(editableString.indexOf(extra), -1); |
| assertEquals(editableString.indexOf(first), firstStart); |
| assertEquals(editableString.indexOf(second), secondStart); |
| assertEquals(editableString, (first + second)); |
| mEditable.append(extra); |
| editableString = mEditable.toString(); |
| assertEquals(mEditable.toString(), (first + second + extra)); |
| view.sanitizeEnd(); |
| assertEquals(mEditable.toString(), (first + second)); |
| } |
| |
| public void testMoreChipPlainText() { |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| String first = (String) mTokenizer.terminateToken("FIRST"); |
| String second = (String) mTokenizer.terminateToken("SECOND"); |
| String third = (String) mTokenizer.terminateToken("THIRD"); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first+second+third); |
| int thirdStart = mEditable.toString().indexOf(third); |
| int thirdEnd = thirdStart + third.trim().length(); |
| view.createMoreChipPlainText(); |
| ImageSpan moreChip = view.getMoreChip(); |
| assertEquals(mEditable.getSpanStart(moreChip), thirdStart); |
| assertEquals(mEditable.getSpanEnd(moreChip), thirdEnd + 1); |
| } |
| |
| public void testCountTokens() { |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| String first = (String) mTokenizer.terminateToken("FIRST"); |
| String second = (String) mTokenizer.terminateToken("SECOND"); |
| String third = (String) mTokenizer.terminateToken("THIRD"); |
| String fourth = "FOURTH,"; |
| String fifth = "FIFTH,"; |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first+second+third+fourth+fifth); |
| assertEquals(view.countTokens(mEditable), 5); |
| } |
| |
| public void testTooManyRecips() { |
| BaseMockRecipientEditTextView view = new BaseMockRecipientEditTextView(getContext()); |
| view.setMoreItem(createTestMoreItem()); |
| for (int i = 0; i < 100; i++) { |
| view.append(mTokenizer.terminateToken(i + "")); |
| } |
| assertEquals(view.countTokens(view.getText()), 100); |
| view.handlePendingChips(); |
| view.createMoreChip(); |
| ImageSpan moreChip = view.getMoreChip(); |
| // We show 2 chips then place a more chip. |
| int secondStart = view.getText().toString().indexOf( |
| (String) mTokenizer.terminateToken(RecipientEditTextView.CHIP_LIMIT + "")); |
| assertEquals(view.getText().getSpanStart(moreChip), secondStart); |
| assertEquals(view.getText().getSpanEnd(moreChip), view.length()); |
| assertEquals(view.getSortedRecipients(), null); |
| } |
| |
| public void testMoreChip() { |
| // Add 3 chips: this is the trigger point at which the more chip will be created. |
| // Test that adding the chips and then creating and removing the more chip, as if |
| // the user were focusing/ removing focus from the chips field. |
| populateMocks(3); |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| String first = (String) mTokenizer.terminateToken("FIRST"); |
| String second = (String) mTokenizer.terminateToken("SECOND"); |
| String third = (String) mTokenizer.terminateToken("THIRD"); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first+second+third); |
| |
| int firstStart = mEditable.toString().indexOf(first); |
| int firstEnd = firstStart + first.trim().length(); |
| int secondStart = mEditable.toString().indexOf(second); |
| int secondEnd = secondStart + second.trim().length(); |
| int thirdStart = mEditable.toString().indexOf(third); |
| int thirdEnd = thirdStart + third.trim().length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| |
| view.createMoreChip(); |
| assertEquals(mEditable.toString(), first+second+third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), firstStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), secondStart); |
| // Find the more chip. |
| ImageSpan moreChip = view.getMoreChip(); |
| assertEquals(mEditable.getSpanStart(moreChip), thirdStart); |
| assertEquals(mEditable.getSpanEnd(moreChip), thirdEnd + 1); |
| |
| view.removeMoreChip(); |
| assertEquals(mEditable.toString(), first+second+third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), firstStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 3]), firstEnd); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), secondStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), thirdStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 1]), thirdEnd); |
| moreChip = view.getMoreChip(); |
| assertEquals(mEditable.getSpanStart(moreChip), -1); |
| |
| // Rinse and repeat, just in case! |
| view.createMoreChip(); |
| assertEquals(mEditable.toString(), first+second+third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), firstStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), secondStart); |
| // Find the more chip. |
| moreChip = view.getMoreChip(); |
| assertEquals(mEditable.getSpanStart(moreChip), thirdStart); |
| assertEquals(mEditable.getSpanEnd(moreChip), thirdEnd + 1); |
| |
| view.removeMoreChip(); |
| assertEquals(mEditable.toString(), first+second+third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), firstStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 3]), firstEnd); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), secondStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), thirdStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 1]), thirdEnd); |
| moreChip = view.getMoreChip(); |
| assertEquals(mEditable.getSpanStart(moreChip), -1); |
| } |
| |
| public void testMoreChipLotsOfUsers() { |
| // Test adding and removing the more chip in the case where we have a lot of users. |
| populateMocks(10); |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| String first = (String) mTokenizer.terminateToken("FIRST"); |
| String second = (String) mTokenizer.terminateToken("SECOND"); |
| String third = (String) mTokenizer.terminateToken("THIRD"); |
| String fourth = (String) mTokenizer.terminateToken("FOURTH"); |
| String fifth = (String) mTokenizer.terminateToken("FIFTH"); |
| String sixth = (String) mTokenizer.terminateToken("SIXTH"); |
| String seventh = (String) mTokenizer.terminateToken("SEVENTH"); |
| String eigth = (String) mTokenizer.terminateToken("EIGHTH"); |
| String ninth = (String) mTokenizer.terminateToken("NINTH"); |
| String tenth = (String) mTokenizer.terminateToken("TENTH"); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first+second+third+fourth+fifth+sixth+seventh+eigth+ninth+tenth); |
| |
| int firstStart = mEditable.toString().indexOf(first); |
| int firstEnd = firstStart + first.trim().length(); |
| int secondStart = mEditable.toString().indexOf(second); |
| int secondEnd = secondStart + second.trim().length(); |
| int thirdStart = mEditable.toString().indexOf(third); |
| int thirdEnd = thirdStart + third.trim().length(); |
| int fourthStart = mEditable.toString().indexOf(fourth); |
| int fourthEnd = fourthStart + fourth.trim().length(); |
| int fifthStart = mEditable.toString().indexOf(fifth); |
| int fifthEnd = fifthStart + fifth.trim().length(); |
| int sixthStart = mEditable.toString().indexOf(sixth); |
| int sixthEnd = sixthStart + sixth.trim().length(); |
| int seventhStart = mEditable.toString().indexOf(seventh); |
| int seventhEnd = seventhStart + seventh.trim().length(); |
| int eighthStart = mEditable.toString().indexOf(eigth); |
| int eighthEnd = eighthStart + eigth.trim().length(); |
| int ninthStart = mEditable.toString().indexOf(ninth); |
| int ninthEnd = ninthStart + ninth.trim().length(); |
| int tenthStart = mEditable.toString().indexOf(tenth); |
| int tenthEnd = tenthStart + tenth.trim().length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 10], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 9], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 8], thirdStart, thirdEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 7], fourthStart, fourthEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 6], fifthStart, fifthEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 5], sixthStart, sixthEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 4], seventhStart, seventhEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], eighthStart, eighthEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], ninthStart, ninthEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], tenthStart, tenthEnd, 0); |
| |
| view.createMoreChip(); |
| assertEquals(mEditable.toString(), first + second + third + fourth + fifth + sixth |
| + seventh + eigth + ninth + tenth); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 10]), firstStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 9]), secondStart); |
| // Find the more chip. |
| ImageSpan moreChip = view.getMoreChip(); |
| assertEquals(mEditable.getSpanStart(moreChip), thirdStart); |
| assertEquals(mEditable.getSpanEnd(moreChip), tenthEnd + 1); |
| |
| view.removeMoreChip(); |
| assertEquals(mEditable.toString(), first + second + third + fourth + fifth + sixth |
| + seventh + eigth + ninth + tenth); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 10]), firstStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 9]), secondStart); |
| |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 8]), thirdStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 7]), fourthStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 6]), fifthStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 5]), sixthStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 4]), seventhStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), eighthStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), ninthStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), tenthStart); |
| moreChip = view.getMoreChip(); |
| assertEquals(mEditable.getSpanStart(moreChip), -1); |
| |
| } |
| |
| public void testMoreChipSpecialChars() { |
| // Make sure the more chip correctly handles extra tokenizer characters in the middle |
| // of chip text. |
| populateMocks(3); |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| String first = (String) mTokenizer.terminateToken("FI,RST"); |
| String second = (String) mTokenizer.terminateToken("SE,COND"); |
| String third = (String) mTokenizer.terminateToken("THI,RD"); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first+second+third); |
| |
| int firstStart = mEditable.toString().indexOf(first); |
| int firstEnd = firstStart + first.trim().length(); |
| int secondStart = mEditable.toString().indexOf(second); |
| int secondEnd = secondStart + second.trim().length(); |
| int thirdStart = mEditable.toString().indexOf(third); |
| int thirdEnd = thirdStart + third.trim().length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| |
| view.createMoreChip(); |
| assertEquals(mEditable.toString(), first+second+third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), firstStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), secondStart); |
| // Find the more chip. |
| ImageSpan moreChip = view.getMoreChip(); |
| assertEquals(mEditable.getSpanStart(moreChip), thirdStart); |
| assertEquals(mEditable.getSpanEnd(moreChip), thirdEnd + 1); |
| |
| view.removeMoreChip(); |
| assertEquals(mEditable.toString(), first+second+third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), firstStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 3]), firstEnd); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), secondStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), thirdStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 1]), thirdEnd); |
| moreChip = view.getMoreChip(); |
| assertEquals(mEditable.getSpanStart(moreChip), -1); |
| } |
| |
| public void testMoreChipDupes() { |
| // Make sure the more chip is correctly added and removed when we have duplicate chips. |
| populateMocks(4); |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| String first = (String) mTokenizer.terminateToken("FIRST"); |
| String second = (String) mTokenizer.terminateToken("SECOND"); |
| String third = (String) mTokenizer.terminateToken("THIRD"); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first+second+third+third); |
| |
| int firstStart = mEditable.toString().indexOf(first); |
| int firstEnd = firstStart + first.trim().length(); |
| int secondStart = mEditable.toString().indexOf(second); |
| int secondEnd = secondStart + second.trim().length(); |
| int thirdStart = mEditable.toString().indexOf(third); |
| int thirdEnd = thirdStart + third.trim().length(); |
| int thirdNextStart = mEditable.toString().indexOf(third, thirdEnd); |
| int thirdNextEnd = thirdNextStart + third.trim().length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 4], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], thirdStart, thirdEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdNextStart, thirdNextEnd, 0); |
| |
| view.createMoreChip(); |
| assertEquals(mEditable.toString(), first+second+third+third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 4]), firstStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), secondStart); |
| // Find the more chip. |
| ImageSpan moreChip = view.getMoreChip(); |
| assertEquals(mEditable.getSpanStart(moreChip), thirdStart); |
| assertEquals(mEditable.getSpanEnd(moreChip), thirdNextEnd + 1); |
| |
| view.removeMoreChip(); |
| assertEquals(mEditable.toString(), first+second+third+third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 4]), firstStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 4]), firstEnd); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), secondStart); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), thirdStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 2]), thirdEnd); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), thirdNextStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 1]), thirdNextEnd); |
| moreChip = view.getMoreChip(); |
| assertEquals(mEditable.getSpanStart(moreChip), -1); |
| } |
| |
| public void testRemoveChip() { |
| // Create 3 chips to start and test removing chips in various postions. |
| populateMocks(3); |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| String first = (String) mTokenizer.terminateToken("FIRST"); |
| String second = (String) mTokenizer.terminateToken("SECOND"); |
| String third = (String) mTokenizer.terminateToken("THIRD"); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + second + third); |
| |
| int firstStart = mEditable.toString().indexOf(first); |
| int firstEnd = firstStart + first.length(); |
| int secondStart = mEditable.toString().indexOf(second); |
| int secondEnd = secondStart + second.length(); |
| int thirdStart = mEditable.toString().indexOf(third); |
| int thirdEnd = thirdStart + third.length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| assertEquals(mEditable.toString(), first + second + third); |
| // Test removing the middle chip. |
| view.removeChip(mMockRecips[mMockRecips.length - 2]); |
| assertEquals(mEditable.toString(), first + third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), firstStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 3]), firstEnd); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), -1); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 2]), -1); |
| int newThirdStart = mEditable.toString().indexOf(third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), newThirdStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 1]), newThirdStart |
| + third.length()); |
| |
| // Test removing the first chip. |
| populateMocks(3); |
| view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + second + third); |
| |
| firstStart = mEditable.toString().indexOf(first); |
| firstEnd = firstStart + first.length(); |
| secondStart = mEditable.toString().indexOf(second); |
| secondEnd = secondStart + second.length(); |
| thirdStart = mEditable.toString().indexOf(third); |
| thirdEnd = thirdStart + third.length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| assertEquals(mEditable.toString(), first + second + third); |
| view.removeChip(mMockRecips[mMockRecips.length - 3]); |
| assertEquals(mEditable.toString(), second + third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), -1); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 3]), -1); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), 0); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 2]), second.length()); |
| newThirdStart = mEditable.toString().indexOf(third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), newThirdStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 1]), newThirdStart |
| + third.length()); |
| |
| // Test removing the last chip. |
| populateMocks(3); |
| view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + second + third); |
| |
| firstStart = mEditable.toString().indexOf(first); |
| firstEnd = firstStart + first.length(); |
| secondStart = mEditable.toString().indexOf(second); |
| secondEnd = secondStart + second.length(); |
| thirdStart = mEditable.toString().indexOf(third); |
| thirdEnd = thirdStart + third.length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| assertEquals(mEditable.toString(), first + second + third); |
| view.removeChip(mMockRecips[mMockRecips.length - 1]); |
| assertEquals(mEditable.toString(), first + second); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), firstStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 3]), firstEnd); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), secondStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 2]), secondEnd); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), -1); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 1]), -1); |
| } |
| |
| public void testReplaceChip() { |
| populateMocks(3); |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| view.setChipBackground(createChipBackground()); |
| view.setChipHeight(48); |
| String first = (String) mTokenizer.terminateToken("FIRST"); |
| String second = (String) mTokenizer.terminateToken("SECOND"); |
| String third = (String) mTokenizer.terminateToken("THIRD"); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + second + third); |
| |
| // Test replacing the first chip with a new chip. |
| int firstStart = mEditable.toString().indexOf(first); |
| int firstEnd = firstStart + first.trim().length(); |
| int secondStart = mEditable.toString().indexOf(second); |
| int secondEnd = secondStart + second.trim().length(); |
| int thirdStart = mEditable.toString().indexOf(third); |
| int thirdEnd = thirdStart + third.trim().length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| assertEquals(mEditable.toString(), first + second + third); |
| view.replaceChip(mMockRecips[mMockRecips.length - 3], RecipientEntry |
| .constructGeneratedEntry("replacement", "replacement@replacement.com", true)); |
| assertEquals(mEditable.toString(), mTokenizer |
| .terminateToken("replacement <replacement@replacement.com>") |
| + second + third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), -1); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 3]), -1); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), mEditable |
| .toString().indexOf(second)); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 2]), mEditable |
| .toString().indexOf(second) |
| + second.trim().length()); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), mEditable |
| .toString().indexOf(third)); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 1]), mEditable |
| .toString().indexOf(third) |
| + third.trim().length()); |
| DrawableRecipientChip[] spans = |
| mEditable.getSpans(0, mEditable.length(), DrawableRecipientChip.class); |
| assertEquals(spans.length, 3); |
| spans = mEditable |
| .getSpans(0, mEditable.toString().indexOf(second) - 1, DrawableRecipientChip.class); |
| assertEquals((String) spans[0].getDisplay(), "replacement"); |
| |
| |
| // Test replacing the middle chip with a new chip. |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + second + third); |
| firstStart = mEditable.toString().indexOf(first); |
| firstEnd = firstStart + first.trim().length(); |
| secondStart = mEditable.toString().indexOf(second); |
| secondEnd = secondStart + second.trim().length(); |
| thirdStart = mEditable.toString().indexOf(third); |
| thirdEnd = thirdStart + third.trim().length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| assertEquals(mEditable.toString(), first + second + third); |
| view.replaceChip(mMockRecips[mMockRecips.length - 2], RecipientEntry |
| .constructGeneratedEntry("replacement", "replacement@replacement.com", true)); |
| assertEquals(mEditable.toString(), first + mTokenizer |
| .terminateToken("replacement <replacement@replacement.com>") + third); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), firstStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 3]), firstEnd); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), -1); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 2]), -1); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), mEditable |
| .toString().indexOf(third)); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 1]), mEditable |
| .toString().indexOf(third) |
| + third.trim().length()); |
| spans = mEditable.getSpans(0, mEditable.length(), DrawableRecipientChip.class); |
| assertEquals(spans.length, 3); |
| spans = mEditable.getSpans(firstEnd, mEditable.toString().indexOf(third) - 1, |
| DrawableRecipientChip.class); |
| assertEquals((String) spans[0].getDisplay(), "replacement"); |
| |
| |
| // Test replacing the last chip with a new chip. |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + second + third); |
| firstStart = mEditable.toString().indexOf(first); |
| firstEnd = firstStart + first.trim().length(); |
| secondStart = mEditable.toString().indexOf(second); |
| secondEnd = secondStart + second.trim().length(); |
| thirdStart = mEditable.toString().indexOf(third); |
| thirdEnd = thirdStart + third.trim().length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| assertEquals(mEditable.toString(), first + second + third); |
| view.replaceChip(mMockRecips[mMockRecips.length - 1], RecipientEntry |
| .constructGeneratedEntry("replacement", "replacement@replacement.com", true)); |
| assertEquals(mEditable.toString(), first + second + mTokenizer |
| .terminateToken("replacement <replacement@replacement.com>")); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 3]), firstStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 3]), firstEnd); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 2]), secondStart); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 2]), secondEnd); |
| assertEquals(mEditable.getSpanStart(mMockRecips[mMockRecips.length - 1]), -1); |
| assertEquals(mEditable.getSpanEnd(mMockRecips[mMockRecips.length - 1]), -1); |
| spans = mEditable.getSpans(0, mEditable.length(), DrawableRecipientChip.class); |
| assertEquals(spans.length, 3); |
| spans = mEditable |
| .getSpans(secondEnd, mEditable.length(), DrawableRecipientChip.class); |
| assertEquals((String) spans[0].getDisplay(), "replacement"); |
| } |
| |
| public void testHandlePaste() { |
| // Start with an empty edit field. |
| // Add an address; the text should be left as is. |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| view.setChipBackground(createChipBackground()); |
| view.setChipHeight(48); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append("user@user.com"); |
| view.setSelection(mEditable.length()); |
| view.handlePaste(); |
| assertEquals(mEditable.getSpans(0, mEditable.length(), DrawableRecipientChip.class).length, 0); |
| assertEquals(mEditable.toString(), "user@user.com"); |
| |
| // Test adding a single address to an empty chips field with a space at |
| // the end of it. The address should stay as text. |
| mEditable = new SpannableStringBuilder(); |
| String tokenizedUser = "user@user.com" + " "; |
| mEditable.append(tokenizedUser); |
| view.setSelection(mEditable.length()); |
| view.handlePaste(); |
| assertEquals(mEditable.getSpans(0, mEditable.length(), DrawableRecipientChip.class).length, 0); |
| assertEquals(mEditable.toString(), tokenizedUser); |
| |
| // Test adding a single address to an empty chips field with a semicolon at |
| // the end of it. The address should become a chip |
| mEditable = new SpannableStringBuilder(); |
| tokenizedUser = "user@user.com;"; |
| mEditable.append(tokenizedUser); |
| view.setSelection(mEditable.length()); |
| view.handlePaste(); |
| assertEquals(mEditable.getSpans(0, mEditable.length(), DrawableRecipientChip.class).length, 1); |
| |
| // Test adding 2 address to an empty chips field. The second to last |
| // address should become a chip and the last address should stay as |
| // text. |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append("user1,user2@user.com"); |
| view.setSelection(mEditable.length()); |
| view.handlePaste(); |
| assertEquals(mEditable.getSpans(0, mEditable.length(), DrawableRecipientChip.class).length, 1); |
| assertEquals(mEditable.getSpans(0, mEditable.toString().indexOf("user2@user.com"), |
| DrawableRecipientChip.class).length, 1); |
| assertEquals(mEditable.toString(), "<user1>, user2@user.com"); |
| |
| // Test adding a single address to the end of existing chips. The existing |
| // chips should remain, and the last address should stay as text. |
| populateMocks(3); |
| String first = (String) mTokenizer.terminateToken("FIRST"); |
| String second = (String) mTokenizer.terminateToken("SECOND"); |
| String third = (String) mTokenizer.terminateToken("THIRD"); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + second + third); |
| view.setSelection(mEditable.length()); |
| int firstStart = mEditable.toString().indexOf(first); |
| int firstEnd = firstStart + first.trim().length(); |
| int secondStart = mEditable.toString().indexOf(second); |
| int secondEnd = secondStart + second.trim().length(); |
| int thirdStart = mEditable.toString().indexOf(third); |
| int thirdEnd = thirdStart + third.trim().length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| |
| mEditable.append("user@user.com"); |
| view.setSelection(mEditable.length()); |
| view.handlePaste(); |
| assertEquals(mEditable.getSpans(0, mEditable.length(), DrawableRecipientChip.class).length, |
| mMockRecips.length); |
| assertEquals(mEditable.toString(), first + second + third + "user@user.com"); |
| |
| // Paste 2 addresses after existing chips. We expect the first address to be turned into |
| // a chip and the second to be left as text. |
| populateMocks(3); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + second + third); |
| |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| |
| mEditable.append("user1, user2@user.com"); |
| view.setSelection(mEditable.length()); |
| view.handlePaste(); |
| assertEquals(mEditable.getSpans(0, mEditable.length(), DrawableRecipientChip.class).length, |
| mMockRecips.length + 1); |
| assertEquals(mEditable.getSpans(mEditable.toString().indexOf("<user1>"), mEditable |
| .toString().indexOf("user2@user.com") - 1, DrawableRecipientChip.class).length, 1); |
| assertEquals(mEditable.getSpans(mEditable.toString().indexOf("user2@user.com"), mEditable |
| .length(), DrawableRecipientChip.class).length, 0); |
| assertEquals(mEditable.toString(), first + second + third + "<user1>, user2@user.com"); |
| |
| // Paste 2 addresses after existing chips. We expect the first address to be turned into |
| // a chip and the second to be left as text. This removes the space seperator char between |
| // addresses. |
| populateMocks(3); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + second + third); |
| |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| |
| mEditable.append("user1,user2@user.com"); |
| view.setSelection(mEditable.length()); |
| view.handlePaste(); |
| assertEquals(mEditable.getSpans(0, mEditable.length(), DrawableRecipientChip.class).length, |
| mMockRecips.length + 1); |
| assertEquals(mEditable.getSpans(mEditable.toString().indexOf("<user1>"), mEditable |
| .toString().indexOf("user2@user.com") - 1, DrawableRecipientChip.class).length, 1); |
| assertEquals(mEditable.getSpans(mEditable.toString().indexOf("user2@user.com"), mEditable |
| .length(), DrawableRecipientChip.class).length, 0); |
| assertEquals(mEditable.toString(), first + second + third + "<user1>, user2@user.com"); |
| |
| // Test a complete token pasted in at the end. It should be turned into a chip. |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append("user1, user2@user.com,"); |
| view.setSelection(mEditable.length()); |
| view.handlePaste(); |
| assertEquals(mEditable.getSpans(0, mEditable.length(), DrawableRecipientChip.class).length, 2); |
| assertEquals(mEditable.getSpans(mEditable.toString().indexOf("<user1>"), mEditable |
| .toString().indexOf("user2@user.com") - 1, DrawableRecipientChip.class).length, 1); |
| assertEquals(mEditable.getSpans(mEditable.toString().indexOf("user2@user.com"), mEditable |
| .length(), DrawableRecipientChip.class).length, 1); |
| assertEquals(mEditable.toString(), "<user1>, <user2@user.com>, "); |
| } |
| |
| public void testGetPastTerminators() { |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| view.setChipBackground(createChipBackground()); |
| view.setChipHeight(48); |
| String test = "test"; |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(test); |
| assertEquals(view.movePastTerminators(mTokenizer.findTokenEnd(mEditable.toString(), 0)), |
| test.length()); |
| |
| test = "test,"; |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(test); |
| assertEquals(view.movePastTerminators(mTokenizer.findTokenEnd(mEditable.toString(), 0)), |
| test.length()); |
| |
| test = "test, "; |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(test); |
| assertEquals(view.movePastTerminators(mTokenizer.findTokenEnd(mEditable.toString(), 0)), |
| test.length()); |
| |
| test = "test;"; |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(test); |
| assertEquals(view.movePastTerminators(mTokenizer.findTokenEnd(mEditable.toString(), 0)), |
| test.length()); |
| |
| test = "test; "; |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(test); |
| assertEquals(view.movePastTerminators(mTokenizer.findTokenEnd(mEditable.toString(), 0)), |
| test.length()); |
| } |
| |
| public void testIsCompletedToken() { |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| view.setChipBackground(createChipBackground()); |
| view.setChipHeight(48); |
| assertTrue(view.isCompletedToken("test;")); |
| assertTrue(view.isCompletedToken("test,")); |
| assertFalse(view.isCompletedToken("test")); |
| assertFalse(view.isCompletedToken("test ")); |
| } |
| |
| public void testGetLastChip() { |
| populateMocks(3); |
| MockRecipientEditTextView view = createViewForTesting(); |
| view.setMoreItem(createTestMoreItem()); |
| view.setChipBackground(createChipBackground()); |
| view.setChipHeight(48); |
| String first = (String) mTokenizer.terminateToken("FIRST"); |
| String second = (String) mTokenizer.terminateToken("SECOND"); |
| String third = (String) mTokenizer.terminateToken("THIRD"); |
| mEditable = new SpannableStringBuilder(); |
| mEditable.append(first + second + third); |
| |
| // Test replacing the first chip with a new chip. |
| int firstStart = mEditable.toString().indexOf(first); |
| int firstEnd = firstStart + first.trim().length(); |
| int secondStart = mEditable.toString().indexOf(second); |
| int secondEnd = secondStart + second.trim().length(); |
| int thirdStart = mEditable.toString().indexOf(third); |
| int thirdEnd = thirdStart + third.trim().length(); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 3], firstStart, firstEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 2], secondStart, secondEnd, 0); |
| mEditable.setSpan(mMockRecips[mMockRecips.length - 1], thirdStart, thirdEnd, 0); |
| assertEquals(view.getLastChip(), mMockRecips[mMockRecips.length - 1]); |
| mEditable.append("extra"); |
| assertEquals(view.getLastChip(), mMockRecips[mMockRecips.length - 1]); |
| } |
| |
| private Drawable createChipBackground() { |
| Bitmap drawable = Bitmap.createBitmap(100, 100, Bitmap.Config.ARGB_8888); |
| return new BitmapDrawable(getContext().getResources(), drawable); |
| } |
| |
| private TextView createTestMoreItem() { |
| TextView view = new TextView(getContext()); |
| view.setText("<xliff:g id='count'>%1$s</xliff:g> more..."); |
| return view; |
| } |
| |
| private void populateMocks(int size) { |
| mMockEntries = new RecipientEntry[size]; |
| for (int i = 0; i < size; i++) { |
| mMockEntries[i] = RecipientEntry.constructGeneratedEntry("user", |
| "user@username.com", true); |
| } |
| mMockRecips = new DrawableRecipientChip[size]; |
| for (int i = 0; i < size; i++) { |
| mMockRecips[i] = new VisibleRecipientChip(null, mMockEntries[i]); |
| } |
| } |
| |
| /** |
| * <p> |
| * Ensure the original text is always accurate, regardless of the type of email. The original |
| * text is used to determine where to display the chip span. If this test fails, it means some |
| * text that should be turned into one whole chip may behave unexpectedly. |
| * </p> |
| * <p> |
| * For example, a bug was seen where |
| * |
| * <pre> |
| * "Android User" <android@example.com> |
| * </pre> |
| * |
| * was converted to |
| * |
| * <pre> |
| * Android User [android@example.com] |
| * </pre> |
| * |
| * where text inside [] is a chip. |
| * </p> |
| */ |
| public void testCreateReplacementChipOriginalText() { |
| // Name in quotes + email address |
| testCreateReplacementChipOriginalText("\"Android User\" <android@example.com>,"); |
| // Name in quotes + email address without brackets |
| testCreateReplacementChipOriginalText("\"Android User\" android@example.com,"); |
| // Name in quotes |
| testCreateReplacementChipOriginalText("\"Android User\","); |
| // Name without quotes + email address |
| testCreateReplacementChipOriginalText("Android User <android@example.com>,"); |
| // Name without quotes |
| testCreateReplacementChipOriginalText("Android User,"); |
| // Email address |
| testCreateReplacementChipOriginalText("<android@example.com>,"); |
| // Email address without brackets |
| testCreateReplacementChipOriginalText("android@example.com,"); |
| } |
| |
| private void testCreateReplacementChipOriginalText(final String email) { |
| // No trailing space |
| attemptCreateReplacementChipOriginalText(email.trim()); |
| // Trailing space |
| attemptCreateReplacementChipOriginalText(email.trim() + " "); |
| } |
| |
| private void attemptCreateReplacementChipOriginalText(final String email) { |
| final RecipientEditTextView view = new RecipientEditTextView(getContext(), null); |
| |
| view.setText(email); |
| view.mPendingChips.add(email); |
| |
| view.createReplacementChip(0, email.length(), view.getText(), true); |
| // The "original text" should be the email without the comma or space(s) |
| assertEquals(email.replaceAll(",\\s*$", ""), |
| view.mTemporaryRecipients.get(0).getOriginalText().toString().trim()); |
| } |
| |
| public void testCreateTokenizedEntryForPhone() { |
| final String phonePattern = "[^\\d]*888[^\\d]*555[^\\d]*1234[^\\d]*"; |
| final String phone1 = "8885551234"; |
| final String phone2 = "888-555-1234"; |
| final String phone3 = "(888) 555-1234"; |
| |
| final RecipientEditTextView view = new RecipientEditTextView(getContext(), null); |
| final BaseRecipientAdapter adapter = new TestBaseRecipientAdapter(getContext(), 10, |
| BaseRecipientAdapter.QUERY_TYPE_PHONE); |
| view.setAdapter(adapter); |
| |
| final RecipientEntry entry1 = view.createTokenizedEntry(phone1); |
| final String destination1 = entry1.getDestination(); |
| assertTrue(phone1 + " failed with " + destination1, |
| Pattern.matches(phonePattern, destination1)); |
| |
| final RecipientEntry entry2 = view.createTokenizedEntry(phone2); |
| final String destination2 = entry2.getDestination(); |
| assertTrue(phone2 + " failed with " + destination2, |
| Pattern.matches(phonePattern, destination2)); |
| |
| final RecipientEntry entry3 = view.createTokenizedEntry(phone3); |
| final String destination3 = entry3.getDestination(); |
| assertTrue(phone3 + " failed with " + destination3, |
| Pattern.matches(phonePattern, destination3)); |
| } |
| } |