diff --git a/java/res/values/styles.xml b/java/res/values/styles.xml
index dbb56ab..4766a22 100644
--- a/java/res/values/styles.xml
+++ b/java/res/values/styles.xml
@@ -124,6 +124,7 @@
         <item name="keyboardTopPadding">0dp</item>
         <item name="keyboardBottomPadding">0dp</item>
         <item name="horizontalGap">0dp</item>
+        <item name="touchPositionCorrectionData">@null</item>
     </style>
     <style
         name="MoreKeysKeyboardView"
@@ -231,6 +232,7 @@
         <item name="keyboardTopPadding">0dp</item>
         <item name="keyboardBottomPadding">0dp</item>
         <item name="horizontalGap">0dp</item>
+        <item name="touchPositionCorrectionData">@null</item>
     </style>
     <style
         name="MoreKeysKeyboardView.Stone"
@@ -300,6 +302,7 @@
         <item name="keyboardTopPadding">0dp</item>
         <item name="keyboardBottomPadding">0dp</item>
         <item name="horizontalGap">0dp</item>
+        <item name="touchPositionCorrectionData">@null</item>
     </style>
     <style
         name="MoreKeysKeyboardView.Gingerbread"
@@ -355,6 +358,7 @@
         <item name="keyboardTopPadding">0dp</item>
         <item name="keyboardBottomPadding">0dp</item>
         <item name="horizontalGap">0dp</item>
+        <item name="touchPositionCorrectionData">@null</item>
     </style>
     <style
         name="MoreKeysKeyboardView.IceCreamSandwich"
diff --git a/java/res/xml/key_styles_currency.xml b/java/res/xml/key_styles_currency.xml
index 6dea16f..1dadbe0 100644
--- a/java/res/xml/key_styles_currency.xml
+++ b/java/res/xml/key_styles_currency.xml
@@ -53,13 +53,13 @@
              22. Spain (es_ES, ca_ES)
              23. Vatican City (it_VA)
         -->
-        <!-- Though Denmark and Turkey don't using Euro as their currencies, but having Euro sign on
-             the symbol keyboard might be useful.  Especially Danish krone (kr) and Turkish lira
-             (TL) can be represented by usual alphabet letters. -->
+        <!-- Though Denmark, Sweden and Turkey don't use Euro as their currency, having the Euro
+             sign on the symbol keyboard might be useful.  Especially Danish krone (kr), Swedish
+             krona (kr) and Turkish lira (TL) can be represented by usual alphabet letters. -->
         <!-- Note: Some locales may not have country code, and it it supposed to indicate the
              country where the language originally/mainly spoken. -->
         <case
-            latin:localeCode="da|de|es|el|fi|fr|it|nl|sk|sl|pt_PT|tr"
+            latin:localeCode="da|de|es|el|fi|fr|it|nl|sk|sl|sv|pt_PT|tr"
         >
             <include
                 latin:keyboardLayout="@xml/key_styles_currency_euro" />
diff --git a/java/res/xml/rows_number_normal.xml b/java/res/xml/rows_number_normal.xml
index c59e262..b77544b 100644
--- a/java/res/xml/rows_number_normal.xml
+++ b/java/res/xml/rows_number_normal.xml
@@ -33,6 +33,8 @@
             latin:keyStyle="numKeyStyle" />
         <Key
             latin:keyLabel="-"
+            latin:moreKeys="+"
+            latin:keyLabelFlags="hasPopupHint"
             latin:keyStyle="numFunctionalKeyStyle"
             latin:keyWidth="fillRight" />
     </Row>
diff --git a/java/res/xml/rows_phone.xml b/java/res/xml/rows_phone.xml
index 630b24e..9299c2a 100644
--- a/java/res/xml/rows_phone.xml
+++ b/java/res/xml/rows_phone.xml
@@ -34,6 +34,8 @@
             latin:keyStyle="num3KeyStyle" />
         <Key
             latin:keyLabel="-"
+            latin:moreKeys="+"
+            latin:keyLabelFlags="hasPopupHint"
             latin:keyStyle="numFunctionalKeyStyle"
             latin:keyWidth="fillRight" />
     </Row>
diff --git a/java/res/xml/rows_phone_symbols.xml b/java/res/xml/rows_phone_symbols.xml
index 7841c56..c13018e 100644
--- a/java/res/xml/rows_phone_symbols.xml
+++ b/java/res/xml/rows_phone_symbols.xml
@@ -37,6 +37,8 @@
             latin:keyStyle="numKeyStyle" />
         <Key
             latin:keyLabel="-"
+            latin:moreKeys="+"
+            latin:keyLabelFlags="hasPopupHint"
             latin:keyStyle="numFunctionalKeyStyle"
             latin:keyWidth="fillRight" />
     </Row>
diff --git a/java/src/com/android/inputmethod/compat/SuggestionSpanUtils.java b/java/src/com/android/inputmethod/compat/SuggestionSpanUtils.java
index 159f436..9a89eed 100644
--- a/java/src/com/android/inputmethod/compat/SuggestionSpanUtils.java
+++ b/java/src/com/android/inputmethod/compat/SuggestionSpanUtils.java
@@ -108,8 +108,8 @@
             CharSequence pickedWord, SuggestedWords suggestedWords, boolean dictionaryAvailable) {
         if (!dictionaryAvailable || TextUtils.isEmpty(pickedWord)
                 || CONSTRUCTOR_SuggestionSpan == null
-                || suggestedWords == null || suggestedWords.size() == 0
-                || suggestedWords.mIsPrediction || suggestedWords.mIsPunctuationSuggestions
+                || suggestedWords.isEmpty() || suggestedWords.mIsPrediction
+                || suggestedWords.mIsPunctuationSuggestions
                 || OBJ_SUGGESTIONS_MAX_SIZE == null) {
             return pickedWord;
         }
diff --git a/java/src/com/android/inputmethod/keyboard/PointerTracker.java b/java/src/com/android/inputmethod/keyboard/PointerTracker.java
index d0f7cb2..92e1f54 100644
--- a/java/src/com/android/inputmethod/keyboard/PointerTracker.java
+++ b/java/src/com/android/inputmethod/keyboard/PointerTracker.java
@@ -702,6 +702,7 @@
             sLastRecognitionTime = 0;
             mListener.onStartBatchInput();
         }
+        mTimerProxy.cancelLongPressTimer();
         final boolean isOldestTracker = sPointerTrackerQueue.getOldestElement() == this;
         mDrawingProxy.showGesturePreviewTrail(this, isOldestTracker);
     }
@@ -807,9 +808,9 @@
         if (!sShouldHandleGesture) {
             return;
         }
-        // A gesture should start only from the letter key.
+        // A gesture should start only from a non-modifier key.
         mIsDetectingGesture = (mKeyboard != null) && mKeyboard.mId.isAlphabetKeyboard()
