diff --git a/java/src/com/android/inputmethod/latin/DictionaryFacilitator.java b/java/src/com/android/inputmethod/latin/DictionaryFacilitator.java
index 6b939cdfe6ac9184b850ccbab213d8cdf6ba965e..9ea1950f5ed9dfde14d33423d74f134c1dddf873 100644
--- a/java/src/com/android/inputmethod/latin/DictionaryFacilitator.java
+++ b/java/src/com/android/inputmethod/latin/DictionaryFacilitator.java
@@ -20,7 +20,7 @@ import android.content.Context;
 import android.util.Pair;
 
 import com.android.inputmethod.annotations.UsedForTesting;
-import com.android.inputmethod.keyboard.KeyboardLayout;
+import com.android.inputmethod.keyboard.Keyboard;
 import com.android.inputmethod.latin.common.ComposedData;
 import com.android.inputmethod.latin.settings.SettingsValuesForSuggestion;
 import com.android.inputmethod.latin.utils.SuggestionResults;
@@ -157,9 +157,9 @@ public interface DictionaryFacilitator {
 
     // TODO: Revise the way to fusion suggestion results.
     SuggestionResults getSuggestionResults(final ComposedData composedData,
-            final NgramContext ngramContext, final long proximityInfoHandle,
+            final NgramContext ngramContext, @Nonnull final Keyboard keyboard,
             final SettingsValuesForSuggestion settingsValuesForSuggestion, final int sessionId,
-            final int inputStyle, final KeyboardLayout keyboardLayout);
+            final int inputStyle);
 
     boolean isValidSpellingWord(final String word);
 
diff --git a/java/src/com/android/inputmethod/latin/DictionaryFacilitatorImpl.java b/java/src/com/android/inputmethod/latin/DictionaryFacilitatorImpl.java
index e963000207a3ad41aea7c686363dc99ebfa2a7b0..6e260f358cc2fba4c8137d1ca058feacf094d7ff 100644
--- a/java/src/com/android/inputmethod/latin/DictionaryFacilitatorImpl.java
+++ b/java/src/com/android/inputmethod/latin/DictionaryFacilitatorImpl.java
@@ -22,7 +22,7 @@ import android.util.Log;
 import android.util.Pair;
 
 import com.android.inputmethod.annotations.UsedForTesting;
-import com.android.inputmethod.keyboard.KeyboardLayout;
+import com.android.inputmethod.keyboard.Keyboard;
 import com.android.inputmethod.latin.NgramContext.WordInfo;
 import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo;
 import com.android.inputmethod.latin.common.ComposedData;
@@ -668,9 +668,10 @@ public class DictionaryFacilitatorImpl implements DictionaryFacilitator {
     // TODO: Revise the way to fusion suggestion results.
     @Override
     public SuggestionResults getSuggestionResults(ComposedData composedData,
-            NgramContext ngramContext, long proximityInfoHandle,
+            NgramContext ngramContext, @Nonnull final Keyboard keyboard,
             SettingsValuesForSuggestion settingsValuesForSuggestion, int sessionId,
-            int inputStyle, KeyboardLayout keyboardLayout) {
+            int inputStyle) {
+        long proximityInfoHandle = keyboard.getProximityInfo().getNativeProximityInfo();
         final DictionaryGroup[] dictionaryGroups = mDictionaryGroups;
         final SuggestionResults suggestionResults = new SuggestionResults(
                 SuggestedWords.MAX_SUGGESTIONS, ngramContext.isBeginningOfSentenceContext());
diff --git a/java/src/com/android/inputmethod/latin/LatinIME.java b/java/src/com/android/inputmethod/latin/LatinIME.java
index 550efa59f733b303a5f2b1ce21cda63c7ae3bb36..9c777d10a8ccc5d611d2cd67b626932b5129cb84 100644
--- a/java/src/com/android/inputmethod/latin/LatinIME.java
+++ b/java/src/com/android/inputmethod/latin/LatinIME.java
@@ -1514,9 +1514,8 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
             callback.onGetSuggestedWords(SuggestedWords.getEmptyInstance());
             return;
         }
-        mInputLogic.getSuggestedWords(mSettings.getCurrent(), keyboard.getProximityInfo(),
-                mKeyboardSwitcher.getKeyboardShiftMode(), inputStyle, sequenceNumber, callback,
-                keyboard.getKeyboardLayout());
+        mInputLogic.getSuggestedWords(mSettings.getCurrent(), keyboard,
+                mKeyboardSwitcher.getKeyboardShiftMode(), inputStyle, sequenceNumber, callback);
     }
 
     @Override
