diff --git a/java/src/com/android/inputmethod/latin/LatinIME.java b/java/src/com/android/inputmethod/latin/LatinIME.java
index aca361905897def1da83de778abc4fed2105aa5e..399d4917c81afc46a72e45c8d9e085dbe923b3cd 100644
--- a/java/src/com/android/inputmethod/latin/LatinIME.java
+++ b/java/src/com/android/inputmethod/latin/LatinIME.java
@@ -217,10 +217,15 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
                         (SuggestedWords) msg.obj, latinIme.mKeyboardSwitcher);
                 break;
             case MSG_RESET_CACHES:
-                latinIme.mInputLogic.retryResetCaches(latinIme.mSettings.getCurrent(),
+                final SettingsValues settingsValues = latinIme.mSettings.getCurrent();
+                if (latinIme.mInputLogic.retryResetCachesAndReturnSuccess(settingsValues,
                         msg.arg1 == 1 /* tryResumeSuggestions */,
-                        msg.arg2 /* remainingTries */,
-                        latinIme.mKeyboardSwitcher, this);
+                        msg.arg2 /* remainingTries */, this /* handler */)) {
+                    // If we were able to reset the caches, then we can reload the keyboard.
+                    // Otherwise, we'll do it when we can.
+                    latinIme.mKeyboardSwitcher.loadKeyboard(latinIme.getCurrentInputEditorInfo(),
+                            settingsValues);
+                }
                 break;
             }
         }
@@ -1257,6 +1262,7 @@ public class LatinIME extends InputMethodService implements KeyboardActionListen
         final int keyY = mainKeyboardView.getKeyY(y);
         mInputLogic.onCodeInput(codePoint, keyX, keyY, mHandler, mKeyboardSwitcher,
                 mSubtypeSwitcher);
+        mKeyboardSwitcher.onCodeInput(codePoint);
     }
 
     // Called from PointerTracker through the KeyboardActionListener interface
diff --git a/java/src/com/android/inputmethod/latin/inputlogic/InputLogic.java b/java/src/com/android/inputmethod/latin/inputlogic/InputLogic.java
index 20be8141174d65f63d314041d410ead18943e540..3c5406545653a82e9ef32c8379a92647665558ac 100644
--- a/java/src/com/android/inputmethod/latin/inputlogic/InputLogic.java
+++ b/java/src/com/android/inputmethod/latin/inputlogic/InputLogic.java
@@ -300,7 +300,6 @@ public final class InputLogic {
                     code, x, y, spaceState, keyboardSwitcher, handler);
             break;
         }
-        keyboardSwitcher.onCodeInput(code);
         // Reset after any single keystroke, except shift, capslock, and symbol-shift
         if (!didAutoCorrect && code != Constants.CODE_SHIFT
                 && code != Constants.CODE_CAPSLOCK
@@ -1699,26 +1698,27 @@ public final class InputLogic {
      * @param settingsValues the current values of the settings.
      * @param tryResumeSuggestions Whether we should resume suggestions or not.
      * @param remainingTries How many times we may try again before giving up.
+     * @return whether true if the caches were successfully reset, false otherwise.
      */
     // TODO: make this private
-    public void retryResetCaches(final SettingsValues settingsValues,
+    public boolean retryResetCachesAndReturnSuccess(final SettingsValues settingsValues,
             final boolean tryResumeSuggestions, final int remainingTries,
             // TODO: remove these arguments
-            final KeyboardSwitcher keyboardSwitcher, final LatinIME.UIHandler handler) {
+            final LatinIME.UIHandler handler) {
         if (!mConnection.resetCachesUponCursorMoveAndReturnSuccess(
                 mConnection.getExpectedSelectionStart(), mConnection.getExpectedSelectionEnd(),
                 false)) {
             if (0 < remainingTries) {
                 handler.postResetCaches(tryResumeSuggestions, remainingTries - 1);
-                return;
+                return false;
             }
-            // If remainingTries is 0, we should stop waiting for new tries, but it's still
-            // better to load the keyboard (less things will be broken).
+            // If remainingTries is 0, we should stop waiting for new tries, however we'll still
+            // return true as we need to perform other tasks (for example, loading the keyboard).
         }
         mConnection.tryFixLyingCursorPosition();
-        keyboardSwitcher.loadKeyboard(getCurrentInputEditorInfo(), settingsValues);
         if (tryResumeSuggestions) {
             handler.postResumeSuggestions();
         }
+        return true;
     }
 }