diff --git a/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/activities/EmulationActivity.java b/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/activities/EmulationActivity.java
index 6b27c08c4a..c4cc9e1f3a 100644
--- a/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/activities/EmulationActivity.java
+++ b/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/activities/EmulationActivity.java
@@ -1,5 +1,6 @@
package org.dolphinemu.dolphinemu.activities;
+import android.app.Fragment;
import android.content.Intent;
import android.os.Bundle;
import android.os.Handler;
@@ -13,8 +14,12 @@ import android.view.MenuItem;
import android.view.MotionEvent;
import android.view.View;
import android.view.ViewTreeObserver;
+import android.view.animation.AccelerateInterpolator;
+import android.view.animation.DecelerateInterpolator;
+import android.view.animation.Interpolator;
import android.widget.FrameLayout;
import android.widget.ImageView;
+import android.widget.LinearLayout;
import com.squareup.picasso.Callback;
import com.squareup.picasso.Picasso;
@@ -22,6 +27,9 @@ import com.squareup.picasso.Picasso;
import org.dolphinemu.dolphinemu.NativeLibrary;
import org.dolphinemu.dolphinemu.R;
import org.dolphinemu.dolphinemu.fragments.EmulationFragment;
+import org.dolphinemu.dolphinemu.fragments.LoadStateFragment;
+import org.dolphinemu.dolphinemu.fragments.MenuFragment;
+import org.dolphinemu.dolphinemu.fragments.SaveStateFragment;
import java.util.List;
@@ -29,14 +37,22 @@ public final class EmulationActivity extends AppCompatActivity
{
private View mDecorView;
private ImageView mImageView;
- private FrameLayout mFrameEmulation;
- private boolean mDeviceHasTouchScreen;
- private boolean mSystemUiVisible;
+ private FrameLayout mFrameEmulation;
+ private LinearLayout mMenuLayout;
+
+ private String mSubmenuFragmentTag;
// So that MainActivity knows which view to invalidate before the return animation.
private int mPosition;
+ private boolean mDeviceHasTouchScreen;
+ private boolean mSystemUiVisible;
+ private boolean mMenuVisible;
+
+ private static Interpolator sDecelerator = new DecelerateInterpolator();
+ private static Interpolator sAccelerator = new AccelerateInterpolator();
+
/**
* Handlers are a way to pass a message to an Activity telling it to do something
* on the UI thread. This Handler responds to any message, even blank ones, by
@@ -52,57 +68,70 @@ public final class EmulationActivity extends AppCompatActivity
};
private String mScreenPath;
private FrameLayout mFrameContent;
+ private String mSelectedTitle;
@Override
protected void onCreate(Bundle savedInstanceState)
{
+ mDeviceHasTouchScreen = getPackageManager().hasSystemFeature("android.hardware.touchscreen");
+
+ int themeId;
+ if (mDeviceHasTouchScreen)
+ {
+ themeId = R.style.DolphinEmulationGamecube;
+
+ // Get a handle to the Window containing the UI.
+ mDecorView = getWindow().getDecorView();
+
+ // Set these options now so that the SurfaceView the game renders into is the right size.
+ mDecorView.setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_STABLE |
+ View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION |
+ View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN);
+
+ // Set the ActionBar to follow the navigation/status bar's visibility changes.
+ mDecorView.setOnSystemUiVisibilityChangeListener(
+ new View.OnSystemUiVisibilityChangeListener()
+ {
+ @Override
+ public void onSystemUiVisibilityChange(int flags)
+ {
+ mSystemUiVisible = (flags & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) == 0;
+
+ if (mSystemUiVisible)
+ {
+ getSupportActionBar().show();
+ hideSystemUiAfterDelay();
+ }
+ else
+ {
+ getSupportActionBar().hide();
+ }
+ }
+ }
+ );
+ }
+ else
+ {
+ themeId = R.style.DolphinEmulationTvGamecube;
+ }
+
+ setTheme(themeId);
super.onCreate(savedInstanceState);
// Picasso will take a while to load these big-ass screenshots. So don't run
// the animation until we say so.
postponeEnterTransition();
- mDeviceHasTouchScreen = getPackageManager().hasSystemFeature("android.hardware.touchscreen");
-
- // Get a handle to the Window containing the UI.
- mDecorView = getWindow().getDecorView();
-
- // Set these options now so that the SurfaceView the game renders into is the right size.
- mDecorView.setSystemUiVisibility(View.SYSTEM_UI_FLAG_LAYOUT_STABLE |
- View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION |
- View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN);
-
- // Set the ActionBar to follow the navigation/status bar's visibility changes.
- mDecorView.setOnSystemUiVisibilityChangeListener(
- new View.OnSystemUiVisibilityChangeListener()
- {
- @Override
- public void onSystemUiVisibilityChange(int flags)
- {
- mSystemUiVisible = (flags & View.SYSTEM_UI_FLAG_HIDE_NAVIGATION) == 0;
-
- if (mSystemUiVisible)
- {
- getSupportActionBar().show();
- hideSystemUiAfterDelay();
- }
- else
- {
- getSupportActionBar().hide();
- }
- }
- }
- );
-
setContentView(R.layout.activity_emulation);
mImageView = (ImageView) findViewById(R.id.image_screenshot);
mFrameContent = (FrameLayout) findViewById(R.id.frame_content);
mFrameEmulation = (FrameLayout) findViewById(R.id.frame_emulation_fragment);
+ mMenuLayout = (LinearLayout) findViewById(R.id.layout_ingame_menu);
Intent gameToEmulate = getIntent();
String path = gameToEmulate.getStringExtra("SelectedGame");
- String title = gameToEmulate.getStringExtra("SelectedTitle");
+ mSelectedTitle = gameToEmulate.getStringExtra("SelectedTitle");
mScreenPath = gameToEmulate.getStringExtra("ScreenPath");
mPosition = gameToEmulate.getIntExtra("GridPosition", -1);
@@ -148,8 +177,6 @@ public final class EmulationActivity extends AppCompatActivity
}
});
- setTitle(title);
-
// Instantiate an EmulationFragment.
EmulationFragment emulationFragment = EmulationFragment.newInstance(path);
@@ -157,6 +184,21 @@ public final class EmulationActivity extends AppCompatActivity
getFragmentManager().beginTransaction()
.add(R.id.frame_emulation_fragment, emulationFragment, EmulationFragment.FRAGMENT_TAG)
.commit();
+
+ if (mDeviceHasTouchScreen)
+ {
+ setTitle(mSelectedTitle);
+ }
+ else
+ {
+ MenuFragment menuFragment = (MenuFragment) getFragmentManager()
+ .findFragmentById(R.id.fragment_menu);
+
+ if (menuFragment != null)
+ {
+ menuFragment.setTitleText(mSelectedTitle);
+ }
+ }
}
@Override
@@ -181,8 +223,11 @@ public final class EmulationActivity extends AppCompatActivity
{
super.onPostCreate(savedInstanceState);
- // Give the user a few seconds to see what the controls look like, then hide them.
- hideSystemUiAfterDelay();
+ if (mDeviceHasTouchScreen)
+ {
+ // Give the user a few seconds to see what the controls look like, then hide them.
+ hideSystemUiAfterDelay();
+ }
}
@Override
@@ -190,36 +235,91 @@ public final class EmulationActivity extends AppCompatActivity
{
super.onWindowFocusChanged(hasFocus);
- if (hasFocus)
+ if (mDeviceHasTouchScreen)
{
- hideSystemUiAfterDelay();
- }
- else
- {
- // If the window loses focus (i.e. a dialog box, or a popup menu is on screen
- // stop hiding the UI.
- mSystemUiHider.removeMessages(0);
+ if (hasFocus)
+ {
+ hideSystemUiAfterDelay();
+ }
+ else
+ {
+ // If the window loses focus (i.e. a dialog box, or a popup menu is on screen
+ // stop hiding the UI.
+ mSystemUiHider.removeMessages(0);
+ }
}
}
@Override
public void onBackPressed()
{
- if (!mDeviceHasTouchScreen && !mSystemUiVisible)
+ if (!mDeviceHasTouchScreen)
{
- showSystemUI();
+ if (mSubmenuFragmentTag != null)
+ {
+ removeMenu();
+ }
+ else
+ {
+ toggleMenu();
+ }
}
else
{
- // Let the system handle it; i.e. quit the activity TODO or show "are you sure?" dialog.
- EmulationFragment fragment = (EmulationFragment) getFragmentManager()
- .findFragmentByTag(EmulationFragment.FRAGMENT_TAG);
- fragment.notifyEmulationStopped();
-
- NativeLibrary.StopEmulation();
+ stopEmulation();
}
}
+ private void toggleMenu()
+ {
+ if (mMenuVisible)
+ {
+ mMenuVisible = false;
+
+ mMenuLayout.animate()
+ .withLayer()
+ .setDuration(200)
+ .setInterpolator(sAccelerator)
+ .alpha(0.0f)
+ .translationX(-400.0f)
+ .withEndAction(new Runnable()
+ {
+ @Override
+ public void run()
+ {
+ if (mMenuVisible)
+ {
+ mMenuLayout.setVisibility(View.GONE);
+ }
+ }
+ });
+ }
+ else
+ {
+ mMenuVisible = true;
+ mMenuLayout.setVisibility(View.VISIBLE);
+
+// mMenuLayout.setTranslationX(-400.0f);
+ mMenuLayout.setAlpha(0.0f);
+
+ mMenuLayout.animate()
+ .withLayer()
+ .setDuration(300)
+ .setInterpolator(sDecelerator)
+ .alpha(1.0f)
+ .translationX(0.0f);
+ }
+ }
+
+ private void stopEmulation()
+ {
+ EmulationFragment fragment = (EmulationFragment) getFragmentManager()
+ .findFragmentByTag(EmulationFragment.FRAGMENT_TAG);
+ fragment.notifyEmulationStopped();
+
+ NativeLibrary.StopEmulation();
+ }
+
public void exitWithAnimation()
{
runOnUiThread(new Runnable()
@@ -257,7 +357,7 @@ public final class EmulationActivity extends AppCompatActivity
mImageView.setVisibility(View.VISIBLE);
mImageView.animate()
.withLayer()
- .setDuration(500)
+ .setDuration(100)
.alpha(1.0f)
.withEndAction(afterShowingScreenshot);
}
@@ -284,7 +384,13 @@ public final class EmulationActivity extends AppCompatActivity
@Override
public boolean onOptionsItemSelected(MenuItem item)
{
- switch (item.getItemId())
+ onMenuItemClicked(item.getItemId());
+ return true;
+ }
+
+ public void onMenuItemClicked(int id)
+ {
+ switch (id)
{
// Enable/Disable input overlay.
case R.id.menu_emulation_input_overlay:
@@ -294,67 +400,78 @@ public final class EmulationActivity extends AppCompatActivity
emulationFragment.toggleInputOverlayVisibility();
- return true;
+ return;
}
// Screenshot capturing
case R.id.menu_emulation_screenshot:
NativeLibrary.SaveScreenShot();
- return true;
+ return;
// Quicksave / Load
case R.id.menu_quicksave:
NativeLibrary.SaveState(9);
- return true;
+ return;
case R.id.menu_quickload:
NativeLibrary.LoadState(9);
- return true;
+ return;
+
+ // TV Menu only
+ case R.id.menu_emulation_save_root:
+ showMenu(SaveStateFragment.FRAGMENT_ID);
+ return;
+
+ case R.id.menu_emulation_load_root:
+ showMenu(LoadStateFragment.FRAGMENT_ID);
+ return;
// Save state slots
case R.id.menu_emulation_save_1:
NativeLibrary.SaveState(0);
- return true;
+ return;
case R.id.menu_emulation_save_2:
NativeLibrary.SaveState(1);
- return true;
+ return;
case R.id.menu_emulation_save_3:
NativeLibrary.SaveState(2);
- return true;
+ return;
case R.id.menu_emulation_save_4:
NativeLibrary.SaveState(3);
- return true;
+ return;
case R.id.menu_emulation_save_5:
NativeLibrary.SaveState(4);
- return true;
+ return;
// Load state slots
case R.id.menu_emulation_load_1:
NativeLibrary.LoadState(0);
- return true;
+ return;
case R.id.menu_emulation_load_2:
NativeLibrary.LoadState(1);
- return true;
+ return;
case R.id.menu_emulation_load_3:
NativeLibrary.LoadState(2);
- return true;
+ return;
case R.id.menu_emulation_load_4:
NativeLibrary.LoadState(3);
- return true;
+ return;
case R.id.menu_emulation_load_5:
NativeLibrary.LoadState(4);
- return true;
+ return;
- default:
- return super.onOptionsItemSelected(item);
+ case R.id.menu_exit:
+ toggleMenu();
+ stopEmulation();
+ return;
}
}
@@ -362,6 +479,11 @@ public final class EmulationActivity extends AppCompatActivity
@Override
public boolean dispatchKeyEvent(KeyEvent event)
{
+ if (mMenuVisible)
+ {
+ return super.dispatchKeyEvent(event);
+ }
+
int action = 0;
switch (event.getAction())
@@ -391,6 +513,11 @@ public final class EmulationActivity extends AppCompatActivity
@Override
public boolean dispatchGenericMotionEvent(MotionEvent event)
{
+ if (mMenuVisible)
+ {
+ return false;
+ }
+
if (((event.getSource() & InputDevice.SOURCE_CLASS_JOYSTICK) == 0))
{
return super.dispatchGenericMotionEvent(event);
@@ -458,4 +585,78 @@ public final class EmulationActivity extends AppCompatActivity
}
});
}
+
+ private void showMenu(int menuId)
+ {
+ Fragment fragment;
+
+ switch (menuId)
+ {
+ case SaveStateFragment.FRAGMENT_ID:
+ fragment = SaveStateFragment.newInstance();
+ mSubmenuFragmentTag = SaveStateFragment.FRAGMENT_TAG;
+ break;
+
+ case LoadStateFragment.FRAGMENT_ID:
+ fragment = LoadStateFragment.newInstance();
+ mSubmenuFragmentTag = LoadStateFragment.FRAGMENT_TAG;
+ break;
+
+ default:
+ return;
+ }
+
+ getFragmentManager().beginTransaction()
+ .setCustomAnimations(R.animator.menu_slide_in, R.animator.menu_slide_out)
+ .replace(R.id.frame_submenu, fragment, mSubmenuFragmentTag)
+ .commit();
+ }
+
+ private void removeMenu()
+ {
+ if (mSubmenuFragmentTag != null)
+ {
+ final Fragment fragment = getFragmentManager().findFragmentByTag(mSubmenuFragmentTag);
+
+ if (fragment != null)
+ {
+ // When removing a fragment without replacement, its aniimation must be done
+ // manually beforehand.
+ fragment.getView().animate()
+ .withLayer()
+ .setDuration(200)
+ .setInterpolator(sAccelerator)
+ .alpha(0.0f)
+ .translationX(600.0f)
+ .withEndAction(new Runnable()
+ {
+ @Override
+ public void run()
+ {
+ if (mMenuVisible)
+ {
+ getFragmentManager().beginTransaction()
+ .remove(fragment)
+ .commit();
+ }
+ }
+ });
+ }
+ else
+ {
+ Log.e("DolphinEmu", "[EmulationActivity] Fragment not found, can't remove.");
+ }
+
+ mSubmenuFragmentTag = null;
+ }
+ else
+ {
+ Log.e("DolphinEmu", "[EmulationActivity] Fragment Tag empty.");
+ }
+ }
+
+ public String getSelectedTitle()
+ {
+ return mSelectedTitle;
+ }
}
diff --git a/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/EmulationFragment.java b/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/EmulationFragment.java
index 9d23736cb6..1eb1684531 100644
--- a/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/EmulationFragment.java
+++ b/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/EmulationFragment.java
@@ -81,9 +81,12 @@ public final class EmulationFragment extends Fragment implements SurfaceHolder.C
mSurfaceView.getHolder().addCallback(this);
// If the input overlay was previously disabled, then don't show it.
- if (!mPreferences.getBoolean("showInputOverlay", true))
+ if (mInputOverlay != null)
{
- mInputOverlay.setVisibility(View.GONE);
+ if (!mPreferences.getBoolean("showInputOverlay", true))
+ {
+ mInputOverlay.setVisibility(View.GONE);
+ }
}
diff --git a/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/LoadStateFragment.java b/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/LoadStateFragment.java
new file mode 100644
index 0000000000..bbd9807b9b
--- /dev/null
+++ b/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/LoadStateFragment.java
@@ -0,0 +1,55 @@
+package org.dolphinemu.dolphinemu.fragments;
+
+import android.app.Fragment;
+import android.os.Bundle;
+import android.support.annotation.Nullable;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.Button;
+import android.widget.GridLayout;
+
+import org.dolphinemu.dolphinemu.BuildConfig;
+import org.dolphinemu.dolphinemu.R;
+import org.dolphinemu.dolphinemu.activities.EmulationActivity;
+
+public final class LoadStateFragment extends Fragment implements View.OnClickListener
+{
+ public static final String FRAGMENT_TAG = BuildConfig.APPLICATION_ID + ".load_state";
+ public static final int FRAGMENT_ID = R.layout.fragment_state_load;
+
+ public static LoadStateFragment newInstance()
+ {
+ LoadStateFragment fragment = new LoadStateFragment();
+
+ // TODO Add any appropriate arguments to this fragment.
+
+ return fragment;
+ }
+
+ @Nullable
+ @Override
+ public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)
+ {
+ View rootView = inflater.inflate(FRAGMENT_ID, container, false);
+
+ GridLayout grid = (GridLayout) rootView.findViewById(R.id.grid_state_slots);
+ for (int childIndex = 0; childIndex < grid.getChildCount(); childIndex++)
+ {
+ Button button = (Button) grid.getChildAt(childIndex);
+
+ button.setOnClickListener(this);
+ }
+
+ // So that item clicked to start this Fragment is no longer the focused item.
+ grid.requestFocus();
+
+ return rootView;
+ }
+
+ @Override
+ public void onClick(View button)
+ {
+ ((EmulationActivity) getActivity()).onMenuItemClicked(button.getId());
+ }
+}
diff --git a/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/MenuFragment.java b/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/MenuFragment.java
new file mode 100644
index 0000000000..d894f32373
--- /dev/null
+++ b/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/MenuFragment.java
@@ -0,0 +1,52 @@
+package org.dolphinemu.dolphinemu.fragments;
+
+import android.app.Fragment;
+import android.os.Bundle;
+import android.support.annotation.Nullable;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.Button;
+import android.widget.LinearLayout;
+import android.widget.TextView;
+
+import org.dolphinemu.dolphinemu.BuildConfig;
+import org.dolphinemu.dolphinemu.R;
+import org.dolphinemu.dolphinemu.activities.EmulationActivity;
+
+public final class MenuFragment extends Fragment implements View.OnClickListener
+{
+ public static final String FRAGMENT_TAG = BuildConfig.APPLICATION_ID + ".ingame_menu";
+ public static final int FRAGMENT_ID = R.layout.fragment_ingame_menu;
+ private TextView mTitleText;
+
+ @Nullable
+ @Override
+ public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)
+ {
+ View rootView = inflater.inflate(FRAGMENT_ID, container, false);
+
+ LinearLayout options = (LinearLayout) rootView.findViewById(R.id.layout_options);
+ for (int childIndex = 0; childIndex < options.getChildCount(); childIndex++)
+ {
+ Button button = (Button) options.getChildAt(childIndex);
+
+ button.setOnClickListener(this);
+ }
+
+ mTitleText = (TextView) rootView.findViewById(R.id.text_game_title);
+
+ return rootView;
+ }
+
+ @Override
+ public void onClick(View button)
+ {
+ ((EmulationActivity) getActivity()).onMenuItemClicked(button.getId());
+ }
+
+ public void setTitleText(String title)
+ {
+ mTitleText.setText(title);
+ }
+}
diff --git a/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/SaveStateFragment.java b/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/SaveStateFragment.java
new file mode 100644
index 0000000000..a5e9e6d441
--- /dev/null
+++ b/Source/Android/app/src/main/java/org/dolphinemu/dolphinemu/fragments/SaveStateFragment.java
@@ -0,0 +1,55 @@
+package org.dolphinemu.dolphinemu.fragments;
+
+import android.app.Fragment;
+import android.os.Bundle;
+import android.support.annotation.Nullable;
+import android.view.LayoutInflater;
+import android.view.View;
+import android.view.ViewGroup;
+import android.widget.Button;
+import android.widget.GridLayout;
+
+import org.dolphinemu.dolphinemu.BuildConfig;
+import org.dolphinemu.dolphinemu.R;
+import org.dolphinemu.dolphinemu.activities.EmulationActivity;
+
+public final class SaveStateFragment extends Fragment implements View.OnClickListener
+{
+ public static final String FRAGMENT_TAG = BuildConfig.APPLICATION_ID + ".save_state";
+ public static final int FRAGMENT_ID = R.layout.fragment_state_save;
+
+ public static SaveStateFragment newInstance()
+ {
+ SaveStateFragment fragment = new SaveStateFragment();
+
+ // TODO Add any appropriate arguments to this fragment.
+
+ return fragment;
+ }
+
+ @Nullable
+ @Override
+ public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState)
+ {
+ View rootView = inflater.inflate(FRAGMENT_ID, container, false);
+
+ GridLayout grid = (GridLayout) rootView.findViewById(R.id.grid_state_slots);
+ for (int childIndex = 0; childIndex < grid.getChildCount(); childIndex++)
+ {
+ Button button = (Button) grid.getChildAt(childIndex);
+
+ button.setOnClickListener(this);
+ }
+
+ // So that item clicked to start this Fragment is no longer the focused item.
+ grid.requestFocus();
+
+ return rootView;
+ }
+
+ @Override
+ public void onClick(View button)
+ {
+ ((EmulationActivity) getActivity()).onMenuItemClicked(button.getId());
+ }
+}
diff --git a/Source/Android/app/src/main/res/animator/menu_slide_in.xml b/Source/Android/app/src/main/res/animator/menu_slide_in.xml
new file mode 100644
index 0000000000..e6f9ae6d8e
--- /dev/null
+++ b/Source/Android/app/src/main/res/animator/menu_slide_in.xml
@@ -0,0 +1,17 @@
+
+
+
+
+
\ No newline at end of file
diff --git a/Source/Android/app/src/main/res/animator/menu_slide_out.xml b/Source/Android/app/src/main/res/animator/menu_slide_out.xml
new file mode 100644
index 0000000000..85c2556e48
--- /dev/null
+++ b/Source/Android/app/src/main/res/animator/menu_slide_out.xml
@@ -0,0 +1,18 @@
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Source/Android/app/src/main/res/layout-television/activity_emulation.xml b/Source/Android/app/src/main/res/layout-television/activity_emulation.xml
new file mode 100644
index 0000000000..06fe747c39
--- /dev/null
+++ b/Source/Android/app/src/main/res/layout-television/activity_emulation.xml
@@ -0,0 +1,44 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Source/Android/app/src/main/res/layout-television/fragment_emulation.xml b/Source/Android/app/src/main/res/layout-television/fragment_emulation.xml
new file mode 100644
index 0000000000..787de65186
--- /dev/null
+++ b/Source/Android/app/src/main/res/layout-television/fragment_emulation.xml
@@ -0,0 +1,14 @@
+
+
+
+
+
diff --git a/Source/Android/app/src/main/res/layout/fragment_ingame_menu.xml b/Source/Android/app/src/main/res/layout/fragment_ingame_menu.xml
new file mode 100644
index 0000000000..44093dc324
--- /dev/null
+++ b/Source/Android/app/src/main/res/layout/fragment_ingame_menu.xml
@@ -0,0 +1,69 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Source/Android/app/src/main/res/layout/fragment_state_load.xml b/Source/Android/app/src/main/res/layout/fragment_state_load.xml
new file mode 100644
index 0000000000..1b04c6ce59
--- /dev/null
+++ b/Source/Android/app/src/main/res/layout/fragment_state_load.xml
@@ -0,0 +1,65 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Source/Android/app/src/main/res/layout/fragment_state_save.xml b/Source/Android/app/src/main/res/layout/fragment_state_save.xml
new file mode 100644
index 0000000000..b5ca1e1ed8
--- /dev/null
+++ b/Source/Android/app/src/main/res/layout/fragment_state_save.xml
@@ -0,0 +1,65 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file
diff --git a/Source/Android/app/src/main/res/values/strings.xml b/Source/Android/app/src/main/res/values/strings.xml
index 3843cfb9b1..1d26cd256d 100644
--- a/Source/Android/app/src/main/res/values/strings.xml
+++ b/Source/Android/app/src/main/res/values/strings.xml
@@ -66,6 +66,7 @@
Slot 3
Slot 4
Slot 5
+ Slot 6
Input
diff --git a/Source/Android/app/src/main/res/values/styles.xml b/Source/Android/app/src/main/res/values/styles.xml
index ba80861700..76ee1f8f55 100644
--- a/Source/Android/app/src/main/res/values/styles.xml
+++ b/Source/Android/app/src/main/res/values/styles.xml
@@ -95,9 +95,48 @@
- @color/dolphin_accent_wiiware
+
+
+
+
+
+
+
+
+
+
+
\ No newline at end of file