diff --git a/app/src/main/java/com/itsaky/androidide/fragments/ProjectsFragment.java b/app/src/main/java/com/itsaky/androidide/fragments/ProjectsFragment.java index fb96dc535..e11766a38 100644 --- a/app/src/main/java/com/itsaky/androidide/fragments/ProjectsFragment.java +++ b/app/src/main/java/com/itsaky/androidide/fragments/ProjectsFragment.java @@ -9,6 +9,7 @@ import android.view.ViewGroup; import android.widget.ProgressBar; import androidx.recyclerview.widget.LinearLayoutManager; import androidx.recyclerview.widget.RecyclerView; +import com.blankj.utilcode.util.FileIOUtils; import com.itsaky.androidide.EditorActivity; import com.itsaky.androidide.adapters.ProjectsListAdapter; import com.itsaky.androidide.app.StudioApp; @@ -22,12 +23,10 @@ import java.io.FileFilter; import java.util.ArrayList; import java.util.List; import java.util.concurrent.Callable; +import java.util.regex.Pattern; import org.json.JSONException; import org.json.JSONObject; -import com.blankj.utilcode.util.FileUtils; -import java.util.stream.Collectors; -import java.util.regex.Pattern; -import com.blankj.utilcode.util.FileIOUtils; +import com.itsaky.androidide.project.utils.ProjectFinder; public class ProjectsFragment extends BaseFragment { @@ -82,142 +81,15 @@ public class ProjectsFragment extends BaseFragment { mProjects = new ArrayList<>(); File[] files = StudioApp.getInstance().listProjects(); for (File file : files) { - if (!file.isDirectory() || file.isHidden()) continue; - File settings = new File(file, "settings.gradle"); - if (!settings.exists()) continue; - String content = FileUtil.readFile(settings.getAbsolutePath()); - if (TextUtils.isEmpty(content)) continue; - AndroidProject project = new AndroidProject(); - for (File module : file.listFiles()) { - if (module.isDirectory() && !module.isHidden()) { - proceedModule(file, module, project); - } - } - - project.setAppName(file.getName()); - project.setProjectPath(file.getAbsolutePath()); - if(project.getMainModule() == null - && project.getModulePaths().size() > 0 - && project.getModulePaths().get(0) != null) { - File f = new File(project.getModulePaths().get(0)); - if(!f.exists() || !f.isDirectory()) continue; - project.setMainModule(f.getName()); - project.setMainSourcePath(new File(f, "src/main/java").getAbsolutePath()); - } + AndroidProject project = ProjectFinder.fromFolder(file); + + if(project == null) + continue; + mProjects.add(project); } } - - private void proceedModule(File file, File module, AndroidProject project) throws JSONException { - final Pattern appPattern = Pattern.compile("apply\\s+plugin\\s*:\\s*(\'|\")com.android.application(\'|\")"); - File projectGradle = new File(file, "build.gradle"); - File moduleGradle = new File(module, "build.gradle"); - File manifest = new File(module, "src/main/AndroidManifest.xml"); - File res = new File(module, "src/main/res"); - if (!module.exists() || !projectGradle.exists() || !moduleGradle.exists() || !manifest.exists()) return; - if (!module.isDirectory() || !moduleGradle.isFile() || !projectGradle.isFile() || !manifest.isFile()) return; - - File java = new File(module, "src/main/java"); - if (java.exists() && java.isDirectory()) - project.addSource(java.getAbsolutePath()) - .addModule(module.getAbsolutePath()); - - File libsFolder = new File(module, "libs"); - if (libsFolder.exists() && libsFolder.isDirectory()) { - File[] libs = libsFolder.listFiles(); - if (libs != null && libs.length > 0) { - for (File lib : libs) - if (lib.getName().endsWith(".jar")) - project.addClasspath(lib.getAbsolutePath()); - } - } - - project.addSource(new File(module, "build/generated/source/buildConfig/debug").getAbsolutePath()); - project.addSource(new File(module, "build/generated/data_binding_base_class_source_out/debug/out").getAbsolutePath()); - - JSONObject obj = new XmlToJson.Builder(FileUtil.readFile(manifest.getAbsolutePath())).build().toJson(); - if (!obj.has("manifest")) return; - String iconPath = null; - if (obj.has("manifest") && obj.getJSONObject("manifest").has("application") && obj.getJSONObject("manifest").getJSONObject("application").has("android:icon")) { - String iconRes = obj.getJSONObject("manifest").getJSONObject("application").getString("android:icon"); - if (iconRes.startsWith("@drawable")) { - final String iconName = iconRes.replace("@drawable/", ""); - File[] drawables = listDrawables(res); - for (File drawable : drawables) { - File[] icons = listFilesNotEndingWith(drawable, ".xml"); - for (File icon : icons) { - String nameWithoutExtension = icon.getName().substring(0, icon.getName().lastIndexOf(".")); - if (nameWithoutExtension.equals(iconName)) { - iconPath = icon.getAbsolutePath(); - break; - } - } - } - } else if (iconRes.startsWith("@mipmap")) { - final String iconName = iconRes.replace("@mipmap/", ""); - File[] drawables = listMipmaps(res); - for (File drawable : drawables) { - File[] icons = listFilesNotEndingWith(drawable, ".xml"); - for (File icon : icons) { - String nameWithoutExtension = icon.getName().substring(0, icon.getName().lastIndexOf(".")); - if (nameWithoutExtension.equals(iconName)) { - iconPath = icon.getAbsolutePath(); - break; - } - } - } - } - } - final String packageName = obj.getJSONObject("manifest").getString("package"); - final String mainModuleName = module.getName(); - - boolean isMainModule = false; - if(project.getMainModule() == null) { - String content = FileIOUtils.readFile2String(moduleGradle); - if(content != null && appPattern.matcher(content).find()) { - isMainModule = true; - project.setMainModule(mainModuleName); - project.setMainSourcePath(new File(module, "src/main/java").getAbsolutePath()); - } - } - - if (iconPath != null) { - project.setIconPath(iconPath); - } - - if(packageName != null && isMainModule) { - project.setPackageName(packageName); - } - } - - private File[] listDrawables(File file) { - return listFolderStartingWith(file, "drawable"); - } - - private File[] listMipmaps(File file) { - return listFolderStartingWith(file, "mipmap"); - } - - private File[] listFolderStartingWith(File file, final String prefix) { - return file.listFiles(new FileFilter(){ - - @Override - public boolean accept(File p1) { - return p1.isDirectory() && p1.getName().startsWith(prefix); - } - }); - } - - private File[] listFilesNotEndingWith(File file, final String suffix) { - return file.listFiles(new FileFilter(){ - - @Override - public boolean accept(File p1) { - return p1.isFile() && !p1.getName().endsWith(suffix); - } - }); - } - + public ProgressBar getProgressBar() { return binding.projectsProgressBar; } diff --git a/app/src/main/java/com/itsaky/androidide/language/java/server/JavaLanguageServer.java b/app/src/main/java/com/itsaky/androidide/language/java/server/JavaLanguageServer.java index 3ec782823..4f478997b 100644 --- a/app/src/main/java/com/itsaky/androidide/language/java/server/JavaLanguageServer.java +++ b/app/src/main/java/com/itsaky/androidide/language/java/server/JavaLanguageServer.java @@ -81,7 +81,7 @@ public class JavaLanguageServer implements ShellServer.Callback { "--add-exports jdk.compiler/com.sun.tools.javac.util=ALL-UNNAMED " + "--add-opens jdk.compiler/com.sun.tools.javac.api=ALL-UNNAMED " + "-cp $JLS_HOME/lib/jls.jar:$JLS_HOME/lib/gson.jar:$JLS_HOME/lib/protobuf.jar " + - "org.javacs.Main"; + "org.javacs.Main --quiet"; private static final String CONTENT_LENGTH = "Content-Length: "; diff --git a/app/src/main/java/com/itsaky/androidide/project/utils/ProjectFinder.java b/app/src/main/java/com/itsaky/androidide/project/utils/ProjectFinder.java new file mode 100644 index 000000000..5ee2a910a --- /dev/null +++ b/app/src/main/java/com/itsaky/androidide/project/utils/ProjectFinder.java @@ -0,0 +1,155 @@ +package com.itsaky.androidide.project.utils; + +import android.text.TextUtils; +import com.blankj.utilcode.util.FileIOUtils; +import com.itsaky.androidide.models.AndroidProject; +import com.itsaky.androidide.utils.FileUtil; +import fr.arnaudguyon.xmltojsonlib.XmlToJson; +import java.io.File; +import java.io.FileFilter; +import java.util.regex.Pattern; +import org.json.JSONException; +import org.json.JSONObject; + +public class ProjectFinder { + + public static AndroidProject fromFolder(File file) { + if (!file.isDirectory() || file.isHidden()) return null; + File settings = new File(file, "settings.gradle"); + if (!settings.exists()) return null; + String content = FileUtil.readFile(settings.getAbsolutePath()); + if (TextUtils.isEmpty(content)) return null; + + AndroidProject project = new AndroidProject(); + for (File module : file.listFiles()) { + if (module.isDirectory() && !module.isHidden()) { + try { + proceedModule(file, module, project); + } catch (JSONException e) { continue; } + } + } + + project.setAppName(file.getName()); + project.setProjectPath(file.getAbsolutePath()); + if(project.getMainModule() == null + && project.getModulePaths().size() > 0 + && project.getModulePaths().get(0) != null) { + File f = new File(project.getModulePaths().get(0)); + if(!f.exists() || !f.isDirectory()) return null; + project.setMainModule(f.getName()); + project.setMainSourcePath(new File(f, "src/main/java").getAbsolutePath()); + } + + return project; + } + + private static void proceedModule(File file, File module, AndroidProject project) throws JSONException { + final Pattern appPattern = Pattern.compile("apply\\s+plugin\\s*:\\s*(\'|\")com.android.application(\'|\")"); + File projectGradle = new File(file, "build.gradle"); + File moduleGradle = new File(module, "build.gradle"); + File manifest = new File(module, "src/main/AndroidManifest.xml"); + File res = new File(module, "src/main/res"); + if (!module.exists() || !projectGradle.exists() || !moduleGradle.exists() || !manifest.exists()) return; + if (!module.isDirectory() || !moduleGradle.isFile() || !projectGradle.isFile() || !manifest.isFile()) return; + + File java = new File(module, "src/main/java"); + if (java.exists() && java.isDirectory()) + project.addSource(java.getAbsolutePath()) + .addModule(module.getAbsolutePath()); + + File libsFolder = new File(module, "libs"); + if (libsFolder.exists() && libsFolder.isDirectory()) { + File[] libs = libsFolder.listFiles(); + if (libs != null && libs.length > 0) { + for (File lib : libs) + if (lib.getName().endsWith(".jar")) + project.addClasspath(lib.getAbsolutePath()); + } + } + + project.addSource(new File(module, "build/generated/source/buildConfig/debug").getAbsolutePath()); + project.addSource(new File(module, "build/generated/data_binding_base_class_source_out/debug/out").getAbsolutePath()); + + JSONObject obj = new XmlToJson.Builder(FileUtil.readFile(manifest.getAbsolutePath())).build().toJson(); + if (!obj.has("manifest")) return; + String iconPath = null; + if (obj.has("manifest") && obj.getJSONObject("manifest").has("application") && obj.getJSONObject("manifest").getJSONObject("application").has("android:icon")) { + String iconRes = obj.getJSONObject("manifest").getJSONObject("application").getString("android:icon"); + if (iconRes.startsWith("@drawable")) { + final String iconName = iconRes.replace("@drawable/", ""); + File[] drawables = listDrawables(res); + for (File drawable : drawables) { + File[] icons = listFilesNotEndingWith(drawable, ".xml"); + for (File icon : icons) { + String nameWithoutExtension = icon.getName().substring(0, icon.getName().lastIndexOf(".")); + if (nameWithoutExtension.equals(iconName)) { + iconPath = icon.getAbsolutePath(); + break; + } + } + } + } else if (iconRes.startsWith("@mipmap")) { + final String iconName = iconRes.replace("@mipmap/", ""); + File[] drawables = listMipmaps(res); + for (File drawable : drawables) { + File[] icons = listFilesNotEndingWith(drawable, ".xml"); + for (File icon : icons) { + String nameWithoutExtension = icon.getName().substring(0, icon.getName().lastIndexOf(".")); + if (nameWithoutExtension.equals(iconName)) { + iconPath = icon.getAbsolutePath(); + break; + } + } + } + } + } + final String packageName = obj.getJSONObject("manifest").getString("package"); + final String mainModuleName = module.getName(); + + boolean isMainModule = false; + if(project.getMainModule() == null) { + String content = FileIOUtils.readFile2String(moduleGradle); + if(content != null && appPattern.matcher(content).find()) { + isMainModule = true; + project.setMainModule(mainModuleName); + project.setMainSourcePath(new File(module, "src/main/java").getAbsolutePath()); + } + } + + if (iconPath != null) { + project.setIconPath(iconPath); + } + + if(packageName != null && isMainModule) { + project.setPackageName(packageName); + } + } + + private static File[] listDrawables(File file) { + return listFolderStartingWith(file, "drawable"); + } + + private static File[] listMipmaps(File file) { + return listFolderStartingWith(file, "mipmap"); + } + + private static File[] listFolderStartingWith(File file, final String prefix) { + return file.listFiles(new FileFilter(){ + + @Override + public boolean accept(File p1) { + return p1.isDirectory() && p1.getName().startsWith(prefix); + } + }); + } + + private static File[] listFilesNotEndingWith(File file, final String suffix) { + return file.listFiles(new FileFilter(){ + + @Override + public boolean accept(File p1) { + return p1.isFile() && !p1.getName().endsWith(suffix); + } + }); + } +}