diff --git a/java/src/com/android/inputmethod/latin/Suggest.java b/java/src/com/android/inputmethod/latin/Suggest.java
index 832fcbcb023e8b1ed1474a5a7776c34adefc0daf..d4915a5e9b17feb671bc39857ee2ff13846e051f 100644
--- a/java/src/com/android/inputmethod/latin/Suggest.java
+++ b/java/src/com/android/inputmethod/latin/Suggest.java
@@ -20,8 +20,7 @@ import android.text.TextUtils;
 
 import static com.android.inputmethod.latin.define.DecoderSpecificConstants.SHOULD_AUTO_CORRECT_USING_NON_WHITE_LISTED_SUGGESTION;
 
-import com.android.inputmethod.keyboard.KeyboardLayout;
-import com.android.inputmethod.keyboard.ProximityInfo;
+import com.android.inputmethod.keyboard.Keyboard;
 import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo;
 import com.android.inputmethod.latin.common.Constants;
 import com.android.inputmethod.latin.common.StringUtils;
@@ -97,19 +96,17 @@ public final class Suggest {
     }
 
     public void getSuggestedWords(final WordComposer wordComposer,
-            final NgramContext ngramContext, final ProximityInfo proximityInfo,
+            final NgramContext ngramContext, final Keyboard keyboard,
             final SettingsValuesForSuggestion settingsValuesForSuggestion,
             final boolean isCorrectionEnabled, final int inputStyle, final int sequenceNumber,
-            final OnGetSuggestedWordsCallback callback,
-            final KeyboardLayout keyboardLayout) {
+            final OnGetSuggestedWordsCallback callback) {
         if (wordComposer.isBatchMode()) {
-            getSuggestedWordsForBatchInput(wordComposer, ngramContext, proximityInfo,
-                    settingsValuesForSuggestion, inputStyle, sequenceNumber, callback,
-                    keyboardLayout);
+            getSuggestedWordsForBatchInput(wordComposer, ngramContext, keyboard,
+                    settingsValuesForSuggestion, inputStyle, sequenceNumber, callback);
         } else {
-            getSuggestedWordsForNonBatchInput(wordComposer, ngramContext, proximityInfo,
+            getSuggestedWordsForNonBatchInput(wordComposer, ngramContext, keyboard,
                     settingsValuesForSuggestion, inputStyle, isCorrectionEnabled,
-                    sequenceNumber, callback, keyboardLayout);
+                    sequenceNumber, callback);
         }
     }
 
