6.6.3 - Alpha5 - 修复示例代码子目录文件自动加载问题; 支持将示例代码文件夹重置为初始内容

This commit is contained in:
SuperMonster003
2025-05-25 20:48:26 +08:00
parent 1fdaf36e7b
commit 38118dd1a4
7 changed files with 104 additions and 58 deletions

View File

@@ -2,9 +2,10 @@ package org.autojs.autojs.model.explorer;
import android.content.Context;
import android.content.res.AssetManager;
import androidx.annotation.Nullable;
import io.reactivex.Observable;
import io.reactivex.Single;
import io.reactivex.schedulers.Schedulers;
import org.autojs.autojs.model.script.ScriptFile;
import org.autojs.autojs.pio.PFile;
import org.autojs.autojs.pio.PFiles;
@@ -14,11 +15,7 @@ import org.autojs.autojs.util.WorkingDirectoryUtils;
import java.io.File;
import java.io.FileFilter;
import java.io.FileNotFoundException;
import java.io.InputStream;
import io.reactivex.Observable;
import io.reactivex.Single;
import io.reactivex.schedulers.Schedulers;
import java.io.IOException;
public class WorkspaceFileProvider extends ExplorerFileProvider {
@@ -88,31 +85,47 @@ public class WorkspaceFileProvider extends ExplorerFileProvider {
return Observable.just(pathOfAsset)
.flatMap(path -> Observable.fromArray(mAssetManager.list(path)))
.map(child -> {
PFile file = new PFile(new File(directory, child).getPath());
if (file.exists()) {
return file;
}
try {
InputStream stream = mAssetManager.open(pathOfAsset + File.separator + child);
PFiles.copyStream(stream, file.getPath());
} catch (FileNotFoundException e) {
file.mkdirs();
}
return file;
PFile localFile = new PFile(new File(directory, child).getPath());
copyAssetRecursively(pathOfAsset + File.separator + child, localFile);
return localFile;
});
}
private void copyAssetRecursively(String assetPath, File dest) throws IOException {
String[] children = mAssetManager.list(assetPath);
if (children == null || children.length == 0) {
if (!dest.exists()) {
try {
PFiles.copyAssetFile(mAssetManager, assetPath, dest.getPath());
} catch (FileNotFoundException ignored) {
/* Ignored. */
}
}
return;
}
if (!dest.exists()) {
dest.mkdirs();
}
for (String child : children) {
copyAssetRecursively(assetPath + File.separator + child, new File(dest, child));
}
}
@Nullable
public Observable<ScriptFile> resetSample(ScriptFile file) {
if (file.getPath().length() <= mSampleDir.getPath().length() + 1) {
if (!file.getPath().startsWith(mSampleDir.getPath())) {
return null;
}
String pathOfSample = file.getPath().substring(mSampleDir.getPath().length());
String pathOfAsset = SAMPLE_PATH + pathOfSample;
return Observable
.fromCallable(() -> {
try (InputStream stream = mAssetManager.open(pathOfAsset)) {
PFiles.copyStream(stream, file.getPath());
try {
if (file.isDirectory()) {
PFiles.copyAssetDir(mAssetManager, pathOfAsset, file.getPath());
} else {
PFiles.copyAssetFile(mAssetManager, pathOfAsset, file.getPath());
}
} catch (FileNotFoundException ignored) {
return new ScriptFile(System.currentTimeMillis() + "\ufeff" + Math.random());
}

View File

@@ -281,23 +281,31 @@ object PFiles {
}
@JvmStatic
@JvmOverloads
@Throws(IOException::class)
fun copyAssetDir(manager: AssetManager, assetsDir: String, toDir: String, list: Array<String?>?) {
fun copyAssetDir(manager: AssetManager, assetsDir: String, toDir: String, list: Array<String?>? = null) {
File(toDir).mkdirs()
val ls = list ?: manager.list(assetsDir) ?: throw IOException("Not a directory: $assetsDir")
ls.forEach { file ->
if (!TextUtils.isEmpty(file)) {
val fullAssetsPath = join(assetsDir, file)
val children = manager.list(fullAssetsPath)
val toPath = join(toDir, file)
if (children.isNullOrEmpty()) {
manager.open(fullAssetsPath).use { stream -> copyStream(stream, join(toDir, file)) }
copyAssetFile(manager, fullAssetsPath, toPath)
} else {
copyAssetDir(manager, fullAssetsPath, join(toDir, file), children)
copyAssetDir(manager, fullAssetsPath, toPath, children)
}
}
}
}
@JvmStatic
@Throws(IOException::class)
fun copyAssetFile(manager: AssetManager, assetFile: String, toPath: String) {
manager.open(assetFile).use { stream -> copyStream(stream, toPath) }
}
fun renameWithoutExtensionAndReturnNewPath(path: String, newName: String): String {
val file = File(path)
val newFile = File(file.parent, newName + "." + getExtension(file.name))

View File

@@ -43,7 +43,7 @@ class Plugins(private val context: Context, private val runtime: PluginRuntime)
try {
val plugin = Plugin.load(context, packageContext, runtime, runtime.topLevelScope)
val scriptCacheDir = getScriptCacheDir(packageName)
copyAssetDir(packageContext.context.assets, plugin.assetsScriptDir, scriptCacheDir.path, null)
copyAssetDir(packageContext.context.assets, plugin.assetsScriptDir, scriptCacheDir.path)
plugin.mainScriptPath = File(scriptCacheDir, "index.js").path
bindService(plugin)
mPlugins[packageName] = plugin

View File

@@ -904,7 +904,7 @@ open class ExplorerView : ThemeColorSwipeRefreshLayout, SwipeRefreshLayout.OnRef
menu.removeItem(R.id.action_set_as_working_dir)
}
val samplePath = PFile(context.filesDir, WorkspaceFileProvider.SAMPLE_PATH).path
if (!(mExplorerItem.path.startsWith(samplePath))) {
if (!mExplorerItem.path.startsWith(samplePath)) {
menu.removeItem(R.id.reset)
}
popupMenu.setOnMenuItemClickListener(this@ExplorerView)
@@ -961,6 +961,10 @@ open class ExplorerView : ThemeColorSwipeRefreshLayout, SwipeRefreshLayout.OnRef
if (!mExplorerPage!!.canBuildApk()) {
menu.removeItem(R.id.action_build_apk)
}
val samplePath = PFile(context.filesDir, WorkspaceFileProvider.SAMPLE_PATH).path
if (!mExplorerPage!!.path.startsWith(samplePath)) {
menu.removeItem(R.id.reset)
}
popupMenu.setOnMenuItemClickListener { item: MenuItem ->
when (item.itemId) {
R.id.action_rename -> {
@@ -979,6 +983,22 @@ open class ExplorerView : ThemeColorSwipeRefreshLayout, SwipeRefreshLayout.OnRef
R.id.action_build_apk -> {
BuildActivity.launch(context, selectedItem!!.path)
}
R.id.reset -> {
val o = Explorers.Providers.workspace()
.resetSample(selectedItem!!.toScriptFile())
if (o == null) {
resetFailed()
} else {
o.observeOn(AndroidSchedulers.mainThread())
.subscribe({ file: ScriptFile ->
if (file.exists()) {
resetSucceeded()
} else {
resetFailed()
}
}, Observers.toastMessage())
}
}
else -> null
} != null
}

View File

@@ -1,20 +1,21 @@
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
<menu
xmlns:android="http://schemas.android.com/apk/res/android">
<item
android:id="@+id/action_rename"
android:title="@string/text_rename" />
android:id="@+id/action_rename"
android:title="@string/text_rename" />
<item
android:id="@+id/action_delete"
android:title="@string/text_delete" />
android:id="@+id/action_delete"
android:title="@string/text_delete" />
<item
android:id="@+id/action_set_as_working_dir"
android:title="@string/text_set_as_working_dir" />
android:id="@+id/action_set_as_working_dir"
android:title="@string/text_set_as_working_dir" />
<item
android:id="@+id/action_build_apk"
android:title="@string/text_build_apk" />
android:id="@+id/action_build_apk"
android:title="@string/text_build_apk" />
<item
android:id="@+id/reset"
android:title="@string/text_reset_to_initial_content" />
</menu>

View File

@@ -1,31 +1,33 @@
<?xml version="1.0" encoding="utf-8"?>
<menu xmlns:android="http://schemas.android.com/apk/res/android">
<menu
xmlns:android="http://schemas.android.com/apk/res/android">
<item
android:id="@+id/rename"
android:title="@string/text_rename" />
android:id="@+id/rename"
android:title="@string/text_rename" />
<item
android:id="@+id/delete"
android:title="@string/text_delete" />
android:id="@+id/delete"
android:title="@string/text_delete" />
<item
android:id="@+id/timed_task"
android:title="@string/text_timed_task" />
android:id="@+id/timed_task"
android:title="@string/text_timed_task" />
<item
android:id="@+id/create_shortcut"
android:title="@string/text_send_shortcut" />
android:id="@+id/create_shortcut"
android:title="@string/text_send_shortcut" />
<item
android:id="@+id/action_build_apk"
android:title="@string/text_build_apk" />
android:id="@+id/action_build_apk"
android:title="@string/text_build_apk" />
<item
android:id="@+id/reset"
android:title="@string/text_reset_to_initial_content" />
android:id="@+id/reset"
android:title="@string/text_reset_to_initial_content" />
<item
android:id="@+id/send"
android:title="@string/text_send" />
android:id="@+id/send"
android:title="@string/text_send" />
<item
android:id="@+id/open_by_other_apps"
android:title="@string/text_open_by_other_apps" />
android:id="@+id/open_by_other_apps"
android:title="@string/text_open_by_other_apps" />
<item
android:id="@+id/run_repeatedly"
android:title="@string/text_run_repeatedly" />
android:id="@+id/run_repeatedly"
android:title="@string/text_run_repeatedly" />
</menu>