Как я могу заставить Слушать Игровые Службы автоматически не войти в систему при запуске?

Google предоставляет библиотеку BaseGameUtils и рекомендует нам BaseGameActivity . Тем не менее, этот класс заставляет игру автоматически входить в игру всякий раз, когда начинается игра. Если игрок не хочет или не может подключиться к своей учетной записи Google, это может занять много времени в начале игры.

Поэтому я не хочу эту функцию. Вместо этого я хочу предоставить кнопку входа. Игрок подключается только при нажатии этой кнопки. И с этого момента каждый раз, когда игрок начинает игру, он автоматически подключается к своей учетной записи Google, не нажимая ни одной кнопки . Как я могу это сделать?

Solutions Collecting From Web of "Как я могу заставить Слушать Игровые Службы автоматически не войти в систему при запуске?"

ОК, я понял, по умолчанию максимальное время автоматического входа – 3 , что означает, что если пользователь отменит 3 раза, то приложение больше никогда не будет (если вы не очистите данные приложения) автоматически войдите. В GameHelper.java

  // Should we start the flow to sign the user in automatically on startup? If so, up to // how many times in the life of the application? static final int DEFAULT_MAX_SIGN_IN_ATTEMPTS = 3; int mMaxAutoSignInAttempts = DEFAULT_MAX_SIGN_IN_ATTEMPTS; 

И он также обеспечивает функцию для установки этого максимального числа

 public void setMaxAutoSignInAttempts(int max) { mMaxAutoSignInAttempts = max; } 

Поэтому, если вам не нужна автоматическая попытка входа в систему , просто вызовите эту функцию

Это если вы не хотите расширять BaseGameActivity

 gameHelper = new GameHelper(this, GameHelper.CLIENT_GAMES); gameHelper.enableDebugLog(true); gameHelper.setup(this); gameHelper.setMaxAutoSignInAttempts(0); 

Или, если вы расширите BaseGameActivity

 getGameHelper().setMaxAutoSignInAttempts(0); 

В файле GameHelper.java имеется логический атрибут mConnectOnStart который по умолчанию имеет значение true. Просто замените его на false :

 boolean mConnectOnStart = false; 

Кроме того, существует метод, позволяющий управлять этим атрибутом извне класса:

 // Not recommended for general use. This method forces the "connect on start" // flag to a given state. This may be useful when using GameHelper in a // non-standard sign-in flow. public void setConnectOnStart(boolean connectOnStart) { debugLog("Forcing mConnectOnStart=" + connectOnStart); mConnectOnStart = connectOnStart; } 

Вы можете использовать метод выше, чтобы настроить свой вход в систему. В моем случае, как и вы, я не хочу автоматически подключаться в первый раз. Но если пользователь был ранее подписан, я хочу автоматически подключиться. Чтобы это getGameHelper() возможным, я изменил метод getGameHelper() который находится в классе BaseGameActivity :

 public GameHelper getGameHelper() { if (mHelper == null) { mHelper = new GameHelper(this, mRequestedClients); mHelper.enableDebugLog(mDebugLog); googlePlaySharedPref = getSharedPreferences("GOOGLE_PLAY", Context.MODE_PRIVATE); boolean wasSignedIn = googlePlaySharedPref.getBoolean("WAS_SIGNED_IN", false); mHelper.setConnectOnStart(wasSignedIn); } return mHelper; } 

Каждый раз метод getGameHelper() вызывается из onStart() в BaseGameActivity . В приведенном выше коде я просто добавил общее предпочтение сохранить, если пользователь был ранее подписан. И вызвал метод setConnectOnStart() соответствии с этим случаем.

Наконец, не забудьте установить "WAS_SIGNED_IN" (или что-то еще, если вы определили с другим именем), разделяемое предпочтение true после того, как пользователь начал вход в систему. Вы можете сделать это в onSignInSucceeded() в классе BaseGameActivity .

Надеюсь, что это поможет вам. Удачи.