-                && !mIsShowingMoreKeysPanel && key != null && Keyboard.isLetterCode(key.mCode);
+                && !mIsShowingMoreKeysPanel && key != null && !key.isModifier();
         if (mIsDetectingGesture) {
             if (getActivePointerTrackerCount() == 1) {
                 sGestureFirstDownTime = eventTime;
@@ -901,7 +902,6 @@
             // Register move event on gesture tracker.
             onGestureMoveEvent(x, y, eventTime, true /* isMajorEvent */, key);
             if (sInGesture) {
-                mTimerProxy.cancelLongPressTimer();
                 mCurrentKey = null;
                 setReleasedKeyGraphics(oldKey);
                 return;
diff --git a/java/src/com/android/inputmethod/keyboard/ProximityInfo.java b/java/src/com/android/inputmethod/keyboard/ProximityInfo.java
index 06a9e92..94fc805 100644
--- a/java/src/com/android/inputmethod/keyboard/ProximityInfo.java
+++ b/java/src/com/android/inputmethod/keyboard/ProximityInfo.java
@@ -18,6 +18,7 @@
 
 import android.graphics.Rect;
 import android.text.TextUtils;
+import android.util.Log;
 
 import com.android.inputmethod.keyboard.internal.TouchPositionCorrection;
 import com.android.inputmethod.latin.Constants;
@@ -26,11 +27,14 @@
 import java.util.Arrays;
 
 public final class ProximityInfo {
+    private static final String TAG = ProximityInfo.class.getSimpleName();
+    private static final boolean DEBUG = false;
+
     /** MAX_PROXIMITY_CHARS_SIZE must be the same as MAX_PROXIMITY_CHARS_SIZE_INTERNAL
      * in defines.h */
     public static final int MAX_PROXIMITY_CHARS_SIZE = 16;
     /** Number of key widths from current touch point to search for nearest keys. */
-    private static float SEARCH_DISTANCE = 1.2f;
+    private static final float SEARCH_DISTANCE = 1.2f;
     private static final Key[] EMPTY_KEY_ARRAY = new Key[0];
     private static final float DEFAULT_TOUCH_POSITION_CORRECTION_RADIUS = 0.15f;
 
@@ -140,9 +144,13 @@
         }
 
         if (touchPositionCorrection != null && touchPositionCorrection.isValid()) {
+            if (DEBUG) {
+                Log.d(TAG, "touchPositionCorrection: ON");
+            }
             sweetSpotCenterXs = new float[keyCount];
             sweetSpotCenterYs = new float[keyCount];
             sweetSpotRadii = new float[keyCount];
+            final int rows = touchPositionCorrection.getRows();
             final float defaultRadius = DEFAULT_TOUCH_POSITION_CORRECTION_RADIUS
                     * (float)Math.hypot(mMostCommonKeyWidth, mMostCommonKeyHeight);
             for (int i = 0; i < keyCount; i++) {
@@ -152,7 +160,7 @@
                 sweetSpotCenterYs[i] = hitBox.exactCenterY();
                 sweetSpotRadii[i] = defaultRadius;
                 final int row = hitBox.top / mMostCommonKeyHeight;
-                if (row < touchPositionCorrection.getRows()) {
+                if (row < rows) {
                     final int hitBoxWidth = hitBox.width();
                     final int hitBoxHeight = hitBox.height();
                     final float hitBoxDiagonal = (float)Math.hypot(hitBoxWidth, hitBoxHeight);
@@ -160,9 +168,18 @@
                     sweetSpotCenterYs[i] += touchPositionCorrection.getY(row) * hitBoxHeight;
                     sweetSpotRadii[i] = touchPositionCorrection.getRadius(row) * hitBoxDiagonal;
                 }
+                if (DEBUG) {
+                    Log.d(TAG, String.format(
+                            "  [%2d] row=%d x/y/r=%7.2f/%7.2f/%5.2f %s code=%s", i, row,
+                            sweetSpotCenterXs[i], sweetSpotCenterYs[i], sweetSpotRadii[i],
+                            row < rows ? "correct" : "default", Keyboard.printableCode(key.mCode)));
+                }
             }
         } else {
             sweetSpotCenterXs = sweetSpotCenterYs = sweetSpotRadii = null;
+            if (DEBUG) {
+                Log.d(TAG, "touchPositionCorrection: OFF");
+            }
         }
 
         return setProximityInfoNative(mLocaleStr, MAX_PROXIMITY_CHARS_SIZE,
diff --git a/java/src/com/android/inputmethod/latin/BinaryDictionary.java b/java/src/com/android/inputmethod/latin/BinaryDictionary.java
index 7184f1d..9c48aa1 100644
--- a/java/src/com/android/inputmethod/latin/BinaryDictionary.java
+++ b/java/src/com/android/inputmethod/latin/BinaryDictionary.java
@@ -31,7 +31,7 @@
  * Implements a static, compacted, binary dictionary of standard words.
  */
 public final class BinaryDictionary extends Dictionary {
-
+    private static final String TAG = BinaryDictionary.class.getSimpleName();
     public static final String DICTIONARY_PACK_AUTHORITY =
             "com.android.inputmethod.latin.dictionarypack";
 
@@ -45,12 +45,9 @@
     public static final int MAX_WORDS = 18;
     public static final int MAX_SPACES = 16;
 
-    private static final String TAG = BinaryDictionary.class.getSimpleName();
     private static final int MAX_PREDICTIONS = 60;
     private static final int MAX_RESULTS = Math.max(MAX_PREDICTIONS, MAX_WORDS);
 
-    private static final int TYPED_LETTER_MULTIPLIER = 2;
-
     private long mNativeDict;
     private final Locale mLocale;
     private final int[] mInputCodePoints = new int[MAX_WORD_LENGTH];
@@ -106,8 +103,7 @@
     }
 
     private native long openNative(String sourceDir, long dictOffset, long dictSize,
-            int typedLetterMultiplier, int fullWordMultiplier, int maxWordLength, int maxWords,
-            int maxPredictions);
+            int fullWordMultiplier, int maxWordLength, int maxWords, int maxPredictions);
     private native void closeNative(long dict);
     private native int getFrequencyNative(long dict, int[] word);
     private native boolean isValidBigramNative(long dict, int[] word1, int[] word2);
@@ -121,8 +117,8 @@
 
     // TODO: Move native dict into session
     private final void loadDictionary(String path, long startOffset, long length) {
-        mNativeDict = openNative(path, startOffset, length, TYPED_LETTER_MULTIPLIER,
-                FULL_WORD_SCORE_MULTIPLIER, MAX_WORD_LENGTH, MAX_WORDS, MAX_PREDICTIONS);
+        mNativeDict = openNative(path, startOffset, length, FULL_WORD_SCORE_MULTIPLIER,
+                MAX_WORD_LENGTH, MAX_WORDS, MAX_PREDICTIONS);
     }
 
     @Override
diff --git a/java/src/com/android/inputmethod/latin/BinaryDictionaryFileDumper.java b/java/src/com/android/inputmethod/latin/BinaryDictionaryFileDumper.java
index b0b65ed..bed31a7 100644
--- a/java/src/com/android/inputmethod/latin/BinaryDictionaryFileDumper.java
+++ b/java/src/com/android/inputmethod/latin/BinaryDictionaryFileDumper.java
@@ -149,7 +149,13 @@
 
         final Uri.Builder wordListUriBuilder = getProviderUriBuilder(id);
         final String finalFileName = BinaryDictionaryGetter.getCacheFileName(id, locale, context);
-        final String tempFileName = BinaryDictionaryGetter.getTempFileName(id, context);
+        String tempFileName;
+        try {
+            tempFileName = BinaryDictionaryGetter.getTempFileName(id, context);
+        } catch (IOException e) {
+            Log.e(TAG, "Can't open the temporary file", e);
+            return null;
+        }
 
         for (int mode = MODE_MIN; mode <= MODE_MAX; ++mode) {
             InputStream originalSourceStream = null;
diff --git a/java/src/com/android/inputmethod/latin/BinaryDictionaryGetter.java b/java/src/com/android/inputmethod/latin/BinaryDictionaryGetter.java
index c747dc6..ecb61b4 100644
--- a/java/src/com/android/inputmethod/latin/BinaryDictionaryGetter.java
+++ b/java/src/com/android/inputmethod/latin/BinaryDictionaryGetter.java
@@ -165,14 +165,9 @@
 
     /**
      * Generates a unique temporary file name in the app cache directory.
-     *
-     * This is unique as long as it doesn't get called twice in the same millisecond by the same
-     * thread, which should be more than enough for our purposes.
      */
-    public static String getTempFileName(String id, Context context) {
-        final String fileName = replaceFileNameDangerousCharacters(id);
-        return context.getCacheDir() + File.separator + fileName + "."
-                + Thread.currentThread().getId() + "." + System.currentTimeMillis();
+    public static String getTempFileName(String id, Context context) throws IOException {
+        return File.createTempFile(replaceFileNameDangerousCharacters(id), null).getAbsolutePath();
     }
 
     /**
diff --git a/java/src/com/android/inputmethod/latin/LatinIME.java b/java/src/com/android/inputmethod/latin/LatinIME.java
index c1b1751..044d6de 100644
--- a/java/src/com/android/inputmethod/latin/LatinIME.java
+++ b/java/src/com/android/inputmethod/latin/LatinIME.java
@@ -1524,8 +1524,8 @@
 
     private void showGesturePreviewAndSuggestionStrip(final SuggestedWords suggestedWords,
             final boolean dismissGestureFloatingPreviewText) {
-        final String batchInputText = (suggestedWords.size() > 0)
-                ? suggestedWords.getWord(0) : null;
+        final String batchInputText = suggestedWords.isEmpty()
+                ? null : suggestedWords.getWord(0);
         final KeyboardView mainKeyboardView = mKeyboardSwitcher.getMainKeyboardView();
         mainKeyboardView.showGestureFloatingPreviewText(batchInputText);
         showSuggestionStrip(suggestedWords, null);
@@ -1543,8 +1543,8 @@
     public void onEndBatchInput(final InputPointers batchPointers) {
         final SuggestedWords suggestedWords = BatchInputUpdater.getInstance().onEndBatchInput(
                 batchPointers, this);
-        final String batchInputText = (suggestedWords.size() > 0)
-                ? suggestedWords.getWord(0) : null;
+        final String batchInputText = suggestedWords.isEmpty()
+                ? null : suggestedWords.getWord(0);
         if (TextUtils.isEmpty(batchInputText)) {
             return;
         }
@@ -1970,19 +1970,15 @@
 
     private void showSuggestionStrip(final SuggestedWords suggestedWords,
             final CharSequence typedWord) {
-        if (null == suggestedWords || suggestedWords.size() <= 0) {
+        if (suggestedWords.isEmpty()) {
             clearSuggestionStrip();
             return;
         }
         final CharSequence autoCorrection;
-        if (suggestedWords.size() > 0) {
-            if (suggestedWords.mWillAutoCorrect) {
-                autoCorrection = suggestedWords.getWord(1);
-            } else {
-                autoCorrection = typedWord;
-            }
+        if (suggestedWords.mWillAutoCorrect) {
+            autoCorrection = suggestedWords.getWord(1);
         } else {
-            autoCorrection = null;
+            autoCorrection = typedWord;
         }
         mWordComposer.setAutoCorrection(autoCorrection);
         final boolean isAutoCorrection = suggestedWords.willAutoCorrect();
diff --git a/java/src/com/android/inputmethod/latin/SuggestedWords.java b/java/src/com/android/inputmethod/latin/SuggestedWords.java
index 52e292a..ad94aff 100644
--- a/java/src/com/android/inputmethod/latin/SuggestedWords.java
+++ b/java/src/com/android/inputmethod/latin/SuggestedWords.java
@@ -53,6 +53,10 @@
         mIsPrediction = isPrediction;
     }
 
+    public boolean isEmpty() {
+        return mSuggestedWordInfoList.isEmpty();
+    }
+
     public int size() {
         return mSuggestedWordInfoList.size();
     }
diff --git a/java/src/com/android/inputmethod/latin/makedict/BinaryDictIOUtils.java b/java/src/com/android/inputmethod/latin/makedict/BinaryDictIOUtils.java
index 7b0231a..40e089f 100644
--- a/java/src/com/android/inputmethod/latin/makedict/BinaryDictIOUtils.java
+++ b/java/src/com/android/inputmethod/latin/makedict/BinaryDictIOUtils.java
@@ -17,18 +17,30 @@
 package com.android.inputmethod.latin.makedict;
 
 import com.android.inputmethod.latin.Constants;
+import com.android.inputmethod.latin.makedict.BinaryDictInputOutput.CharEncoding;
 import com.android.inputmethod.latin.makedict.BinaryDictInputOutput.FusionDictionaryBufferInterface;
 import com.android.inputmethod.latin.makedict.FormatSpec.FileHeader;
 import com.android.inputmethod.latin.makedict.FormatSpec.FormatOptions;
 import com.android.inputmethod.latin.makedict.FusionDictionary.CharGroup;
+import com.android.inputmethod.latin.makedict.FusionDictionary.WeightedString;
 
 import java.io.IOException;
+import java.io.OutputStream;
 import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Iterator;
 import java.util.Map;
 import java.util.Stack;
 
 public final class BinaryDictIOUtils {
     private static final boolean DBG = false;
+    private static final int MSB24 = 0x800000;
+    private static final int SINT24_MAX = 0x7FFFFF;
+    private static final int MAX_JUMPS = 10000;
+
+    private BinaryDictIOUtils() {
+        // This utility class is not publicly instantiable.
+    }
 
     private static final class Position {
         public static final int NOT_READ_GROUPCOUNT = -1;
@@ -90,7 +102,9 @@
 
             final boolean isMovedGroup = BinaryDictInputOutput.isMovedGroup(info.mFlags,
                     formatOptions);
-            if (!isMovedGroup
+            final boolean isDeletedGroup = BinaryDictInputOutput.isDeletedGroup(info.mFlags,
+                    formatOptions);
+            if (!isMovedGroup && !isDeletedGroup
                     && info.mFrequency != FusionDictionary.CharGroup.NOT_A_TERMINAL) {// found word
                 words.put(info.mOriginalAddress, new String(pushedChars, 0, index));
                 frequencies.put(info.mOriginalAddress, info.mFrequency);
@@ -165,19 +179,19 @@
             if (wordPos >= wordLen) return FormatSpec.NOT_VALID_WORD;
 
             do {
-                int groupOffset = buffer.position() - header.mHeaderSize;
                 final int charGroupCount = BinaryDictInputOutput.readCharGroupCount(buffer);
-                groupOffset += BinaryDictInputOutput.getGroupCountSize(charGroupCount);
-
                 boolean foundNextCharGroup = false;
                 for (int i = 0; i < charGroupCount; ++i) {
                     final int charGroupPos = buffer.position();
                     final CharGroupInfo currentInfo = BinaryDictInputOutput.readCharGroup(buffer,
                             buffer.position(), header.mFormatOptions);
-                    if (BinaryDictInputOutput.isMovedGroup(currentInfo.mFlags,
-                            header.mFormatOptions)) {
-                        continue;
-                    }
+                    final boolean isMovedGroup =
+                            BinaryDictInputOutput.isMovedGroup(currentInfo.mFlags,
+                                    header.mFormatOptions);
+                    final boolean isDeletedGroup =
+                            BinaryDictInputOutput.isDeletedGroup(currentInfo.mFlags,
+                                    header.mFormatOptions);
+                    if (isMovedGroup) continue;
                     boolean same = true;
                     for (int p = 0, j = word.offsetByCodePoints(0, wordPos);
                             p < currentInfo.mCharacters.length;
@@ -192,7 +206,8 @@
                     if (same) {
                         // found the group matches the word.
                         if (wordPos + currentInfo.mCharacters.length == wordLen) {
-                            if (currentInfo.mFrequency == CharGroup.NOT_A_TERMINAL) {
+                            if (currentInfo.mFrequency == CharGroup.NOT_A_TERMINAL
+                                    || isDeletedGroup) {
                                 return FormatSpec.NOT_VALID_WORD;
                             } else {
                                 return charGroupPos;
@@ -206,7 +221,6 @@
                         buffer.position(currentInfo.mChildrenAddress);
                         break;
                     }
-                    groupOffset = currentInfo.mEndAddress;
                 }
 
                 // If we found the next char group, it is under the file pointer.
@@ -228,6 +242,10 @@
         return FormatSpec.NOT_VALID_WORD;
     }
 
+    private static int markAsDeleted(final int flags) {
+        return (flags & (~FormatSpec.MASK_GROUP_ADDRESS_TYPE)) | FormatSpec.FLAG_IS_DELETED;
+    }
+
     /**
      * Delete the word from the binary file.
      *
@@ -245,21 +263,58 @@
 
         buffer.position(wordPosition);
         final int flags = buffer.readUnsignedByte();
-        final int newFlags = flags ^ FormatSpec.FLAG_IS_TERMINAL;
         buffer.position(wordPosition);
-        buffer.put((byte)newFlags);
+        buffer.put((byte)markAsDeleted(flags));
     }
 
-    private static void putSInt24(final FusionDictionaryBufferInterface buffer,
+    /**
+     * @return the size written, in bytes. Always 3 bytes.
+     */
+    private static int writeSInt24ToBuffer(final FusionDictionaryBufferInterface buffer,
             final int value) {
         final int absValue = Math.abs(value);
         buffer.put((byte)(((value < 0 ? 0x80 : 0) | (absValue >> 16)) & 0xFF));
         buffer.put((byte)((absValue >> 8) & 0xFF));
         buffer.put((byte)(absValue & 0xFF));
+        return 3;
     }
 
     /**
-     * Update a parent address in a CharGroup that is addressed by groupOriginAddress.
+     * @return the size written, in bytes. Always 3 bytes.
+     */
+    private static int writeSInt24ToStream(final OutputStream destination, final int value)
+            throws IOException {
+        final int absValue = Math.abs(value);
+        destination.write((byte)(((value < 0 ? 0x80 : 0) | (absValue >> 16)) & 0xFF));
+        destination.write((byte)((absValue >> 8) & 0xFF));
+        destination.write((byte)(absValue & 0xFF));
+        return 3;
+    }
+
+    /**
+     * @return the size written, in bytes. 1, 2, or 3 bytes.
+     */
+    private static int writeVariableAddress(final OutputStream destination, final int value)
+            throws IOException {
+        switch (BinaryDictInputOutput.getByteSize(value)) {
+        case 1:
+            destination.write((byte)value);
+            break;
+        case 2:
+            destination.write((byte)(0xFF & (value >> 8)));
+            destination.write((byte)(0xFF & value));
+            break;
+        case 3:
+            destination.write((byte)(0xFF & (value >> 16)));
+            destination.write((byte)(0xFF & (value >> 8)));
+            destination.write((byte)(0xFF & value));
+            break;
+        }
+        return BinaryDictInputOutput.getByteSize(value);
+    }
+
+    /**
+     * Update a parent address in a CharGroup that is referred to by groupOriginAddress.
      *
      * @param buffer the buffer to write.
      * @param groupOriginAddress the address of the group.
@@ -275,8 +330,644 @@
             throw new RuntimeException("this file format does not support parent addresses");
         }
         final int flags = buffer.readUnsignedByte();
+        if (BinaryDictInputOutput.isMovedGroup(flags, formatOptions)) {
+            // if the group is moved, the parent address is stored in the destination group.
+            // We are guaranteed to process the destination group later, so there is no need to
+            // update anything here.
+            buffer.position(originalPosition);
+            return;
+        }
+        if (DBG) {
+            MakedictLog.d("update parent address flags=" + flags + ", " + groupOriginAddress);
+        }
         final int parentOffset = newParentAddress - groupOriginAddress;
-        putSInt24(buffer, parentOffset);
+        writeSInt24ToBuffer(buffer, parentOffset);
         buffer.position(originalPosition);
     }
+
+    private static void skipCharGroup(final FusionDictionaryBufferInterface buffer,
+            final FormatOptions formatOptions) {
+        final int flags = buffer.readUnsignedByte();
+        BinaryDictInputOutput.readParentAddress(buffer, formatOptions);
+        skipString(buffer, (flags & FormatSpec.FLAG_HAS_MULTIPLE_CHARS) != 0);
+        BinaryDictInputOutput.readChildrenAddress(buffer, flags, formatOptions);
+        if ((flags & FormatSpec.FLAG_IS_TERMINAL) != 0) buffer.readUnsignedByte();
+        if ((flags & FormatSpec.FLAG_HAS_SHORTCUT_TARGETS) != 0) {
+            final int shortcutsSize = buffer.readUnsignedShort();
+            buffer.position(buffer.position() + shortcutsSize
+                    - FormatSpec.GROUP_SHORTCUT_LIST_SIZE_SIZE);
+        }
+        if ((flags & FormatSpec.FLAG_HAS_BIGRAMS) != 0) {
+            int bigramCount = 0;
+            while (bigramCount++ < FormatSpec.MAX_BIGRAMS_IN_A_GROUP) {
+                final int bigramFlags = buffer.readUnsignedByte();
+                switch (bigramFlags & FormatSpec.MASK_ATTRIBUTE_ADDRESS_TYPE) {
+                    case FormatSpec.FLAG_ATTRIBUTE_ADDRESS_TYPE_ONEBYTE:
+                        buffer.readUnsignedByte();
+                        break;
+                    case FormatSpec.FLAG_ATTRIBUTE_ADDRESS_TYPE_TWOBYTES:
+                        buffer.readUnsignedShort();
+                        break;
+                    case FormatSpec.FLAG_ATTRIBUTE_ADDRESS_TYPE_THREEBYTES:
+                        buffer.readUnsignedInt24();
+                        break;
+                }
+                if ((bigramFlags & FormatSpec.FLAG_ATTRIBUTE_HAS_NEXT) == 0) break;
+            }
+            if (bigramCount >= FormatSpec.MAX_BIGRAMS_IN_A_GROUP) {
+                throw new RuntimeException("Too many bigrams in a group.");
+            }
+        }
+    }
+
+    /**
+     * Update parent addresses in a Node that is referred to by nodeOriginAddress.
+     *
+     * @param buffer the buffer to be modified.
+     * @param nodeOriginAddress the address of a modified Node.
+     * @param newParentAddress the address to be written.
+     * @param formatOptions file format options.
+     */
+    public static void updateParentAddresses(final FusionDictionaryBufferInterface buffer,
+            final int nodeOriginAddress, final int newParentAddress,
+            final FormatOptions formatOptions) {
+        final int originalPosition = buffer.position();
+        buffer.position(nodeOriginAddress);
+        do {
+            final int count = BinaryDictInputOutput.readCharGroupCount(buffer);
+            for (int i = 0; i < count; ++i) {
+                updateParentAddress(buffer, buffer.position(), newParentAddress, formatOptions);
+                skipCharGroup(buffer, formatOptions);
+            }
+            final int forwardLinkAddress = buffer.readUnsignedInt24();
+            buffer.position(forwardLinkAddress);
+        } while (formatOptions.mSupportsDynamicUpdate
+                && buffer.position() != FormatSpec.NO_FORWARD_LINK_ADDRESS);
+        buffer.position(originalPosition);
+    }
+
+    private static void skipString(final FusionDictionaryBufferInterface buffer,
+            final boolean hasMultipleChars) {
+        if (hasMultipleChars) {
+            int character = CharEncoding.readChar(buffer);
+            while (character != FormatSpec.INVALID_CHARACTER) {
+                character = CharEncoding.readChar(buffer);
+            }
+        } else {
+            CharEncoding.readChar(buffer);
+        }
+    }
+
+    /**
+     * Write a string to a stream.
+     *
+     * @param destination the stream to write.
+     * @param word the string to be written.
+     * @return the size written, in bytes.
+     * @throws IOException
+     */
+    private static int writeString(final OutputStream destination, final String word)
+            throws IOException {
+        int size = 0;
+        final int length = word.length();
+        for (int i = 0; i < length; i = word.offsetByCodePoints(i, 1)) {
+            final int codePoint = word.codePointAt(i);
+            if (CharEncoding.getCharSize(codePoint) == 1) {
+                destination.write((byte)codePoint);
+                size++;
+            } else {
+                destination.write((byte)(0xFF & (codePoint >> 16)));
+                destination.write((byte)(0xFF & (codePoint >> 8)));
+                destination.write((byte)(0xFF & codePoint));
+                size += 3;
+            }
+        }
+        destination.write((byte)FormatSpec.GROUP_CHARACTERS_TERMINATOR);
+        size += FormatSpec.GROUP_TERMINATOR_SIZE;
+        return size;
+    }
+
+    /**
+     * Update a children address in a CharGroup that is addressed by groupOriginAddress.
+     *
+     * @param buffer the buffer to write.
+     * @param groupOriginAddress the address of the group.
+     * @param newChildrenAddress the absolute address of the child.
+     * @param formatOptions file format options.
+     */
+    public static void updateChildrenAddress(final FusionDictionaryBufferInterface buffer,
+            final int groupOriginAddress, final int newChildrenAddress,
+            final FormatOptions formatOptions) {
+        final int originalPosition = buffer.position();
+        buffer.position(groupOriginAddress);
+        final int flags = buffer.readUnsignedByte();
+        final int parentAddress = BinaryDictInputOutput.readParentAddress(buffer, formatOptions);
+        skipString(buffer, (flags & FormatSpec.FLAG_HAS_MULTIPLE_CHARS) != 0);
+        if ((flags & FormatSpec.FLAG_IS_TERMINAL) != 0) buffer.readUnsignedByte();
+        final int childrenOffset = newChildrenAddress == FormatSpec.NO_CHILDREN_ADDRESS
+                ? FormatSpec.NO_CHILDREN_ADDRESS : newChildrenAddress - buffer.position();
+        writeSInt24ToBuffer(buffer, childrenOffset);
+        buffer.position(originalPosition);
+    }
+
+    /**
+     * Write a char group to an output stream.
+     * A char group is an in-memory representation of a node in trie.
+     * A char group info is an on-disk representation of a node.
+     *
+     * @param destination the stream to write.
+     * @param info the char group info to be written.
+     * @return the size written, in bytes.
+     */
+    public static int writeCharGroup(final OutputStream destination, final CharGroupInfo info)
+            throws IOException {
+        int size = FormatSpec.GROUP_FLAGS_SIZE;
+        destination.write((byte)info.mFlags);
+        final int parentOffset = info.mParentAddress == FormatSpec.NO_PARENT_ADDRESS ?
+                FormatSpec.NO_PARENT_ADDRESS : info.mParentAddress - info.mOriginalAddress;
+        size += writeSInt24ToStream(destination, parentOffset);
+
+        for (int i = 0; i < info.mCharacters.length; ++i) {
+            if (CharEncoding.getCharSize(info.mCharacters[i]) == 1) {
+                destination.write((byte)info.mCharacters[i]);
+                size++;
+            } else {
+                size += writeSInt24ToStream(destination, info.mCharacters[i]);
+            }
+        }
+        if (info.mCharacters.length > 1) {
+            destination.write((byte)FormatSpec.GROUP_CHARACTERS_TERMINATOR);
+            size++;
+        }
+
+        if ((info.mFlags & FormatSpec.FLAG_IS_TERMINAL) != 0) {
+            destination.write((byte)info.mFrequency);
+            size++;
+        }
+
+        if (DBG) {
+            MakedictLog.d("writeCharGroup origin=" + info.mOriginalAddress + ", size=" + size
+                    + ", child=" + info.mChildrenAddress + ", characters ="
+                    + new String(info.mCharacters, 0, info.mCharacters.length));
+        }
+        final int childrenOffset = info.mChildrenAddress == FormatSpec.NO_CHILDREN_ADDRESS ?
+                0 : info.mChildrenAddress - (info.mOriginalAddress + size);
+        writeSInt24ToStream(destination, childrenOffset);
+        size += FormatSpec.SIGNED_CHILDREN_ADDRESS_SIZE;
+
+        if (info.mShortcutTargets != null && info.mShortcutTargets.size() > 0) {
+            final int shortcutListSize =
+                    BinaryDictInputOutput.getShortcutListSize(info.mShortcutTargets);
+            destination.write((byte)(shortcutListSize >> 8));
+            destination.write((byte)(shortcutListSize & 0xFF));
+            size += 2;
+            final Iterator<WeightedString> shortcutIterator = info.mShortcutTargets.iterator();
+            while (shortcutIterator.hasNext()) {
+                final WeightedString target = shortcutIterator.next();
+                destination.write((byte)BinaryDictInputOutput.makeShortcutFlags(
+                        shortcutIterator.hasNext(), target.mFrequency));
+                size++;
+                size += writeString(destination, target.mWord);
+            }
+        }
+
+        if (info.mBigrams != null) {
+            // TODO: Consolidate this code with the code that computes the size of the bigram list
+            //        in BinaryDictionaryInputOutput#computeActualNodeSize
+            for (int i = 0; i < info.mBigrams.size(); ++i) {
+
+                final int bigramFrequency = info.mBigrams.get(i).mFrequency;
+                int bigramFlags = (i < info.mBigrams.size() - 1)
+                        ? FormatSpec.FLAG_ATTRIBUTE_HAS_NEXT : 0;
+                size++;
+                final int bigramOffset = info.mBigrams.get(i).mAddress - (info.mOriginalAddress
+                        + size);
+                bigramFlags |= (bigramOffset < 0) ? FormatSpec.FLAG_ATTRIBUTE_OFFSET_NEGATIVE : 0;
+                switch (BinaryDictInputOutput.getByteSize(bigramOffset)) {
+                case 1:
+                    bigramFlags |= FormatSpec.FLAG_ATTRIBUTE_ADDRESS_TYPE_ONEBYTE;
+                    break;
+                case 2:
+                    bigramFlags |= FormatSpec.FLAG_ATTRIBUTE_ADDRESS_TYPE_TWOBYTES;
+                    break;
+                case 3:
+                    bigramFlags |= FormatSpec.FLAG_ATTRIBUTE_ADDRESS_TYPE_THREEBYTES;
+                    break;
+                }
+                bigramFlags |= bigramFrequency & FormatSpec.FLAG_ATTRIBUTE_FREQUENCY;
+                destination.write((byte)bigramFlags);
+                size += writeVariableAddress(destination, Math.abs(bigramOffset));
+            }
+        }
+        return size;
+    }
+
+    private static void updateForwardLink(final FusionDictionaryBufferInterface buffer,
+            final int nodeOriginAddress, final int newNodeAddress,
+            final FormatOptions formatOptions) {
+        buffer.position(nodeOriginAddress);
+        int jumpCount = 0;
+        while (jumpCount++ < MAX_JUMPS) {
+            final int count = BinaryDictInputOutput.readCharGroupCount(buffer);
+            for (int i = 0; i < count; ++i) skipCharGroup(buffer, formatOptions);
+            final int forwardLinkAddress = buffer.readUnsignedInt24();
+            if (forwardLinkAddress == FormatSpec.NO_FORWARD_LINK_ADDRESS) {
+                buffer.position(buffer.position() - FormatSpec.FORWARD_LINK_ADDRESS_SIZE);
+                writeSInt24ToBuffer(buffer, newNodeAddress);
+                return;
+            }
+            buffer.position(forwardLinkAddress);
+        }
+        if (DBG && jumpCount >= MAX_JUMPS) {
+            throw new RuntimeException("too many jumps, probably a bug.");
+        }
+    }
+
+    /**
+     * Helper method to move a char group to the tail of the file.
+     */
+    private static int moveCharGroup(final OutputStream destination,
+            final FusionDictionaryBufferInterface buffer, final CharGroupInfo info,
+            final int nodeOriginAddress, final int oldGroupAddress,
+            final FormatOptions formatOptions) throws IOException {
+        updateParentAddress(buffer, oldGroupAddress, buffer.limit() + 1, formatOptions);
+        buffer.position(oldGroupAddress);
+        final int currentFlags = buffer.readUnsignedByte();
+        buffer.position(oldGroupAddress);
+        buffer.put((byte)(FormatSpec.FLAG_IS_MOVED | (currentFlags
+                & (~FormatSpec.MASK_MOVE_AND_DELETE_FLAG))));
+        int size = FormatSpec.GROUP_FLAGS_SIZE;
+        updateForwardLink(buffer, nodeOriginAddress, buffer.limit(), formatOptions);
+        size += writeNode(destination, new CharGroupInfo[] { info });
+        return size;
+    }
+
+    /**
+     * Compute the size of the char group.
+     */
+    private static int computeGroupSize(final CharGroupInfo info,
+            final FormatOptions formatOptions) {
+        int size = FormatSpec.GROUP_FLAGS_SIZE + FormatSpec.PARENT_ADDRESS_SIZE
+                + BinaryDictInputOutput.getGroupCharactersSize(info.mCharacters)
+                + BinaryDictInputOutput.getChildrenAddressSize(info.mFlags, formatOptions);
+        if ((info.mFlags & FormatSpec.FLAG_IS_TERMINAL) != 0) {
+            size += FormatSpec.GROUP_FREQUENCY_SIZE;
+        }
+        if (info.mShortcutTargets != null && !info.mShortcutTargets.isEmpty()) {
+            size += BinaryDictInputOutput.getShortcutListSize(info.mShortcutTargets);
+        }
+        if (info.mBigrams != null) {
+            for (final PendingAttribute attr : info.mBigrams) {
+                size += FormatSpec.GROUP_FLAGS_SIZE;
+                size += BinaryDictInputOutput.getByteSize(attr.mAddress);
+            }
+        }
+        return size;
+    }
+
+    /**
+     * Write a node to the stream.
+     *
+     * @param destination the stream to write.
+     * @param infos groups to be written.
+     * @return the size written, in bytes.
+     * @throws IOException
+     */
+    private static int writeNode(final OutputStream destination, final CharGroupInfo[] infos)
+            throws IOException {
+        int size = BinaryDictInputOutput.getGroupCountSize(infos.length);
+        switch (BinaryDictInputOutput.getGroupCountSize(infos.length)) {
+            case 1:
+                destination.write((byte)infos.length);
+                break;
+            case 2:
+                destination.write((byte)(infos.length >> 8));
+                destination.write((byte)(infos.length & 0xFF));
+                break;
+            default:
+                throw new RuntimeException("Invalid group count size.");
+        }
+        for (final CharGroupInfo info : infos) size += writeCharGroup(destination, info);
+        writeSInt24ToStream(destination, FormatSpec.NO_FORWARD_LINK_ADDRESS);
+        return size + FormatSpec.FORWARD_LINK_ADDRESS_SIZE;
+    }
+
+    /**
+     * Move a group that is referred to by oldGroupOrigin to the tail of the file.
+     * And set the children address to the byte after the group.
+     *
+     * @param nodeOrigin the address of the tail of the file.
+     * @param characters
+     * @param length
+     * @param flags
+     * @param frequency
+     * @param parentAddress
+     * @param shortcutTargets
+     * @param bigrams
+     * @param destination the stream representing the tail of the file.
+     * @param buffer the buffer representing the (constant-size) body of the file.
+     * @param oldNodeOrigin
+     * @param oldGroupOrigin
+     * @param formatOptions
+     * @return the size written, in bytes.
+     * @throws IOException
+     */
+    private static int moveGroup(final int nodeOrigin, final int[] characters, final int length,
+            final int flags, final int frequency, final int parentAddress,
+            final ArrayList<WeightedString> shortcutTargets,
+            final ArrayList<PendingAttribute> bigrams, final OutputStream destination,
+            final FusionDictionaryBufferInterface buffer, final int oldNodeOrigin,
+            final int oldGroupOrigin, final FormatOptions formatOptions) throws IOException {
+        int size = 0;
+        final int newGroupOrigin = nodeOrigin + 1;
+        final int[] writtenCharacters = Arrays.copyOfRange(characters, 0, length);
+        final CharGroupInfo tmpInfo = new CharGroupInfo(newGroupOrigin, -1 /* endAddress */,
+                flags, writtenCharacters, frequency, parentAddress, FormatSpec.NO_CHILDREN_ADDRESS,
+                shortcutTargets, bigrams);
+        size = computeGroupSize(tmpInfo, formatOptions);
+        final CharGroupInfo newInfo = new CharGroupInfo(newGroupOrigin, newGroupOrigin + size,
+                flags, writtenCharacters, frequency, parentAddress,
+                nodeOrigin + 1 + size + FormatSpec.FORWARD_LINK_ADDRESS_SIZE, shortcutTargets,
+                bigrams);
+        moveCharGroup(destination, buffer, newInfo, oldNodeOrigin, oldGroupOrigin, formatOptions);
+        return 1 + size + FormatSpec.FORWARD_LINK_ADDRESS_SIZE;
+    }
+
+    /**
+     * Insert a word into a binary dictionary.
+     *
+     * @param buffer
+     * @param destination
+     * @param word
+     * @param frequency
+     * @param bigramStrings
+     * @param shortcuts
+     * @throws IOException
+     * @throws UnsupportedFormatException
+     */
+    // TODO: Support batch insertion.
+    public static void insertWord(final FusionDictionaryBufferInterface buffer,
+            final OutputStream destination, final String word, final int frequency,
+            final ArrayList<WeightedString> bigramStrings,
+            final ArrayList<WeightedString> shortcuts, final boolean isNotAWord,
+            final boolean isBlackListEntry)
+                    throws IOException, UnsupportedFormatException {
+        final ArrayList<PendingAttribute> bigrams = new ArrayList<PendingAttribute>();
+        if (bigramStrings != null) {
+            for (final WeightedString bigram : bigramStrings) {
+                int position = getTerminalPosition(buffer, bigram.mWord);
+                if (position == FormatSpec.NOT_VALID_WORD) {
+                    // TODO: figure out what is the correct thing to do here.
+                } else {
+                    bigrams.add(new PendingAttribute(bigram.mFrequency, position));
+                }
+            }
+        }
+
+        final boolean isTerminal = true;
+        final boolean hasBigrams = !bigrams.isEmpty();
+        final boolean hasShortcuts = shortcuts != null && !shortcuts.isEmpty();
+
+        // find the insert position of the word.
+        if (buffer.position() != 0) buffer.position(0);
+        final FileHeader header = BinaryDictInputOutput.readHeader(buffer);
+
+        int wordPos = 0, address = buffer.position(), nodeOriginAddress = buffer.position();
+        final int[] codePoints = FusionDictionary.getCodePoints(word);
+        final int wordLen = codePoints.length;
+
+        for (int depth = 0; depth < Constants.Dictionary.MAX_WORD_LENGTH; ++depth) {
+            if (wordPos >= wordLen) break;
+            nodeOriginAddress = buffer.position();
+            int nodeParentAddress = -1;
+            final int charGroupCount = BinaryDictInputOutput.readCharGroupCount(buffer);
+            boolean foundNextGroup = false;
+
+            for (int i = 0; i < charGroupCount; ++i) {
+                address = buffer.position();
+                final CharGroupInfo currentInfo = BinaryDictInputOutput.readCharGroup(buffer,
+                        buffer.position(), header.mFormatOptions);
+                final boolean isMovedGroup = BinaryDictInputOutput.isMovedGroup(currentInfo.mFlags,
+                        header.mFormatOptions);
+                if (isMovedGroup) continue;
+                nodeParentAddress = (currentInfo.mParentAddress == FormatSpec.NO_PARENT_ADDRESS)
+                        ? FormatSpec.NO_PARENT_ADDRESS : currentInfo.mParentAddress + address;
+                boolean matched = true;
+                for (int p = 0; p < currentInfo.mCharacters.length; ++p) {
+                    if (wordPos + p >= wordLen) {
+                        /*
+                         * splitting
+                         * before
+                         *  abcd - ef
+                         *
+                         * insert "abc"
+                         *
+                         * after
+                         *  abc - d - ef
+                         */
+                        final int newNodeAddress = buffer.limit();
+                        final int flags = BinaryDictInputOutput.makeCharGroupFlags(p > 1,
+                                isTerminal, 0, hasShortcuts, hasBigrams, false /* isNotAWord */,
+                                false /* isBlackListEntry */, header.mFormatOptions);
+                        int written = moveGroup(newNodeAddress, currentInfo.mCharacters, p, flags,
+                                frequency, nodeParentAddress, shortcuts, bigrams, destination,
+                                buffer, nodeOriginAddress, address, header.mFormatOptions);
+
+                        final int[] characters2 = Arrays.copyOfRange(currentInfo.mCharacters, p,
+                                currentInfo.mCharacters.length);
+                        if (currentInfo.mChildrenAddress != FormatSpec.NO_CHILDREN_ADDRESS) {
+                            updateParentAddresses(buffer, currentInfo.mChildrenAddress,
+                                    newNodeAddress + written + 1, header.mFormatOptions);
+                        }
+                        final CharGroupInfo newInfo2 = new CharGroupInfo(
+                                newNodeAddress + written + 1, -1 /* endAddress */,
+                                currentInfo.mFlags, characters2, currentInfo.mFrequency,
+                                newNodeAddress + 1, currentInfo.mChildrenAddress,
+                                currentInfo.mShortcutTargets, currentInfo.mBigrams);
+                        writeNode(destination, new CharGroupInfo[] { newInfo2 });
+                        return;
+                    } else if (codePoints[wordPos + p] != currentInfo.mCharacters[p]) {
+                        if (p > 0) {
+                            /*
+                             * splitting
+                             * before
+                             *   ab - cd
+                             *
+                             * insert "ac"
+                             *
+                             * after
+                             *   a - b - cd
+                             *     |
+                             *     - c
+                             */
+
+                            final int newNodeAddress = buffer.limit();
+                            final int childrenAddress = currentInfo.mChildrenAddress;
+
+                            // move prefix
+                            final int prefixFlags = BinaryDictInputOutput.makeCharGroupFlags(p > 1,
+                                    false /* isTerminal */, 0 /* childrenAddressSize*/,
+                                    false /* hasShortcut */, false /* hasBigrams */,
+                                    false /* isNotAWord */, false /* isBlackListEntry */,
+                                    header.mFormatOptions);
+                            int written = moveGroup(newNodeAddress, currentInfo.mCharacters, p,
+                                    prefixFlags, -1 /* frequency */, nodeParentAddress, null, null,
+                                    destination, buffer, nodeOriginAddress, address,
+                                    header.mFormatOptions);
+
+                            final int[] suffixCharacters = Arrays.copyOfRange(
+                                    currentInfo.mCharacters, p, currentInfo.mCharacters.length);
+                            if (currentInfo.mChildrenAddress != FormatSpec.NO_CHILDREN_ADDRESS) {
+                                updateParentAddresses(buffer, currentInfo.mChildrenAddress,
+                                        newNodeAddress + written + 1, header.mFormatOptions);
+                            }
+                            final int suffixFlags = BinaryDictInputOutput.makeCharGroupFlags(
+                                    suffixCharacters.length > 1,
+                                    (currentInfo.mFlags & FormatSpec.FLAG_IS_TERMINAL) != 0,
+                                    0 /* childrenAddressSize */,
+                                    (currentInfo.mFlags & FormatSpec.FLAG_HAS_SHORTCUT_TARGETS)
+                                            != 0,
+                                    (currentInfo.mFlags & FormatSpec.FLAG_HAS_BIGRAMS) != 0,
+                                    isNotAWord, isBlackListEntry, header.mFormatOptions);
+                            final CharGroupInfo suffixInfo = new CharGroupInfo(
+                                    newNodeAddress + written + 1, -1 /* endAddress */, suffixFlags,
+                                    suffixCharacters, currentInfo.mFrequency, newNodeAddress + 1,
+                                    currentInfo.mChildrenAddress, currentInfo.mShortcutTargets,
+                                    currentInfo.mBigrams);
+                            written += computeGroupSize(suffixInfo, header.mFormatOptions) + 1;
+
+                            final int[] newCharacters = Arrays.copyOfRange(codePoints, wordPos + p,
+                                    codePoints.length);
+                            final int flags = BinaryDictInputOutput.makeCharGroupFlags(
+                                    newCharacters.length > 1, isTerminal,
+                                    0 /* childrenAddressSize */, hasShortcuts, hasBigrams,
+                                    isNotAWord, isBlackListEntry, header.mFormatOptions);
+                            final CharGroupInfo newInfo = new CharGroupInfo(
+                                    newNodeAddress + written, -1 /* endAddress */, flags,
+                                    newCharacters, frequency, newNodeAddress + 1,
+                                    FormatSpec.NO_CHILDREN_ADDRESS, shortcuts, bigrams);
+                            writeNode(destination, new CharGroupInfo[] { suffixInfo, newInfo });
+                            return;
+                        }
+                        matched = false;
+                        break;
+                    }
+                }
+
+                if (matched) {
+                    if (wordPos + currentInfo.mCharacters.length == wordLen) {
+                        // the word exists in the dictionary.
+                        // only update group.
+                        final int newNodeAddress = buffer.limit();
+                        final boolean hasMultipleChars = currentInfo.mCharacters.length > 1;
+                        final int flags = BinaryDictInputOutput.makeCharGroupFlags(hasMultipleChars,
+                                isTerminal, 0 /* childrenAddressSize */, hasShortcuts, hasBigrams,
+                                isNotAWord, isBlackListEntry, header.mFormatOptions);
+                        final CharGroupInfo newInfo = new CharGroupInfo(newNodeAddress + 1,
+                                -1 /* endAddress */, flags, currentInfo.mCharacters, frequency,
+                                nodeParentAddress, currentInfo.mChildrenAddress, shortcuts,
+                                bigrams);
+                        moveCharGroup(destination, buffer, newInfo, nodeOriginAddress, address,
+                                header.mFormatOptions);
+                        return;
+                    }
+                    wordPos += currentInfo.mCharacters.length;
+                    if (currentInfo.mChildrenAddress == FormatSpec.NO_CHILDREN_ADDRESS) {
+                        /*
+                         * found the prefix of the word.
+                         * make new node and link to the node from this group.
+                         *
+                         * before
+                         * ab - cd
+                         *
+                         * insert "abcde"
+                         *
+                         * after
+                         * ab - cd - e
+                         */
+                        final int newNodeAddress = buffer.limit();
+                        updateChildrenAddress(buffer, address, newNodeAddress,
+                                header.mFormatOptions);
+                        final int newGroupAddress = newNodeAddress + 1;
+                        final boolean hasMultipleChars = (wordLen - wordPos) > 1;
+                        final int flags = BinaryDictInputOutput.makeCharGroupFlags(hasMultipleChars,
+                                isTerminal, 0 /* childrenAddressSize */, hasShortcuts, hasBigrams,
+                                isNotAWord, isBlackListEntry, header.mFormatOptions);
+                        final int[] characters = Arrays.copyOfRange(codePoints, wordPos, wordLen);
+                        final CharGroupInfo newInfo = new CharGroupInfo(newGroupAddress, -1, flags,
+                                characters, frequency, address, FormatSpec.NO_CHILDREN_ADDRESS,
+                                shortcuts, bigrams);
+                        writeNode(destination, new CharGroupInfo[] { newInfo });
+                        return;
+                    }
+                    buffer.position(currentInfo.mChildrenAddress);
+                    foundNextGroup = true;
+                    break;
+                }
+            }
+
+            if (foundNextGroup) continue;
+
+            // reached the end of the array.
+            final int linkAddressPosition = buffer.position();
+            int nextLink = buffer.readUnsignedInt24();
+            if ((nextLink & MSB24) != 0) {
+                nextLink = -(nextLink & SINT24_MAX);
+            }
+            if (nextLink == FormatSpec.NO_FORWARD_LINK_ADDRESS) {
+                /*
+                 * expand this node.
+                 *
+                 * before
+                 * ab - cd
+                 *
+                 * insert "abef"
+                 *
+                 * after
+                 * ab - cd
+                 *    |
+                 *    - ef
+                 */
+
+                // change the forward link address.
+                final int newNodeAddress = buffer.limit();
+                buffer.position(linkAddressPosition);
+                writeSInt24ToBuffer(buffer, newNodeAddress);
+
+                final int[] characters = Arrays.copyOfRange(codePoints, wordPos, wordLen);
+                final int flags = BinaryDictInputOutput.makeCharGroupFlags(characters.length > 1,
+                        isTerminal, 0 /* childrenAddressSize */, hasShortcuts, hasBigrams,
+                        isNotAWord, isBlackListEntry, header.mFormatOptions);
+                final CharGroupInfo newInfo = new CharGroupInfo(newNodeAddress + 1,
+                        -1 /* endAddress */, flags, characters, frequency, nodeParentAddress,
+                        FormatSpec.NO_CHILDREN_ADDRESS, shortcuts, bigrams);
+                writeNode(destination, new CharGroupInfo[]{ newInfo });
+                return;
+            } else {
+                depth--;
+                buffer.position(nextLink);
+            }
+        }
+    }
+
+    /**
+     * Find a word from the buffer.
+     *
+     * @param buffer the buffer representing the body of the dictionary file.
+     * @param word the word searched
+     * @return the found group
+     * @throws IOException
+     * @throws UnsupportedFormatException
+     */
+    public static CharGroupInfo findWordFromBuffer(final FusionDictionaryBufferInterface buffer,
+            final String word) throws IOException, UnsupportedFormatException {
+        int position = getTerminalPosition(buffer, word);
+        if (position != FormatSpec.NOT_VALID_WORD) {
+            buffer.position(0);
+            final FileHeader header = BinaryDictInputOutput.readHeader(buffer);
+            buffer.position(position);
+            return BinaryDictInputOutput.readCharGroup(buffer, position, header.mFormatOptions);
+        }
+        return null;
+    }
 }
diff --git a/java/src/com/android/inputmethod/latin/makedict/BinaryDictInputOutput.java b/java/src/com/android/inputmethod/latin/makedict/BinaryDictInputOutput.java
index b431a4d..2d39094 100644
--- a/java/src/com/android/inputmethod/latin/makedict/BinaryDictInputOutput.java
+++ b/java/src/com/android/inputmethod/latin/makedict/BinaryDictInputOutput.java
@@ -124,8 +124,7 @@
     /**
      * A class grouping utility function for our specific character encoding.
      */
-    private static final class CharEncoding {
-
+    static final class CharEncoding {
         private static final int MINIMAL_ONE_BYTE_CHARACTER_VALUE = 0x20;
         private static final int MAXIMAL_ONE_BYTE_CHARACTER_VALUE = 0xFF;
 
@@ -154,7 +153,7 @@
          * @param character the character code.
          * @return the size in binary encoded-form, either 1 or 3 bytes.
          */
-        private static int getCharSize(final int character) {
+        static int getCharSize(final int character) {
             // See char encoding in FusionDictionary.java
             if (fitsOnOneByte(character)) return 1;
             if (FormatSpec.INVALID_CHARACTER == character) return 1;
@@ -263,7 +262,7 @@
          * @param buffer the buffer, positioned over an encoded character.
          * @return the character code.
          */
-        private static int readChar(final FusionDictionaryBufferInterface buffer) {
+        static int readChar(final FusionDictionaryBufferInterface buffer) {
             int character = buffer.readUnsignedByte();
             if (!fitsOnOneByte(character)) {
                 if (FormatSpec.GROUP_CHARACTERS_TERMINATOR == character) {
@@ -277,6 +276,21 @@
     }
 
     /**
+     * Compute the binary size of the character array.
+     *
+     * If only one character, this is the size of this character. If many, it's the sum of their
+     * sizes + 1 byte for the terminator.
+     *
+     * @param characters the character array
+     * @return the size of the char array, including the terminator if any
+     */
+    static int getGroupCharactersSize(final int[] characters) {
+        int size = CharEncoding.getCharArraySize(characters);
+        if (characters.length > 1) size += FormatSpec.GROUP_TERMINATOR_SIZE;
+        return size;
+    }
+
+    /**
      * Compute the binary size of the character array in a group
      *
      * If only one character, this is the size of this character. If many, it's the sum of their
@@ -286,9 +300,7 @@
      * @return the size of the char array, including the terminator if any
      */
     private static int getGroupCharactersSize(final CharGroup group) {
-        int size = CharEncoding.getCharArraySize(group.mChars);
-        if (group.hasSeveralChars()) size += FormatSpec.GROUP_TERMINATOR_SIZE;
-        return size;
+        return getGroupCharactersSize(group.mChars);
     }
 
     /**
@@ -338,7 +350,7 @@
      * This is known in advance and does not change according to position in the file
      * like address lists do.
      */
-    private static int getShortcutListSize(final ArrayList<WeightedString> shortcutList) {
+    static int getShortcutListSize(final ArrayList<WeightedString> shortcutList) {
         if (null == shortcutList) return 0;
         int size = FormatSpec.GROUP_SHORTCUT_LIST_SIZE_SIZE;
         for (final WeightedString shortcut : shortcutList) {
@@ -399,7 +411,16 @@
      * Helper method to check whether the group is moved.
      */
     public static boolean isMovedGroup(final int flags, final FormatOptions options) {
-        return options.mSupportsDynamicUpdate && ((flags & FormatSpec.FLAG_IS_MOVED) == 1);
+        return options.mSupportsDynamicUpdate
+                && ((flags & FormatSpec.MASK_GROUP_ADDRESS_TYPE) == FormatSpec.FLAG_IS_MOVED);
+    }
+
+    /**
+     * Helper method to check whether the group is deleted.
+     */
+    public static boolean isDeletedGroup(final int flags, final FormatOptions formatOptions) {
+        return formatOptions.mSupportsDynamicUpdate
+                && ((flags & FormatSpec.MASK_GROUP_ADDRESS_TYPE) == FormatSpec.FLAG_IS_DELETED);
     }
 
     /**
@@ -439,7 +460,7 @@
      * @param address the address
      * @return the byte size.
      */
-    private static int getByteSize(final int address) {
+    static int getByteSize(final int address) {
         assert(address <= UINT24_MAX);
         if (!hasChildrenAddress(address)) {
             return 0;
@@ -721,51 +742,58 @@
         return 3;
     }
 
+    /**
+     * Makes the flag value for a char group.
+     *
+     * @param hasMultipleChars whether the group has multiple chars.
+     * @param isTerminal whether the group is terminal.
+     * @param childrenAddressSize the size of a children address.
+     * @param hasShortcuts whether the group has shortcuts.
+     * @param hasBigrams whether the group has bigrams.
+     * @param isNotAWord whether the group is not a word.
+     * @param isBlackListEntry whether the group is a blacklist entry.
+     * @param formatOptions file format options.
+     * @return the flags
+     */
+    static int makeCharGroupFlags(final boolean hasMultipleChars, final boolean isTerminal,
+            final int childrenAddressSize, final boolean hasShortcuts, final boolean hasBigrams,
+            final boolean isNotAWord, final boolean isBlackListEntry,
+            final FormatOptions formatOptions) {
+        byte flags = 0;
+        if (hasMultipleChars) flags |= FormatSpec.FLAG_HAS_MULTIPLE_CHARS;
+        if (isTerminal) flags |= FormatSpec.FLAG_IS_TERMINAL;
+        if (formatOptions.mSupportsDynamicUpdate) {
+            flags |= FormatSpec.FLAG_IS_NOT_MOVED;
+        } else if (true) {
+            switch (childrenAddressSize) {
+                case 1:
+                    flags |= FormatSpec.FLAG_GROUP_ADDRESS_TYPE_ONEBYTE;
+                    break;
+                case 2:
+                    flags |= FormatSpec.FLAG_GROUP_ADDRESS_TYPE_TWOBYTES;
+                    break;
+                case 3:
+                    flags |= FormatSpec.FLAG_GROUP_ADDRESS_TYPE_THREEBYTES;
+                    break;
+                case 0:
+                    flags |= FormatSpec.FLAG_GROUP_ADDRESS_TYPE_NOADDRESS;
+                    break;
+                default:
+                    throw new RuntimeException("Node with a strange address");
+            }
+        }
+        if (hasShortcuts) flags |= FormatSpec.FLAG_HAS_SHORTCUT_TARGETS;
+        if (hasBigrams) flags |= FormatSpec.FLAG_HAS_BIGRAMS;
+        if (isNotAWord) flags |= FormatSpec.FLAG_IS_NOT_A_WORD;
+        if (isBlackListEntry) flags |= FormatSpec.FLAG_IS_BLACKLISTED;
+        return flags;
+    }
+
     private static byte makeCharGroupFlags(final CharGroup group, final int groupAddress,
             final int childrenOffset, final FormatOptions formatOptions) {
-        byte flags = 0;
-        if (group.mChars.length > 1) flags |= FormatSpec.FLAG_HAS_MULTIPLE_CHARS;
-        if (group.mFrequency >= 0) {
-            flags |= FormatSpec.FLAG_IS_TERMINAL;
-        }
-        if (null != group.mChildren) {
-            final int byteSize = formatOptions.mSupportsDynamicUpdate
-                    ? FormatSpec.SIGNED_CHILDREN_ADDRESS_SIZE : getByteSize(childrenOffset);
-            switch (byteSize) {
-            case 1:
-                flags |= FormatSpec.FLAG_GROUP_ADDRESS_TYPE_ONEBYTE;
-                break;
-            case 2:
-                flags |= FormatSpec.FLAG_GROUP_ADDRESS_TYPE_TWOBYTES;
-                break;
-            case 3:
-                flags |= FormatSpec.FLAG_GROUP_ADDRESS_TYPE_THREEBYTES;
-                break;
-            default:
-                throw new RuntimeException("Node with a strange address");
-            }
-        } else if (formatOptions.mSupportsDynamicUpdate) {
-            flags |= FormatSpec.FLAG_GROUP_ADDRESS_TYPE_THREEBYTES;
-        }
-        if (null != group.mShortcutTargets) {
-            if (DBG && 0 == group.mShortcutTargets.size()) {
-                throw new RuntimeException("0-sized shortcut list must be null");
-            }
-            flags |= FormatSpec.FLAG_HAS_SHORTCUT_TARGETS;
-        }
-        if (null != group.mBigrams) {
-            if (DBG && 0 == group.mBigrams.size()) {
-                throw new RuntimeException("0-sized bigram list must be null");
-            }
-            flags |= FormatSpec.FLAG_HAS_BIGRAMS;
-        }
-        if (group.mIsNotAWord) {
-            flags |= FormatSpec.FLAG_IS_NOT_A_WORD;
-        }
-        if (group.mIsBlacklistEntry) {
-            flags |= FormatSpec.FLAG_IS_BLACKLISTED;
-        }
-        return flags;
+        return (byte) makeCharGroupFlags(group.mChars.length > 1, group.mFrequency >= 0,
+                getByteSize(childrenOffset), group.mShortcutTargets != null, group.mBigrams != null,
+                group.mIsNotAWord, group.mIsBlacklistEntry, formatOptions);
     }
 
     /**
@@ -859,7 +887,7 @@
      * @param frequency the frequency of the attribute, 0..15
      * @return the flags
      */
-    private static final int makeShortcutFlags(final boolean more, final int frequency) {
+    static final int makeShortcutFlags(final boolean more, final int frequency) {
         return (more ? FormatSpec.FLAG_ATTRIBUTE_HAS_NEXT : 0)
                 + (frequency & FormatSpec.FLAG_ATTRIBUTE_FREQUENCY);
     }
@@ -897,6 +925,7 @@
      */
     private static int writePlacedNode(final FusionDictionary dict, byte[] buffer,
             final Node node, final FormatOptions formatOptions) {
+        // TODO: Make the code in common with BinaryDictIOUtils#writeCharGroup
         int index = node.mCachedAddress;
 
         final int groupCount = node.mData.size();
@@ -1178,7 +1207,7 @@
     // Input methods: Read a binary dictionary to memory.
     // readDictionaryBinary is the public entry point for them.
 
-    private static int getChildrenAddressSize(final int optionFlags,
+    static int getChildrenAddressSize(final int optionFlags,
             final FormatOptions formatOptions) {
         if (formatOptions.mSupportsDynamicUpdate) return FormatSpec.SIGNED_CHILDREN_ADDRESS_SIZE;
         switch (optionFlags & FormatSpec.MASK_GROUP_ADDRESS_TYPE) {
@@ -1194,7 +1223,7 @@
         }
     }
 
-    private static int readChildrenAddress(final FusionDictionaryBufferInterface buffer,
+    static int readChildrenAddress(final FusionDictionaryBufferInterface buffer,
             final int optionFlags, final FormatOptions options) {
         if (options.mSupportsDynamicUpdate) {
             final int address = buffer.readUnsignedInt24();
@@ -1219,7 +1248,7 @@
         }
     }
 
-    private static int readParentAddress(final FusionDictionaryBufferInterface buffer,
+    static int readParentAddress(final FusionDictionaryBufferInterface buffer,
             final FormatOptions formatOptions) {
         if (supportsDynamicUpdate(formatOptions)) {
             final int parentAddress = buffer.readUnsignedInt24();
@@ -1290,7 +1319,8 @@
         ArrayList<PendingAttribute> bigrams = null;
         if (0 != (flags & FormatSpec.FLAG_HAS_BIGRAMS)) {
             bigrams = new ArrayList<PendingAttribute>();
-            while (true) {
+            int bigramCount = 0;
+            while (bigramCount++ < FormatSpec.MAX_BIGRAMS_IN_A_GROUP) {
                 final int bigramFlags = buffer.readUnsignedByte();
                 ++addressPointer;
                 final int sign = 0 == (bigramFlags & FormatSpec.FLAG_ATTRIBUTE_OFFSET_NEGATIVE)
@@ -1318,6 +1348,9 @@
                         bigramAddress));
                 if (0 == (bigramFlags & FormatSpec.FLAG_ATTRIBUTE_HAS_NEXT)) break;
             }
+            if (bigramCount >= FormatSpec.MAX_BIGRAMS_IN_A_GROUP) {
+                MakedictLog.d("too many bigrams in a group.");
+            }
         }
         return new CharGroupInfo(originalGroupAddress, addressPointer, flags, characters, frequency,
                 parentAddress, childrenAddress, shortcutTargets, bigrams);
diff --git a/java/src/com/android/inputmethod/latin/makedict/FormatSpec.java b/java/src/com/android/inputmethod/latin/makedict/FormatSpec.java
index b3fbb9f..e88a4ae 100644
--- a/java/src/com/android/inputmethod/latin/makedict/FormatSpec.java
+++ b/java/src/com/android/inputmethod/latin/makedict/FormatSpec.java
@@ -59,9 +59,11 @@
      * l |                                   10 = 2 bytes     : FLAG_GROUP_ADDRESS_TYPE_TWOBYTES
      * a |                                   11 = 3 bytes     : FLAG_GROUP_ADDRESS_TYPE_THREEBYTES
      * g | ELSE
-     * s |   is moved ?              2 bits, 11 = no
-     *   |                                   01 = yes
+     * s |   is moved ?              2 bits, 11 = no          : FLAG_IS_NOT_MOVED
+     *   |                              This must be the same as FLAG_GROUP_ADDRESS_TYPE_THREEBYTES
+     *   |                                   01 = yes         : FLAG_IS_MOVED
      *   |                        the new address is stored in the same place as the parent address
+     *   |   is deleted?                     10 = yes         : FLAG_IS_DELETED
      *   | has several chars ?         1 bit, 1 = yes, 0 = no   : FLAG_HAS_MULTIPLE_CHARS
      *   | has a terminal ?            1 bit, 1 = yes, 0 = no   : FLAG_IS_TERMINAL
      *   | has shortcut targets ?      1 bit, 1 = yes, 0 = no   : FLAG_HAS_SHORTCUT_TARGETS
@@ -170,6 +172,7 @@
     static final int PARENT_ADDRESS_SIZE = 3;
     static final int FORWARD_LINK_ADDRESS_SIZE = 3;
 
+    // These flags are used only in the static dictionary.
     static final int MASK_GROUP_ADDRESS_TYPE = 0xC0;
     static final int FLAG_GROUP_ADDRESS_TYPE_NOADDRESS = 0x00;
     static final int FLAG_GROUP_ADDRESS_TYPE_ONEBYTE = 0x40;
@@ -183,7 +186,13 @@
     static final int FLAG_HAS_BIGRAMS = 0x04;
     static final int FLAG_IS_NOT_A_WORD = 0x02;
     static final int FLAG_IS_BLACKLISTED = 0x01;
-    static final int FLAG_IS_MOVED = 0x40;
+
+    // These flags are used only in the dynamic dictionary.
+    static final int MASK_MOVE_AND_DELETE_FLAG = 0xC0;
+    static final int FIXED_BIT_OF_DYNAMIC_UPDATE_MOVE = 0x40;
+    static final int FLAG_IS_MOVED = 0x00 | FIXED_BIT_OF_DYNAMIC_UPDATE_MOVE;
+    static final int FLAG_IS_NOT_MOVED = 0x80 | FIXED_BIT_OF_DYNAMIC_UPDATE_MOVE;
+    static final int FLAG_IS_DELETED = 0x80;
 
     static final int FLAG_ATTRIBUTE_HAS_NEXT = 0x80;
     static final int FLAG_ATTRIBUTE_OFFSET_NEGATIVE = 0x40;
@@ -210,6 +219,7 @@
 
     static final int MAX_CHARGROUPS_FOR_ONE_BYTE_CHARGROUP_COUNT = 0x7F; // 127
     static final int MAX_CHARGROUPS_IN_A_NODE = 0x7FFF; // 32767
+    static final int MAX_BIGRAMS_IN_A_GROUP = 10000;
 
     static final int MAX_TERMINAL_FREQUENCY = 255;
     static final int MAX_BIGRAM_FREQUENCY = 15;
diff --git a/java/src/com/android/inputmethod/latin/makedict/FusionDictionary.java b/java/src/com/android/inputmethod/latin/makedict/FusionDictionary.java
index 3193ef4..6f1faa1 100644
--- a/java/src/com/android/inputmethod/latin/makedict/FusionDictionary.java
+++ b/java/src/com/android/inputmethod/latin/makedict/FusionDictionary.java
@@ -279,7 +279,7 @@
     /**
      * Helper method to convert a String to an int array.
      */
-    static private int[] getCodePoints(final String word) {
+    static int[] getCodePoints(final String word) {
         // TODO: this is a copy-paste of the contents of StringUtils.toCodePointArray,
         // which is not visible from the makedict package. Factor this code.
         final char[] characters = word.toCharArray();
diff --git a/java/src/com/android/inputmethod/latin/suggestions/MoreSuggestions.java b/java/src/com/android/inputmethod/latin/suggestions/MoreSuggestions.java
index 4e9fd19..4262695 100644
--- a/java/src/com/android/inputmethod/latin/suggestions/MoreSuggestions.java
+++ b/java/src/com/android/inputmethod/latin/suggestions/MoreSuggestions.java
@@ -22,7 +22,6 @@
 
 import com.android.inputmethod.keyboard.Key;
 import com.android.inputmethod.keyboard.Keyboard;
-import com.android.inputmethod.keyboard.KeyboardSwitcher;
 import com.android.inputmethod.keyboard.internal.KeyboardBuilder;
 import com.android.inputmethod.keyboard.internal.KeyboardIconsSet;
 import com.android.inputmethod.keyboard.internal.KeyboardParams;
@@ -176,11 +175,11 @@
         }
 
         public Builder layout(final SuggestedWords suggestions, final int fromPos,
-                final int maxWidth, final int minWidth, final int maxRow) {
-            final Keyboard keyboard = KeyboardSwitcher.getInstance().getKeyboard();
+                final int maxWidth, final int minWidth, final int maxRow,
+                final Keyboard parentKeyboard) {
             final int xmlId = R.xml.kbd_suggestions_pane_template;
-            load(xmlId, keyboard.mId);
-            mParams.mVerticalGap = mParams.mTopPadding = keyboard.mVerticalGap / 2;
+            load(xmlId, parentKeyboard.mId);
+            mParams.mVerticalGap = mParams.mTopPadding = parentKeyboard.mVerticalGap / 2;
 
             mPaneView.updateKeyboardGeometry(mParams.mDefaultRowHeight);
             final int count = mParams.layout(suggestions, fromPos, maxWidth, minWidth, maxRow,
diff --git a/java/src/com/android/inputmethod/latin/suggestions/MoreSuggestionsView.java b/java/src/com/android/inputmethod/latin/suggestions/MoreSuggestionsView.java
index 03a2e73..6cdd9e2 100644
--- a/java/src/com/android/inputmethod/latin/suggestions/MoreSuggestionsView.java
+++ b/java/src/com/android/inputmethod/latin/suggestions/MoreSuggestionsView.java
@@ -56,17 +56,17 @@
     final KeyboardActionListener mSuggestionsPaneListener =
             new KeyboardActionListener.Adapter() {
         @Override
-        public void onPressKey(int primaryCode) {
+        public void onPressKey(final int primaryCode) {
             mListener.onPressKey(primaryCode);
         }
 
         @Override
-        public void onReleaseKey(int primaryCode, boolean withSliding) {
+        public void onReleaseKey(final int primaryCode, final boolean withSliding) {
             mListener.onReleaseKey(primaryCode, withSliding);
         }
 
         @Override
-        public void onCodeInput(int primaryCode, int x, int y) {
+        public void onCodeInput(final int primaryCode, final int x, final int y) {
             final int index = primaryCode - MoreSuggestions.SUGGESTION_CODE_BASE;
             if (index >= 0 && index < SuggestionStripView.MAX_SUGGESTIONS) {
                 mListener.onCustomRequest(index);
@@ -79,11 +79,12 @@
         }
     };
 
-    public MoreSuggestionsView(Context context, AttributeSet attrs) {
+    public MoreSuggestionsView(final Context context, final AttributeSet attrs) {
         this(context, attrs, R.attr.moreSuggestionsViewStyle);
     }
 
-    public MoreSuggestionsView(Context context, AttributeSet attrs, int defStyle) {
+    public MoreSuggestionsView(final Context context, final AttributeSet attrs,
+            final int defStyle) {
         super(context, attrs, defStyle);
 
         final Resources res = context.getResources();
@@ -94,7 +95,7 @@
     }
 
     @Override
-    protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
+    protected void onMeasure(final int widthMeasureSpec, final int heightMeasureSpec) {
         final Keyboard keyboard = getKeyboard();
         if (keyboard != null) {
             final int width = keyboard.mOccupiedWidth + getPaddingLeft() + getPaddingRight();
@@ -110,7 +111,7 @@
     }
 
     @Override
-    public void setKeyboard(Keyboard keyboard) {
+    public void setKeyboard(final Keyboard keyboard) {
         super.setKeyboard(keyboard);
         mModalPanelKeyDetector.setKeyboard(keyboard, -getPaddingLeft(), -getPaddingTop());
         mSlidingPanelKeyDetector.setKeyboard(keyboard, -getPaddingLeft(),
@@ -138,15 +139,16 @@
     }
 
     @Override
-    public void setKeyPreviewPopupEnabled(boolean previewEnabled, int delay) {
+    public void setKeyPreviewPopupEnabled(final boolean previewEnabled, final int delay) {
         // Suggestions pane needs no pop-up key preview displayed, so we pass always false with a
         // delay of 0. The delay does not matter actually since the popup is not shown anyway.
         super.setKeyPreviewPopupEnabled(false, 0);
     }
 
     @Override
-    public void showMoreKeysPanel(View parentView, Controller controller, int pointX, int pointY,
-            PopupWindow window, KeyboardActionListener listener) {
+    public void showMoreKeysPanel(final View parentView, final Controller controller,
+            final int pointX, final int pointY, final PopupWindow window,
+            final KeyboardActionListener listener) {
         mController = controller;
         mListener = listener;
         final View container = (View)getParent();
@@ -179,12 +181,12 @@
     }
 
     @Override
-    public int translateX(int x) {
+    public int translateX(final int x) {
         return x - mOriginX;
     }
 
     @Override
-    public int translateY(int y) {
+    public int translateY(final int y) {
         return y - mOriginY;
     }
 
@@ -211,7 +213,7 @@
     };
 
     @Override
-    public boolean onTouchEvent(MotionEvent me) {
+    public boolean onTouchEvent(final MotionEvent me) {
         final int action = me.getAction();
         final long eventTime = me.getEventTime();
         final int index = me.getActionIndex();
diff --git a/java/src/com/android/inputmethod/latin/suggestions/SuggestionStripView.java b/java/src/com/android/inputmethod/latin/suggestions/SuggestionStripView.java
index e926fa2..6056af9 100644
--- a/java/src/com/android/inputmethod/latin/suggestions/SuggestionStripView.java
+++ b/java/src/com/android/inputmethod/latin/suggestions/SuggestionStripView.java
@@ -52,7 +52,9 @@
 import android.widget.RelativeLayout;
 import android.widget.TextView;
 
+import com.android.inputmethod.keyboard.Keyboard;
 import com.android.inputmethod.keyboard.KeyboardActionListener;
+import com.android.inputmethod.keyboard.KeyboardSwitcher;
 import com.android.inputmethod.keyboard.KeyboardView;
 import com.android.inputmethod.keyboard.MoreKeysPanel;
 import com.android.inputmethod.keyboard.PointerTracker;
@@ -83,7 +85,7 @@
     static final boolean DBG = LatinImeLogger.sDBG;
 
     private final ViewGroup mSuggestionsStrip;
-    private KeyboardView mKeyboardView;
+    KeyboardView mKeyboardView;
 
     private final View mMoreSuggestionsContainer;
     private final MoreSuggestionsView mMoreSuggestionsView;
@@ -97,8 +99,8 @@
     private final PopupWindow mPreviewPopup;
     private final TextView mPreviewText;
 
-    private Listener mListener;
-    private SuggestedWords mSuggestedWords = SuggestedWords.EMPTY;
+    Listener mListener;
+    SuggestedWords mSuggestedWords = SuggestedWords.EMPTY;
 
     private final SuggestionStripViewParams mParams;
     private static final float MIN_TEXT_XSCALE = 0.70f;
@@ -108,12 +110,12 @@
     private static final class UiHandler extends StaticInnerHandlerWrapper<SuggestionStripView> {
         private static final int MSG_HIDE_PREVIEW = 0;
 
-        public UiHandler(SuggestionStripView outerInstance) {
+        public UiHandler(final SuggestionStripView outerInstance) {
             super(outerInstance);
         }
 
         @Override
-        public void dispatchMessage(Message msg) {
+        public void dispatchMessage(final Message msg) {
             final SuggestionStripView suggestionStripView = getOuterInstance();
             switch (msg.what) {
             case MSG_HIDE_PREVIEW:
@@ -177,8 +179,9 @@
         private final TextView mLeftwardsArrowView;
         private final TextView mHintToSaveView;
 
-        public SuggestionStripViewParams(Context context, AttributeSet attrs, int defStyle,
-                ArrayList<TextView> words, ArrayList<View> dividers, ArrayList<TextView> infos) {
+        public SuggestionStripViewParams(final Context context, final AttributeSet attrs,
+                final int defStyle, final ArrayList<TextView> words, final ArrayList<View> dividers,
+                final ArrayList<TextView> infos) {
             mWords = words;
             mDividers = dividers;
             mInfos = infos;
@@ -250,7 +253,7 @@
             return mMaxMoreSuggestionsRow * mMoreSuggestionsRowHeight + mMoreSuggestionsBottomGap;
         }
 
-        public int setMoreSuggestionsHeight(int remainingHeight) {
+        public int setMoreSuggestionsHeight(final int remainingHeight) {
             final int currentHeight = getMoreSuggestionsHeight();
             if (currentHeight <= remainingHeight) {
                 return currentHeight;
@@ -262,7 +265,8 @@
             return newHeight;
         }
 
-        private static Drawable getMoreSuggestionsHint(Resources res, float textSize, int color) {
+        private static Drawable getMoreSuggestionsHint(final Resources res, final float textSize,
+                final int color) {
             final Paint paint = new Paint();
             paint.setAntiAlias(true);
             paint.setTextAlign(Align.CENTER);
@@ -279,7 +283,8 @@
             return new BitmapDrawable(res, buffer);
         }
 
-        private CharSequence getStyledSuggestionWord(SuggestedWords suggestedWords, int pos) {
+        private CharSequence getStyledSuggestionWord(final SuggestedWords suggestedWords,
+                final int pos) {
             final CharSequence word = suggestedWords.getWord(pos);
             final boolean isAutoCorrect = pos == 1 && suggestedWords.willAutoCorrect();
             final boolean isTypedWordValid = pos == 0 && suggestedWords.mTypedWordValid;
@@ -299,7 +304,7 @@
             return spannedWord;
         }
 
-        private int getWordPosition(int index, SuggestedWords suggestedWords) {
+        private int getWordPosition(final int index, final SuggestedWords suggestedWords) {
             // TODO: This works for 3 suggestions. Revisit this algorithm when there are 5 or more
             // suggestions.
             final int centerPos = suggestedWords.willAutoCorrect() ? 1 : 0;
@@ -312,7 +317,8 @@
             }
         }
 
-        private int getSuggestionTextColor(int index, SuggestedWords suggestedWords, int pos) {
+        private int getSuggestionTextColor(final int index, final SuggestedWords suggestedWords,
+                final int pos) {
             // TODO: Need to revisit this logic with bigram suggestions
             final boolean isSuggested = (pos != 0);
 
@@ -355,8 +361,8 @@
             params.gravity = Gravity.CENTER;
         }
 
-        public void layout(SuggestedWords suggestedWords, ViewGroup stripView, ViewGroup placer,
-                int stripWidth) {
+        public void layout(final SuggestedWords suggestedWords, final ViewGroup stripView,
+                final ViewGroup placer, final int stripWidth) {
             if (suggestedWords.mIsPunctuationSuggestions) {
                 layoutPunctuationSuggestions(suggestedWords, stripView);
                 return;
@@ -418,14 +424,14 @@
             }
         }
 
-        private int getSuggestionWidth(int index, int maxWidth) {
+        private int getSuggestionWidth(final int index, final int maxWidth) {
             final int paddings = mPadding * mSuggestionsCountInStrip;
             final int dividers = mDividerWidth * (mSuggestionsCountInStrip - 1);
             final int availableWidth = maxWidth - paddings - dividers;
             return (int)(availableWidth * getSuggestionWeight(index));
         }
 
-        private float getSuggestionWeight(int index) {
+        private float getSuggestionWeight(final int index) {
             if (index == mCenterSuggestionIndex) {
                 return mCenterSuggestionWeight;
             } else {
@@ -434,7 +440,7 @@
             }
         }
 
-        private void setupTexts(SuggestedWords suggestedWords, int countInStrip) {
+        private void setupTexts(final SuggestedWords suggestedWords, final int countInStrip) {
             mTexts.clear();
             final int count = Math.min(suggestedWords.size(), countInStrip);
             for (int pos = 0; pos < count; pos++) {
@@ -447,8 +453,8 @@
             }
         }
 
-        private void layoutPunctuationSuggestions(SuggestedWords suggestedWords,
-                ViewGroup stripView) {
+        private void layoutPunctuationSuggestions(final SuggestedWords suggestedWords,
+                final ViewGroup stripView) {
             final int countInStrip = Math.min(suggestedWords.size(), PUNCTUATIONS_IN_STRIP);
             for (int index = 0; index < countInStrip; index++) {
                 if (index != 0) {
@@ -469,8 +475,8 @@
             mMoreSuggestionsAvailable = false;
         }
 
-        public void layoutAddToDictionaryHint(CharSequence word, ViewGroup stripView,
-                int stripWidth, CharSequence hintText, OnClickListener listener) {
+        public void layoutAddToDictionaryHint(final CharSequence word, final ViewGroup stripView,
+                final int stripWidth, final CharSequence hintText, final OnClickListener listener) {
             final int width = stripWidth - mDividerWidth - mPadding * 2;
 
             final TextView wordView = mWordToSaveView;
@@ -511,11 +517,11 @@
             return (CharSequence)mWordToSaveView.getTag();
         }
 
-        public boolean isAddToDictionaryShowing(View v) {
+        public boolean isAddToDictionaryShowing(final View v) {
             return v == mWordToSaveView || v == mHintToSaveView || v == mLeftwardsArrowView;
         }
 
-        private static void setLayoutWeight(View v, float weight, int height) {
+        private static void setLayoutWeight(final View v, final float weight, final int height) {
             final ViewGroup.LayoutParams lp = v.getLayoutParams();
             if (lp instanceof LinearLayout.LayoutParams) {
                 final LinearLayout.LayoutParams llp = (LinearLayout.LayoutParams)lp;
@@ -525,7 +531,8 @@
             }
         }
 
-        private static float getTextScaleX(CharSequence text, int maxWidth, TextPaint paint) {
+        private static float getTextScaleX(final CharSequence text, final int maxWidth,
+                final TextPaint paint) {
             paint.setTextScaleX(1.0f);
             final int width = getTextWidth(text, paint);
             if (width <= maxWidth) {
@@ -534,8 +541,8 @@
             return maxWidth / (float)width;
         }
 
-        private static CharSequence getEllipsizedText(CharSequence text, int maxWidth,
-                TextPaint paint) {
+        private static CharSequence getEllipsizedText(final CharSequence text, final int maxWidth,
+                final TextPaint paint) {
             if (text == null) return null;
             paint.setTextScaleX(1.0f);
             final int width = getTextWidth(text, paint);
@@ -556,7 +563,7 @@
             return ellipsized;
         }
 
-        private static int getTextWidth(CharSequence text, TextPaint paint) {
+        private static int getTextWidth(final CharSequence text, final TextPaint paint) {
             if (TextUtils.isEmpty(text)) return 0;
             final Typeface savedTypeface = paint.getTypeface();
             paint.setTypeface(getTextTypeface(text));
@@ -571,7 +578,7 @@
             return width;
         }
 
-        private static Typeface getTextTypeface(CharSequence text) {
+        private static Typeface getTextTypeface(final CharSequence text) {
             if (!(text instanceof SpannableString))
                 return Typeface.DEFAULT;
 
@@ -593,11 +600,12 @@
      * @param context
      * @param attrs
      */
-    public SuggestionStripView(Context context, AttributeSet attrs) {
+    public SuggestionStripView(final Context context, final AttributeSet attrs) {
         this(context, attrs, R.attr.suggestionStripViewStyle);
     }
 
-    public SuggestionStripView(Context context, AttributeSet attrs, int defStyle) {
+    public SuggestionStripView(final Context context, final AttributeSet attrs,
+            final int defStyle) {
         super(context, attrs, defStyle);
 
         final LayoutInflater inflater = LayoutInflater.from(context);
@@ -658,15 +666,12 @@
      * A connection back to the input method.
      * @param listener
      */
-    public void setListener(Listener listener, View inputView) {
+    public void setListener(final Listener listener, final View inputView) {
         mListener = listener;
         mKeyboardView = (KeyboardView)inputView.findViewById(R.id.keyboard_view);
     }
 
-    public void setSuggestions(SuggestedWords suggestedWords) {
-        if (suggestedWords == null)
-            return;
-
+    public void setSuggestions(final SuggestedWords suggestedWords) {
         clear();
         mSuggestedWords = suggestedWords;
         mParams.layout(mSuggestedWords, mSuggestionsStrip, this, getWidth());
@@ -675,7 +680,7 @@
         }
     }
 
-    public int setMoreSuggestionsHeight(int remainingHeight) {
+    public int setMoreSuggestionsHeight(final int remainingHeight) {
         return mParams.setMoreSuggestionsHeight(remainingHeight);
     }
 
@@ -684,7 +689,7 @@
                 && mParams.isAddToDictionaryShowing(mSuggestionsStrip.getChildAt(0));
     }
 
-    public void showAddToDictionaryHint(CharSequence word, CharSequence hintText) {
+    public void showAddToDictionaryHint(final CharSequence word, final CharSequence hintText) {
         clear();
         mParams.layoutAddToDictionaryHint(word, mSuggestionsStrip, getWidth(), hintText, this);
     }
@@ -708,14 +713,14 @@
         dismissMoreSuggestions();
     }
 
-    private void hidePreview() {
+    void hidePreview() {
         mPreviewPopup.dismiss();
     }
 
     private final KeyboardActionListener mMoreSuggestionsListener =
             new KeyboardActionListener.Adapter() {
         @Override
-        public boolean onCustomRequest(int requestCode) {
+        public boolean onCustomRequest(final int requestCode) {
             final int index = requestCode;
             final CharSequence word = mSuggestedWords.getWord(index);
             mListener.pickSuggestionManually(index, word);
@@ -737,7 +742,7 @@
         }
     };
 
-    private boolean dismissMoreSuggestions() {
+    boolean dismissMoreSuggestions() {
         if (mMoreSuggestionsWindow.isShowing()) {
             mMoreSuggestionsWindow.dismiss();
             return true;
@@ -746,41 +751,42 @@
     }
 
     @Override
-    public boolean onLongClick(View view) {
+    public boolean onLongClick(final View view) {
         return showMoreSuggestions();
     }
 
-    private boolean showMoreSuggestions() {
-        final SuggestionStripViewParams params = mParams;
-        if (params.mMoreSuggestionsAvailable) {
-            final int stripWidth = getWidth();
-            final View container = mMoreSuggestionsContainer;
-            final int maxWidth = stripWidth - container.getPaddingLeft()
-                    - container.getPaddingRight();
-            final MoreSuggestions.Builder builder = mMoreSuggestionsBuilder;
-            builder.layout(mSuggestedWords, params.mSuggestionsCountInStrip, maxWidth,
-                    (int)(maxWidth * params.mMinMoreSuggestionsWidth),
-                    params.getMaxMoreSuggestionsRow());
-            mMoreSuggestionsView.setKeyboard(builder.build());
-            container.measure(
-                    ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
-
-            final MoreKeysPanel moreKeysPanel = mMoreSuggestionsView;
-            final int pointX = stripWidth / 2;
-            final int pointY = -params.mMoreSuggestionsBottomGap;
-            moreKeysPanel.showMoreKeysPanel(
-                    this, mMoreSuggestionsController, pointX, pointY,
-                    mMoreSuggestionsWindow, mMoreSuggestionsListener);
-            mMoreSuggestionsMode = MORE_SUGGESTIONS_CHECKING_MODAL_OR_SLIDING;
-            mOriginX = mLastX;
-            mOriginY = mLastY;
-            mKeyboardView.dimEntireKeyboard(true);
-            for (int i = 0; i < params.mSuggestionsCountInStrip; i++) {
-                mWords.get(i).setPressed(false);
-            }
-            return true;
+    boolean showMoreSuggestions() {
+        final Keyboard parentKeyboard = KeyboardSwitcher.getInstance().getKeyboard();
+        if (parentKeyboard == null) {
+            return false;
         }
-        return false;
+        final SuggestionStripViewParams params = mParams;
+        if (!params.mMoreSuggestionsAvailable) {
+            return false;
+        }
+        final int stripWidth = getWidth();
+        final View container = mMoreSuggestionsContainer;
+        final int maxWidth = stripWidth - container.getPaddingLeft() - container.getPaddingRight();
+        final MoreSuggestions.Builder builder = mMoreSuggestionsBuilder;
+        builder.layout(mSuggestedWords, params.mSuggestionsCountInStrip, maxWidth,
+                (int)(maxWidth * params.mMinMoreSuggestionsWidth),
+                params.getMaxMoreSuggestionsRow(), parentKeyboard);
+        mMoreSuggestionsView.setKeyboard(builder.build());
+        container.measure(ViewGroup.LayoutParams.WRAP_CONTENT, ViewGroup.LayoutParams.WRAP_CONTENT);
+
+        final MoreKeysPanel moreKeysPanel = mMoreSuggestionsView;
+        final int pointX = stripWidth / 2;
+        final int pointY = -params.mMoreSuggestionsBottomGap;
+        moreKeysPanel.showMoreKeysPanel(this, mMoreSuggestionsController, pointX, pointY,
+                mMoreSuggestionsWindow, mMoreSuggestionsListener);
+        mMoreSuggestionsMode = MORE_SUGGESTIONS_CHECKING_MODAL_OR_SLIDING;
+        mOriginX = mLastX;
+        mOriginY = mLastY;
+        mKeyboardView.dimEntireKeyboard(true);
+        for (int i = 0; i < params.mSuggestionsCountInStrip; i++) {
+            mWords.get(i).setPressed(false);
+        }
+        return true;
     }
 
     // Working variables for onLongClick and dispatchTouchEvent.
@@ -807,7 +813,7 @@
     };
 
     @Override
-    public boolean dispatchTouchEvent(MotionEvent me) {
+    public boolean dispatchTouchEvent(final MotionEvent me) {
         if (!mMoreSuggestionsWindow.isShowing()
                 || mMoreSuggestionsMode == MORE_SUGGESTIONS_IN_MODAL_MODE) {
             mLastX = (int)me.getX();
@@ -849,7 +855,7 @@
     }
 
     @Override
-    public void onClick(View view) {
+    public void onClick(final View view) {
         if (mParams.isAddToDictionaryShowing(view)) {
             mListener.addWordToUserDictionary(mParams.getAddToDictionaryWord().toString());
             clear();
diff --git a/native/jni/com_android_inputmethod_keyboard_ProximityInfo.cpp b/native/jni/com_android_inputmethod_keyboard_ProximityInfo.cpp
index 560b3a5..2423bb5 100644
--- a/native/jni/com_android_inputmethod_keyboard_ProximityInfo.cpp
+++ b/native/jni/com_android_inputmethod_keyboard_ProximityInfo.cpp
@@ -17,6 +17,7 @@
 #define LOG_TAG "LatinIME: jni: ProximityInfo"
 
 #include "com_android_inputmethod_keyboard_ProximityInfo.h"
+#include "defines.h"
 #include "jni.h"
 #include "jni_common.h"
 #include "proximity_info.h"
@@ -41,7 +42,7 @@
     delete pi;
 }
 
-static JNINativeMethod sKeyboardMethods[] = {
+static JNINativeMethod sMethods[] = {
     {"setProximityInfoNative", "(Ljava/lang/String;IIIIII[II[I[I[I[I[I[F[F[F)J",
             reinterpret_cast<void *>(latinime_Keyboard_setProximityInfo)},
     {"releaseProximityInfoNative", "(J)V", reinterpret_cast<void *>(latinime_Keyboard_release)}
@@ -49,7 +50,6 @@
 
 int register_ProximityInfo(JNIEnv *env) {
     const char *const kClassPathName = "com/android/inputmethod/keyboard/ProximityInfo";
-    return registerNativeMethods(env, kClassPathName, sKeyboardMethods,
-            sizeof(sKeyboardMethods) / sizeof(sKeyboardMethods[0]));
+    return registerNativeMethods(env, kClassPathName, sMethods, NELEMS(sMethods));
 }
 } // namespace latinime
diff --git a/native/jni/com_android_inputmethod_latin_BinaryDictionary.cpp b/native/jni/com_android_inputmethod_latin_BinaryDictionary.cpp
index dd2513f..42f7da9 100644
--- a/native/jni/com_android_inputmethod_latin_BinaryDictionary.cpp
+++ b/native/jni/com_android_inputmethod_latin_BinaryDictionary.cpp
@@ -44,9 +44,8 @@
 static void releaseDictBuf(const void *dictBuf, const size_t length, const int fd);
 
 static jlong latinime_BinaryDictionary_open(JNIEnv *env, jobject object,
-        jstring sourceDir, jlong dictOffset, jlong dictSize,
-        jint typedLetterMultiplier, jint fullWordMultiplier, jint maxWordLength, jint maxWords,
-        jint maxPredictions) {
+        jstring sourceDir, jlong dictOffset, jlong dictSize, jint fullWordMultiplier,
+        jint maxWordLength, jint maxWords, jint maxPredictions) {
     PROF_OPEN;
     PROF_START(66);
     const jsize sourceDirUtf8Length = env->GetStringUTFLength(sourceDir);
@@ -121,7 +120,7 @@
 #endif // USE_MMAP_FOR_DICTIONARY
     } else {
         dictionary = new Dictionary(dictBuf, static_cast<int>(dictSize), fd, adjust,
-                typedLetterMultiplier, fullWordMultiplier, maxWordLength, maxWords, maxPredictions);
+                fullWordMultiplier, maxWordLength, maxWords, maxPredictions);
     }
     PROF_END(66);
     PROF_CLOSE;
@@ -277,7 +276,7 @@
 }
 
 static JNINativeMethod sMethods[] = {
-    {"openNative", "(Ljava/lang/String;JJIIIII)J",
+    {"openNative", "(Ljava/lang/String;JJIIII)J",
             reinterpret_cast<void *>(latinime_BinaryDictionary_open)},
     {"closeNative", "(J)V", reinterpret_cast<void *>(latinime_BinaryDictionary_close)},
     {"getSuggestionsNative", "(JJJ[I[I[I[I[IIIZ[IZ[C[I[I[I)I",
@@ -294,7 +293,6 @@
 
 int register_BinaryDictionary(JNIEnv *env) {
     const char *const kClassPathName = "com/android/inputmethod/latin/BinaryDictionary";
-    return registerNativeMethods(env, kClassPathName, sMethods,
-            sizeof(sMethods) / sizeof(sMethods[0]));
+    return registerNativeMethods(env, kClassPathName, sMethods, NELEMS(sMethods));
 }
 } // namespace latinime
diff --git a/native/jni/com_android_inputmethod_latin_DicTraverseSession.cpp b/native/jni/com_android_inputmethod_latin_DicTraverseSession.cpp
index 5d405f1..7bb8dc5 100644
--- a/native/jni/com_android_inputmethod_latin_DicTraverseSession.cpp
+++ b/native/jni/com_android_inputmethod_latin_DicTraverseSession.cpp
@@ -17,6 +17,7 @@
 #define LOG_TAG "LatinIME: jni: Session"
 
 #include "com_android_inputmethod_latin_DicTraverseSession.h"
+#include "defines.h"
 #include "dic_traverse_wrapper.h"
 #include "jni.h"
 #include "jni_common.h"
@@ -57,7 +58,6 @@
 
 int register_DicTraverseSession(JNIEnv *env) {
     const char *const kClassPathName = "com/android/inputmethod/latin/DicTraverseSession";
-    return registerNativeMethods(env, kClassPathName, sMethods,
-            sizeof(sMethods) / sizeof(sMethods[0]));
+    return registerNativeMethods(env, kClassPathName, sMethods, NELEMS(sMethods));
 }
 } // namespace latinime
diff --git a/native/jni/src/char_utils.cpp b/native/jni/src/char_utils.cpp
index d0547a9..9d27cad 100644
--- a/native/jni/src/char_utils.cpp
+++ b/native/jni/src/char_utils.cpp
@@ -17,6 +17,7 @@
 #include <cstdlib>
 
 #include "char_utils.h"
+#include "defines.h"
 
 namespace latinime {
 
@@ -33,7 +34,7 @@
 //
 //    unsigned short c, cc, ccc, ccc2;
 //    for (c = 0; c < 0xFFFF ; c++) {
-//        if (c < sizeof(BASE_CHARS) / sizeof(BASE_CHARS[0])) {
+//        if (c < NELEMS(BASE_CHARS)) {
 //            cc = BASE_CHARS[c];
 //        } else {
 //            cc = c;
@@ -894,9 +895,7 @@
 unsigned short latin_tolower(const unsigned short c) {
     struct LatinCapitalSmallPair *p =
             static_cast<struct LatinCapitalSmallPair *>(bsearch(&c, SORTED_CHAR_MAP,
-                    sizeof(SORTED_CHAR_MAP) / sizeof(SORTED_CHAR_MAP[0]),
-                    sizeof(SORTED_CHAR_MAP[0]),
-                    compare_pair_capital));
+                    NELEMS(SORTED_CHAR_MAP), sizeof(SORTED_CHAR_MAP[0]), compare_pair_capital));
     return p ? p->small : c;
 }
 } // namespace latinime
diff --git a/native/jni/src/correction.cpp b/native/jni/src/correction.cpp
index 524abe9..d57b0e3 100644
--- a/native/jni/src/correction.cpp
+++ b/native/jni/src/correction.cpp
@@ -1118,7 +1118,7 @@
     const int distance = editDistance(before, beforeLength, after, afterLength);
     int spaceCount = 0;
     for (int i = 0; i < afterLength; ++i) {
-        if (after[i] == CODE_SPACE) {
+        if (after[i] == KEYCODE_SPACE) {
             ++spaceCount;
         }
     }
diff --git a/native/jni/src/correction.h b/native/jni/src/correction.h
index f016d54..a099853 100644
--- a/native/jni/src/correction.h
+++ b/native/jni/src/correction.h
@@ -116,7 +116,6 @@
         static int editDistance(const unsigned short *before,
                 const int beforeLength, const unsigned short *after, const int afterLength);
      private:
-        static const int CODE_SPACE = ' ';
         static const int MAX_INITIAL_SCORE = 255;
     };
 
diff --git a/native/jni/src/defines.h b/native/jni/src/defines.h
index ea0f0ef..942068a 100644
--- a/native/jni/src/defines.h
+++ b/native/jni/src/defines.h
@@ -219,6 +219,8 @@
 #define DEBUG_CORRECTION false
 #define DEBUG_CORRECTION_FREQ false
 #define DEBUG_WORDS_PRIORITY_QUEUE false
+#define DEBUG_SAMPLING_POINTS true
+#define DEBUG_POINTS_PROBABILITY true
 
 #ifdef FLAG_FULL_DBG
 #define DEBUG_GEO_FULL true
@@ -239,6 +241,8 @@
 #define DEBUG_CORRECTION false
 #define DEBUG_CORRECTION_FREQ false
 #define DEBUG_WORDS_PRIORITY_QUEUE false
+#define DEBUG_SAMPLING_POINTS false
+#define DEBUG_POINTS_PROBABILITY false
 
 #define DEBUG_GEO_FULL false
 
@@ -344,8 +348,8 @@
 #define MULTIPLE_WORDS_DEMOTION_RATE 80
 #define MIN_INPUT_LENGTH_FOR_THREE_OR_MORE_WORDS_CORRECTION 6
 
-#define TWO_WORDS_CORRECTION_WITH_OTHER_ERROR_THRESHOLD 0.35
-#define START_TWO_WORDS_CORRECTION_THRESHOLD 0.185
+#define TWO_WORDS_CORRECTION_WITH_OTHER_ERROR_THRESHOLD 0.35f
+#define START_TWO_WORDS_CORRECTION_THRESHOLD 0.185f
 /* heuristic... This should be changed if we change the unit of the frequency. */
 #define SUPPRESS_SHORT_MULTIPLE_WORDS_THRESHOLD_FREQ (MAX_FREQ * 58 / 100)
 
@@ -392,6 +396,8 @@
 template<typename T> inline T min(T a, T b) { return a < b ? a : b; }
 template<typename T> inline T max(T a, T b) { return a > b ? a : b; }
 
+#define NELEMS(x) (sizeof(x) / sizeof((x)[0]))
+
 // The ratio of neutral area radius to sweet spot radius.
 #define NEUTRAL_AREA_RADIUS_RATIO 1.3f
 
diff --git a/native/jni/src/dictionary.cpp b/native/jni/src/dictionary.cpp
index 2fbe83e..81789cc 100644
--- a/native/jni/src/dictionary.cpp
+++ b/native/jni/src/dictionary.cpp
@@ -30,13 +30,12 @@
 
 // TODO: Change the type of all keyCodes to uint32_t
 Dictionary::Dictionary(void *dict, int dictSize, int mmapFd, int dictBufAdjust,
-        int typedLetterMultiplier, int fullWordMultiplier, int maxWordLength, int maxWords,
-        int maxPredictions)
+        int fullWordMultiplier, int maxWordLength, int maxWords, int maxPredictions)
         : mDict(static_cast<unsigned char *>(dict)),
           mOffsetDict((static_cast<unsigned char *>(dict)) + BinaryFormat::getHeaderSize(mDict)),
           mDictSize(dictSize), mMmapFd(mmapFd), mDictBufAdjust(dictBufAdjust),
-          mUnigramDictionary(new UnigramDictionary(mOffsetDict, typedLetterMultiplier,
-                  fullWordMultiplier, maxWordLength, maxWords, BinaryFormat::getFlags(mDict))),
+          mUnigramDictionary(new UnigramDictionary(mOffsetDict, fullWordMultiplier, maxWordLength,
+                  maxWords, BinaryFormat::getFlags(mDict))),
           mBigramDictionary(new BigramDictionary(mOffsetDict, maxWordLength, maxPredictions)),
           mGestureDecoder(new GestureDecoderWrapper(maxWordLength, maxWords)) {
     if (DEBUG_DICT) {
diff --git a/native/jni/src/dictionary.h b/native/jni/src/dictionary.h
index a135889..120ca5f 100644
--- a/native/jni/src/dictionary.h
+++ b/native/jni/src/dictionary.h
@@ -41,8 +41,8 @@
     const static int KIND_SHORTCUT = 7; // A shortcut
     const static int KIND_PREDICTION = 8; // A prediction (== a suggestion with no input)
 
-    Dictionary(void *dict, int dictSize, int mmapFd, int dictBufAdjust, int typedLetterMultipler,
-            int fullWordMultiplier, int maxWordLength, int maxWords, int maxPredictions);
+    Dictionary(void *dict, int dictSize, int mmapFd, int dictBufAdjust, int fullWordMultiplier,
+            int maxWordLength, int maxWords, int maxPredictions);
 
     int getSuggestions(ProximityInfo *proximityInfo, void *traverseSession, int *xcoordinates,
             int *ycoordinates, int *times, int *pointerIds, int *codes, int codesSize,
diff --git a/native/jni/src/geometry_utils.h b/native/jni/src/geometry_utils.h
index 31359e1..ee7c985 100644
--- a/native/jni/src/geometry_utils.h
+++ b/native/jni/src/geometry_utils.h
@@ -85,5 +85,24 @@
     }
     return getSquaredDistanceFloat(x, y, projectionX, projectionY);
 }
+
+// Normal distribution N(u, sigma^2).
+struct NormalDistribution {
+    NormalDistribution(const float u, const float sigma)
+            : mU(u), mSigma(sigma),
+              mPreComputedNonExpPart(1.0f / sqrtf(2.0f * M_PI_F * SQUARE_FLOAT(sigma))),
+              mPreComputedExponentPart(-1.0f / (2.0f * SQUARE_FLOAT(sigma))) {}
+
+    float getProbabilityDensity(const float x) {
+        const float shiftedX = x - mU;
+        return mPreComputedNonExpPart * expf(mPreComputedExponentPart * SQUARE_FLOAT(shiftedX));
+    }
+private:
+    DISALLOW_IMPLICIT_CONSTRUCTORS(NormalDistribution);
+    float mU; // mean value
+    float mSigma; // standard deviation
+    float mPreComputedNonExpPart; // = 1 / sqrt(2 * PI * sigma^2)
+    float mPreComputedExponentPart; // = -1 / (2 * sigma^2)
+};
 } // namespace latinime
 #endif // LATINIME_GEOMETRY_UTILS_H
diff --git a/native/jni/src/proximity_info.cpp b/native/jni/src/proximity_info.cpp
index fde93b5..e2aa156 100644
--- a/native/jni/src/proximity_info.cpp
+++ b/native/jni/src/proximity_info.cpp
@@ -239,6 +239,9 @@
         // We do not have the coordinate data
         return NOT_AN_INDEX;
     }
+    if (c == NOT_A_CODE_POINT) {
+        return NOT_AN_INDEX;
+    }
     const int lowerCode = static_cast<int>(toLowerCase(c));
     hash_map_compat<int, int>::const_iterator mapPos = mCodeToKeyMap.find(lowerCode);
     if (mapPos != mCodeToKeyMap.end()) {
@@ -296,9 +299,7 @@
     return 0;
 }
 
-int ProximityInfo::getKeyKeyDistanceG(int key0, int key1) const {
-    const int keyId0 = getKeyIndexOf(key0);
-    const int keyId1 = getKeyIndexOf(key1);
+int ProximityInfo::getKeyKeyDistanceG(const int keyId0, const int keyId1) const {
     if (keyId0 >= 0 && keyId1 >= 0) {
         return mKeyKeyDistancesG[keyId0][keyId1];
     }
diff --git a/native/jni/src/proximity_info.h b/native/jni/src/proximity_info.h
index 70942aa..7ee15d5 100644
--- a/native/jni/src/proximity_info.h
+++ b/native/jni/src/proximity_info.h
@@ -109,7 +109,7 @@
     int getKeyCenterYOfCodePointG(int charCode) const;
     int getKeyCenterXOfKeyIdG(int keyId) const;
     int getKeyCenterYOfKeyIdG(int keyId) const;
-    int getKeyKeyDistanceG(int key0, int key1) const;
+    int getKeyKeyDistanceG(int keyId0, int keyId1) const;
 
  private:
     DISALLOW_IMPLICIT_CONSTRUCTORS(ProximityInfo);
diff --git a/native/jni/src/proximity_info_state.cpp b/native/jni/src/proximity_info_state.cpp
index 392ec81..d41acda 100644
--- a/native/jni/src/proximity_info_state.cpp
+++ b/native/jni/src/proximity_info_state.cpp
@@ -15,6 +15,7 @@
  */
 
 #include <cstring> // for memset()
+#include <sstream> // for debug prints
 #include <stdint.h>
 
 #define LOG_TAG "LatinIME: proximity_info_state.cpp"
@@ -104,7 +105,10 @@
         mLengthCache.clear();
         mDistanceCache.clear();
         mNearKeysVector.clear();
+        mSearchKeysVector.clear();
         mRelativeSpeeds.clear();
+        mCharProbabilities.clear();
+        mDirections.clear();
     }
     if (DEBUG_GEO_FULL) {
         AKLOGI("Init ProximityInfoState: reused points =  %d, last input size = %d",
@@ -130,6 +134,10 @@
         NearKeysDistanceMap *currentNearKeysDistances = &nearKeysDistances[0];
         NearKeysDistanceMap *prevNearKeysDistances = &nearKeysDistances[1];
         NearKeysDistanceMap *prevPrevNearKeysDistances = &nearKeysDistances[2];
+        // "sumAngle" is accumulated by each angle of input points. And when "sumAngle" exceeds
+        // the threshold we save that point, reset sumAngle. This aims to keep the figure of
+        // the curve.
+        float sumAngle = 0.0f;
 
         for (int i = pushTouchPointStartIndex; i <= lastInputIndex; ++i) {
             // Assuming pointerId == 0 if pointerIds is null.
@@ -142,9 +150,18 @@
                 const int x = proximityOnly ? NOT_A_COORDINATE : xCoordinates[i];
                 const int y = proximityOnly ? NOT_A_COORDINATE : yCoordinates[i];
                 const int time = times ? times[i] : -1;
+
+                if (i > 1) {
+                    const float prevAngle = getAngle(xCoordinates[i - 2], yCoordinates[i - 2],
+                            xCoordinates[i - 1], yCoordinates[i - 1]);
+                    const float currentAngle =
+                            getAngle(xCoordinates[i - 1], yCoordinates[i - 1], x, y);
+                    sumAngle += getAngleDiff(prevAngle, currentAngle);
+                }
+
                 if (pushTouchPoint(i, c, x, y, time, isGeometric /* do sampling */,
-                        i == lastInputIndex, currentNearKeysDistances, prevNearKeysDistances,
-                        prevPrevNearKeysDistances)) {
+                        i == lastInputIndex, sumAngle, currentNearKeysDistances,
+                        prevNearKeysDistances, prevPrevNearKeysDistances)) {
                     // Previous point information was popped.
                     NearKeysDistanceMap *tmp = prevNearKeysDistances;
                     prevNearKeysDistances = currentNearKeysDistances;
@@ -154,6 +171,7 @@
                     prevPrevNearKeysDistances = prevNearKeysDistances;
                     prevNearKeysDistances = currentNearKeysDistances;
                     currentNearKeysDistances = tmp;
+                    sumAngle = 0.0f;
                 }
             }
         }
@@ -161,43 +179,68 @@
     }
 
     if (mInputSize > 0 && isGeometric) {
-        int sumDuration = mTimes.back() - mTimes.front();
-        int sumLength = mLengthCache.back() - mLengthCache.front();
-        float averageSpeed = static_cast<float>(sumLength) / static_cast<float>(sumDuration);
+        // Relative speed calculation.
+        const int sumDuration = mTimes.back() - mTimes.front();
+        const int sumLength = mLengthCache.back() - mLengthCache.front();
+        const float averageSpeed = static_cast<float>(sumLength) / static_cast<float>(sumDuration);
         mRelativeSpeeds.resize(mInputSize);
         for (int i = lastSavedInputSize; i < mInputSize; ++i) {
             const int index = mInputIndice[i];
             int length = 0;
             int duration = 0;
-            if (index == 0 && index < inputSize - 1) {
-                length = getDistanceInt(xCoordinates[index], yCoordinates[index],
-                        xCoordinates[index + 1], yCoordinates[index + 1]);
-                duration = times[index + 1] - times[index];
-            } else if (index == inputSize - 1 && index > 0) {
-                length = getDistanceInt(xCoordinates[index - 1], yCoordinates[index - 1],
-                        xCoordinates[index], yCoordinates[index]);
-                duration = times[index] - times[index - 1];
-            } else if (0 < index && index < inputSize - 1) {
-                length = getDistanceInt(xCoordinates[index - 1], yCoordinates[index - 1],
-                        xCoordinates[index], yCoordinates[index])
-                        + getDistanceInt(xCoordinates[index], yCoordinates[index],
-                                xCoordinates[index + 1], yCoordinates[index + 1]);
-                duration = times[index + 1] - times[index - 1];
-            } else {
-                length = 0;
-                duration = 1;
+
+            // Calculate velocity by using distances and durations of
+            // NUM_POINTS_FOR_SPEED_CALCULATION points for both forward and backward.
+            static const int NUM_POINTS_FOR_SPEED_CALCULATION = 2;
+            for (int j = index; j < min(inputSize - 1, index + NUM_POINTS_FOR_SPEED_CALCULATION);
+                    ++j) {
+                if (i < mInputSize - 1 && j >= mInputIndice[i + 1]) {
+                    break;
+                }
+                length += getDistanceInt(xCoordinates[j], yCoordinates[j],
+                        xCoordinates[j + 1], yCoordinates[j + 1]);
+                duration += times[j + 1] - times[j];
             }
-            const float speed = static_cast<float>(length) / static_cast<float>(duration);
-            mRelativeSpeeds[i] = speed / averageSpeed;
+            for (int j = index - 1; j >= max(0, index - NUM_POINTS_FOR_SPEED_CALCULATION); --j) {
+                if (i > 0 && j < mInputIndice[i - 1]) {
+                    break;
+                }
+                length += getDistanceInt(xCoordinates[j], yCoordinates[j],
+                        xCoordinates[j + 1], yCoordinates[j + 1]);
+                duration += times[j + 1] - times[j];
+            }
+            if (duration == 0 || sumDuration == 0) {
+                // Cannot calculate speed; thus, it gives an average value (1.0);
+                mRelativeSpeeds[i] = 1.0f;
+            } else {
+                const float speed = static_cast<float>(length) / static_cast<float>(duration);
+                mRelativeSpeeds[i] = speed / averageSpeed;
+            }
+        }
+
+        // Direction calculation.
+        mDirections.resize(mInputSize - 1);
+        for (int i = max(0, lastSavedInputSize - 1); i < mInputSize - 1; ++i) {
+            mDirections[i] = getDirection(i, i + 1);
+        }
+
+    }
+
+    if (DEBUG_GEO_FULL) {
+        for (int i = 0; i < mInputSize; ++i) {
+            AKLOGI("Sampled(%d): x = %d, y = %d, time = %d", i, mInputXs[i], mInputYs[i],
+                    mTimes[i]);
         }
     }
 
     if (mInputSize > 0) {
         const int keyCount = mProximityInfo->getKeyCount();
         mNearKeysVector.resize(mInputSize);
+        mSearchKeysVector.resize(mInputSize);
         mDistanceCache.resize(mInputSize * keyCount);
         for (int i = lastSavedInputSize; i < mInputSize; ++i) {
             mNearKeysVector[i].reset();
+            mSearchKeysVector[i].reset();
             static const float NEAR_KEY_NORMALIZED_SQUARED_THRESHOLD = 4.0f;
             for (int k = 0; k < keyCount; ++k) {
                 const int index = i * keyCount + k;
@@ -207,29 +250,53 @@
                         mProximityInfo->getNormalizedSquaredDistanceFromCenterFloatG(k, x, y);
                 mDistanceCache[index] = normalizedSquaredDistance;
                 if (normalizedSquaredDistance < NEAR_KEY_NORMALIZED_SQUARED_THRESHOLD) {
-                    mNearKeysVector[i].set(k, 1);
+                    mNearKeysVector[i][k] = true;
                 }
             }
         }
+        if (isGeometric) {
+            // updates probabilities of skipping or mapping each key for all points.
+            updateAlignPointProbabilities(lastSavedInputSize);
 
-        static const float READ_FORWORD_LENGTH_SCALE = 0.95f;
-        const int readForwordLength = static_cast<int>(
-                hypotf(mProximityInfo->getKeyboardWidth(), mProximityInfo->getKeyboardHeight())
-                * READ_FORWORD_LENGTH_SCALE);
-        for (int i = 0; i < mInputSize; ++i) {
-            if (DEBUG_GEO_FULL) {
-                AKLOGI("Sampled(%d): x = %d, y = %d, time = %d", i, mInputXs[i], mInputYs[i],
-                        mTimes[i]);
-            }
-            for (int j = max(i + 1, lastSavedInputSize); j < mInputSize; ++j) {
-                if (mLengthCache[j] - mLengthCache[i] >= readForwordLength) {
-                    break;
+            static const float READ_FORWORD_LENGTH_SCALE = 0.95f;
+            const int readForwordLength = static_cast<int>(
+                    hypotf(mProximityInfo->getKeyboardWidth(), mProximityInfo->getKeyboardHeight())
+                            * READ_FORWORD_LENGTH_SCALE);
+            for (int i = 0; i < mInputSize; ++i) {
+                if (i >= lastSavedInputSize) {
+                    mSearchKeysVector[i].reset();
                 }
-                mNearKeysVector[i] |= mNearKeysVector[j];
+                for (int j = max(i, lastSavedInputSize); j < mInputSize; ++j) {
+                    if (mLengthCache[j] - mLengthCache[i] >= readForwordLength) {
+                        break;
+                    }
+                    mSearchKeysVector[i] |= mNearKeysVector[j];
+                }
             }
         }
     }
 
+    if (DEBUG_SAMPLING_POINTS) {
+        std::stringstream originalX, originalY, sampledX, sampledY;
+        for (int i = 0; i < inputSize; ++i) {
+            originalX << xCoordinates[i];
+            originalY << yCoordinates[i];
+            if (i != inputSize - 1) {
+                originalX << ";";
+                originalY << ";";
+            }
+        }
+        for (int i = 0; i < mInputSize; ++i) {
+            sampledX << mInputXs[i];
+            sampledY << mInputYs[i];
+            if (i != mInputSize - 1) {
+                sampledX << ";";
+                sampledY << ";";
+            }
+        }
+        AKLOGI("\n%s, %s,\n%s, %s,\n", originalX.str().c_str(), originalY.str().c_str(),
+                sampledX.str().c_str(), sampledY.str().c_str());
+    }
     // end
     ///////////////////////
 
@@ -294,7 +361,7 @@
 // the given point and the nearest key position.
 float ProximityInfoState::updateNearKeysDistances(const int x, const int y,
         NearKeysDistanceMap *const currentNearKeysDistances) {
-    static const float NEAR_KEY_THRESHOLD = 4.0f;
+    static const float NEAR_KEY_THRESHOLD = 2.0f;
 
     currentNearKeysDistances->clear();
     const int keyCount = mProximityInfo->getKeyCount();
@@ -332,64 +399,49 @@
 // Calculating a point score that indicates usefulness of the point.
 float ProximityInfoState::getPointScore(
         const int x, const int y, const int time, const bool lastPoint, const float nearest,
-        const NearKeysDistanceMap *const currentNearKeysDistances,
+        const float sumAngle, const NearKeysDistanceMap *const currentNearKeysDistances,
         const NearKeysDistanceMap *const prevNearKeysDistances,
         const NearKeysDistanceMap *const prevPrevNearKeysDistances) const {
     static const int DISTANCE_BASE_SCALE = 100;
-    static const int SAVE_DISTANCE_SCALE = 200;
-    static const int SKIP_DISTANCE_SCALE = 25;
-    static const int CHECK_LOCALMIN_DISTANCE_THRESHOLD_SCALE = 40;
-    static const int STRAIGHT_SKIP_DISTANCE_THRESHOLD_SCALE = 50;
-    static const int CORNER_CHECK_DISTANCE_THRESHOLD_SCALE = 27;
-    static const float SAVE_DISTANCE_SCORE = 2.0f;
-    static const float SKIP_DISTANCE_SCORE = -1.0f;
-    static const float CHECK_LOCALMIN_DISTANCE_SCORE = -1.0f;
-    static const float STRAIGHT_ANGLE_THRESHOLD = M_PI_F / 36.0f;
-    static const float STRAIGHT_SKIP_NEAREST_DISTANCE_THRESHOLD = 0.5f;
-    static const float STRAIGHT_SKIP_SCORE = -1.0f;
-    static const float CORNER_ANGLE_THRESHOLD = M_PI_F / 2.0f;
+    static const float NEAR_KEY_THRESHOLD = 0.6f;
+    static const int CORNER_CHECK_DISTANCE_THRESHOLD_SCALE = 25;
+    static const float NOT_LOCALMIN_DISTANCE_SCORE = -1.0f;
+    static const float LOCALMIN_DISTANCE_AND_NEAR_TO_KEY_SCORE = 1.0f;
+    static const float CORNER_ANGLE_THRESHOLD = M_PI_F * 2.0f / 3.0f;
+    static const float CORNER_SUM_ANGLE_THRESHOLD = M_PI_F / 4.0f;
     static const float CORNER_SCORE = 1.0f;
 
-    const std::size_t size = mInputXs.size();
-    if (size <= 1) {
+    const size_t size = mInputXs.size();
+    // If there is only one point, add this point. Besides, if the previous point's distance map
+    // is empty, we re-compute nearby keys distances from the current point.
+    // Note that the current point is the first point in the incremental input that needs to
+    // be re-computed.
+    if (size <= 1 || prevNearKeysDistances->empty()) {
         return 0.0f;
     }
+
     const int baseSampleRate = mProximityInfo->getMostCommonKeyWidth();
-    const int distNext = getDistanceInt(x, y, mInputXs.back(), mInputYs.back())
-            * DISTANCE_BASE_SCALE;
     const int distPrev = getDistanceInt(mInputXs.back(), mInputYs.back(),
             mInputXs[size - 2], mInputYs[size - 2]) * DISTANCE_BASE_SCALE;
     float score = 0.0f;
 
-    // Sum of distances
-    if (distPrev + distNext > baseSampleRate * SAVE_DISTANCE_SCALE) {
-        score +=  SAVE_DISTANCE_SCORE;
-    }
-    // Distance
-    if (distPrev < baseSampleRate * SKIP_DISTANCE_SCALE) {
-        score += SKIP_DISTANCE_SCORE;
-    }
     // Location
-    if (distPrev < baseSampleRate * CHECK_LOCALMIN_DISTANCE_THRESHOLD_SCALE) {
-        if (!isPrevLocalMin(currentNearKeysDistances, prevNearKeysDistances,
-            prevPrevNearKeysDistances)) {
-            score += CHECK_LOCALMIN_DISTANCE_SCORE;
-        }
+    if (!isPrevLocalMin(currentNearKeysDistances, prevNearKeysDistances,
+        prevPrevNearKeysDistances)) {
+        score += NOT_LOCALMIN_DISTANCE_SCORE;
+    } else if (nearest < NEAR_KEY_THRESHOLD) {
+        // Promote points nearby keys
+        score += LOCALMIN_DISTANCE_AND_NEAR_TO_KEY_SCORE;
     }
     // Angle
     const float angle1 = getAngle(x, y, mInputXs.back(), mInputYs.back());
     const float angle2 = getAngle(mInputXs.back(), mInputYs.back(),
             mInputXs[size - 2], mInputYs[size - 2]);
     const float angleDiff = getAngleDiff(angle1, angle2);
-    // Skip straight
-    if (nearest > STRAIGHT_SKIP_NEAREST_DISTANCE_THRESHOLD
-            && distPrev < baseSampleRate * STRAIGHT_SKIP_DISTANCE_THRESHOLD_SCALE
-            && angleDiff < STRAIGHT_ANGLE_THRESHOLD) {
-        score += STRAIGHT_SKIP_SCORE;
-    }
+
     // Save corner
     if (distPrev > baseSampleRate * CORNER_CHECK_DISTANCE_THRESHOLD_SCALE
-            && angleDiff > CORNER_ANGLE_THRESHOLD) {
+            && (sumAngle > CORNER_SUM_ANGLE_THRESHOLD || angleDiff > CORNER_ANGLE_THRESHOLD)) {
         score += CORNER_SCORE;
     }
     return score;
@@ -398,17 +450,17 @@
 // Sampling touch point and pushing information to vectors.
 // Returning if previous point is popped or not.
 bool ProximityInfoState::pushTouchPoint(const int inputIndex, const int nodeChar, int x, int y,
-        const int time, const bool sample, const bool isLastPoint,
+        const int time, const bool sample, const bool isLastPoint, const float sumAngle,
         NearKeysDistanceMap *const currentNearKeysDistances,
         const NearKeysDistanceMap *const prevNearKeysDistances,
         const NearKeysDistanceMap *const prevPrevNearKeysDistances) {
-    static const float LAST_POINT_SKIP_DISTANCE_SCALE = 0.25f;
+    static const int LAST_POINT_SKIP_DISTANCE_SCALE = 4;
 
     size_t size = mInputXs.size();
     bool popped = false;
     if (nodeChar < 0 && sample) {
         const float nearest = updateNearKeysDistances(x, y, currentNearKeysDistances);
-        const float score = getPointScore(x, y, time, isLastPoint, nearest,
+        const float score = getPointScore(x, y, time, isLastPoint, nearest, sumAngle,
                 currentNearKeysDistances, prevNearKeysDistances, prevPrevNearKeysDistances);
         if (score < 0) {
             // Pop previous point because it would be useless.
@@ -419,36 +471,18 @@
             popped = false;
         }
         // Check if the last point should be skipped.
-        if (isLastPoint) {
-            if (size > 0 && getDistanceFloat(x, y, mInputXs.back(), mInputYs.back())
-                    < mProximityInfo->getMostCommonKeyWidth() * LAST_POINT_SKIP_DISTANCE_SCALE) {
+        if (isLastPoint && size > 0) {
+            if (getDistanceInt(x, y, mInputXs.back(), mInputYs.back())
+                    * LAST_POINT_SKIP_DISTANCE_SCALE < mProximityInfo->getMostCommonKeyWidth()) {
+                // This point is not used because it's too close to the previous point.
                 if (DEBUG_GEO_FULL) {
-                    AKLOGI("p0: size = %zd, x = %d, y = %d, lx = %d, ly = %d, dist = %f, "
-                           "width = %f", size, x, y, mInputXs.back(), mInputYs.back(),
-                           getDistanceFloat(x, y, mInputXs.back(), mInputYs.back()),
+                    AKLOGI("p0: size = %zd, x = %d, y = %d, lx = %d, ly = %d, dist = %d, "
+                           "width = %d", size, x, y, mInputXs.back(), mInputYs.back(),
+                           getDistanceInt(x, y, mInputXs.back(), mInputYs.back()),
                            mProximityInfo->getMostCommonKeyWidth()
-                                   * LAST_POINT_SKIP_DISTANCE_SCALE);
+                                   / LAST_POINT_SKIP_DISTANCE_SCALE);
                 }
                 return popped;
-            } else if (size > 1) {
-                int minChar = 0;
-                float minDist = mMaxPointToKeyLength;
-                for (NearKeysDistanceMap::const_iterator it = currentNearKeysDistances->begin();
-                        it != currentNearKeysDistances->end(); ++it) {
-                    if (minDist > it->second) {
-                        minChar = it->first;
-                        minDist = it->second;
-                    }
-                }
-                NearKeysDistanceMap::const_iterator itPP =
-                        prevNearKeysDistances->find(minChar);
-                if (itPP != prevNearKeysDistances->end() && minDist > itPP->second) {
-                    if (DEBUG_GEO_FULL) {
-                        AKLOGI("p1: char = %c, minDist = %f, prevNear key minDist = %f",
-                                minChar, itPP->second, minDist);
-                    }
-                    return popped;
-                }
             }
         }
     }
@@ -503,12 +537,11 @@
     return 0;
 }
 
-float ProximityInfoState::getPointToKeyLength(const int inputIndex, const int codePoint,
-        const float scale) const {
+float ProximityInfoState::getPointToKeyLength(const int inputIndex, const int codePoint) const {
     const int keyId = mProximityInfo->getKeyIndexOf(codePoint);
     if (keyId != NOT_AN_INDEX) {
         const int index = inputIndex * mProximityInfo->getKeyCount() + keyId;
-        return min(mDistanceCache[index] * scale, mMaxPointToKeyLength);
+        return min(mDistanceCache[index], mMaxPointToKeyLength);
     }
     if (isSkippableChar(codePoint)) {
         return 0.0f;
@@ -517,8 +550,17 @@
     return MAX_POINT_TO_KEY_LENGTH;
 }
 
+float ProximityInfoState::getPointToKeyByIdLength(const int inputIndex, const int keyId) const {
+    if (keyId != NOT_AN_INDEX) {
+        const int index = inputIndex * mProximityInfo->getKeyCount() + keyId;
+        return min(mDistanceCache[index], mMaxPointToKeyLength);
+    }
+    // If the char is not a key on the keyboard then return the max length.
+    return static_cast<float>(MAX_POINT_TO_KEY_LENGTH);
+}
+
 int ProximityInfoState::getSpaceY() const {
-    const int keyId = mProximityInfo->getKeyIndexOf(' ');
+    const int keyId = mProximityInfo->getKeyIndexOf(KEYCODE_SPACE);
     return mProximityInfo->getKeyCenterYOfKeyIdG(keyId);
 }
 
@@ -538,8 +580,9 @@
         return filterSize;
     }
     int newFilterSize = filterSize;
-    for (int j = 0; j < mProximityInfo->getKeyCount(); ++j) {
-        if (mNearKeysVector[index].test(j)) {
+    const int keyCount = mProximityInfo->getKeyCount();
+    for (int j = 0; j < keyCount; ++j) {
+        if (mSearchKeysVector[index].test(j)) {
             const int32_t keyCodePoint = mProximityInfo->getCodePointOf(j);
             bool insert = true;
             // TODO: Avoid linear search
@@ -557,6 +600,12 @@
     return newFilterSize;
 }
 
+bool ProximityInfoState::isKeyInSerchKeysAfterIndex(const int index, const int keyId) const {
+    ASSERT(keyId >= 0);
+    ASSERT(index >= 0 && index < mInputSize);
+    return mSearchKeysVector[index].test(keyId);
+}
+
 void ProximityInfoState::popInputData() {
     mInputXs.pop_back();
     mInputYs.pop_back();
@@ -565,4 +614,389 @@
     mInputIndice.pop_back();
 }
 
+float ProximityInfoState::getDirection(const int index0, const int index1) const {
+    if (index0 < 0 || index0 > mInputSize - 1) {
+        return 0.0f;
+    }
+    if (index1 < 0 || index1 > mInputSize - 1) {
+        return 0.0f;
+    }
+    const int x1 = mInputXs[index0];
+    const int y1 = mInputYs[index0];
+    const int x2 = mInputXs[index1];
+    const int y2 = mInputYs[index1];
+    return getAngle(x1, y1, x2, y2);
+}
+
+float ProximityInfoState::getPointAngle(const int index) const {
+    if (index <= 0 || index >= mInputSize - 1) {
+        return 0.0f;
+    }
+    const float previousDirection = getDirection(index - 1, index);
+    const float nextDirection = getDirection(index, index + 1);
+    const float directionDiff = getAngleDiff(previousDirection, nextDirection);
+    return directionDiff;
+}
+
+float ProximityInfoState::getPointsAngle(
+        const int index0, const int index1, const int index2) const {
+    if (index0 < 0 || index0 > mInputSize - 1) {
+        return 0.0f;
+    }
+    if (index1 < 0 || index1 > mInputSize - 1) {
+        return 0.0f;
+    }
+    if (index2 < 0 || index2 > mInputSize - 1) {
+        return 0.0f;
+    }
+    const float previousDirection = getDirection(index0, index1);
+    const float nextDirection = getDirection(index1, index2);
+    return getAngleDiff(previousDirection, nextDirection);
+}
+
+float ProximityInfoState::getLineToKeyDistance(
+        const int from, const int to, const int keyId, const bool extend) const {
+    if (from < 0 || from > mInputSize - 1) {
+        return 0.0f;
+    }
+    if (to < 0 || to > mInputSize - 1) {
+        return 0.0f;
+    }
+    const int x0 = mInputXs[from];
+    const int y0 = mInputYs[from];
+    const int x1 = mInputXs[to];
+    const int y1 = mInputYs[to];
+
+    const int keyX = mProximityInfo->getKeyCenterXOfKeyIdG(keyId);
+    const int keyY = mProximityInfo->getKeyCenterYOfKeyIdG(keyId);
+
+    return pointToLineSegSquaredDistanceFloat(keyX, keyY, x0, y0, x1, y1, extend);
+}
+
+// Updates probabilities of aligning to some keys and skipping.
+// Word suggestion should be based on this probabilities.
+void ProximityInfoState::updateAlignPointProbabilities(const int start) {
+    static const float MIN_PROBABILITY = 0.000001f;
+    static const float MAX_SKIP_PROBABILITY = 0.95f;
+    static const float SKIP_FIRST_POINT_PROBABILITY = 0.01f;
+    static const float SKIP_LAST_POINT_PROBABILITY = 0.1f;
+    static const float MIN_SPEED_RATE_FOR_SKIP_PROBABILITY = 0.15f;
+    static const float SPEED_WEIGHT_FOR_SKIP_PROBABILITY = 0.9f;
+    static const float SLOW_STRAIGHT_WEIGHT_FOR_SKIP_PROBABILITY = 0.6f;
+    static const float NEAREST_DISTANCE_WEIGHT = 0.5f;
+    static const float NEAREST_DISTANCE_BIAS = 0.5f;
+    static const float NEAREST_DISTANCE_WEIGHT_FOR_LAST = 0.6f;
+    static const float NEAREST_DISTANCE_BIAS_FOR_LAST = 0.4f;
+
+    static const float ANGLE_WEIGHT = 0.90f;
+    static const float DEEP_CORNER_ANGLE_THRESHOLD = M_PI_F * 60.0f / 180.0f;
+    static const float SKIP_DEEP_CORNER_PROBABILITY = 0.1f;
+    static const float CORNER_ANGLE_THRESHOLD = M_PI_F * 30.0f / 180.0f;
+    static const float STRAIGHT_ANGLE_THRESHOLD = M_PI_F * 15.0f / 180.0f;
+    static const float SKIP_CORNER_PROBABILITY = 0.4f;
+    static const float SPEED_MARGIN = 0.1f;
+    static const float CENTER_VALUE_OF_NORMALIZED_DISTRIBUTION = 0.0f;
+
+    const int keyCount = mProximityInfo->getKeyCount();
+    mCharProbabilities.resize(mInputSize);
+    // Calculates probabilities of using a point as a correlated point with the character
+    // for each point.
+    for (int i = start; i < mInputSize; ++i) {
+        mCharProbabilities[i].clear();
+        // First, calculates skip probability. Starts form MIN_SKIP_PROBABILITY.
+        // Note that all values that are multiplied to this probability should be in [0.0, 1.0];
+        float skipProbability = MAX_SKIP_PROBABILITY;
+
+        const float currentAngle = getPointAngle(i);
+        const float relativeSpeed = getRelativeSpeed(i);
+
+        float nearestKeyDistance = static_cast<float>(MAX_POINT_TO_KEY_LENGTH);
+        for (int j = 0; j < keyCount; ++j) {
+            if (mNearKeysVector[i].test(j)) {
+                const float distance = getPointToKeyByIdLength(i, j);
+                if (distance < nearestKeyDistance) {
+                    nearestKeyDistance = distance;
+                }
+            }
+        }
+
+        if (i == 0) {
+            skipProbability *= min(1.0f, nearestKeyDistance * NEAREST_DISTANCE_WEIGHT
+                    + NEAREST_DISTANCE_BIAS);
+            // Promote the first point
+            skipProbability *= SKIP_FIRST_POINT_PROBABILITY;
+        } else if (i == mInputSize - 1) {
+            skipProbability *= min(1.0f, nearestKeyDistance * NEAREST_DISTANCE_WEIGHT_FOR_LAST
+                    + NEAREST_DISTANCE_BIAS_FOR_LAST);
+            // Promote the last point
+            skipProbability *= SKIP_LAST_POINT_PROBABILITY;
+        } else {
+            // If the current speed is relatively slower than adjacent keys, we promote this point.
+            if (getRelativeSpeed(i - 1) - SPEED_MARGIN > relativeSpeed
+                    && relativeSpeed < getRelativeSpeed(i + 1) - SPEED_MARGIN) {
+                if (currentAngle < CORNER_ANGLE_THRESHOLD) {
+                    skipProbability *= min(1.0f, relativeSpeed
+                            * SLOW_STRAIGHT_WEIGHT_FOR_SKIP_PROBABILITY);
+                } else {
+                    // If the angle is small enough, we promote this point more. (e.g. pit vs put)
+                    skipProbability *= min(1.0f, relativeSpeed * SPEED_WEIGHT_FOR_SKIP_PROBABILITY
+                            + MIN_SPEED_RATE_FOR_SKIP_PROBABILITY);
+                }
+            }
+
+            skipProbability *= min(1.0f, relativeSpeed * nearestKeyDistance *
+                    NEAREST_DISTANCE_WEIGHT + NEAREST_DISTANCE_BIAS);
+
+            // Adjusts skip probability by a rate depending on angle.
+            // ANGLE_RATE of skipProbability is adjusted by current angle.
+            skipProbability *= (M_PI_F - currentAngle) / M_PI_F * ANGLE_WEIGHT
+                    + (1.0f - ANGLE_WEIGHT);
+            if (currentAngle > DEEP_CORNER_ANGLE_THRESHOLD) {
+                skipProbability *= SKIP_DEEP_CORNER_PROBABILITY;
+            }
+            // We assume the angle of this point is the angle for point[i], point[i - 2]
+            // and point[i - 3]. The reason why we don't use the angle for point[i], point[i - 1]
+            // and point[i - 2] is this angle can be more affected by the noise.
+            const float prevAngle = getPointsAngle(i, i - 2, i - 3);
+            if (i >= 3 && prevAngle < STRAIGHT_ANGLE_THRESHOLD
+                    && currentAngle > CORNER_ANGLE_THRESHOLD) {
+                skipProbability *= SKIP_CORNER_PROBABILITY;
+            }
+        }
+
+        // probabilities must be in [0.0, MAX_SKIP_PROBABILITY];
+        ASSERT(skipProbability >= 0.0f);
+        ASSERT(skipProbability <= MAX_SKIP_PROBABILITY);
+        mCharProbabilities[i][NOT_AN_INDEX] = skipProbability;
+
+        // Second, calculates key probabilities by dividing the rest probability
+        // (1.0f - skipProbability).
+        const float inputCharProbability = 1.0f - skipProbability;
+
+        // TODO: The variance is critical for accuracy; thus, adjusting these parameter by machine
+        // learning or something would be efficient.
+        static const float SPEEDxANGLE_WEIGHT_FOR_STANDARD_DIVIATION = 0.3f;
+        static const float MAX_SPEEDxANGLE_RATE_FOR_STANDERD_DIVIATION = 0.25f;
+        static const float SPEEDxNEAREST_WEIGHT_FOR_STANDARD_DIVIATION = 0.5f;
+        static const float MAX_SPEEDxNEAREST_RATE_FOR_STANDERD_DIVIATION = 0.15f;
+        static const float MIN_STANDERD_DIVIATION = 0.37f;
+
+        const float speedxAngleRate = min(relativeSpeed * currentAngle / M_PI_F
+                * SPEEDxANGLE_WEIGHT_FOR_STANDARD_DIVIATION,
+                        MAX_SPEEDxANGLE_RATE_FOR_STANDERD_DIVIATION);
+        const float speedxNearestKeyDistanceRate = min(relativeSpeed * nearestKeyDistance
+                * SPEEDxNEAREST_WEIGHT_FOR_STANDARD_DIVIATION,
+                        MAX_SPEEDxNEAREST_RATE_FOR_STANDERD_DIVIATION);
+        const float sigma = speedxAngleRate + speedxNearestKeyDistanceRate + MIN_STANDERD_DIVIATION;
+
+        NormalDistribution distribution(CENTER_VALUE_OF_NORMALIZED_DISTRIBUTION, sigma);
+        static const float PREV_DISTANCE_WEIGHT = 0.5f;
+        static const float NEXT_DISTANCE_WEIGHT = 0.6f;
+        // Summing up probability densities of all near keys.
+        float sumOfProbabilityDensities = 0.0f;
+        for (int j = 0; j < keyCount; ++j) {
+            if (mNearKeysVector[i].test(j)) {
+                float distance = sqrtf(getPointToKeyByIdLength(i, j));
+                if (i == 0 && i != mInputSize - 1) {
+                    // For the first point, weighted average of distances from first point and the
+                    // next point to the key is used as a point to key distance.
+                    const float nextDistance = sqrtf(getPointToKeyByIdLength(i + 1, j));
+                    if (nextDistance < distance) {
+                        // The distance of the first point tends to bigger than continuing
+                        // points because the first touch by the user can be sloppy.
+                        // So we promote the first point if the distance of that point is larger
+                        // than the distance of the next point.
+                        distance = (distance + nextDistance * NEXT_DISTANCE_WEIGHT)
+                                / (1.0f + NEXT_DISTANCE_WEIGHT);
+                    }
+                } else if (i != 0 && i == mInputSize - 1) {
+                    // For the first point, weighted average of distances from last point and
+                    // the previous point to the key is used as a point to key distance.
+                    const float previousDistance = sqrtf(getPointToKeyByIdLength(i - 1, j));
+                    if (previousDistance < distance) {
+                        // The distance of the last point tends to bigger than continuing points
+                        // because the last touch by the user can be sloppy. So we promote the
+                        // last point if the distance of that point is larger than the distance of
+                        // the previous point.
+                        distance = (distance + previousDistance * PREV_DISTANCE_WEIGHT)
+                                / (1.0f + PREV_DISTANCE_WEIGHT);
+                    }
+                }
+                // TODO: Promote the first point when the extended line from the next input is near
+                // from a key. Also, promote the last point as well.
+                sumOfProbabilityDensities += distribution.getProbabilityDensity(distance);
+            }
+        }
+
+        // Split the probability of an input point to keys that are close to the input point.
+        for (int j = 0; j < keyCount; ++j) {
+            if (mNearKeysVector[i].test(j)) {
+                float distance = sqrtf(getPointToKeyByIdLength(i, j));
+                if (i == 0 && i != mInputSize - 1) {
+                    // For the first point, weighted average of distances from the first point and
+                    // the next point to the key is used as a point to key distance.
+                    const float prevDistance = sqrtf(getPointToKeyByIdLength(i + 1, j));
+                    if (prevDistance < distance) {
+                        distance = (distance + prevDistance * NEXT_DISTANCE_WEIGHT)
+                                / (1.0f + NEXT_DISTANCE_WEIGHT);
+                    }
+                } else if (i != 0 && i == mInputSize - 1) {
+                    // For the first point, weighted average of distances from last point and
+                    // the previous point to the key is used as a point to key distance.
+                    const float prevDistance = sqrtf(getPointToKeyByIdLength(i - 1, j));
+                    if (prevDistance < distance) {
+                        distance = (distance + prevDistance * PREV_DISTANCE_WEIGHT)
+                                / (1.0f + PREV_DISTANCE_WEIGHT);
+                    }
+                }
+                const float probabilityDensity = distribution.getProbabilityDensity(distance);
+                const float probability = inputCharProbability * probabilityDensity
+                        / sumOfProbabilityDensities;
+                mCharProbabilities[i][j] = probability;
+            }
+        }
+    }
+
+
+    if (DEBUG_POINTS_PROBABILITY) {
+        for (int i = 0; i < mInputSize; ++i) {
+            std::stringstream sstream;
+            sstream << i << ", ";
+            sstream << "("<< mInputXs[i] << ", ";
+            sstream << ", "<< mInputYs[i] << "), ";
+            sstream << "Speed: "<< getRelativeSpeed(i) << ", ";
+            sstream << "Angle: "<< getPointAngle(i) << ", \n";
+
+            for (hash_map_compat<int, float>::iterator it = mCharProbabilities[i].begin();
+                    it != mCharProbabilities[i].end(); ++it) {
+                if (it->first == NOT_AN_INDEX) {
+                    sstream << it->first
+                            << "(skip):"
+                            << it->second
+                            << "\n";
+                } else {
+                    sstream << it->first
+                            << "("
+                            << static_cast<char>(mProximityInfo->getCodePointOf(it->first))
+                            << "):"
+                            << it->second
+                            << "\n";
+                }
+            }
+            AKLOGI("%s", sstream.str().c_str());
+        }
+    }
+
+    // Decrease key probabilities of points which don't have the highest probability of that key
+    // among nearby points. Probabilities of the first point and the last point are not suppressed.
+    for (int i = max(start, 1); i < mInputSize; ++i) {
+        for (int j = i + 1; j < mInputSize; ++j) {
+            if (!suppressCharProbabilities(i, j)) {
+                break;
+            }
+        }
+        for (int j = i - 1; j >= max(start, 0); --j) {
+            if (!suppressCharProbabilities(i, j)) {
+                break;
+            }
+        }
+    }
+
+    // Converting from raw probabilities to log probabilities to calculate spatial distance.
+    for (int i = start; i < mInputSize; ++i) {
+        for (int j = 0; j < keyCount; ++j) {
+            hash_map_compat<int, float>::iterator it = mCharProbabilities[i].find(j);
+            if (it == mCharProbabilities[i].end()){
+                mNearKeysVector[i].reset(j);
+            } else if(it->second < MIN_PROBABILITY) {
+                // Erases from near keys vector because it has very low probability.
+                mNearKeysVector[i].reset(j);
+                mCharProbabilities[i].erase(j);
+            } else {
+                it->second = -logf(it->second);
+            }
+        }
+        mCharProbabilities[i][NOT_AN_INDEX] = -logf(mCharProbabilities[i][NOT_AN_INDEX]);
+    }
+}
+
+// Decreases char probabilities of index0 by checking probabilities of a near point (index1) and
+// increases char probabilities of index1 by checking probabilities of index0.
+bool ProximityInfoState::suppressCharProbabilities(const int index0, const int index1) {
+    ASSERT(0 <= index0 && index0 < mInputSize);
+    ASSERT(0 <= index1 && index1 < mInputSize);
+
+    static const float SUPPRESSION_LENGTH_WEIGHT = 1.5f;
+    static const float MIN_SUPPRESSION_RATE = 0.1f;
+    static const float SUPPRESSION_WEIGHT = 0.5f;
+    static const float SUPPRESSION_WEIGHT_FOR_PROBABILITY_GAIN = 0.1f;
+    static const float SKIP_PROBABALITY_WEIGHT_FOR_PROBABILITY_GAIN = 0.3f;
+
+    const float keyWidthFloat = static_cast<float>(mProximityInfo->getMostCommonKeyWidth());
+    const float diff = fabsf(static_cast<float>(mLengthCache[index0] - mLengthCache[index1]));
+    if (diff > keyWidthFloat * SUPPRESSION_LENGTH_WEIGHT) {
+        return false;
+    }
+    const float suppressionRate = MIN_SUPPRESSION_RATE
+            + diff / keyWidthFloat / SUPPRESSION_LENGTH_WEIGHT * SUPPRESSION_WEIGHT;
+    for (hash_map_compat<int, float>::iterator it = mCharProbabilities[index0].begin();
+            it != mCharProbabilities[index0].end(); ++it) {
+        hash_map_compat<int, float>::iterator it2 =  mCharProbabilities[index1].find(it->first);
+        if (it2 != mCharProbabilities[index1].end() && it->second < it2->second) {
+            const float newProbability = it->second * suppressionRate;
+            const float suppression = it->second - newProbability;
+            it->second = newProbability;
+            // mCharProbabilities[index0][NOT_AN_INDEX] is the probability of skipping this point.
+            mCharProbabilities[index0][NOT_AN_INDEX] += suppression;
+
+            // Add the probability of the same key nearby index1
+            const float probabilityGain = min(suppression * SUPPRESSION_WEIGHT_FOR_PROBABILITY_GAIN,
+                    mCharProbabilities[index1][NOT_AN_INDEX]
+                            * SKIP_PROBABALITY_WEIGHT_FOR_PROBABILITY_GAIN);
+            it2->second += probabilityGain;
+            mCharProbabilities[index1][NOT_AN_INDEX] -= probabilityGain;
+        }
+    }
+    return true;
+}
+
+// Get a word that is detected by tracing highest probability sequence into charBuf and returns
+// probability of generating the word.
+float ProximityInfoState::getHighestProbabilitySequence(uint16_t *const charBuf) const {
+    static const float DEMOTION_LOG_PROBABILITY = 0.3f;
+    int index = 0;
+    float sumLogProbability = 0.0f;
+    // TODO: Current implementation is greedy algorithm. DP would be efficient for many cases.
+    for (int i = 0; i < mInputSize && index < MAX_WORD_LENGTH_INTERNAL - 1; ++i) {
+        float minLogProbability = static_cast<float>(MAX_POINT_TO_KEY_LENGTH);
+        int character = NOT_AN_INDEX;
+        for (hash_map_compat<int, float>::const_iterator it = mCharProbabilities[i].begin();
+                it != mCharProbabilities[i].end(); ++it) {
+            const float logProbability = (it->first != NOT_AN_INDEX)
+                    ? it->second + DEMOTION_LOG_PROBABILITY : it->second;
+            if (logProbability < minLogProbability) {
+                minLogProbability = logProbability;
+                character = it->first;
+            }
+        }
+        if (character != NOT_AN_INDEX) {
+            charBuf[index] = mProximityInfo->getCodePointOf(character);
+            index++;
+        }
+        sumLogProbability += minLogProbability;
+    }
+    charBuf[index] = '\0';
+    return sumLogProbability;
+}
+
+// Returns a probability of mapping index to keyIndex.
+float ProximityInfoState::getProbability(const int index, const int keyIndex) const {
+    ASSERT(0 <= index && index < mInputSize);
+    hash_map_compat<int, float>::const_iterator it = mCharProbabilities[index].find(keyIndex);
+    if (it != mCharProbabilities[index].end()) {
+        return it->second;
+    }
+    return static_cast<float>(MAX_POINT_TO_KEY_LENGTH);
+}
+
 } // namespace latinime
diff --git a/native/jni/src/proximity_info_state.h b/native/jni/src/proximity_info_state.h
index c1ec76c..1a3f286 100644
--- a/native/jni/src/proximity_info_state.h
+++ b/native/jni/src/proximity_info_state.h
@@ -55,7 +55,8 @@
               mHasTouchPositionCorrectionData(false), mMostCommonKeyWidthSquare(0), mLocaleStr(),
               mKeyCount(0), mCellHeight(0), mCellWidth(0), mGridHeight(0), mGridWidth(0),
               mIsContinuationPossible(false), mInputXs(), mInputYs(), mTimes(), mInputIndice(),
-              mDistanceCache(), mLengthCache(), mRelativeSpeeds(), mNearKeysVector(),
+              mDistanceCache(), mLengthCache(), mRelativeSpeeds(), mDirections(),
+              mCharProbabilities(), mNearKeysVector(), mSearchKeysVector(),
               mTouchPositionCorrectionEnabled(false), mInputSize(0) {
         memset(mInputCodes, 0, sizeof(mInputCodes));
         memset(mNormalizedSquaredDistances, 0, sizeof(mNormalizedSquaredDistances));
@@ -213,7 +214,8 @@
         return mIsContinuationPossible;
     }
 
-    float getPointToKeyLength(const int inputIndex, const int charCode, const float scale) const;
+    float getPointToKeyLength(const int inputIndex, const int charCode) const;
+    float getPointToKeyByIdLength(const int inputIndex, const int keyId) const;
 
     int getSpaceY() const;
 
@@ -223,6 +225,25 @@
     float getRelativeSpeed(const int index) const {
         return mRelativeSpeeds[index];
     }
+
+    float getDirection(const int index) const {
+        return mDirections[index];
+    }
+    // get xy direction
+    float getDirection(const int x, const int y) const;
+
+    float getPointAngle(const int index) const;
+    // Returns angle of three points. x, y, and z are indices.
+    float getPointsAngle(const int index0, const int index1, const int index2) const;
+
+    float getHighestProbabilitySequence(uint16_t *const charBuf) const;
+
+    float getProbability(const int index, const int charCode) const;
+
+    float getLineToKeyDistance(
+            const int from, const int to, const int keyId, const bool extend) const;
+
+    bool isKeyInSerchKeysAfterIndex(const int index, const int keyId) const;
  private:
     DISALLOW_COPY_AND_ASSIGN(ProximityInfoState);
     typedef hash_map_compat<int, float> NearKeysDistanceMap;
@@ -235,7 +256,7 @@
             const int keyIndex, const int inputIndex) const;
 
     bool pushTouchPoint(const int inputIndex, const int nodeChar, int x, int y, const int time,
-            const bool sample, const bool isLastPoint,
+            const bool sample, const bool isLastPoint, const float sumAngle,
             NearKeysDistanceMap *const currentNearKeysDistances,
             const NearKeysDistanceMap *const prevNearKeysDistances,
             const NearKeysDistanceMap *const prevPrevNearKeysDistances);
@@ -259,12 +280,14 @@
             const NearKeysDistanceMap *const prevPrevNearKeysDistances) const;
     float getPointScore(
             const int x, const int y, const int time, const bool last, const float nearest,
-            const NearKeysDistanceMap *const currentNearKeysDistances,
+            const float sumAngle, const NearKeysDistanceMap *const currentNearKeysDistances,
             const NearKeysDistanceMap *const prevNearKeysDistances,
             const NearKeysDistanceMap *const prevPrevNearKeysDistances) const;
     bool checkAndReturnIsContinuationPossible(const int inputSize, const int *const xCoordinates,
             const int *const yCoordinates, const int *const times);
     void popInputData();
+    void updateAlignPointProbabilities(const int start);
+    bool suppressCharProbabilities(const int index1, const int index2);
 
     // const
     const ProximityInfo *mProximityInfo;
@@ -286,7 +309,18 @@
     std::vector<float> mDistanceCache;
     std::vector<int>  mLengthCache;
     std::vector<float> mRelativeSpeeds;
+    std::vector<float> mDirections;
+    // probabilities of skipping or mapping to a key for each point.
+    std::vector<hash_map_compat<int, float> > mCharProbabilities;
+    // The vector for the key code set which holds nearby keys for each sampled input point
+    // 1. Used to calculate the probability of the key
+    // 2. Used to calculate mSearchKeysVector
     std::vector<NearKeycodesSet> mNearKeysVector;
+    // The vector for the key code set which holds nearby keys of some trailing sampled input points
+    // for each sampled input point. These nearby keys contain the next characters which can be in
+    // the dictionary. Specifically, currently we are looking for keys nearby trailing sampled
+    // inputs including the current input point.
+    std::vector<NearKeycodesSet> mSearchKeysVector;
     bool mTouchPositionCorrectionEnabled;
     int32_t mInputCodes[MAX_PROXIMITY_CHARS_SIZE_INTERNAL * MAX_WORD_LENGTH_INTERNAL];
     int mNormalizedSquaredDistances[MAX_PROXIMITY_CHARS_SIZE_INTERNAL * MAX_WORD_LENGTH_INTERNAL];
diff --git a/native/jni/src/unigram_dictionary.cpp b/native/jni/src/unigram_dictionary.cpp
index 49d044f..3b485a0 100644
--- a/native/jni/src/unigram_dictionary.cpp
+++ b/native/jni/src/unigram_dictionary.cpp
@@ -41,14 +41,12 @@
         { 'o', 'e', 0x0153 } }; // U+0153 : LATIN SMALL LIGATURE OE
 
 // TODO: check the header
-UnigramDictionary::UnigramDictionary(const uint8_t *const streamStart, int typedLetterMultiplier,
-        int fullWordMultiplier, int maxWordLength, int maxWords, const unsigned int flags)
-    : DICT_ROOT(streamStart), MAX_WORD_LENGTH(maxWordLength), MAX_WORDS(maxWords),
-    TYPED_LETTER_MULTIPLIER(typedLetterMultiplier), FULL_WORD_MULTIPLIER(fullWordMultiplier),
-      // TODO : remove this variable.
-    ROOT_POS(0),
-    BYTES_IN_ONE_CHAR(sizeof(int)),
-    MAX_DIGRAPH_SEARCH_DEPTH(DEFAULT_MAX_DIGRAPH_SEARCH_DEPTH), FLAGS(flags) {
+UnigramDictionary::UnigramDictionary(const uint8_t *const streamStart, int fullWordMultiplier,
+        int maxWordLength, int maxWords, const unsigned int flags)
+        : DICT_ROOT(streamStart), MAX_WORD_LENGTH(maxWordLength), MAX_WORDS(maxWords),
+          FULL_WORD_MULTIPLIER(fullWordMultiplier), // TODO : remove this variable.
+          ROOT_POS(0), BYTES_IN_ONE_CHAR(sizeof(int)),
+          MAX_DIGRAPH_SEARCH_DEPTH(DEFAULT_MAX_DIGRAPH_SEARCH_DEPTH), FLAGS(flags) {
     if (DEBUG_DICT) {
         AKLOGI("UnigramDictionary - constructor");
     }
@@ -188,8 +186,7 @@
         getWordWithDigraphSuggestionsRec(proximityInfo, xcoordinates, ycoordinates, codesBuffer,
                 xCoordinatesBuffer, yCoordinatesBuffer, codesSize, bigramMap, bigramFilter,
                 useFullEditDistance, codes, codesSize, 0, codesBuffer, &masterCorrection,
-                &queuePool, GERMAN_UMLAUT_DIGRAPHS,
-                sizeof(GERMAN_UMLAUT_DIGRAPHS) / sizeof(GERMAN_UMLAUT_DIGRAPHS[0]));
+                &queuePool, GERMAN_UMLAUT_DIGRAPHS, NELEMS(GERMAN_UMLAUT_DIGRAPHS));
     } else if (BinaryFormat::REQUIRES_FRENCH_LIGATURES_PROCESSING & FLAGS) {
         int codesBuffer[getCodesBufferSize(codes, codesSize)];
         int xCoordinatesBuffer[codesSize];
@@ -197,8 +194,7 @@
         getWordWithDigraphSuggestionsRec(proximityInfo, xcoordinates, ycoordinates, codesBuffer,
                 xCoordinatesBuffer, yCoordinatesBuffer, codesSize, bigramMap, bigramFilter,
                 useFullEditDistance, codes, codesSize, 0, codesBuffer, &masterCorrection,
-                &queuePool, FRENCH_LIGATURES_DIGRAPHS,
-                sizeof(FRENCH_LIGATURES_DIGRAPHS) / sizeof(FRENCH_LIGATURES_DIGRAPHS[0]));
+                &queuePool, FRENCH_LIGATURES_DIGRAPHS, NELEMS(FRENCH_LIGATURES_DIGRAPHS));
     } else { // Normal processing
         getWordSuggestions(proximityInfo, xcoordinates, ycoordinates, codes, codesSize,
                 bigramMap, bigramFilter, useFullEditDistance, &masterCorrection, &queuePool);
@@ -314,8 +310,6 @@
     correction->initCorrection(proximityInfo, inputSize, maxDepth);
 }
 
-static const char SPACE = ' ';
-
 void UnigramDictionary::getOneWordSuggestions(ProximityInfo *proximityInfo,
         const int *xcoordinates, const int *ycoordinates, const int *codes,
         const std::map<int, int> *bigramMap, const uint8_t *bigramFilter,
@@ -570,7 +564,7 @@
         if (outputWordStartPos + nextWordLength >= MAX_WORD_LENGTH) {
             return FLAG_MULTIPLE_SUGGEST_SKIP;
         }
-        outputWord[tempOutputWordLength] = SPACE;
+        outputWord[tempOutputWordLength] = KEYCODE_SPACE;
         if (outputWordLength) {
             ++*outputWordLength;
         }
diff --git a/native/jni/src/unigram_dictionary.h b/native/jni/src/unigram_dictionary.h
index 57129bb..244d78d 100644
--- a/native/jni/src/unigram_dictionary.h
+++ b/native/jni/src/unigram_dictionary.h
@@ -39,8 +39,8 @@
     static const int FLAG_MULTIPLE_SUGGEST_ABORT = 0;
     static const int FLAG_MULTIPLE_SUGGEST_SKIP = 1;
     static const int FLAG_MULTIPLE_SUGGEST_CONTINUE = 2;
-    UnigramDictionary(const uint8_t *const streamStart, int typedLetterMultipler,
-            int fullWordMultiplier, int maxWordLength, int maxWords, const unsigned int flags);
+    UnigramDictionary(const uint8_t *const streamStart, int fullWordMultiplier, int maxWordLength,
+            int maxWords, const unsigned int flags);
     int getFrequency(const int32_t *const inWord, const int length) const;
     int getBigramPosition(int pos, unsigned short *word, int offset, int length) const;
     int getSuggestions(ProximityInfo *proximityInfo, const int *xcoordinates,
@@ -115,7 +115,6 @@
     const uint8_t *const DICT_ROOT;
     const int MAX_WORD_LENGTH;
     const int MAX_WORDS;
-    const int TYPED_LETTER_MULTIPLIER;
     const int FULL_WORD_MULTIPLIER;
     const int ROOT_POS;
     const unsigned int BYTES_IN_ONE_CHAR;
diff --git a/tests/src/com/android/inputmethod/latin/BlueUnderlineTests.java b/tests/src/com/android/inputmethod/latin/BlueUnderlineTests.java
index a9947c1..2544bd8 100644
--- a/tests/src/com/android/inputmethod/latin/BlueUnderlineTests.java
+++ b/tests/src/com/android/inputmethod/latin/BlueUnderlineTests.java
@@ -88,17 +88,19 @@
 
     public void testBlueUnderlineDisappearsWhenCursorMoved() {
         final String STRING_TO_TYPE = "tgis";
+        final int typedLength = STRING_TO_TYPE.length();
         final int NEW_CURSOR_POSITION = 0;
         type(STRING_TO_TYPE);
         sleep(DELAY_TO_WAIT_FOR_UNDERLINE);
         // Simulate the onUpdateSelection() event
-        mLatinIME.onUpdateSelection(0, 0, STRING_TO_TYPE.length(), STRING_TO_TYPE.length(), -1, -1);
+        mLatinIME.onUpdateSelection(0, 0, typedLength, typedLength, -1, -1);
         runMessages();
         // Here the blue underline has been set. testBlueUnderline() is testing for this already,
         // so let's not test it here again.
         // Now simulate the user moving the cursor.
         mInputConnection.setSelection(NEW_CURSOR_POSITION, NEW_CURSOR_POSITION);
-        mLatinIME.onUpdateSelection(0, 0, NEW_CURSOR_POSITION, NEW_CURSOR_POSITION, -1, -1);
+        mLatinIME.onUpdateSelection(typedLength, typedLength,
+                NEW_CURSOR_POSITION, NEW_CURSOR_POSITION, -1, -1);
         sleep(DELAY_TO_WAIT_FOR_UNDERLINE);
         runMessages();
         final SpanGetter span = new SpanGetter(mTextView.getText(), SuggestionSpan.class);
diff --git a/tests/src/com/android/inputmethod/latin/InputLogicTests.java b/tests/src/com/android/inputmethod/latin/InputLogicTests.java
index 38e57aa..3b9eda2 100644
--- a/tests/src/com/android/inputmethod/latin/InputLogicTests.java
+++ b/tests/src/com/android/inputmethod/latin/InputLogicTests.java
@@ -86,6 +86,7 @@
 
     public void testDeleteSelection() {
         final String STRING_TO_TYPE = "some text delete me some text";
+        final int typedLength = STRING_TO_TYPE.length();
         final int SELECTION_START = 10;
         final int SELECTION_END = 19;
         final String EXPECTED_RESULT = "some text  some text";
@@ -94,10 +95,11 @@
         // Send once to simulate the cursor actually responding to the move caused by typing.
         // This is necessary because LatinIME is bookkeeping to avoid confusing a real cursor
         // move with a move triggered by LatinIME inputting stuff.
-        mLatinIME.onUpdateSelection(0, 0, STRING_TO_TYPE.length(), STRING_TO_TYPE.length(), -1, -1);
+        mLatinIME.onUpdateSelection(0, 0, typedLength, typedLength, -1, -1);
         mInputConnection.setSelection(SELECTION_START, SELECTION_END);
         // And now we simulate the user actually selecting some text.
-        mLatinIME.onUpdateSelection(0, 0, SELECTION_START, SELECTION_END, -1, -1);
+        mLatinIME.onUpdateSelection(typedLength, typedLength,
+                SELECTION_START, SELECTION_END, -1, -1);
         type(Keyboard.CODE_DELETE);
         assertEquals("delete selection", EXPECTED_RESULT, mTextView.getText().toString());
     }
@@ -163,12 +165,14 @@
 
     public void testBackspaceAtStartAfterAutocorrect() {
         final String STRING_TO_TYPE = "tgis ";
+        final int typedLength = STRING_TO_TYPE.length();
         final String EXPECTED_RESULT = "this ";
         final int NEW_CURSOR_POSITION = 0;
         type(STRING_TO_TYPE);
-        mLatinIME.onUpdateSelection(0, 0, STRING_TO_TYPE.length(), STRING_TO_TYPE.length(), -1, -1);
+        mLatinIME.onUpdateSelection(0, 0, typedLength, typedLength, -1, -1);
         mInputConnection.setSelection(NEW_CURSOR_POSITION, NEW_CURSOR_POSITION);
-        mLatinIME.onUpdateSelection(0, 0, NEW_CURSOR_POSITION, NEW_CURSOR_POSITION, -1, -1);
+        mLatinIME.onUpdateSelection(typedLength, typedLength,
+                NEW_CURSOR_POSITION, NEW_CURSOR_POSITION, -1, -1);
         type(Keyboard.CODE_DELETE);
         assertEquals("auto correct then move cursor to start of line then backspace",
                 EXPECTED_RESULT, mTextView.getText().toString());
@@ -176,12 +180,14 @@
 
     public void testAutoCorrectThenMoveCursorThenBackspace() {
         final String STRING_TO_TYPE = "and tgis ";
+        final int typedLength = STRING_TO_TYPE.length();
         final String EXPECTED_RESULT = "andthis ";
         final int NEW_CURSOR_POSITION = STRING_TO_TYPE.indexOf('t');
         type(STRING_TO_TYPE);
-        mLatinIME.onUpdateSelection(0, 0, STRING_TO_TYPE.length(), STRING_TO_TYPE.length(), -1, -1);
+        mLatinIME.onUpdateSelection(0, 0, typedLength, typedLength, -1, -1);
         mInputConnection.setSelection(NEW_CURSOR_POSITION, NEW_CURSOR_POSITION);
-        mLatinIME.onUpdateSelection(0, 0, NEW_CURSOR_POSITION, NEW_CURSOR_POSITION, -1, -1);
+        mLatinIME.onUpdateSelection(typedLength, typedLength,
+                NEW_CURSOR_POSITION, NEW_CURSOR_POSITION, -1, -1);
         type(Keyboard.CODE_DELETE);
         assertEquals("auto correct then move cursor then backspace",
                 EXPECTED_RESULT, mTextView.getText().toString());
diff --git a/tests/src/com/android/inputmethod/latin/InputLogicTestsNonEnglish.java b/tests/src/com/android/inputmethod/latin/InputLogicTestsNonEnglish.java
index 78143ac..42823f5 100644
--- a/tests/src/com/android/inputmethod/latin/InputLogicTestsNonEnglish.java
+++ b/tests/src/com/android/inputmethod/latin/InputLogicTestsNonEnglish.java
@@ -16,7 +16,10 @@
 
 package com.android.inputmethod.latin;
 
+import com.android.inputmethod.latin.suggestions.SuggestionStripView;
+
 public class InputLogicTestsNonEnglish extends InputTestsBase {
+    final String NEXT_WORD_PREDICTION_OPTION = "next_word_prediction";
 
     public void testAutoCorrectForFrench() {
         final String STRING_TO_TYPE = "irq ";
@@ -43,16 +46,40 @@
         final String WORD_TO_TYPE = "test ";
         final String PUNCTUATION_FROM_STRIP = "!";
         final String EXPECTED_RESULT = "test !!";
+        final boolean defaultNextWordPredictionOption =
+                mLatinIME.getResources().getBoolean(R.bool.config_default_next_word_prediction);
+        final boolean previousNextWordPredictionOption =
+                setBooleanPreference(NEXT_WORD_PREDICTION_OPTION, false,
+                        defaultNextWordPredictionOption);
+        try {
+            changeLanguage("fr");
+            type(WORD_TO_TYPE);
+            sleep(DELAY_TO_WAIT_FOR_UNDERLINE);
+            runMessages();
+            assertTrue("type word then type space should display punctuation strip",
+                    mLatinIME.isShowingPunctuationList());
+            pickSuggestionManually(0, PUNCTUATION_FROM_STRIP);
+            pickSuggestionManually(0, PUNCTUATION_FROM_STRIP);
+            assertEquals("type word then type space then punctuation from strip twice for French",
+                    EXPECTED_RESULT, mTextView.getText().toString());
+        } finally {
+            setBooleanPreference(NEXT_WORD_PREDICTION_OPTION, previousNextWordPredictionOption,
+                    defaultNextWordPredictionOption);
+        }
+    }
+
+    public void testWordThenSpaceDisplaysPredictions() {
+        final String WORD_TO_TYPE = "beaujolais ";
+        final String EXPECTED_RESULT = "nouveau";
         changeLanguage("fr");
         type(WORD_TO_TYPE);
         sleep(DELAY_TO_WAIT_FOR_UNDERLINE);
         runMessages();
-        assertTrue("type word then type space should display punctuation strip",
-                mLatinIME.isShowingPunctuationList());
-        pickSuggestionManually(0, PUNCTUATION_FROM_STRIP);
-        pickSuggestionManually(0, PUNCTUATION_FROM_STRIP);
-        assertEquals("type word then type space then punctuation from strip twice for French",
-                EXPECTED_RESULT, mTextView.getText().toString());
+        final SuggestionStripView suggestionStripView =
+                (SuggestionStripView)mInputView.findViewById(R.id.suggestion_strip_view);
+        final SuggestedWords suggestedWords = suggestionStripView.getSuggestions();
+        assertEquals("type word then type space yields predictions for French",
+                EXPECTED_RESULT, suggestedWords.getWord(0));
     }
 
     public void testAutoCorrectForGerman() {
diff --git a/tests/src/com/android/inputmethod/latin/InputTestsBase.java b/tests/src/com/android/inputmethod/latin/InputTestsBase.java
index fe58cb8..eb50020 100644
--- a/tests/src/com/android/inputmethod/latin/InputTestsBase.java
+++ b/tests/src/com/android/inputmethod/latin/InputTestsBase.java
@@ -53,6 +53,7 @@
     protected LatinIME mLatinIME;
     protected Keyboard mKeyboard;
     protected MyTextView mTextView;
+    protected View mInputView;
     protected InputConnection mInputConnection;
     private final HashMap<String, InputMethodSubtype> mSubtypeMap =
             new HashMap<String, InputMethodSubtype>();
@@ -150,9 +151,9 @@
         final LayoutInflater inflater =
                 (LayoutInflater)getContext().getSystemService(Context.LAYOUT_INFLATER_SERVICE);
         final ViewGroup vg = new FrameLayout(getContext());
-        final View inputView = inflater.inflate(R.layout.input_view, vg);
+        mInputView = inflater.inflate(R.layout.input_view, vg);
         mLatinIME.onCreateInputMethodInterface().startInput(ic, ei);
-        mLatinIME.setInputView(inputView);
+        mLatinIME.setInputView(mInputView);
         mLatinIME.onBindInput();
         mLatinIME.onCreateInputView();
         mLatinIME.onStartInputView(ei, false);
@@ -211,7 +212,7 @@
         // any subsequent post in this queue. However the queue itself is still fully functional!
         // If we have a way of resetting "queue.mQuiting" then we can continue using it as normal,
         // coming back to this method to run the messages.
-        MessageQueue queue = looper.getQueue();
+        MessageQueue queue = Looper.myQueue();
         try {
             // However there is no way of doing it externally, and mQuiting is private.
             // So... get out the big guns.
diff --git a/tests/src/com/android/inputmethod/latin/UserHistoryDictIOUtilsTests.java b/tests/src/com/android/inputmethod/latin/UserHistoryDictIOUtilsTests.java
index 70f916c..66c9e18 100644
--- a/tests/src/com/android/inputmethod/latin/UserHistoryDictIOUtilsTests.java
+++ b/tests/src/com/android/inputmethod/latin/UserHistoryDictIOUtilsTests.java
@@ -188,7 +188,7 @@
 
         File file = null;
         try {
-            file = File.createTempFile("testReadAndWrite", ".dict");
+            file = File.createTempFile("testReadAndWrite", ".dict", getContext().getCacheDir());
         } catch (IOException e) {
             Log.d(TAG, "IOException while creating a temporary file: " + e);
         }
diff --git a/tests/src/com/android/inputmethod/latin/UserHistoryDictionaryTests.java b/tests/src/com/android/inputmethod/latin/UserHistoryDictionaryTests.java
index f2a17d2..7536f64 100644
--- a/tests/src/com/android/inputmethod/latin/UserHistoryDictionaryTests.java
+++ b/tests/src/com/android/inputmethod/latin/UserHistoryDictionaryTests.java
@@ -23,6 +23,8 @@
 import android.test.AndroidTestCase;
 import android.util.Log;
 
+import java.io.File;
+import java.io.IOException;
 import java.util.ArrayList;
 import java.util.List;
 import java.util.Random;
@@ -76,34 +78,43 @@
     }
 
     public void testRandomWords() {
-        Log.d(TAG, "This test can be used for profiling.");
-        Log.d(TAG, "Usage: please set UserHisotoryDictionary.PROFILE_SAVE_RESTORE to true.");
-        final int numberOfWords = 1000;
-        final Random random = new Random(123456);
-        List<String> words = generateWords(numberOfWords, random);
-
-        final String locale = "testRandomWords";
-        final UserHistoryDictionary dict = UserHistoryDictionary.getInstance(getContext(),
-                locale, mPrefs);
-        dict.isTest = true;
-
-        addToDict(dict, words);
-
+        File dictFile = null;
         try {
-            Log.d(TAG, "waiting for adding the word ...");
-            Thread.sleep(2000);
-        } catch (InterruptedException e) {
-            Log.d(TAG, "InterruptedException: " + e);
-        }
+            Log.d(TAG, "This test can be used for profiling.");
+            Log.d(TAG, "Usage: please set UserHisotoryDictionary.PROFILE_SAVE_RESTORE to true.");
+            final int numberOfWords = 1000;
+            final Random random = new Random(123456);
+            List<String> words = generateWords(numberOfWords, random);
 
-        // write to file
-        dict.close();
+            final String locale = "testRandomWords";
+            final String fileName = "UserHistoryDictionary." + locale + ".dict";
+            dictFile = new File(getContext().getFilesDir(), fileName);
+            final UserHistoryDictionary dict = UserHistoryDictionary.getInstance(getContext(),
+                    locale, mPrefs);
+            dict.isTest = true;
 
-        try {
-            Log.d(TAG, "waiting for writing ...");
-            Thread.sleep(5000);
-        } catch (InterruptedException e) {
-            Log.d(TAG, "InterruptedException: " + e);
+            addToDict(dict, words);
+
+            try {
+                Log.d(TAG, "waiting for adding the word ...");
+                Thread.sleep(2000);
+            } catch (InterruptedException e) {
+                Log.d(TAG, "InterruptedException: " + e);
+            }
+
+            // write to file
+            dict.close();
+
+            try {
+                Log.d(TAG, "waiting for writing ...");
+                Thread.sleep(5000);
+            } catch (InterruptedException e) {
+                Log.d(TAG, "InterruptedException: " + e);
+            }
+        } finally {
+            if (dictFile != null) {
+                dictFile.delete();
+            }
         }
     }
 }
diff --git a/tests/src/com/android/inputmethod/latin/makedict/BinaryDictIOTests.java b/tests/src/com/android/inputmethod/latin/makedict/BinaryDictIOTests.java
index 2f95431..b6f6fea 100644
--- a/tests/src/com/android/inputmethod/latin/makedict/BinaryDictIOTests.java
+++ b/tests/src/com/android/inputmethod/latin/makedict/BinaryDictIOTests.java
@@ -271,7 +271,7 @@
             final String message) {
         File file = null;
         try {
-            file = File.createTempFile("runReadAndWrite", ".dict");
+            file = File.createTempFile("runReadAndWrite", ".dict", getContext().getCacheDir());
         } catch (IOException e) {
             Log.e(TAG, "IOException: " + e);
         }
@@ -412,7 +412,7 @@
             final FormatSpec.FormatOptions formatOptions, final String message) {
         File file = null;
         try {
-            file = File.createTempFile("runReadUnigrams", ".dict");
+            file = File.createTempFile("runReadUnigrams", ".dict", getContext().getCacheDir());
         } catch (IOException e) {
             Log.e(TAG, "IOException: " + e);
         }
@@ -510,7 +510,8 @@
     public void testGetTerminalPosition() {
         File file = null;
         try {
-            file = File.createTempFile("testGetTerminalPosition", ".dict");
+            file = File.createTempFile("testGetTerminalPosition", ".dict",
+                    getContext().getCacheDir());
         } catch (IOException e) {
             // do nothing
         }
@@ -561,7 +562,7 @@
     public void testDeleteWord() {
         File file = null;
         try {
-            file = File.createTempFile("testDeleteWord", ".dict");
+            file = File.createTempFile("testDeleteWord", ".dict", getContext().getCacheDir());
         } catch (IOException e) {
             // do nothing
         }
diff --git a/tests/src/com/android/inputmethod/latin/makedict/BinaryDictIOUtilsTests.java b/tests/src/com/android/inputmethod/latin/makedict/BinaryDictIOUtilsTests.java
new file mode 100644
index 0000000..3185168
--- /dev/null
+++ b/tests/src/com/android/inputmethod/latin/makedict/BinaryDictIOUtilsTests.java
@@ -0,0 +1,397 @@
+/*
+ * Copyright (C) 2012 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.inputmethod.latin.makedict;
+
+import com.android.inputmethod.latin.CollectionUtils;
+import com.android.inputmethod.latin.makedict.BinaryDictInputOutput.ByteBufferWrapper;
+import com.android.inputmethod.latin.makedict.BinaryDictInputOutput.CharEncoding;
+import com.android.inputmethod.latin.makedict.BinaryDictInputOutput.FusionDictionaryBufferInterface;
+import com.android.inputmethod.latin.makedict.FormatSpec.FileHeader;
+import com.android.inputmethod.latin.makedict.FusionDictionary.Node;
+import com.android.inputmethod.latin.makedict.FusionDictionary.WeightedString;
+
+import android.test.AndroidTestCase;
+import android.test.MoreAsserts;
+import android.util.Log;
+
+import java.io.BufferedOutputStream;
+import java.io.BufferedWriter;
+import java.io.File;
+import java.io.FileInputStream;
+import java.io.FileOutputStream;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.io.RandomAccessFile;
+import java.nio.channels.FileChannel;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.HashMap;
+import java.util.Random;
+
+public class BinaryDictIOUtilsTests  extends AndroidTestCase {
+    private static final String TAG = BinaryDictIOUtilsTests.class.getSimpleName();
+    private static final FormatSpec.FormatOptions FORMAT_OPTIONS =
+            new FormatSpec.FormatOptions(3, true);
+    private static final int MAX_UNIGRAMS = 1500;
+
+    private static final ArrayList<String> sWords = CollectionUtils.newArrayList();
+
+    private static final String[] CHARACTERS = {
+        "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m",
+        "n", "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z",
+        "\u00FC" /* ü */, "\u00E2" /* â */, "\u00F1" /* ñ */, // accented characters
+        "\u4E9C" /* 亜 */, "\u4F0A" /* 伊 */, "\u5B87" /* 宇 */, // kanji
+        "\uD841\uDE28" /* 𠘨 */, "\uD840\uDC0B" /* 𠀋 */, "\uD861\uDeD7" /* 𨛗 */ // surrogate pair
+    };
+
+    public BinaryDictIOUtilsTests() {
+        super();
+        final Random random = new Random(123456);
+        sWords.clear();
+        for (int i = 0; i < MAX_UNIGRAMS; ++i) {
+            sWords.add(generateWord(random.nextInt()));
+        }
+    }
+
+    // Utilities for test
+    private String generateWord(final int value) {
+        final int lengthOfChars = CHARACTERS.length;
+        StringBuilder builder = new StringBuilder("");
+        long lvalue = Math.abs((long)value);
+        while (lvalue > 0) {
+            builder.append(CHARACTERS[(int)(lvalue % lengthOfChars)]);
+            lvalue /= lengthOfChars;
+        }
+        if (builder.toString().equals("")) return "a";
+        return builder.toString();
+    }
+
+    private static void printCharGroup(final CharGroupInfo info) {
+        Log.d(TAG, "    CharGroup at " + info.mOriginalAddress);
+        Log.d(TAG, "        flags = " + info.mFlags);
+        Log.d(TAG, "        parentAddress = " + info.mParentAddress);
+        Log.d(TAG, "        characters = " + new String(info.mCharacters, 0,
+                info.mCharacters.length));
+        if (info.mFrequency != -1) Log.d(TAG, "        frequency = " + info.mFrequency);
+        if (info.mChildrenAddress == FormatSpec.NO_CHILDREN_ADDRESS) {
+            Log.d(TAG, "        children address = no children address");
+        } else {
+            Log.d(TAG, "        children address = " + info.mChildrenAddress);
+        }
+        if (info.mShortcutTargets != null) {
+            for (final WeightedString ws : info.mShortcutTargets) {
+                Log.d(TAG, "        shortcuts = " + ws.mWord);
+            }
+        }
+        if (info.mBigrams != null) {
+            for (final PendingAttribute attr : info.mBigrams) {
+                Log.d(TAG, "        bigram = " + attr.mAddress);
+            }
+        }
+        Log.d(TAG, "    end address = " + info.mEndAddress);
+    }
+
+    private static void printNode(final FusionDictionaryBufferInterface buffer,
+            final FormatSpec.FormatOptions formatOptions) {
+        Log.d(TAG, "Node at " + buffer.position());
+        final int count = BinaryDictInputOutput.readCharGroupCount(buffer);
+        Log.d(TAG, "    charGroupCount = " + count);
+        for (int i = 0; i < count; ++i) {
+            final CharGroupInfo currentInfo = BinaryDictInputOutput.readCharGroup(buffer,
+                    buffer.position(), formatOptions);
+            printCharGroup(currentInfo);
+        }
+        if (formatOptions.mSupportsDynamicUpdate) {
+            final int forwardLinkAddress = buffer.readUnsignedInt24();
+            Log.d(TAG, "    forwardLinkAddress = " + forwardLinkAddress);
+        }
+    }
+
+    private static void printBinaryFile(final FusionDictionaryBufferInterface buffer)
+            throws IOException, UnsupportedFormatException {
+        FileHeader header = BinaryDictInputOutput.readHeader(buffer);
+        while (buffer.position() < buffer.limit()) {
+            printNode(buffer, header.mFormatOptions);
+        }
+    }
+
+    private int getWordPosition(final File file, final String word) {
+        int position = FormatSpec.NOT_VALID_WORD;
+        FileInputStream inStream = null;
+        try {
+            inStream = new FileInputStream(file);
+            final FusionDictionaryBufferInterface buffer = new ByteBufferWrapper(
+                    inStream.getChannel().map(FileChannel.MapMode.READ_ONLY, 0, file.length()));
+            position = BinaryDictIOUtils.getTerminalPosition(buffer, word);
+        } catch (IOException e) {
+        } catch (UnsupportedFormatException e) {
+        } finally {
+            if (inStream != null) {
+                try {
+                    inStream.close();
+                } catch (IOException e) {
+                    // do nothing
+                }
+            }
+        }
+        return position;
+    }
+
+    private CharGroupInfo findWordFromFile(final File file, final String word) {
+        FileInputStream inStream = null;
+        CharGroupInfo info = null;
+        try {
+            inStream = new FileInputStream(file);
+            final FusionDictionaryBufferInterface buffer = new ByteBufferWrapper(
+                    inStream.getChannel().map(FileChannel.MapMode.READ_ONLY, 0, file.length()));
+            info = BinaryDictIOUtils.findWordFromBuffer(buffer, word);
+        } catch (IOException e) {
+        } catch (UnsupportedFormatException e) {
+        } finally {
+            if (inStream != null) {
+                try {
+                    inStream.close();
+                } catch (IOException e) {
+                    // do nothing
+                }
+            }
+        }
+        return info;
+    }
+
+    // return amount of time to insert a word
+    private long insertAndCheckWord(final File file, final String word, final int frequency,
+            final boolean exist, final ArrayList<WeightedString> bigrams,
+            final ArrayList<WeightedString> shortcuts) {
+        RandomAccessFile raFile = null;
+        BufferedOutputStream outStream = null;
+        FusionDictionaryBufferInterface buffer = null;
+        long amountOfTime = -1;
+        try {
+            raFile = new RandomAccessFile(file, "rw");
+            buffer = new ByteBufferWrapper(raFile.getChannel().map(
+                    FileChannel.MapMode.READ_WRITE, 0, file.length()));
+            outStream = new BufferedOutputStream(new FileOutputStream(file, true));
+
+            if (!exist) {
+                assertEquals(FormatSpec.NOT_VALID_WORD, getWordPosition(file, word));
+            }
+            final long now = System.nanoTime();
+            BinaryDictIOUtils.insertWord(buffer, outStream, word, frequency, bigrams, shortcuts,
+                    false, false);
+            amountOfTime = System.nanoTime() - now;
+            outStream.flush();
+            MoreAsserts.assertNotEqual(FormatSpec.NOT_VALID_WORD, getWordPosition(file, word));
+            outStream.close();
+            raFile.close();
+        } catch (IOException e) {
+        } catch (UnsupportedFormatException e) {
+        } finally {
+            if (outStream != null) {
+                try {
+                    outStream.close();
+                } catch (IOException e) {
+                    // do nothing
+                }
+            }
+            if (raFile != null) {
+                try {
+                    raFile.close();
+                } catch (IOException e) {
+                    // do nothing
+                }
+            }
+        }
+        return amountOfTime;
+    }
+
+    private void deleteWord(final File file, final String word) {
+        RandomAccessFile raFile = null;
+        FusionDictionaryBufferInterface buffer = null;
+        try {
+            raFile = new RandomAccessFile(file, "rw");
+            buffer = new ByteBufferWrapper(raFile.getChannel().map(
+                    FileChannel.MapMode.READ_WRITE, 0, file.length()));
+            BinaryDictIOUtils.deleteWord(buffer, word);
+        } catch (IOException e) {
+        } catch (UnsupportedFormatException e) {
+        } finally {
+            if (raFile != null) {
+                try {
+                    raFile.close();
+                } catch (IOException e) {
+                    // do nothing
+                }
+            }
+        }
+    }
+
+    private void checkReverseLookup(final File file, final String word, final int position) {
+        FileInputStream inStream = null;
+        try {
+            inStream = new FileInputStream(file);
+            final FusionDictionaryBufferInterface buffer = new ByteBufferWrapper(
+                    inStream.getChannel().map(FileChannel.MapMode.READ_ONLY, 0, file.length()));
+            final FileHeader header = BinaryDictInputOutput.readHeader(buffer);
+            assertEquals(word, BinaryDictInputOutput.getWordAtAddress(buffer, header.mHeaderSize,
+                    position - header.mHeaderSize, header.mFormatOptions));
+        } catch (IOException e) {
+        } catch (UnsupportedFormatException e) {
+        } finally {
+            if (inStream != null) {
+                try {
+                    inStream.close();
+                } catch (IOException e) {
+                    // do nothing
+                }
+            }
+        }
+    }
+
+    public void testInsertWord() {
+        File file = null;
+        try {
+            file = File.createTempFile("testInsertWord", ".dict", getContext().getCacheDir());
+        } catch (IOException e) {
+            fail("IOException while creating temporary file: " + e);
+        }
+
+        // set an initial dictionary.
+        final FusionDictionary dict = new FusionDictionary(new Node(),
+                new FusionDictionary.DictionaryOptions(new HashMap<String,String>(), false, false));
+        dict.add("abcd", 10, null, false);
+
+        try {
+            final FileOutputStream out = new FileOutputStream(file);
+            BinaryDictInputOutput.writeDictionaryBinary(out, dict, FORMAT_OPTIONS);
+            out.close();
+        } catch (IOException e) {
+            fail("IOException while writing an initial dictionary : " + e);
+        } catch (UnsupportedFormatException e) {
+            fail("UnsupportedFormatException while writing an initial dictionary : " + e);
+        }
+
+        MoreAsserts.assertNotEqual(FormatSpec.NOT_VALID_WORD, getWordPosition(file, "abcd"));
+        insertAndCheckWord(file, "abcde", 10, false, null, null);
+
+        insertAndCheckWord(file, "abcdefghijklmn", 10, false, null, null);
+        checkReverseLookup(file, "abcdefghijklmn", getWordPosition(file, "abcdefghijklmn"));
+
+        insertAndCheckWord(file, "abcdabcd", 10, false, null, null);
+        checkReverseLookup(file, "abcdabcd", getWordPosition(file, "abcdabcd"));
+
+        // update the existing word.
+        insertAndCheckWord(file, "abcdabcd", 15, true, null, null);
+
+        // split 1
+        insertAndCheckWord(file, "ab", 20, false, null, null);
+
+        // split 2
+        insertAndCheckWord(file, "ami", 30, false, null, null);
+
+        deleteWord(file, "ami");
+        assertEquals(FormatSpec.NOT_VALID_WORD, getWordPosition(file, "ami"));
+
+        insertAndCheckWord(file, "abcdabfg", 30, false, null, null);
+
+        deleteWord(file, "abcd");
+        assertEquals(FormatSpec.NOT_VALID_WORD, getWordPosition(file, "abcd"));
+    }
+
+    public void testInsertWordWithBigrams() {
+        File file = null;
+        try {
+            file = File.createTempFile("testInsertWordWithBigrams", ".dict",
+                    getContext().getCacheDir());
+        } catch (IOException e) {
+            fail("IOException while creating temporary file: " + e);
+        }
+
+        // set an initial dictionary.
+        final FusionDictionary dict = new FusionDictionary(new Node(),
+                new FusionDictionary.DictionaryOptions(new HashMap<String,String>(), false, false));
+        dict.add("abcd", 10, null, false);
+        dict.add("efgh", 15, null, false);
+
+        try {
+            final FileOutputStream out = new FileOutputStream(file);
+            BinaryDictInputOutput.writeDictionaryBinary(out, dict, FORMAT_OPTIONS);
+            out.close();
+        } catch (IOException e) {
+            fail("IOException while writing an initial dictionary : " + e);
+        } catch (UnsupportedFormatException e) {
+            fail("UnsupportedFormatException while writing an initial dictionary : " + e);
+        }
+
+        final ArrayList<WeightedString> banana = new ArrayList<WeightedString>();
+        banana.add(new WeightedString("banana", 10));
+
+        insertAndCheckWord(file, "banana", 0, false, null, null);
+        insertAndCheckWord(file, "recursive", 60, true, banana, null);
+
+        final CharGroupInfo info = findWordFromFile(file, "recursive");
+        int bananaPos = getWordPosition(file, "banana");
+        assertNotNull(info.mBigrams);
+        assertEquals(info.mBigrams.size(), 1);
+        assertEquals(info.mBigrams.get(0).mAddress, bananaPos);
+    }
+
+    public void testRandomWords() {
+        File file = null;
+        try {
+            file = File.createTempFile("testRandomWord", ".dict", getContext().getCacheDir());
+        } catch (IOException e) {
+        }
+        assertNotNull(file);
+
+        // set an initial dictionary.
+        final FusionDictionary dict = new FusionDictionary(new Node(),
+                new FusionDictionary.DictionaryOptions(new HashMap<String, String>(), false,
+                        false));
+        dict.add("initial", 10, null, false);
+
+        try {
+            final FileOutputStream out = new FileOutputStream(file);
+            BinaryDictInputOutput.writeDictionaryBinary(out, dict, FORMAT_OPTIONS);
+            out.close();
+        } catch (IOException e) {
+            assertTrue(false);
+        } catch (UnsupportedFormatException e) {
+            assertTrue(false);
+        }
+
+        long maxTimeToInsert = 0, sum = 0;
+        long minTimeToInsert = 100000000; // 1000000000 is an upper bound for minTimeToInsert.
+        int cnt = 0;
+        for (final String word : sWords) {
+            final long diff = insertAndCheckWord(file, word,
+                    cnt % FormatSpec.MAX_TERMINAL_FREQUENCY, false, null, null);
+            maxTimeToInsert = Math.max(maxTimeToInsert, diff);
+            minTimeToInsert = Math.min(minTimeToInsert, diff);
+            sum += diff;
+            cnt++;
+        }
+        cnt = 0;
+        for (final String word : sWords) {
+            MoreAsserts.assertNotEqual(FormatSpec.NOT_VALID_WORD, getWordPosition(file, word));
+        }
+
+        Log.d(TAG, "max = " + ((double)maxTimeToInsert/1000000) + " ms.");
+        Log.d(TAG, "min = " + ((double)minTimeToInsert/1000000) + " ms.");
+        Log.d(TAG, "avg = " + ((double)sum/MAX_UNIGRAMS/1000000) + " ms.");
+    }
+}
