aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--java/src/com/android/inputmethod/dictionarypack/DictionarySettingsFragment.java14
-rw-r--r--java/src/com/android/inputmethod/dictionarypack/WordListPreference.java5
-rw-r--r--native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.cpp60
-rw-r--r--native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.h5
-rw-r--r--tests/src/com/android/inputmethod/latin/makedict/BinaryDictDecoderEncoderTests.java36
-rw-r--r--tests/src/com/android/inputmethod/latin/settings/SpacingAndPunctuationsTests.java40
6 files changed, 139 insertions, 21 deletions
diff --git a/java/src/com/android/inputmethod/dictionarypack/DictionarySettingsFragment.java b/java/src/com/android/inputmethod/dictionarypack/DictionarySettingsFragment.java
index 7bbd041e7..d18639741 100644
--- a/java/src/com/android/inputmethod/dictionarypack/DictionarySettingsFragment.java
+++ b/java/src/com/android/inputmethod/dictionarypack/DictionarySettingsFragment.java
@@ -317,15 +317,19 @@ public final class DictionarySettingsFragment extends PreferenceFragment
final WordListPreference pref;
if (null != oldPreference
&& oldPreference.mVersion == version
+ && oldPreference.hasStatus(status)
&& oldPreference.mLocale.equals(locale)) {
- // If the old preference has all the new attributes, reuse it. We test
- // for version and locale because although attributes other than status
- // need to be the same, others have been tested through the key of the
- // map. Also, status may differ so we don't want to use #equals() here.
+ // If the old preference has all the new attributes, reuse it. Ideally, we
+ // should reuse the old pref even if its status is different and call
+ // setStatus here, but setStatus calls Preference#setSummary() which needs
+ // to be done on the UI thread and we're not on the UI thread here. We
+ // could do all this work on the UI thread, but in this case it's probably
+ // lighter to stay on a background thread and throw this old preference out.
pref = oldPreference;
- pref.setStatus(status);
} else {
// Otherwise, discard it and create a new one instead.
+ // TODO: when the status is different from the old one, we need to
+ // animate the old one out before animating the new one in.
pref = new WordListPreference(activity, mDictionaryListInterfaceState,
mClientId, wordlistId, version, locale, description, status,
filesize);
diff --git a/java/src/com/android/inputmethod/dictionarypack/WordListPreference.java b/java/src/com/android/inputmethod/dictionarypack/WordListPreference.java
index ba1fce1a8..aea16af0d 100644
--- a/java/src/com/android/inputmethod/dictionarypack/WordListPreference.java
+++ b/java/src/com/android/inputmethod/dictionarypack/WordListPreference.java
@@ -98,6 +98,10 @@ public final class WordListPreference extends Preference {
setSummary(getSummary(status));
}
+ public boolean hasStatus(final int status) {
+ return status == mStatus;
+ }
+
@Override
public View onCreateView(final ViewGroup parent) {
final View orphanedView = mInterfaceState.findFirstOrphanedView();
@@ -217,6 +221,7 @@ public final class WordListPreference extends Preference {
progressBar.setIds(mClientId, mWordlistId);
progressBar.setMax(mFilesize);
final boolean showProgressBar = (MetadataDbHelper.STATUS_DOWNLOADING == mStatus);
+ setSummary(getSummary(mStatus));
status.setVisibility(showProgressBar ? View.INVISIBLE : View.VISIBLE);
progressBar.setVisibility(showProgressBar ? View.VISIBLE : View.INVISIBLE);
diff --git a/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.cpp b/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.cpp
index 8172e70b6..bf38dffa5 100644
--- a/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.cpp
+++ b/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.cpp
@@ -20,6 +20,7 @@
#include "defines.h"
#include "suggest/core/dicnode/dic_node.h"
#include "suggest/core/dicnode/dic_node_vector.h"
+#include "suggest/core/dictionary/binary_dictionary_bigrams_iterator.h"
#include "suggest/policyimpl/dictionary/structure/pt_common/dynamic_pt_reading_helper.h"
#include "suggest/policyimpl/dictionary/structure/v2/patricia_trie_reading_utils.h"
#include "suggest/policyimpl/dictionary/utils/probability_utils.h"
@@ -303,4 +304,63 @@ int PatriciaTriePolicy::createAndGetLeavingChildNode(const DicNode *const dicNod
return siblingPos;
}
+const WordProperty PatriciaTriePolicy::getWordProperty(const int *const codePoints,
+ const int codePointCount) const {
+ const int ptNodePos = getTerminalPtNodePositionOfWord(codePoints, codePointCount,
+ false /* forceLowerCaseSearch */);
+ if (ptNodePos == NOT_A_DICT_POS) {
+ AKLOGE("getWordProperty was called for invalid word.");
+ return WordProperty();
+ }
+ const PtNodeParams ptNodeParams = mPtNodeReader.fetchNodeInfoInBufferFromPtNodePos(ptNodePos);
+ std::vector<int> codePointVector(ptNodeParams.getCodePoints(),
+ ptNodeParams.getCodePoints() + ptNodeParams.getCodePointCount());
+ // Fetch bigram information.
+ std::vector<WordProperty::BigramProperty> bigrams;
+ const int bigramListPos = getBigramsPositionOfPtNode(ptNodePos);
+ int bigramWord1CodePoints[MAX_WORD_LENGTH];
+ BinaryDictionaryBigramsIterator bigramsIt(getBigramsStructurePolicy(), bigramListPos);
+ while (bigramsIt.hasNext()) {
+ // Fetch the next bigram information and forward the iterator.
+ bigramsIt.next();
+ // Skip the entry if the entry has been deleted. This never happens for ver2 dicts.
+ if (bigramsIt.getBigramPos() != NOT_A_DICT_POS) {
+ int word1Probability = NOT_A_PROBABILITY;
+ int word1CodePointCount = getCodePointsAndProbabilityAndReturnCodePointCount(
+ bigramsIt.getBigramPos(), MAX_WORD_LENGTH, bigramWord1CodePoints,
+ &word1Probability);
+ std::vector<int> word1(bigramWord1CodePoints,
+ bigramWord1CodePoints + word1CodePointCount);
+ bigrams.push_back(WordProperty::BigramProperty(&word1, bigramsIt.getProbability(),
+ NOT_A_TIMESTAMP /* timestamp */, 0 /* level */, 0 /* count */));
+ }
+ }
+ // Fetch shortcut information.
+ std::vector<WordProperty::ShortcutProperty> shortcuts;
+ int shortcutPos = getShortcutPositionOfPtNode(ptNodePos);
+ if (shortcutPos != NOT_A_DICT_POS) {
+ int shortcutTargetCodePoints[MAX_WORD_LENGTH];
+ ShortcutListReadingUtils::getShortcutListSizeAndForwardPointer(mDictRoot, &shortcutPos);
+ bool hasNext = true;
+ while (hasNext) {
+ const ShortcutListReadingUtils::ShortcutFlags shortcutFlags =
+ ShortcutListReadingUtils::getFlagsAndForwardPointer(mDictRoot, &shortcutPos);
+ hasNext = ShortcutListReadingUtils::hasNext(shortcutFlags);
+ const int shortcutTargetLength = ShortcutListReadingUtils::readShortcutTarget(
+ mDictRoot, MAX_WORD_LENGTH, shortcutTargetCodePoints, &shortcutPos);
+ std::vector<int> shortcutTarget(shortcutTargetCodePoints,
+ shortcutTargetCodePoints + shortcutTargetLength);
+ const int shortcutProbability =
+ ShortcutListReadingUtils::getProbabilityFromFlags(shortcutFlags);
+ shortcuts.push_back(
+ WordProperty::ShortcutProperty(&shortcutTarget, shortcutProbability));
+ }
+ }
+ return WordProperty(&codePointVector, ptNodeParams.isNotAWord(),
+ ptNodeParams.isBlacklisted(), ptNodeParams.hasBigrams(),
+ ptNodeParams.hasShortcutTargets(), ptNodeParams.getProbability(),
+ NOT_A_TIMESTAMP /* timestamp */, 0 /* level */, 0 /* count */,
+ &bigrams, &shortcuts);
+}
+
} // namespace latinime
diff --git a/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.h b/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.h
index 1ce7f85d4..da4be87ce 100644
--- a/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.h
+++ b/native/jni/src/suggest/policyimpl/dictionary/structure/v2/patricia_trie_policy.h
@@ -128,10 +128,7 @@ class PatriciaTriePolicy : public DictionaryStructureWithBufferPolicy {
}
const WordProperty getWordProperty(const int *const codePoints,
- const int codePointCount) const {
- // getWordProperty is not supported.
- return WordProperty();
- }
+ const int codePointCount) const;
int getNextWordAndNextToken(const int token, int *const outCodePoints) {
// getNextWordAndNextToken is not supported.
diff --git a/tests/src/com/android/inputmethod/latin/makedict/BinaryDictDecoderEncoderTests.java b/tests/src/com/android/inputmethod/latin/makedict/BinaryDictDecoderEncoderTests.java
index 141730de9..28388b4a0 100644
--- a/tests/src/com/android/inputmethod/latin/makedict/BinaryDictDecoderEncoderTests.java
+++ b/tests/src/com/android/inputmethod/latin/makedict/BinaryDictDecoderEncoderTests.java
@@ -39,6 +39,7 @@ import java.util.Arrays;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
+import java.util.Locale;
import java.util.Map.Entry;
import java.util.Random;
import java.util.Set;
@@ -596,4 +597,39 @@ public class BinaryDictDecoderEncoderTests extends AndroidTestCase {
Log.d(TAG, result);
}
}
+
+ public void testVer2DictGetWordProperty() {
+ final FormatOptions formatOptions = BinaryDictUtils.VERSION2_OPTIONS;
+ final ArrayList<String> words = sWords;
+ final HashMap<String, List<String>> shortcuts = sShortcuts;
+ final String dictName = "testGetWordProperty";
+ final String dictVersion = Long.toString(System.currentTimeMillis());
+ final FusionDictionary dict = new FusionDictionary(new PtNodeArray(),
+ BinaryDictUtils.makeDictionaryOptions(dictName, dictVersion, formatOptions));
+ addUnigrams(words.size(), dict, words, shortcuts);
+ addBigrams(dict, words, sEmptyBigrams);
+ final File file = BinaryDictUtils.getDictFile(dictName, dictVersion, formatOptions,
+ getContext().getCacheDir());
+ file.delete();
+ timeWritingDictToFile(file, dict, formatOptions);
+ final BinaryDictionary binaryDictionary = new BinaryDictionary(file.getAbsolutePath(),
+ 0 /* offset */, file.length(), true /* useFullEditDistance */,
+ Locale.ENGLISH, dictName, false /* isUpdatable */);
+ for (final String word : words) {
+ final WordProperty wordProperty = binaryDictionary.getWordProperty(word);
+ assertEquals(word, wordProperty.mWord);
+ assertEquals(UNIGRAM_FREQ, wordProperty.getProbability());
+ if (shortcuts.containsKey(word)) {
+ assertEquals(shortcuts.get(word).size(), wordProperty.mShortcutTargets.size());
+ final List<String> shortcutList = shortcuts.get(word);
+ assertTrue(wordProperty.mHasShortcuts);
+ for (final WeightedString shortcutTarget : wordProperty.mShortcutTargets) {
+ assertTrue(shortcutList.contains(shortcutTarget.mWord));
+ assertEquals(UNIGRAM_FREQ, shortcutTarget.getProbability());
+ shortcutList.remove(shortcutTarget.mWord);
+ }
+ assertTrue(shortcutList.isEmpty());
+ }
+ }
+ }
}
diff --git a/tests/src/com/android/inputmethod/latin/settings/SpacingAndPunctuationsTests.java b/tests/src/com/android/inputmethod/latin/settings/SpacingAndPunctuationsTests.java
index 09920bfe9..24af09484 100644
--- a/tests/src/com/android/inputmethod/latin/settings/SpacingAndPunctuationsTests.java
+++ b/tests/src/com/android/inputmethod/latin/settings/SpacingAndPunctuationsTests.java
@@ -373,37 +373,53 @@ public class SpacingAndPunctuationsTests extends AndroidTestCase {
assertTrue(SWISS_GERMAN.mUsesGermanRules);
}
- private static final String[] PUNCTUATION_LABELS = {
+ private static final String[] PUNCTUATION_LABELS_LTR = {
"!", "?", ",", ":", ";", "\"", "(", ")", "'", "-", "/", "@", "_"
};
- private static final String[] PUNCTUATION_WORDS_LTR = PUNCTUATION_LABELS;
- private static final String[] PUNCTUATION_WORDS_RTL = {
+ private static final String[] PUNCTUATION_WORDS_LTR = PUNCTUATION_LABELS_LTR;
+ private static final String[] PUNCTUATION_WORDS_HEBREW = {
"!", "?", ",", ":", ";", "\"", ")", "(", "'", "-", "/", "@", "_"
};
+ // U+061F: "؟" ARABIC QUESTION MARK
+ // U+060C: "،" ARABIC COMMA
+ // U+061B: "؛" ARABIC SEMICOLON
+ private static final String[] PUNCTUATION_LABELS_ARABIC_PERSIAN = {
+ "!", "\u061F", "\u060C", ":", "\u061B", "\"", "(", ")", "'", "-", "/", "@", "_"
+ };
+ private static final String[] PUNCTUATION_WORDS_ARABIC_PERSIAN = {
+ "!", "\u061F", "\u060C", ":", "\u061B", "\"", ")", "(", "'", "-", "/", "@", "_"
+ };
private static void testingStandardPunctuationSuggestions(final SpacingAndPunctuations sp,
- final String[] punctuationWords) {
+ final String[] punctuationLabels, final String[] punctuationWords) {
final SuggestedWords suggestedWords = sp.mSuggestPuncList;
assertFalse("typedWordValid", suggestedWords.mTypedWordValid);
assertFalse("willAutoCorrect", suggestedWords.mWillAutoCorrect);
assertTrue("isPunctuationSuggestions", suggestedWords.isPunctuationSuggestions());
assertFalse("isObsoleteSuggestions", suggestedWords.mIsObsoleteSuggestions);
assertFalse("isPrediction", suggestedWords.mIsPrediction);
- assertEquals("size", PUNCTUATION_LABELS.length, suggestedWords.size());
+ assertEquals("size", punctuationLabels.length, suggestedWords.size());
for (int index = 0; index < suggestedWords.size(); index++) {
assertEquals("punctuation label at " + index,
- PUNCTUATION_LABELS[index], suggestedWords.getLabel(index));
+ punctuationLabels[index], suggestedWords.getLabel(index));
assertEquals("punctuation word at " + index,
punctuationWords[index], suggestedWords.getWord(index));
}
}
+ // TODO: Add tests for tablet as well
public void testPunctuationSuggestions() {
- testingStandardPunctuationSuggestions(ENGLISH, PUNCTUATION_WORDS_LTR);
- testingStandardPunctuationSuggestions(FRENCH, PUNCTUATION_WORDS_LTR);
- testingStandardPunctuationSuggestions(GERMAN, PUNCTUATION_WORDS_LTR);
- testingStandardPunctuationSuggestions(ARABIC, PUNCTUATION_WORDS_RTL);
- testingStandardPunctuationSuggestions(PERSIAN, PUNCTUATION_WORDS_RTL);
- testingStandardPunctuationSuggestions(HEBREW, PUNCTUATION_WORDS_RTL);
+ testingStandardPunctuationSuggestions(ENGLISH,
+ PUNCTUATION_LABELS_LTR, PUNCTUATION_WORDS_LTR);
+ testingStandardPunctuationSuggestions(FRENCH,
+ PUNCTUATION_LABELS_LTR, PUNCTUATION_WORDS_LTR);
+ testingStandardPunctuationSuggestions(GERMAN,
+ PUNCTUATION_LABELS_LTR, PUNCTUATION_WORDS_LTR);
+ testingStandardPunctuationSuggestions(ARABIC,
+ PUNCTUATION_LABELS_ARABIC_PERSIAN, PUNCTUATION_WORDS_ARABIC_PERSIAN);
+ testingStandardPunctuationSuggestions(PERSIAN,
+ PUNCTUATION_LABELS_ARABIC_PERSIAN, PUNCTUATION_WORDS_ARABIC_PERSIAN);
+ testingStandardPunctuationSuggestions(HEBREW,
+ PUNCTUATION_LABELS_LTR, PUNCTUATION_WORDS_HEBREW);
}
}