Я сделал это так, я не знаю, если это лучший способ сделать это. Я изменил класс GameHelper, чтобы он сохранял предпочтения пользователя в общих предпочтениях:

 ... public class GameHelper implements GoogleApiClient.ConnectionCallbacks, GoogleApiClient.OnConnectionFailedListener { .... // Whether to automatically try to sign in on onStart(). We only set this // to true when the sign-in process fails or the user explicitly signs out. // We set it back to false when the user initiates the sign in process. boolean mConnectOnStart = false; ... /** Call this method from your Activity's onStart(). */ public void onStart(Activity act) { mActivity = act; mAppContext = act.getApplicationContext(); debugLog("onStart"); assertConfigured("onStart"); SharedPreferences sp = mAppContext.getSharedPreferences(GAMEHELPER_SHARED_PREFS, Context.MODE_PRIVATE); mConnectOnStart = sp.getBoolean(KEY_AUTO_SIGN_IN, false); if (mConnectOnStart) { ... } ... /** Sign out and disconnect from the APIs. */ public void signOut() { ... // Ready to disconnect debugLog("Disconnecting client."); mConnectOnStart = false; SharedPreferences.Editor editor = mAppContext.getSharedPreferences(GAMEHELPER_SHARED_PREFS, Context.MODE_PRIVATE).edit(); editor.putBoolean(KEY_AUTO_SIGN_IN, false); editor.commit(); mConnecting = false; mGoogleApiClient.disconnect(); } ... /** * Starts a user-initiated sign-in flow. This should be called when the user * clicks on a "Sign In" button. As a result, authentication/consent dialogs * may show up. At the end of the process, the GameHelperListener's * onSignInSucceeded() or onSignInFailed() methods will be called. */ public void beginUserInitiatedSignIn() { debugLog("beginUserInitiatedSignIn: resetting attempt count."); resetSignInCancellations(); mSignInCancelled = false; mConnectOnStart = true; SharedPreferences.Editor editor = mAppContext.getSharedPreferences(GAMEHELPER_SHARED_PREFS, Context.MODE_PRIVATE).edit(); editor.putBoolean(KEY_AUTO_SIGN_IN, true); editor.commit(); if (mGoogleApiClient.isConnected()) { ... } ... private final String GAMEHELPER_SHARED_PREFS = "GAMEHELPER_SHARED_PREFS"; private final String KEY_SIGN_IN_CANCELLATIONS = "KEY_SIGN_IN_CANCELLATIONS"; private final String KEY_AUTO_SIGN_IN = "KEY_AUTO_SIGN_IN"; ... } 

См. https://github.com/playgameservices/android-samples/blob/master/FAQ.txt строку 54, почему вы автоматически входите в систему

Вызовите getGameHelper().setConnectOnStart(false); From onCreate

Фактически, код от Google работает точно так же, как вы говорите во втором абзаце.

Я хочу предоставить кнопку входа. Игрок подключается только при нажатии этой кнопки. И с этого момента каждый раз, когда игрок начинает игру, он автоматически подключается к своей учетной записи Google, не нажимая ни одной кнопки. Как я могу это сделать?

  1. Метод Helper.setup создает клиентов

  2. OnStart смотрит на внутреннее логическое значение для автоматического входа. Если пользователь был ранее подключен (и пользователь не выходил из системы, или не было ошибки при отключении), он попытается восстановить вход.

  3. BeginUserInitiatedSignIn установит логический логин в автоматическом режиме, если инициировано успешное соединение

  4. OnStop будет только прекращать соединения изящно, он не сбрасывает логические

Таким образом, единственный способ, с помощью которого пользователь видит входной сигнал в процессе запуска вашего приложения, – это если startUserInitiatedSignIn каким-то образом вызывается перед нажатием кнопки.

Убедитесь, что ваш beginUserInitiatedSignIn не находится в вашем методе onStart и не вызывается, кроме как с помощью других средств, кроме нажатия на кнопку входа в систему, и пользователь НЕ зарегистрирован.

  @Override protected void onCreate(Bundle b) { super.onCreate(b); mHelper = new GameHelper(this); if (mDebugLog) { mHelper.enableDebugLog(mDebugLog, mDebugTag); } mHelper.setup(this, mRequestedClients, mAdditionalScopes); } @Override protected void onStart() { super.onStart(); mHelper.onStart(this); } @Override protected void onStop() { super.onStop(); mHelper.onStop(); } protected void beginUserInitiatedSignIn() { mHelper.beginUserInitiatedSignIn(); } 

Из класса BaseGameUtil

/ ** * Пример базового класса для игр. Эта реализация заботится о настройке * объекта GamesClient и управлении его жизненным циклом. Подклассам нужно только * переопределить методы @link {#onSignInSucceeded} и @link {#onSignInFailed} abstract *. Чтобы инициировать входной поток, когда пользователь нажимает кнопку входа *, подклассы должны вызывать @link {#beginUserInitiatedSignIn}. По умолчанию * этот класс создает экземпляр объекта GamesClient. Если объекты PlusClient или * AppStateClient также нужны, вызовите конструктор BaseGameActivity (int) * и укажите запрашиваемых клиентов. Например, для запроса * PlusClient и GamesClient используйте BaseGameActivity (CLIENT_GAMES | CLIENT_PLUS). * Чтобы запросить всех доступных клиентов, используйте BaseGameActivity (CLIENT_ALL). * Кроме того, вы также можете указать запрашиваемых клиентов через * @link {#setRequestedClients}, но вы должны сделать это до вызова @link {#onCreate} *, иначе вызов не будет иметь никакого эффекта. * * @author Бруно Оливейра (Google)