Merge pull request #10231 from JosJuice/android-dir-init-livedata
Android: Make DirectoryInitialization use LiveData
This commit is contained in:
commit
15ff70baba
|
@ -63,7 +63,7 @@ public class AppLinkActivity extends FragmentActivity
|
|||
private void initResources()
|
||||
{
|
||||
mAfterDirectoryInitializationRunner = new AfterDirectoryInitializationRunner();
|
||||
mAfterDirectoryInitializationRunner.run(this, true, () -> tryPlay(playAction));
|
||||
mAfterDirectoryInitializationRunner.runWithLifecycle(this, true, () -> tryPlay(playAction));
|
||||
|
||||
GameFileCacheManager.isLoading().observe(this, (isLoading) ->
|
||||
{
|
||||
|
@ -122,11 +122,7 @@ public class AppLinkActivity extends FragmentActivity
|
|||
|
||||
private void startGame(GameFile game)
|
||||
{
|
||||
if (mAfterDirectoryInitializationRunner != null)
|
||||
{
|
||||
mAfterDirectoryInitializationRunner.cancel();
|
||||
mAfterDirectoryInitializationRunner = null;
|
||||
}
|
||||
mAfterDirectoryInitializationRunner.cancel();
|
||||
EmulationActivity.launch(this, GameFileCacheManager.findSecondDiscAndGetPaths(game), false);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -176,7 +176,7 @@ public final class EmulationActivity extends AppCompatActivity
|
|||
if (sIgnoreLaunchRequests)
|
||||
return;
|
||||
|
||||
new AfterDirectoryInitializationRunner().run(activity, true, () ->
|
||||
new AfterDirectoryInitializationRunner().runWithLifecycle(activity, true, () ->
|
||||
{
|
||||
if (FileBrowserHelper.isPathEmptyOrValid(StringSetting.MAIN_DEFAULT_ISO) &&
|
||||
FileBrowserHelper.isPathEmptyOrValid(StringSetting.MAIN_FS_PATH) &&
|
||||
|
|
|
@ -74,8 +74,7 @@ public final class SettingsActivity extends AppCompatActivity implements Setting
|
|||
MenuTag menuTag = (MenuTag) launcher.getSerializableExtra(ARG_MENU_TAG);
|
||||
|
||||
mPresenter = new SettingsActivityPresenter(this, getSettings());
|
||||
mPresenter.onCreate(savedInstanceState, menuTag, gameID, revision, isWii,
|
||||
getApplicationContext());
|
||||
mPresenter.onCreate(savedInstanceState, menuTag, gameID, revision, isWii, this);
|
||||
}
|
||||
|
||||
@Override
|
||||
|
|
|
@ -2,10 +2,11 @@
|
|||
|
||||
package org.dolphinemu.dolphinemu.features.settings.ui;
|
||||
|
||||
import android.content.Context;
|
||||
import android.os.Bundle;
|
||||
import android.text.TextUtils;
|
||||
|
||||
import androidx.core.app.ComponentActivity;
|
||||
|
||||
import org.dolphinemu.dolphinemu.R;
|
||||
import org.dolphinemu.dolphinemu.features.settings.model.Settings;
|
||||
import org.dolphinemu.dolphinemu.utils.AfterDirectoryInitializationRunner;
|
||||
|
@ -22,13 +23,11 @@ public final class SettingsActivityPresenter
|
|||
|
||||
private boolean mShouldSave;
|
||||
|
||||
private AfterDirectoryInitializationRunner mAfterDirectoryInitializationRunner;
|
||||
|
||||
private MenuTag mMenuTag;
|
||||
private String mGameId;
|
||||
private int mRevision;
|
||||
private boolean mIsWii;
|
||||
private Context mContext;
|
||||
private ComponentActivity mActivity;
|
||||
|
||||
SettingsActivityPresenter(SettingsActivityView view, Settings settings)
|
||||
{
|
||||
|
@ -37,13 +36,13 @@ public final class SettingsActivityPresenter
|
|||
}
|
||||
|
||||
public void onCreate(Bundle savedInstanceState, MenuTag menuTag, String gameId, int revision,
|
||||
boolean isWii, Context context)
|
||||
boolean isWii, ComponentActivity activity)
|
||||
{
|
||||
this.mMenuTag = menuTag;
|
||||
this.mGameId = gameId;
|
||||
this.mRevision = revision;
|
||||
this.mIsWii = isWii;
|
||||
this.mContext = context;
|
||||
this.mActivity = activity;
|
||||
|
||||
mShouldSave = savedInstanceState != null && savedInstanceState.getBoolean(KEY_SHOULD_SAVE);
|
||||
}
|
||||
|
@ -95,9 +94,9 @@ public final class SettingsActivityPresenter
|
|||
{
|
||||
mView.showLoading();
|
||||
|
||||
mAfterDirectoryInitializationRunner = new AfterDirectoryInitializationRunner();
|
||||
mAfterDirectoryInitializationRunner.setFinishedCallback(mView::hideLoading);
|
||||
mAfterDirectoryInitializationRunner.run(mContext, true, this::loadSettingsUI);
|
||||
new AfterDirectoryInitializationRunner()
|
||||
.setFinishedCallback(mView::hideLoading)
|
||||
.runWithLifecycle(mActivity, true, this::loadSettingsUI);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -114,16 +113,10 @@ public final class SettingsActivityPresenter
|
|||
|
||||
public void onStop(boolean finishing)
|
||||
{
|
||||
if (mAfterDirectoryInitializationRunner != null)
|
||||
{
|
||||
mAfterDirectoryInitializationRunner.cancel();
|
||||
mAfterDirectoryInitializationRunner = null;
|
||||
}
|
||||
|
||||
if (mSettings != null && finishing && mShouldSave)
|
||||
{
|
||||
Log.debug("[SettingsActivity] Settings activity stopping. Saving settings to INI...");
|
||||
mSettings.saveSettings(mView, mContext);
|
||||
mSettings.saveSettings(mView, mActivity);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -172,7 +165,7 @@ public final class SettingsActivityPresenter
|
|||
break;
|
||||
|
||||
case 2:
|
||||
mView.showToastMessage(mContext.getString(R.string.make_sure_continuous_scan_enabled));
|
||||
mView.showToastMessage(mActivity.getString(R.string.make_sure_continuous_scan_enabled));
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -26,6 +26,7 @@ public final class GameFileCacheManager
|
|||
private static GameFileCache gameFileCache = null;
|
||||
private static final MutableLiveData<GameFile[]> gameFiles =
|
||||
new MutableLiveData<>(new GameFile[]{});
|
||||
private static boolean runRescanAfterLoad = false;
|
||||
|
||||
private static final ExecutorService executor = Executors.newFixedThreadPool(1);
|
||||
private static final MutableLiveData<Boolean> loadInProgress = new MutableLiveData<>(false);
|
||||
|
@ -127,7 +128,7 @@ public final class GameFileCacheManager
|
|||
if (!loadInProgress.getValue())
|
||||
{
|
||||
loadInProgress.setValue(true);
|
||||
new AfterDirectoryInitializationRunner().run(context, false,
|
||||
new AfterDirectoryInitializationRunner().runWithoutLifecycle(context, false,
|
||||
() -> executor.execute(GameFileCacheManager::load));
|
||||
}
|
||||
}
|
||||
|
@ -135,14 +136,15 @@ public final class GameFileCacheManager
|
|||
/**
|
||||
* Asynchronously scans for games in the user's configured folders,
|
||||
* updating the game file cache with the results.
|
||||
* If startLoad hasn't been called before this, this has no effect.
|
||||
* If loading the game file cache hasn't started or hasn't finished,
|
||||
* the execution of this will be postponed until it finishes.
|
||||
*/
|
||||
public static void startRescan(Context context)
|
||||
{
|
||||
if (!rescanInProgress.getValue())
|
||||
{
|
||||
rescanInProgress.setValue(true);
|
||||
new AfterDirectoryInitializationRunner().run(context, false,
|
||||
new AfterDirectoryInitializationRunner().runWithoutLifecycle(context, false,
|
||||
() -> executor.execute(GameFileCacheManager::rescan));
|
||||
}
|
||||
}
|
||||
|
@ -190,17 +192,33 @@ public final class GameFileCacheManager
|
|||
}
|
||||
}
|
||||
|
||||
if (runRescanAfterLoad)
|
||||
{
|
||||
rescanInProgress.postValue(true);
|
||||
}
|
||||
|
||||
loadInProgress.postValue(false);
|
||||
|
||||
if (runRescanAfterLoad)
|
||||
{
|
||||
runRescanAfterLoad = false;
|
||||
rescan();
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Scans for games in the user's configured folders,
|
||||
* updating the game file cache with the results.
|
||||
* If load hasn't been called before this, this has no effect.
|
||||
* If load hasn't been called before this, the execution of this
|
||||
* will be postponed until after load runs.
|
||||
*/
|
||||
private static void rescan()
|
||||
{
|
||||
if (gameFileCache != null)
|
||||
if (gameFileCache == null)
|
||||
{
|
||||
runRescanAfterLoad = true;
|
||||
}
|
||||
else
|
||||
{
|
||||
String[] gamePaths = GameFileCache.getAllGamePaths();
|
||||
|
||||
|
|
|
@ -73,7 +73,7 @@ public final class MainActivity extends AppCompatActivity
|
|||
if (!DirectoryInitialization.isWaitingForWriteAccess(this))
|
||||
{
|
||||
new AfterDirectoryInitializationRunner()
|
||||
.run(this, false, this::setPlatformTabsAndStartGameFileCacheService);
|
||||
.runWithLifecycle(this, false, this::setPlatformTabsAndStartGameFileCacheService);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -86,7 +86,7 @@ public final class MainActivity extends AppCompatActivity
|
|||
{
|
||||
DirectoryInitialization.start(this);
|
||||
new AfterDirectoryInitializationRunner()
|
||||
.run(this, false, this::setPlatformTabsAndStartGameFileCacheService);
|
||||
.runWithLifecycle(this, false, this::setPlatformTabsAndStartGameFileCacheService);
|
||||
}
|
||||
|
||||
mPresenter.onResume();
|
||||
|
@ -254,7 +254,7 @@ public final class MainActivity extends AppCompatActivity
|
|||
|
||||
DirectoryInitialization.start(this);
|
||||
new AfterDirectoryInitializationRunner()
|
||||
.run(this, false, this::setPlatformTabsAndStartGameFileCacheService);
|
||||
.runWithLifecycle(this, false, this::setPlatformTabsAndStartGameFileCacheService);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
@ -73,7 +73,7 @@ public final class MainPresenter
|
|||
mView.launchFileListActivity();
|
||||
}
|
||||
|
||||
public boolean handleOptionSelection(int itemId, Context context)
|
||||
public boolean handleOptionSelection(int itemId, ComponentActivity activity)
|
||||
{
|
||||
switch (itemId)
|
||||
{
|
||||
|
@ -83,7 +83,7 @@ public final class MainPresenter
|
|||
|
||||
case R.id.menu_refresh:
|
||||
mView.setRefreshing(true);
|
||||
GameFileCacheManager.startRescan(context);
|
||||
GameFileCacheManager.startRescan(activity);
|
||||
return true;
|
||||
|
||||
case R.id.button_add_directory:
|
||||
|
@ -95,17 +95,17 @@ public final class MainPresenter
|
|||
return true;
|
||||
|
||||
case R.id.menu_install_wad:
|
||||
new AfterDirectoryInitializationRunner().run(context, true,
|
||||
new AfterDirectoryInitializationRunner().runWithLifecycle(activity, true,
|
||||
() -> mView.launchOpenFileActivity(REQUEST_WAD_FILE));
|
||||
return true;
|
||||
|
||||
case R.id.menu_import_wii_save:
|
||||
new AfterDirectoryInitializationRunner().run(context, true,
|
||||
new AfterDirectoryInitializationRunner().runWithLifecycle(activity, true,
|
||||
() -> mView.launchOpenFileActivity(REQUEST_WII_SAVE_FILE));
|
||||
return true;
|
||||
|
||||
case R.id.menu_import_nand_backup:
|
||||
new AfterDirectoryInitializationRunner().run(context, true,
|
||||
new AfterDirectoryInitializationRunner().runWithLifecycle(activity, true,
|
||||
() -> mView.launchOpenFileActivity(REQUEST_NAND_BIN_FILE));
|
||||
return true;
|
||||
}
|
||||
|
@ -121,12 +121,9 @@ public final class MainPresenter
|
|||
mDirToAdd = null;
|
||||
}
|
||||
|
||||
if (sShouldRescanLibrary && !GameFileCacheManager.isRescanning().getValue())
|
||||
if (sShouldRescanLibrary)
|
||||
{
|
||||
new AfterDirectoryInitializationRunner().run(mActivity, false, () ->
|
||||
{
|
||||
GameFileCacheManager.startRescan(mActivity);
|
||||
});
|
||||
GameFileCacheManager.startRescan(mActivity);
|
||||
}
|
||||
|
||||
sShouldRescanLibrary = true;
|
||||
|
|
|
@ -3,30 +3,33 @@
|
|||
package org.dolphinemu.dolphinemu.utils;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.IntentFilter;
|
||||
import android.widget.Toast;
|
||||
|
||||
import androidx.localbroadcastmanager.content.LocalBroadcastManager;
|
||||
import androidx.core.app.ComponentActivity;
|
||||
import androidx.lifecycle.Observer;
|
||||
|
||||
import org.dolphinemu.dolphinemu.R;
|
||||
import org.dolphinemu.dolphinemu.utils.DirectoryInitialization.DirectoryInitializationState;
|
||||
|
||||
public class AfterDirectoryInitializationRunner
|
||||
{
|
||||
private DirectoryStateReceiver mDirectoryStateReceiver;
|
||||
private LocalBroadcastManager mLocalBroadcastManager;
|
||||
|
||||
private Observer<DirectoryInitializationState> mObserver;
|
||||
private Runnable mUnregisterCallback;
|
||||
|
||||
/**
|
||||
* Sets a Runnable which will be called when:
|
||||
*
|
||||
* 1. The Runnable supplied to {@link #run} is just about to run, or
|
||||
* 2. {@link #run} was called with abortOnFailure == true and there is a failure
|
||||
* 1. The Runnable supplied to {@link #runWithLifecycle}/{@link #runWithoutLifecycle}
|
||||
* is just about to run, or
|
||||
* 2. {@link #runWithLifecycle}/{@link #runWithoutLifecycle} was called with
|
||||
* abortOnFailure == true and there is a failure
|
||||
*
|
||||
* @return this
|
||||
*/
|
||||
public void setFinishedCallback(Runnable runnable)
|
||||
public AfterDirectoryInitializationRunner setFinishedCallback(Runnable runnable)
|
||||
{
|
||||
mUnregisterCallback = runnable;
|
||||
return this;
|
||||
}
|
||||
|
||||
private void runFinishedCallback()
|
||||
|
@ -48,13 +51,16 @@ public class AfterDirectoryInitializationRunner
|
|||
*
|
||||
* Calling this function multiple times per object is not supported.
|
||||
*
|
||||
* If abortOnFailure is true and the user has not granted the required
|
||||
* permission or the external storage was not found, a message will be
|
||||
* shown to the user and the Runnable will not run. If it is false, the
|
||||
* attempt to run the Runnable will never be aborted, and the Runnable
|
||||
* If abortOnFailure is true and external storage was not found, a message
|
||||
* will be shown to the user and the Runnable will not run. If it is false,
|
||||
* the attempt to run the Runnable will never be aborted, and the Runnable
|
||||
* is guaranteed to run if directory initialization ever finishes.
|
||||
*
|
||||
* If the passed-in activity gets destroyed before this operation finishes,
|
||||
* it will be automatically canceled.
|
||||
*/
|
||||
public void run(Context context, boolean abortOnFailure, Runnable runnable)
|
||||
public void runWithLifecycle(ComponentActivity activity, boolean abortOnFailure,
|
||||
Runnable runnable)
|
||||
{
|
||||
if (DirectoryInitialization.areDolphinDirectoriesReady())
|
||||
{
|
||||
|
@ -62,19 +68,58 @@ public class AfterDirectoryInitializationRunner
|
|||
runnable.run();
|
||||
}
|
||||
else if (abortOnFailure &&
|
||||
showErrorMessage(context, DirectoryInitialization.getDolphinDirectoriesState()))
|
||||
showErrorMessage(activity,
|
||||
DirectoryInitialization.getDolphinDirectoriesState().getValue()))
|
||||
{
|
||||
runFinishedCallback();
|
||||
}
|
||||
else
|
||||
{
|
||||
runAfterInitialization(context, abortOnFailure, runnable);
|
||||
mObserver = createObserver(activity, abortOnFailure, runnable);
|
||||
DirectoryInitialization.getDolphinDirectoriesState().observe(activity, mObserver);
|
||||
}
|
||||
}
|
||||
|
||||
private void runAfterInitialization(Context context, boolean abortOnFailure, Runnable runnable)
|
||||
/**
|
||||
* Executes a Runnable after directory initialization has finished.
|
||||
*
|
||||
* If this is called when directory initialization already is done,
|
||||
* the Runnable will be executed immediately. If this is called before
|
||||
* directory initialization is done, the Runnable will be executed
|
||||
* after directory initialization finishes successfully, or never
|
||||
* in case directory initialization doesn't finish successfully.
|
||||
*
|
||||
* Calling this function multiple times per object is not supported.
|
||||
*
|
||||
* If abortOnFailure is true and external storage was not found, a message
|
||||
* will be shown to the user and the Runnable will not run. If it is false,
|
||||
* the attempt to run the Runnable will never be aborted, and the Runnable
|
||||
* is guaranteed to run if directory initialization ever finishes.
|
||||
*/
|
||||
public void runWithoutLifecycle(Context context, boolean abortOnFailure, Runnable runnable)
|
||||
{
|
||||
mDirectoryStateReceiver = new DirectoryStateReceiver(state ->
|
||||
if (DirectoryInitialization.areDolphinDirectoriesReady())
|
||||
{
|
||||
runFinishedCallback();
|
||||
runnable.run();
|
||||
}
|
||||
else if (abortOnFailure &&
|
||||
showErrorMessage(context,
|
||||
DirectoryInitialization.getDolphinDirectoriesState().getValue()))
|
||||
{
|
||||
runFinishedCallback();
|
||||
}
|
||||
else
|
||||
{
|
||||
mObserver = createObserver(context, abortOnFailure, runnable);
|
||||
DirectoryInitialization.getDolphinDirectoriesState().observeForever(mObserver);
|
||||
}
|
||||
}
|
||||
|
||||
private Observer<DirectoryInitializationState> createObserver(Context context,
|
||||
boolean abortOnFailure, Runnable runnable)
|
||||
{
|
||||
return (state) ->
|
||||
{
|
||||
boolean done = state == DirectoryInitializationState.DOLPHIN_DIRECTORIES_INITIALIZED;
|
||||
|
||||
|
@ -93,22 +138,12 @@ public class AfterDirectoryInitializationRunner
|
|||
{
|
||||
runnable.run();
|
||||
}
|
||||
});
|
||||
|
||||
mLocalBroadcastManager = LocalBroadcastManager.getInstance(context);
|
||||
|
||||
IntentFilter statusIntentFilter = new IntentFilter(DirectoryInitialization.BROADCAST_ACTION);
|
||||
mLocalBroadcastManager.registerReceiver(mDirectoryStateReceiver, statusIntentFilter);
|
||||
};
|
||||
}
|
||||
|
||||
public void cancel()
|
||||
{
|
||||
if (mDirectoryStateReceiver != null)
|
||||
{
|
||||
mLocalBroadcastManager.unregisterReceiver(mDirectoryStateReceiver);
|
||||
mDirectoryStateReceiver = null;
|
||||
mLocalBroadcastManager = null;
|
||||
}
|
||||
DirectoryInitialization.getDolphinDirectoriesState().removeObserver(mObserver);
|
||||
}
|
||||
|
||||
private static boolean showErrorMessage(Context context, DirectoryInitializationState state)
|
||||
|
|
|
@ -25,7 +25,7 @@ public class Analytics
|
|||
|
||||
public static void checkAnalyticsInit(Context context)
|
||||
{
|
||||
new AfterDirectoryInitializationRunner().run(context, false, () ->
|
||||
new AfterDirectoryInitializationRunner().runWithoutLifecycle(context, false, () ->
|
||||
{
|
||||
if (!BooleanSetting.MAIN_ANALYTICS_PERMISSION_ASKED.getBooleanGlobal())
|
||||
{
|
||||
|
|
|
@ -6,7 +6,6 @@
|
|||
package org.dolphinemu.dolphinemu.utils;
|
||||
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
import android.content.SharedPreferences;
|
||||
import android.os.Build;
|
||||
import android.os.Environment;
|
||||
|
@ -14,18 +13,17 @@ import android.preference.PreferenceManager;
|
|||
|
||||
import androidx.annotation.NonNull;
|
||||
import androidx.annotation.Nullable;
|
||||
import androidx.localbroadcastmanager.content.LocalBroadcastManager;
|
||||
import androidx.lifecycle.LiveData;
|
||||
import androidx.lifecycle.MutableLiveData;
|
||||
|
||||
import org.dolphinemu.dolphinemu.NativeLibrary;
|
||||
import org.dolphinemu.dolphinemu.activities.EmulationActivity;
|
||||
|
||||
import java.io.File;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.FileOutputStream;
|
||||
import java.io.IOException;
|
||||
import java.io.InputStream;
|
||||
import java.io.OutputStream;
|
||||
import java.util.concurrent.atomic.AtomicBoolean;
|
||||
|
||||
/**
|
||||
* A service that spawns its own thread in order to copy several binary and shader files
|
||||
|
@ -33,30 +31,29 @@ import java.util.concurrent.atomic.AtomicBoolean;
|
|||
*/
|
||||
public final class DirectoryInitialization
|
||||
{
|
||||
public static final String BROADCAST_ACTION =
|
||||
"org.dolphinemu.dolphinemu.DIRECTORY_INITIALIZATION";
|
||||
|
||||
public static final String EXTRA_STATE = "directoryState";
|
||||
private static final int WiimoteNewVersion = 5; // Last changed in PR 8907
|
||||
private static volatile DirectoryInitializationState directoryState =
|
||||
DirectoryInitializationState.NOT_YET_INITIALIZED;
|
||||
private static final MutableLiveData<DirectoryInitializationState> directoryState =
|
||||
new MutableLiveData<>(DirectoryInitializationState.NOT_YET_INITIALIZED);
|
||||
private static volatile boolean areDirectoriesAvailable = false;
|
||||
private static String userPath;
|
||||
private static AtomicBoolean isDolphinDirectoryInitializationRunning = new AtomicBoolean(false);
|
||||
private static boolean isUsingLegacyUserDirectory = false;
|
||||
|
||||
public enum DirectoryInitializationState
|
||||
{
|
||||
NOT_YET_INITIALIZED,
|
||||
INITIALIZING,
|
||||
DOLPHIN_DIRECTORIES_INITIALIZED,
|
||||
CANT_FIND_EXTERNAL_STORAGE
|
||||
}
|
||||
|
||||
public static void start(Context context)
|
||||
{
|
||||
if (!isDolphinDirectoryInitializationRunning.compareAndSet(false, true))
|
||||
if (directoryState.getValue() == DirectoryInitializationState.INITIALIZING)
|
||||
return;
|
||||
|
||||
directoryState.setValue(DirectoryInitializationState.INITIALIZING);
|
||||
|
||||
// Can take a few seconds to run, so don't block UI thread.
|
||||
//noinspection TrivialFunctionalExpressionUsage
|
||||
((Runnable) () -> init(context)).run();
|
||||
|
@ -64,7 +61,7 @@ public final class DirectoryInitialization
|
|||
|
||||
private static void init(Context context)
|
||||
{
|
||||
if (directoryState != DirectoryInitializationState.DOLPHIN_DIRECTORIES_INITIALIZED)
|
||||
if (directoryState.getValue() != DirectoryInitializationState.DOLPHIN_DIRECTORIES_INITIALIZED)
|
||||
{
|
||||
if (setDolphinUserDirectory(context))
|
||||
{
|
||||
|
@ -82,16 +79,13 @@ public final class DirectoryInitialization
|
|||
EmulationActivity.updateWiimoteNewIniPreferences(context);
|
||||
}
|
||||
|
||||
directoryState = DirectoryInitializationState.DOLPHIN_DIRECTORIES_INITIALIZED;
|
||||
directoryState.postValue(DirectoryInitializationState.DOLPHIN_DIRECTORIES_INITIALIZED);
|
||||
}
|
||||
else
|
||||
{
|
||||
directoryState = DirectoryInitializationState.CANT_FIND_EXTERNAL_STORAGE;
|
||||
directoryState.postValue(DirectoryInitializationState.CANT_FIND_EXTERNAL_STORAGE);
|
||||
}
|
||||
}
|
||||
|
||||
isDolphinDirectoryInitializationRunning.set(false);
|
||||
sendBroadcastState(directoryState, context);
|
||||
}
|
||||
|
||||
@Nullable
|
||||
|
@ -216,17 +210,18 @@ public final class DirectoryInitialization
|
|||
|
||||
public static boolean shouldStart(Context context)
|
||||
{
|
||||
return !isDolphinDirectoryInitializationRunning.get() &&
|
||||
getDolphinDirectoriesState() == DirectoryInitializationState.NOT_YET_INITIALIZED &&
|
||||
return getDolphinDirectoriesState().getValue() ==
|
||||
DirectoryInitializationState.NOT_YET_INITIALIZED &&
|
||||
!isWaitingForWriteAccess(context);
|
||||
}
|
||||
|
||||
public static boolean areDolphinDirectoriesReady()
|
||||
{
|
||||
return directoryState == DirectoryInitializationState.DOLPHIN_DIRECTORIES_INITIALIZED;
|
||||
return directoryState.getValue() ==
|
||||
DirectoryInitializationState.DOLPHIN_DIRECTORIES_INITIALIZED;
|
||||
}
|
||||
|
||||
public static DirectoryInitializationState getDolphinDirectoriesState()
|
||||
public static LiveData<DirectoryInitializationState> getDolphinDirectoriesState()
|
||||
{
|
||||
return directoryState;
|
||||
}
|
||||
|
@ -241,14 +236,6 @@ public final class DirectoryInitialization
|
|||
return userPath;
|
||||
}
|
||||
|
||||
private static void sendBroadcastState(DirectoryInitializationState state, Context context)
|
||||
{
|
||||
Intent localIntent =
|
||||
new Intent(BROADCAST_ACTION)
|
||||
.putExtra(EXTRA_STATE, state);
|
||||
LocalBroadcastManager.getInstance(context).sendBroadcast(localIntent);
|
||||
}
|
||||
|
||||
private static boolean copyAsset(String asset, File output, Boolean overwrite, Context context)
|
||||
{
|
||||
Log.verbose("[DirectoryInitialization] Copying File " + asset + " to " + output);
|
||||
|
@ -400,7 +387,7 @@ public final class DirectoryInitialization
|
|||
public static boolean isWaitingForWriteAccess(Context context)
|
||||
{
|
||||
// This first check is only for performance, not correctness
|
||||
if (getDolphinDirectoriesState() != DirectoryInitializationState.NOT_YET_INITIALIZED)
|
||||
if (directoryState.getValue() != DirectoryInitializationState.NOT_YET_INITIALIZED)
|
||||
return false;
|
||||
|
||||
return preferLegacyUserDirectory(context) && !PermissionsHandler.hasWriteAccess(context);
|
||||
|
|
|
@ -1,27 +0,0 @@
|
|||
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
package org.dolphinemu.dolphinemu.utils;
|
||||
|
||||
import android.content.BroadcastReceiver;
|
||||
import android.content.Context;
|
||||
import android.content.Intent;
|
||||
|
||||
import org.dolphinemu.dolphinemu.utils.DirectoryInitialization.DirectoryInitializationState;
|
||||
|
||||
public class DirectoryStateReceiver extends BroadcastReceiver
|
||||
{
|
||||
Action1<DirectoryInitializationState> callback;
|
||||
|
||||
public DirectoryStateReceiver(Action1<DirectoryInitializationState> callback)
|
||||
{
|
||||
this.callback = callback;
|
||||
}
|
||||
|
||||
@Override
|
||||
public void onReceive(Context context, Intent intent)
|
||||
{
|
||||
DirectoryInitializationState state = (DirectoryInitializationState) intent
|
||||
.getSerializableExtra(DirectoryInitialization.EXTRA_STATE);
|
||||
callback.call(state);
|
||||
}
|
||||
}
|
|
@ -79,7 +79,7 @@ public final class StartupHandler
|
|||
final Instant lastOpened = Instant.ofEpochMilli(lastOpen);
|
||||
if (current.isAfter(lastOpened.plus(6, ChronoUnit.HOURS)))
|
||||
{
|
||||
new AfterDirectoryInitializationRunner().run(context, false,
|
||||
new AfterDirectoryInitializationRunner().runWithoutLifecycle(context, false,
|
||||
NativeLibrary::ReportStartToAnalytics);
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in New Issue