@@ -165,11 +162,10 @@ public final class Suggest {
     // Retrieves suggestions for non-batch input (typing, recorrection, predictions...)
     // and calls the callback function with the suggestions.
     private void getSuggestedWordsForNonBatchInput(final WordComposer wordComposer,
-            final NgramContext ngramContext, final ProximityInfo proximityInfo,
+            final NgramContext ngramContext, final Keyboard keyboard,
             final SettingsValuesForSuggestion settingsValuesForSuggestion,
             final int inputStyleIfNotPrediction, final boolean isCorrectionEnabled,
-            final int sequenceNumber, final OnGetSuggestedWordsCallback callback,
-            final KeyboardLayout keyboardLayout) {
+            final int sequenceNumber, final OnGetSuggestedWordsCallback callback) {
         final String typedWordString = wordComposer.getTypedWord();
         final int trailingSingleQuotesCount =
                 StringUtils.getTrailingSingleQuotesCount(typedWordString);
@@ -178,9 +174,8 @@ public final class Suggest {
                 : typedWordString;
 
         final SuggestionResults suggestionResults = mDictionaryFacilitator.getSuggestionResults(
-                wordComposer.getComposedDataSnapshot(), ngramContext,
-                proximityInfo.getNativeProximityInfo(), settingsValuesForSuggestion,
-                SESSION_ID_TYPING, inputStyleIfNotPrediction, keyboardLayout);
+                wordComposer.getComposedDataSnapshot(), ngramContext, keyboard,
+                settingsValuesForSuggestion, SESSION_ID_TYPING, inputStyleIfNotPrediction);
         final Locale mostProbableLocale = mDictionaryFacilitator.getMostProbableLocale();
         final ArrayList<SuggestedWordInfo> suggestionsContainer =
                 getTransformedSuggestedWordInfoList(wordComposer, suggestionResults,
@@ -346,15 +341,13 @@ public final class Suggest {
     // Retrieves suggestions for the batch input
     // and calls the callback function with the suggestions.
     private void getSuggestedWordsForBatchInput(final WordComposer wordComposer,
-            final NgramContext ngramContext, final ProximityInfo proximityInfo,
+            final NgramContext ngramContext, final Keyboard keyboard,
             final SettingsValuesForSuggestion settingsValuesForSuggestion,
             final int inputStyle, final int sequenceNumber,
-            final OnGetSuggestedWordsCallback callback,
-            final KeyboardLayout keyboardLayout) {
+            final OnGetSuggestedWordsCallback callback) {
         final SuggestionResults suggestionResults = mDictionaryFacilitator.getSuggestionResults(
-                wordComposer.getComposedDataSnapshot(), ngramContext,
-                proximityInfo.getNativeProximityInfo(), settingsValuesForSuggestion,
-                SESSION_ID_GESTURE, inputStyle, keyboardLayout);
+                wordComposer.getComposedDataSnapshot(), ngramContext, keyboard,
+                settingsValuesForSuggestion, SESSION_ID_GESTURE, inputStyle);
         // For transforming words that don't come from a dictionary, because it's our best bet
         final Locale defaultLocale = mDictionaryFacilitator.getMostProbableLocale();
         final ArrayList<SuggestedWordInfo> suggestionsContainer =
diff --git a/java/src/com/android/inputmethod/latin/inputlogic/InputLogic.java b/java/src/com/android/inputmethod/latin/inputlogic/InputLogic.java
index 57aa59190cc4d9b7ecaa0e478d39c0ea16edfcb2..7907aaa166d65f9bdde4f0018d51b8b2d8f526c2 100644
--- a/java/src/com/android/inputmethod/latin/inputlogic/InputLogic.java
+++ b/java/src/com/android/inputmethod/latin/inputlogic/InputLogic.java
@@ -32,9 +32,8 @@ import android.view.inputmethod.EditorInfo;
 import com.android.inputmethod.compat.SuggestionSpanUtils;
 import com.android.inputmethod.event.Event;
 import com.android.inputmethod.event.InputTransaction;
-import com.android.inputmethod.keyboard.KeyboardLayout;
+import com.android.inputmethod.keyboard.Keyboard;
 import com.android.inputmethod.keyboard.KeyboardSwitcher;
-import com.android.inputmethod.keyboard.ProximityInfo;
 import com.android.inputmethod.latin.Dictionary;
 import com.android.inputmethod.latin.DictionaryFacilitator;
 import com.android.inputmethod.latin.LastComposedWord;
@@ -2165,9 +2164,8 @@ public final class InputLogic {
     }
 
     public void getSuggestedWords(final SettingsValues settingsValues,
-            final ProximityInfo proximityInfo, final int keyboardShiftMode, final int inputStyle,
-            final int sequenceNumber, final OnGetSuggestedWordsCallback callback,
-            final KeyboardLayout keyboardLayout) {
+            final Keyboard keyboard, final int keyboardShiftMode, final int inputStyle,
+            final int sequenceNumber, final OnGetSuggestedWordsCallback callback) {
         mWordComposer.adviseCapitalizedModeBeforeFetchingSuggestions(
                 getActualCapsMode(settingsValues, keyboardShiftMode));
         mSuggest.getSuggestedWords(mWordComposer,
@@ -2177,11 +2175,11 @@ public final class InputLogic {
                         // a word, it's whatever is *before* the half-committed word in the buffer,
                         // hence 2; if we aren't, we should just skip whitespace if any, so 1.
                         mWordComposer.isComposingWord() ? 2 : 1),
-                proximityInfo,
+                keyboard,
                 new SettingsValuesForSuggestion(settingsValues.mBlockPotentiallyOffensive,
                         settingsValues.mPhraseGestureEnabled),
                 settingsValues.mAutoCorrectionEnabledPerUserSettings,
-                inputStyle, sequenceNumber, callback, keyboardLayout);
+                inputStyle, sequenceNumber, callback);
     }
 
     /**
diff --git a/java/src/com/android/inputmethod/latin/spellcheck/AndroidSpellCheckerService.java b/java/src/com/android/inputmethod/latin/spellcheck/AndroidSpellCheckerService.java
index 9822c5725c55a96205065cccc82dcf63b2f5d911..f04f093f0948f0c7a1a4655c0e9ae637ad0e1df0 100644
--- a/java/src/com/android/inputmethod/latin/spellcheck/AndroidSpellCheckerService.java
+++ b/java/src/com/android/inputmethod/latin/spellcheck/AndroidSpellCheckerService.java
@@ -28,9 +28,7 @@ import android.util.Log;
 
 import com.android.inputmethod.keyboard.Keyboard;
 import com.android.inputmethod.keyboard.KeyboardId;
-import com.android.inputmethod.keyboard.KeyboardLayout;
 import com.android.inputmethod.keyboard.KeyboardLayoutSet;
-import com.android.inputmethod.keyboard.ProximityInfo;
 import com.android.inputmethod.latin.DictionaryFacilitator;
 import com.android.inputmethod.latin.DictionaryFacilitatorLruCache;
 import com.android.inputmethod.latin.NgramContext;
@@ -48,6 +46,8 @@ import java.util.concurrent.ConcurrentHashMap;
 import java.util.concurrent.ConcurrentLinkedQueue;
 import java.util.concurrent.Semaphore;
 
+import javax.annotation.Nonnull;
+
 /**
  * Service for spell checking, using LatinIME's dictionaries and mechanisms.
  */
@@ -193,7 +193,7 @@ public final class AndroidSpellCheckerService extends SpellCheckerService
 
     public SuggestionResults getSuggestionResults(final Locale locale,
             final ComposedData composedData, final NgramContext ngramContext,
-            final ProximityInfo proximityInfo, final KeyboardLayout keyboardLayout) {
+            @Nonnull final Keyboard keyboard) {
         Integer sessionId = null;
         mSemaphore.acquireUninterruptibly();
         try {
@@ -201,8 +201,8 @@ public final class AndroidSpellCheckerService extends SpellCheckerService
             DictionaryFacilitator dictionaryFacilitatorForLocale =
                     mDictionaryFacilitatorCache.get(locale);
             return dictionaryFacilitatorForLocale.getSuggestionResults(composedData, ngramContext,
-                    proximityInfo.getNativeProximityInfo(), mSettingsValuesForSuggestion,
-                    sessionId, SuggestedWords.INPUT_STYLE_TYPING, keyboardLayout);
+                    keyboard, mSettingsValuesForSuggestion,
+                    sessionId, SuggestedWords.INPUT_STYLE_TYPING);
         } finally {
             if (sessionId != null) {
                 mSessionIdPool.add(sessionId);
diff --git a/java/src/com/android/inputmethod/latin/spellcheck/AndroidWordLevelSpellCheckerSession.java b/java/src/com/android/inputmethod/latin/spellcheck/AndroidWordLevelSpellCheckerSession.java
index 1c43a4b71aa5bfa20c9f26f7a604fa6e5f63fa6c..5c1915c6cba2541e3151e8c2ab337ff6952e2708 100644
--- a/java/src/com/android/inputmethod/latin/spellcheck/AndroidWordLevelSpellCheckerSession.java
+++ b/java/src/com/android/inputmethod/latin/spellcheck/AndroidWordLevelSpellCheckerSession.java
@@ -29,18 +29,11 @@ import android.view.textservice.TextInfo;
 
 import com.android.inputmethod.compat.SuggestionsInfoCompatUtils;
 import com.android.inputmethod.keyboard.Keyboard;
-import com.android.inputmethod.keyboard.KeyboardLayout;
-import com.android.inputmethod.keyboard.ProximityInfo;
 import com.android.inputmethod.latin.NgramContext;
-import com.android.inputmethod.latin.SuggestedWords;
 import com.android.inputmethod.latin.SuggestedWords.SuggestedWordInfo;
 import com.android.inputmethod.latin.WordComposer;
-import com.android.inputmethod.latin.common.ComposedData;
 import com.android.inputmethod.latin.common.Constants;
-import com.android.inputmethod.latin.common.CoordinateUtils;
-import com.android.inputmethod.latin.common.InputPointers;
 import com.android.inputmethod.latin.common.LocaleUtils;
-import com.android.inputmethod.latin.common.ResizableIntArray;
 import com.android.inputmethod.latin.common.StringUtils;
 import com.android.inputmethod.latin.utils.BinaryDictionaryUtils;
 import com.android.inputmethod.latin.utils.ScriptUtils;
@@ -272,26 +265,20 @@ public abstract class AndroidWordLevelSpellCheckerSession extends Session {
                         false /* reportAsTypo */);
             }
             final Keyboard keyboard = mService.getKeyboardForLocale(mLocale);
+            if (null == keyboard) {
+                Log.d(TAG, "No keyboard for locale: " + mLocale);
+                // If there is no keyboard for this locale, don't do any spell-checking.
+                return AndroidSpellCheckerService.getNotInDictEmptySuggestions(
+                        false /* reportAsTypo */);
+            }
             final WordComposer composer = new WordComposer();
             final int[] codePoints = StringUtils.toCodePointArray(text);
             final int[] coordinates;
-            final ProximityInfo proximityInfo;
-            final KeyboardLayout keyboardLayout;
-            if (null == keyboard) {
-                coordinates = CoordinateUtils.newCoordinateArray(codePoints.length,
-                        Constants.NOT_A_COORDINATE, Constants.NOT_A_COORDINATE);
-                proximityInfo = null;
-                keyboardLayout = null;
-            } else {
-                coordinates = keyboard.getCoordinates(codePoints);
-                proximityInfo = keyboard.getProximityInfo();
-                keyboardLayout = keyboard.getKeyboardLayout();
-            }
+            coordinates = keyboard.getCoordinates(codePoints);
             composer.setComposingWord(codePoints, coordinates);
             // TODO: Don't gather suggestions if the limit is <= 0 unless necessary
             final SuggestionResults suggestionResults = mService.getSuggestionResults(
-                    mLocale, composer.getComposedDataSnapshot(), ngramContext, proximityInfo,
-                    keyboardLayout);
+                    mLocale, composer.getComposedDataSnapshot(), ngramContext, keyboard);
             final Result result = getResult(capitalizeType, mLocale, suggestionsLimit,
                     mService.getRecommendedThreshold(), text, suggestionResults);
             isInDict = isInDictForAnyCapitalization(text, capitalizeType);