diff --git a/app_pojavlauncher/src/main/java/net/kdt/pojavlaunch/fragments/MainMenuFragment.java b/app_pojavlauncher/src/main/java/net/kdt/pojavlaunch/fragments/MainMenuFragment.java index 1754723b9d..137320896d 100644 --- a/app_pojavlauncher/src/main/java/net/kdt/pojavlaunch/fragments/MainMenuFragment.java +++ b/app_pojavlauncher/src/main/java/net/kdt/pojavlaunch/fragments/MainMenuFragment.java @@ -23,9 +23,6 @@ import com.kdt.mcgui.mcVersionSpinner; import net.kdt.pojavlaunch.CustomControlsActivity; -import net.kdt.pojavlaunch.fragments.ManageModsFragment; -import net.kdt.pojavlaunch.fragments.SearchModFragment; -import net.kdt.pojavlaunch.prefs.screens.LauncherPreferenceFragment; import net.kdt.pojavlaunch.R; import net.kdt.pojavlaunch.Tools; import net.kdt.pojavlaunch.extra.ExtraConstants; @@ -54,8 +51,6 @@ public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceStat Button mInstallJarButton = view.findViewById(R.id.install_jar_button); Button mShareLogsButton = view.findViewById(R.id.share_logs_button); Button mOpenDirectoryButton = view.findViewById(R.id.open_files_button); - Button mModStoreButton = view.findViewById(R.id.mod_store_button); - Button mSettingsMenuButton = view.findViewById(R.id.settings_menu_button); ImageButton mEditProfileButton = view.findViewById(R.id.edit_profile_button); Button mPlayButton = view.findViewById(R.id.play_button); @@ -64,16 +59,6 @@ public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceStat mNewsButton.setOnClickListener(v -> Tools.openURL(requireActivity(), Tools.URL_HOME)); mDiscordButton.setOnClickListener(v -> Tools.openURL(requireActivity(), getString(R.string.discord_invite))); mCustomControlButton.setOnClickListener(v -> startActivity(new Intent(requireContext(), CustomControlsActivity.class))); - - // Mod Store → open mod search fragment - if (mModStoreButton != null) - mModStoreButton.setOnClickListener(v -> Tools.swapFragment(requireActivity(), - SearchModFragment.class, SearchModFragment.TAG, null)); - - // Settings → open settings fragment - if (mSettingsMenuButton != null) - mSettingsMenuButton.setOnClickListener(v -> Tools.swapFragment(requireActivity(), - LauncherPreferenceFragment.class, "SETTINGS", null)); if (hasOnlineProfile()) { mInstallJarButton.setOnClickListener(v -> runInstallerWithConfirmation(false)); mInstallJarButton.setOnLongClickListener(v -> { @@ -90,7 +75,12 @@ public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceStat mShareLogsButton.setOnClickListener((v) -> shareLog(requireContext())); mOpenDirectoryButton.setOnClickListener((v)-> { - Tools.swapFragment(requireActivity(), ManageModsFragment.class, ManageModsFragment.TAG, null); + if (Tools.isDemoProfile(v.getContext())){ // Say a different message when on demo profile since they might see the hidden demo folder + hasNoOnlineProfileDialog(getActivity(), getString(R.string.demo_unsupported), getString(R.string.change_account)); + } else if (!hasOnlineProfile()) { // Otherwise display the generic pop-up to log in + hasNoOnlineProfileDialog(requireActivity()); + } else openPath(v.getContext(), getCurrentProfileDirectory(), false); + }); diff --git a/app_pojavlauncher/src/main/java/net/kdt/pojavlaunch/fragments/ManageModsFragment.java b/app_pojavlauncher/src/main/java/net/kdt/pojavlaunch/fragments/ManageModsFragment.java deleted file mode 100644 index 25fcb5a152..0000000000 --- a/app_pojavlauncher/src/main/java/net/kdt/pojavlaunch/fragments/ManageModsFragment.java +++ /dev/null @@ -1,94 +0,0 @@ -package net.kdt.pojavlaunch.fragments; - -import android.os.Bundle; -import android.view.View; -import android.widget.ImageButton; -import android.widget.TextView; - -import androidx.annotation.NonNull; -import androidx.annotation.Nullable; -import androidx.fragment.app.Fragment; -import androidx.recyclerview.widget.LinearLayoutManager; -import androidx.recyclerview.widget.RecyclerView; - -import net.kdt.pojavlaunch.R; -import net.kdt.pojavlaunch.Tools; -import net.kdt.pojavlaunch.modloaders.InstalledModAdapter; -import net.kdt.pojavlaunch.prefs.LauncherPreferences; -import net.kdt.pojavlaunch.value.launcherprofiles.LauncherProfiles; -import net.kdt.pojavlaunch.value.launcherprofiles.MinecraftProfile; - -import java.io.File; - -public class ManageModsFragment extends Fragment { - - public static final String TAG = "ManageModsFragment"; - - public ManageModsFragment() { - super(R.layout.fragment_manage_mods); - } - - @Override - public void onViewCreated(@NonNull View view, @Nullable Bundle savedInstanceState) { - ImageButton backButton = view.findViewById(R.id.manage_mods_back); - ImageButton addButton = view.findViewById(R.id.manage_mods_add); - TextView title = view.findViewById(R.id.manage_mods_title); - RecyclerView recycler = view.findViewById(R.id.manage_mods_recycler); - View emptyState = view.findViewById(R.id.manage_mods_empty); - - // Back - backButton.setOnClickListener(v -> Tools.removeCurrentFragment(requireActivity())); - - // Add → open mod store - addButton.setOnClickListener(v -> - Tools.swapFragment(requireActivity(), SearchModFragment.class, SearchModFragment.TAG, null)); - - // Title: "ProfileName - Mods" - String profileName = getCurrentProfileName(); - title.setText(profileName.isEmpty() - ? getString(R.string.mcl_button_manage_mods) - : profileName + " - Mods"); - - // Build mod list - File modsDir = getModsDir(); - InstalledModAdapter adapter = new InstalledModAdapter(modsDir, isEmpty -> { - recycler.setVisibility(isEmpty ? View.GONE : View.VISIBLE); - emptyState.setVisibility(isEmpty ? View.VISIBLE : View.GONE); - }); - - recycler.setLayoutManager(new LinearLayoutManager(requireContext())); - recycler.setAdapter(adapter); - } - - // ── Helpers ───────────────────────────────────────────────────────────── - - private String getCurrentProfileName() { - try { - String key = LauncherPreferences.DEFAULT_PREF - .getString(LauncherPreferences.PREF_KEY_CURRENT_PROFILE, null); - if (key == null || key.isEmpty()) return ""; - LauncherProfiles.load(); - MinecraftProfile profile = LauncherProfiles.mainProfileJson.profiles.get(key); - if (profile == null) return ""; - return profile.name != null ? profile.name : key; - } catch (Exception e) { - return ""; - } - } - - private File getModsDir() { - try { - String key = LauncherPreferences.DEFAULT_PREF - .getString(LauncherPreferences.PREF_KEY_CURRENT_PROFILE, null); - if (key != null && !key.isEmpty()) { - LauncherProfiles.load(); - MinecraftProfile profile = LauncherProfiles.mainProfileJson.profiles.get(key); - if (profile != null) { - File gameDir = Tools.getGameDirPath(profile); - return new File(gameDir, "mods"); - } - } - } catch (Exception ignored) {} - return new File(Tools.DIR_GAME_NEW, "mods"); - } -} diff --git a/app_pojavlauncher/src/main/java/net/kdt/pojavlaunch/modloaders/InstalledModAdapter.java b/app_pojavlauncher/src/main/java/net/kdt/pojavlaunch/modloaders/InstalledModAdapter.java deleted file mode 100644 index 1d08190fb2..0000000000 --- a/app_pojavlauncher/src/main/java/net/kdt/pojavlaunch/modloaders/InstalledModAdapter.java +++ /dev/null @@ -1,159 +0,0 @@ -package net.kdt.pojavlaunch.modloaders; - -import android.app.AlertDialog; -import android.content.Context; -import android.view.LayoutInflater; -import android.view.View; -import android.view.ViewGroup; -import android.widget.ImageButton; -import android.widget.ImageView; -import android.widget.TextView; - -import androidx.annotation.NonNull; -import androidx.appcompat.widget.SwitchCompat; -import androidx.recyclerview.widget.RecyclerView; - -import net.kdt.pojavlaunch.R; - -import java.io.File; -import java.util.ArrayList; -import java.util.Arrays; -import java.util.List; - -/** - * Adapter for the installed mods list (fragment_manage_mods). - * Enable/disable works by renaming .jar <-> .jar.disabled - * Delete removes the file permanently after confirmation. - */ -public class InstalledModAdapter extends RecyclerView.Adapter { - - public interface EmptyStateListener { - void onEmptyStateChanged(boolean isEmpty); - } - - private final List mMods = new ArrayList<>(); - private final EmptyStateListener mEmptyListener; - - public InstalledModAdapter(File modsDir, EmptyStateListener listener) { - mEmptyListener = listener; - if (modsDir != null && modsDir.isDirectory()) { - File[] files = modsDir.listFiles(f -> f.isFile() && - (f.getName().endsWith(".jar") || f.getName().endsWith(".jar.disabled"))); - if (files != null) { - Arrays.sort(files, (a, b) -> a.getName().compareToIgnoreCase(b.getName())); - for (File f : files) mMods.add(new ModEntry(f)); - } - } - notifyEmptyState(); - } - - @NonNull - @Override - public ModViewHolder onCreateViewHolder(@NonNull ViewGroup parent, int viewType) { - View v = LayoutInflater.from(parent.getContext()) - .inflate(R.layout.item_installed_mod, parent, false); - return new ModViewHolder(v); - } - - @Override - public void onBindViewHolder(@NonNull ModViewHolder holder, int position) { - ModEntry entry = mMods.get(position); - holder.bind(entry, position); - } - - @Override - public int getItemCount() { - return mMods.size(); - } - - private void notifyEmptyState() { - if (mEmptyListener != null) mEmptyListener.onEmptyStateChanged(mMods.isEmpty()); - } - - // ── ViewHolder ───────────────────────────────────────────────────────── - - class ModViewHolder extends RecyclerView.ViewHolder { - final ImageView icon; - final TextView name, version, description; - final SwitchCompat toggle; - final ImageButton delete; - - ModViewHolder(@NonNull View itemView) { - super(itemView); - icon = itemView.findViewById(R.id.installed_mod_icon); - name = itemView.findViewById(R.id.installed_mod_name); - version = itemView.findViewById(R.id.installed_mod_description); // reuse description row for version info - description = itemView.findViewById(R.id.installed_mod_version); - toggle = itemView.findViewById(R.id.installed_mod_toggle); - delete = itemView.findViewById(R.id.installed_mod_delete); - } - - void bind(ModEntry entry, int position) { - name.setText(entry.displayName()); - version.setText(entry.file.getName()); - description.setText(""); - - // Toggle state — suppress listener while setting - toggle.setOnCheckedChangeListener(null); - toggle.setChecked(entry.enabled); - toggle.setOnCheckedChangeListener((btn, isChecked) -> { - entry.setEnabled(isChecked); - }); - - // Delete with confirmation - delete.setOnClickListener(v -> { - Context ctx = v.getContext(); - new AlertDialog.Builder(ctx) - .setTitle(ctx.getString(R.string.manage_mods_delete_confirm, entry.displayName())) - .setNegativeButton(android.R.string.cancel, null) - .setPositiveButton(android.R.string.ok, (d, i) -> { - entry.file.delete(); - int pos = getAdapterPosition(); - if (pos != RecyclerView.NO_ID) { - mMods.remove(pos); - notifyItemRemoved(pos); - notifyEmptyState(); - } - }) - .show(); - }); - } - } - - // ── ModEntry ─────────────────────────────────────────────────────────── - - static class ModEntry { - File file; - boolean enabled; - - ModEntry(File f) { - this.file = f; - this.enabled = !f.getName().endsWith(".disabled"); - } - - /** Human-readable name: strip .jar / .jar.disabled suffix */ - String displayName() { - String n = file.getName(); - if (n.endsWith(".jar.disabled")) n = n.substring(0, n.length() - 13); - else if (n.endsWith(".jar")) n = n.substring(0, n.length() - 4); - return n; - } - - /** Rename file to toggle enabled state */ - void setEnabled(boolean enable) { - if (enable == this.enabled) return; - File target; - if (enable) { - // Remove .disabled suffix - String newName = file.getName().replace(".jar.disabled", ".jar"); - target = new File(file.getParent(), newName); - } else { - target = new File(file.getParent(), file.getName() + ".disabled"); - } - if (file.renameTo(target)) { - file = target; - this.enabled = enable; - } - } - } -} diff --git a/app_pojavlauncher/src/main/res/layout/activity_pojav_launcher.xml b/app_pojavlauncher/src/main/res/layout/activity_pojav_launcher.xml index cd011b9934..b4d20e0378 100644 --- a/app_pojavlauncher/src/main/res/layout/activity_pojav_launcher.xml +++ b/app_pojavlauncher/src/main/res/layout/activity_pojav_launcher.xml @@ -10,8 +10,10 @@ android:id="@+id/account_spinner" android:layout_width="match_parent" android:layout_height="@dimen/_52sdp" + android:dropDownWidth="@dimen/_250sdp" android:dropDownVerticalOffset="@dimen/_52sdp" + app:layout_constraintTop_toTopOf="parent" /> + - + + + + \ No newline at end of file diff --git a/app_pojavlauncher/src/main/res/layout/fragment_launcher.xml b/app_pojavlauncher/src/main/res/layout/fragment_launcher.xml index 80d10a57b4..ad6f7229d1 100644 --- a/app_pojavlauncher/src/main/res/layout/fragment_launcher.xml +++ b/app_pojavlauncher/src/main/res/layout/fragment_launcher.xml @@ -1,188 +1,142 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - + xmlns:android="http://schemas.android.com/apk/res/android" + xmlns:app="http://schemas.android.com/apk/res-auto" + xmlns:tools="http://schemas.android.com/tools" + android:id="@+id/fragment_menu_main" + android:gravity="top" + android:layout_width="fill_parent" + android:layout_height="fill_parent" + android:orientation="vertical" + android:background="@color/background_app" + > + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/app_pojavlauncher/src/main/res/layout/fragment_manage_mods.xml b/app_pojavlauncher/src/main/res/layout/fragment_manage_mods.xml deleted file mode 100644 index 0b3ded9e97..0000000000 --- a/app_pojavlauncher/src/main/res/layout/fragment_manage_mods.xml +++ /dev/null @@ -1,77 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/app_pojavlauncher/src/main/res/layout/item_installed_mod.xml b/app_pojavlauncher/src/main/res/layout/item_installed_mod.xml deleted file mode 100644 index 85ec97f470..0000000000 --- a/app_pojavlauncher/src/main/res/layout/item_installed_mod.xml +++ /dev/null @@ -1,103 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - diff --git a/app_pojavlauncher/src/main/res/layout/view_mod.xml b/app_pojavlauncher/src/main/res/layout/view_mod.xml index fb01be89a6..cfca0a84a2 100644 --- a/app_pojavlauncher/src/main/res/layout/view_mod.xml +++ b/app_pojavlauncher/src/main/res/layout/view_mod.xml @@ -5,34 +5,35 @@ xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="wrap_content" - android:background="@drawable/background_card" + android:background="@drawable/background_line" + android:paddingHorizontal="@dimen/_2sdp" + android:paddingVertical="@dimen/_2sdp" android:layout_marginVertical="@dimen/padding_medium" - android:foreground="?attr/selectableItemBackground" - android:clickable="true" - android:focusable="true"> + > - - + tools:src="@mipmap/ic_launcher_foreground" + /> + + tools:src="@mipmap/ic_launcher_foreground" /> - + tools:text="Feed the beast - Reforged" /> - + tools:text="Feed the beast - Reforged is a machine and magic focused modpack, with no respect for the minimum requirements of minecraft. Very long text" /> + + + app:layout_constraintTop_toBottomOf="@id/mod_thumbnail_imageview"/> + + - + \ No newline at end of file diff --git a/app_pojavlauncher/src/main/res/values/colors.xml b/app_pojavlauncher/src/main/res/values/colors.xml index fb7f6d7185..11c78ffb0e 100644 --- a/app_pojavlauncher/src/main/res/values/colors.xml +++ b/app_pojavlauncher/src/main/res/values/colors.xml @@ -12,5 +12,4 @@ #FFFFFF #B2B2B2 - #FF757575 diff --git a/app_pojavlauncher/src/main/res/values/strings.xml b/app_pojavlauncher/src/main/res/values/strings.xml index 9c6ee704d3..29abdf299d 100644 --- a/app_pojavlauncher/src/main/res/values/strings.xml +++ b/app_pojavlauncher/src/main/res/values/strings.xml @@ -92,10 +92,6 @@ Wait Select Retry - Back - Add - No mods installed for this profile. - Delete %s? Default Off @@ -430,13 +426,6 @@ Change controller key bindings Allows you to modify the keyboard keys bound to each controller button Discord - Quick Actions - Instance Tools - Mod Store - Settings - Manage Mods & Tools - Install Modpack (.mrpack/zip) - Delete Your GPU is not capable of rendering above 7 render distance without Sodium or other similar mods. The render distance will be automatically reduced when you click "OK". Open game directory https://discord.gg/8WzF2RVAq4