Home | History | Annotate | Download | only in tests
      1 /*
      2  * Copyright (C) 2014 The Android Open Source Project
      3  *
      4  * Licensed under the Apache License, Version 2.0 (the "License");
      5  * you may not use this file except in compliance with the License.
      6  * You may obtain a copy of the License at
      7  *
      8  *      http://www.apache.org/licenses/LICENSE-2.0
      9  *
     10  * Unless required by applicable law or agreed to in writing, software
     11  * distributed under the License is distributed on an "AS IS" BASIS,
     12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
     13  * See the License for the specific language governing permissions and
     14  * limitations under the License.
     15  */
     16 
     17 package com.android.inputmethod.keyboard.layout.tests;
     18 
     19 import android.util.Log;
     20 import android.view.inputmethod.InputMethodSubtype;
     21 
     22 import com.android.inputmethod.keyboard.Key;
     23 import com.android.inputmethod.keyboard.Keyboard;
     24 import com.android.inputmethod.keyboard.KeyboardId;
     25 import com.android.inputmethod.keyboard.KeyboardLayoutSet;
     26 import com.android.inputmethod.keyboard.KeyboardLayoutSetTestsBase;
     27 import com.android.inputmethod.keyboard.KeyboardTheme;
     28 import com.android.inputmethod.keyboard.layout.LayoutBase;
     29 import com.android.inputmethod.keyboard.layout.expected.AbstractLayoutBase;
     30 import com.android.inputmethod.keyboard.layout.expected.ActualKeyboardBuilder;
     31 import com.android.inputmethod.keyboard.layout.expected.ExpectedKey;
     32 import com.android.inputmethod.keyboard.layout.expected.ExpectedKey.ExpectedAdditionalMoreKey;
     33 import com.android.inputmethod.keyboard.layout.expected.ExpectedKeyboardBuilder;
     34 import com.android.inputmethod.latin.utils.SubtypeLocaleUtils;
     35 
     36 import java.util.Arrays;
     37 
     38 /**
     39  * Base class for keyboard layout unit test.
     40  */
     41 abstract class LayoutTestsBase extends KeyboardLayoutSetTestsBase {
     42     private LayoutBase mLayout;
     43     private InputMethodSubtype mSubtype;
     44     private String mLogTag;
     45     private KeyboardLayoutSet mKeyboardLayoutSet;
     46 
     47     @Override
     48     protected void setUp() throws Exception {
     49         super.setUp();
     50 
     51         mLayout = getLayout();
     52         mSubtype = getSubtype(mLayout.getLocale(), mLayout.getName());
     53         mLogTag = SubtypeLocaleUtils.getSubtypeNameForLogging(mSubtype) + "/"
     54                 + (isPhone() ? "phone" : "tablet");
     55         // TODO: Test with language switch key enabled and disabled.
     56         mKeyboardLayoutSet = createKeyboardLayoutSet(mSubtype, null /* editorInfo */,
     57                 true /* voiceInputKeyEnabled */, true /* languageSwitchKeyEnabled */,
     58                 false /* splitLayoutEnabled */);
     59     }
     60 
     61     @Override
     62     protected int getKeyboardThemeForTests() {
     63         return KeyboardTheme.THEME_ID_KLP;
     64     }
     65 
     66     // Those helper methods have a lower case name to be readable when defining expected keyboard
     67     // layouts.
     68 
     69     // Helper method to create an {@link ExpectedKey} object that has the label.
     70     static ExpectedKey key(final String label, final ExpectedKey ... moreKeys) {
     71         return AbstractLayoutBase.key(label, moreKeys);
     72     }
     73 
     74     // Helper method to create an {@link ExpectedKey} object that has the label and the output text.
     75     static ExpectedKey key(final String label, final String outputText,
     76             final ExpectedKey ... moreKeys) {
     77         return AbstractLayoutBase.key(label, outputText, moreKeys);
     78     }
     79 
     80     // Helper method to create an {@link ExpectedKey} object that has new "more keys".
     81     static ExpectedKey key(final ExpectedKey key, final ExpectedKey ... moreKeys) {
     82         return AbstractLayoutBase.key(key, moreKeys);
     83     }
     84 
     85     // Helper method to create an {@link ExpectedAdditionalMoreKey} object for an
     86     // "additional more key" that has the label.
     87     public static ExpectedAdditionalMoreKey additionalMoreKey(final String label) {
     88         return AbstractLayoutBase.additionalMoreKey(label);
     89     }
     90 
     91     // Helper method to create an {@link ExpectedKey} object for a "more key" that has the label.
     92     static ExpectedKey moreKey(final String label) {
     93         return AbstractLayoutBase.moreKey(label);
     94     }
     95 
     96     // Helper method to create an {@link ExpectedKey} object for a "more key" that has the label
     97     // and the output text.
     98     static ExpectedKey moreKey(final String label, final String outputText) {
     99         return AbstractLayoutBase.moreKey(label, outputText);
    100     }
    101 
    102     // Helper method to create {@link ExpectedKey} array by joining {@link ExpectedKey},
    103     // {@link ExpectedKey} array, and {@link String}.
    104     static ExpectedKey[] joinMoreKeys(final Object ... moreKeys) {
    105         return AbstractLayoutBase.joinKeys(moreKeys);
    106     }
    107 
    108     // Helper method to create {@link ExpectedKey} array by joining {@link ExpectedKey},
    109     // {@link ExpectedKey} array, and {@link String}.
    110     static ExpectedKey[] joinKeys(final Object ... keys) {
    111         return AbstractLayoutBase.joinKeys(keys);
    112     }
    113 
    114     // Keyboard layout for testing subtype.
    115     abstract LayoutBase getLayout();
    116 
    117     ExpectedKeyboardBuilder setAccentedLetters(final ExpectedKeyboardBuilder builder) {
    118         return builder;
    119     }
    120 
    121     // TODO: Add phone, phone symbols, number, number password layout tests.
    122 
    123     public final void testLayouts() {
    124         doKeyboardTests(KeyboardId.ELEMENT_ALPHABET);
    125         doKeyboardTests(KeyboardId.ELEMENT_ALPHABET_AUTOMATIC_SHIFTED);
    126         doKeyboardTests(KeyboardId.ELEMENT_ALPHABET_MANUAL_SHIFTED);
    127         doKeyboardTests(KeyboardId.ELEMENT_ALPHABET_SHIFT_LOCKED);
    128         doKeyboardTests(KeyboardId.ELEMENT_ALPHABET_SHIFT_LOCK_SHIFTED);
    129         doKeyboardTests(KeyboardId.ELEMENT_SYMBOLS);
    130         doKeyboardTests(KeyboardId.ELEMENT_SYMBOLS_SHIFTED);
    131     }
    132 
    133     // Comparing expected keyboard and actual keyboard.
    134     private void doKeyboardTests(final int elementId) {
    135         final ExpectedKey[][] expectedKeyboard = mLayout.getLayout(isPhone(), elementId);
    136         // Skip test if no keyboard is defined.
    137         if (expectedKeyboard == null) {
    138             return;
    139         }
    140         final String tag = mLogTag + "/" + KeyboardId.elementIdToName(elementId);
    141         // Create actual keyboard object.
    142         final Keyboard keyboard = mKeyboardLayoutSet.getKeyboard(elementId);
    143         // Create actual keyboard to be compared with the expected keyboard.
    144         final Key[][] actualKeyboard = ActualKeyboardBuilder.buildKeyboard(
    145                 keyboard.getSortedKeys());
    146 
    147         // Dump human readable definition of expected/actual keyboards.
    148         Log.d(tag, "expected=\n" + ExpectedKeyboardBuilder.toString(expectedKeyboard));
    149         Log.d(tag, "actual  =\n" + ActualKeyboardBuilder.toString(actualKeyboard));
    150         // Test both keyboards have the same number of rows.
    151         assertEquals(tag + " labels"
    152                 + "\nexpected=" + ExpectedKeyboardBuilder.toString(expectedKeyboard)
    153                 + "\nactual  =" + ActualKeyboardBuilder.toString(actualKeyboard),
    154                 expectedKeyboard.length, actualKeyboard.length);
    155         for (int r = 0; r < actualKeyboard.length; r++) {
    156             final int row = r + 1;
    157             // Test both keyboards' rows have the same number of columns.
    158             assertEquals(tag + " labels row=" + row
    159                     + "\nexpected=" + Arrays.toString(expectedKeyboard[r])
    160                     + "\nactual  =" + ActualKeyboardBuilder.toString(actualKeyboard[r]),
    161                     expectedKeyboard[r].length, actualKeyboard[r].length);
    162             for (int c = 0; c < actualKeyboard[r].length; c++) {
    163                 final int column = c + 1;
    164                 final Key actualKey = actualKeyboard[r][c];
    165                 final ExpectedKey expectedKey = expectedKeyboard[r][c];
    166                 // Test both keyboards' keys have the same visual outlook and key output.
    167                 assertTrue(tag + " labels row,column=" + row + "," + column
    168                         + "\nexpected=" + expectedKey
    169                         + "\nactual  =" + ActualKeyboardBuilder.toString(actualKey),
    170                         expectedKey.equalsTo(actualKey));
    171             }
    172         }
    173     }
    174 }
    175