Improvements to UI/UX

This commit makes a few improvements to the UI/UX:
* Crop Game Icons to ImageView
* Controller Support for Game List
* EmulationActivity is fullscreen now
This commit is contained in:
◱ PixelyIon 2020-04-24 17:09:13 +05:30
parent f909c00e31
commit 4d787c904e
22 changed files with 232 additions and 182 deletions

View File

@ -2,7 +2,7 @@
# For more details, see # For more details, see
# http://developer.android.com/guide/developing/tools/proguard.html # http://developer.android.com/guide/developing/tools/proguard.html
-keep class emu.skyline.loader.TitleEntry { -keep class emu.skyline.loader.AppEntry {
void writeObject(java.io.ObjectOutputStream); void writeObject(java.io.ObjectOutputStream);
void readObject(java.io.ObjectInputStream); void readObject(java.io.ObjectInputStream);
} }

View File

@ -3,7 +3,7 @@
* Copyright © 2020 Skyline Team and Contributors (https://github.com/skyline-emu/) * Copyright © 2020 Skyline Team and Contributors (https://github.com/skyline-emu/)
*/ */
package emu.skyline.utility package emu.skyline
import android.content.ComponentName import android.content.ComponentName
import android.content.Intent import android.content.Intent
@ -11,14 +11,13 @@ import android.content.pm.ShortcutInfo
import android.content.pm.ShortcutManager import android.content.pm.ShortcutManager
import android.graphics.drawable.Icon import android.graphics.drawable.Icon
import android.os.Bundle import android.os.Bundle
import android.view.KeyEvent
import android.view.LayoutInflater import android.view.LayoutInflater
import android.view.View import android.view.View
import android.view.ViewGroup import android.view.ViewGroup
import androidx.core.graphics.drawable.toBitmap import androidx.core.graphics.drawable.toBitmap
import com.google.android.material.bottomsheet.BottomSheetBehavior import com.google.android.material.bottomsheet.BottomSheetBehavior
import com.google.android.material.bottomsheet.BottomSheetDialogFragment import com.google.android.material.bottomsheet.BottomSheetDialogFragment
import emu.skyline.EmulationActivity
import emu.skyline.R
import emu.skyline.adapter.AppItem import emu.skyline.adapter.AppItem
import kotlinx.android.synthetic.main.app_dialog.* import kotlinx.android.synthetic.main.app_dialog.*
@ -37,13 +36,22 @@ class AppDialog(val item: AppItem? = null) : BottomSheetDialogFragment() {
} }
/** /**
* This expands the bottom sheet so that it's fully visible * This expands the bottom sheet so that it's fully visible and map the B button to back
*/ */
override fun onStart() { override fun onStart() {
super.onStart() super.onStart()
val behavior = BottomSheetBehavior.from(requireView().parent as View) val behavior = BottomSheetBehavior.from(requireView().parent as View)
behavior.state = BottomSheetBehavior.STATE_EXPANDED behavior.state = BottomSheetBehavior.STATE_EXPANDED
dialog?.setOnKeyListener { _, keyCode, event ->
if (keyCode == KeyEvent.KEYCODE_BUTTON_B && event.action == KeyEvent.ACTION_DOWN) {
dialog?.onBackPressed()
true
} else {
false
}
}
} }
/** /**
@ -59,6 +67,13 @@ class AppDialog(val item: AppItem? = null) : BottomSheetDialogFragment() {
game_title.text = item.title game_title.text = item.title
game_subtitle.text = item.subTitle ?: getString(R.string.metadata_missing) game_subtitle.text = item.subTitle ?: getString(R.string.metadata_missing)
game_play.setOnClickListener {
val intent = Intent(activity, EmulationActivity::class.java)
intent.data = item.uri
startActivity(intent)
}
val shortcutManager = activity?.getSystemService(ShortcutManager::class.java)!! val shortcutManager = activity?.getSystemService(ShortcutManager::class.java)!!
game_pin.isEnabled = shortcutManager.isRequestPinShortcutSupported game_pin.isEnabled = shortcutManager.isRequestPinShortcutSupported
@ -76,13 +91,6 @@ class AppDialog(val item: AppItem? = null) : BottomSheetDialogFragment() {
shortcutManager.requestPinShortcut(info.build(), null) shortcutManager.requestPinShortcut(info.build(), null)
} }
game_play.setOnClickListener {
val intent = Intent(activity, EmulationActivity::class.java)
intent.data = item.uri
startActivity(intent)
}
} else } else
activity?.supportFragmentManager?.beginTransaction()?.remove(this)?.commit() activity?.supportFragmentManager?.beginTransaction()?.remove(this)?.commit()
} }

View File

@ -13,7 +13,7 @@ import android.os.ParcelFileDescriptor
import android.util.Log import android.util.Log
import android.view.Surface import android.view.Surface
import android.view.SurfaceHolder import android.view.SurfaceHolder
import android.view.WindowManager import android.view.View
import androidx.appcompat.app.AppCompatActivity import androidx.appcompat.app.AppCompatActivity
import androidx.preference.PreferenceManager import androidx.preference.PreferenceManager
import emu.skyline.loader.getRomFormat import emu.skyline.loader.getRomFormat
@ -121,7 +121,12 @@ class EmulationActivity : AppCompatActivity(), SurfaceHolder.Callback {
setContentView(R.layout.emu_activity) setContentView(R.layout.emu_activity)
window.setFlags(WindowManager.LayoutParams.FLAG_FULLSCREEN, WindowManager.LayoutParams.FLAG_FULLSCREEN) window.decorView.systemUiVisibility = (View.SYSTEM_UI_FLAG_IMMERSIVE
or View.SYSTEM_UI_FLAG_LAYOUT_STABLE
or View.SYSTEM_UI_FLAG_LAYOUT_HIDE_NAVIGATION
or View.SYSTEM_UI_FLAG_LAYOUT_FULLSCREEN
or View.SYSTEM_UI_FLAG_HIDE_NAVIGATION
or View.SYSTEM_UI_FLAG_FULLSCREEN)
val preference = File("${applicationInfo.dataDir}/shared_prefs/${applicationInfo.packageName}_preferences.xml") val preference = File("${applicationInfo.dataDir}/shared_prefs/${applicationInfo.packageName}_preferences.xml")
preferenceFd = ParcelFileDescriptor.open(preference, ParcelFileDescriptor.MODE_READ_WRITE) preferenceFd = ParcelFileDescriptor.open(preference, ParcelFileDescriptor.MODE_READ_WRITE)

View File

@ -7,6 +7,7 @@ package emu.skyline
import android.content.Intent import android.content.Intent
import android.content.SharedPreferences import android.content.SharedPreferences
import android.content.pm.ActivityInfo
import android.net.Uri import android.net.Uri
import android.os.Bundle import android.os.Bundle
import android.util.Log import android.util.Log
@ -29,7 +30,6 @@ import emu.skyline.adapter.GridLayoutSpan
import emu.skyline.adapter.LayoutType import emu.skyline.adapter.LayoutType
import emu.skyline.loader.BaseLoader import emu.skyline.loader.BaseLoader
import emu.skyline.loader.NroLoader import emu.skyline.loader.NroLoader
import emu.skyline.utility.AppDialog
import emu.skyline.utility.RandomAccessDocument import emu.skyline.utility.RandomAccessDocument
import kotlinx.android.synthetic.main.main_activity.* import kotlinx.android.synthetic.main.main_activity.*
import kotlinx.android.synthetic.main.titlebar.* import kotlinx.android.synthetic.main.titlebar.*
@ -101,7 +101,10 @@ class MainActivity : AppCompatActivity(), View.OnClickListener, View.OnLongClick
thread(start = true) { thread(start = true) {
val snackbar = Snackbar.make(findViewById(android.R.id.content), getString(R.string.searching_roms), Snackbar.LENGTH_INDEFINITE) val snackbar = Snackbar.make(findViewById(android.R.id.content), getString(R.string.searching_roms), Snackbar.LENGTH_INDEFINITE)
runOnUiThread { snackbar.show() } runOnUiThread {
snackbar.show()
requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_LOCKED
}
try { try {
runOnUiThread { adapter.clear() } runOnUiThread { adapter.clear() }
@ -134,7 +137,10 @@ class MainActivity : AppCompatActivity(), View.OnClickListener, View.OnLongClick
} }
} }
runOnUiThread { snackbar.dismiss() } runOnUiThread {
snackbar.dismiss()
requestedOrientation = ActivityInfo.SCREEN_ORIENTATION_UNSPECIFIED
}
} }
} }
@ -184,6 +190,23 @@ class MainActivity : AppCompatActivity(), View.OnClickListener, View.OnLongClick
} }
} }
app_list.addOnScrollListener(object : RecyclerView.OnScrollListener() {
var y : Int = 0
override fun onScrolled(recyclerView : RecyclerView, dx : Int, dy : Int) {
y += dy
if (!app_list.isInTouchMode) {
if (y == 0)
toolbar_layout.setExpanded(true)
else
toolbar_layout.setExpanded(false)
}
super.onScrolled(recyclerView, dx, dy)
}
})
if (sharedPreferences.getString("search_location", "") == "") { if (sharedPreferences.getString("search_location", "") == "") {
val intent = Intent(Intent.ACTION_OPEN_DOCUMENT_TREE) val intent = Intent(Intent.ACTION_OPEN_DOCUMENT_TREE)
intent.flags = Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION or Intent.FLAG_GRANT_PREFIX_URI_PERMISSION or Intent.FLAG_GRANT_READ_URI_PERMISSION intent.flags = Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION or Intent.FLAG_GRANT_PREFIX_URI_PERMISSION or Intent.FLAG_GRANT_READ_URI_PERMISSION

View File

@ -155,6 +155,8 @@ internal class AppAdapter(val context: Context?, private val layoutType: LayoutT
if (context is View.OnLongClickListener) if (context is View.OnLongClickListener)
holder.card!!.setOnLongClickListener(context as View.OnLongClickListener) holder.card!!.setOnLongClickListener(context as View.OnLongClickListener)
holder.title.isSelected = true
} }
} else if (viewType == Header.ordinal) { } else if (viewType == Header.ordinal) {
val view = inflater.inflate(R.layout.section_item, parent, false) val view = inflater.inflate(R.layout.section_item, parent, false)

View File

@ -4,6 +4,7 @@
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_gravity="center_horizontal" android:layout_gravity="center_horizontal"
android:nextFocusRight="@id/game_play"
android:padding="16dp"> android:padding="16dp">
<com.google.android.material.imageview.ShapeableImageView <com.google.android.material.imageview.ShapeableImageView
@ -11,6 +12,7 @@
android:layout_width="150dp" android:layout_width="150dp"
android:layout_height="150dp" android:layout_height="150dp"
android:contentDescription="@string/icon" android:contentDescription="@string/icon"
android:focusable="false"
app:shapeAppearanceOverlay="@style/roundedAppImage" /> app:shapeAppearanceOverlay="@style/roundedAppImage" />
<LinearLayout <LinearLayout
@ -47,6 +49,7 @@
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginEnd="6dp" android:layout_marginEnd="6dp"
android:focusedByDefault="true"
android:text="@string/play" android:text="@string/play"
app:icon="@drawable/ic_play" /> app:icon="@drawable/ic_play" />

View File

@ -16,38 +16,46 @@
card_view:cardCornerRadius="4dp"> card_view:cardCornerRadius="4dp">
<RelativeLayout <RelativeLayout
android:layout_width="wrap_content" android:layout_width="155dp"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_gravity="center" android:layout_gravity="center"
android:orientation="vertical"> android:orientation="vertical">
<ImageView <ImageView
android:id="@+id/icon" android:id="@+id/icon"
android:layout_width="150dp" android:layout_width="match_parent"
android:layout_height="150dp" android:layout_height="155dp"
android:layout_alignParentTop="false" android:layout_alignParentTop="false"
android:layout_centerHorizontal="true" android:layout_centerHorizontal="true"
android:contentDescription="@string/icon" /> android:contentDescription="@string/icon"
android:scaleType="centerCrop" />
<TextView <TextView
android:id="@+id/text_title" android:id="@+id/text_title"
android:layout_width="150dp" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_below="@id/icon" android:layout_below="@id/icon"
android:ellipsize="marquee"
android:marqueeRepeatLimit="marquee_forever"
android:paddingStart="15dp" android:paddingStart="15dp"
android:paddingTop="15dp" android:paddingTop="10dp"
android:paddingEnd="15dp" android:paddingEnd="15dp"
android:singleLine="true"
android:textAlignment="center" android:textAlignment="center"
android:textAppearance="?android:attr/textAppearanceListItem" android:textAppearance="?android:attr/textAppearanceListItem"
tools:ignore="RelativeOverlap" /> tools:ignore="RelativeOverlap" />
<TextView <TextView
android:id="@+id/text_subtitle" android:id="@+id/text_subtitle"
android:layout_width="150dp" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_below="@id/text_title" android:layout_below="@id/text_title"
android:layout_alignStart="@id/text_title" android:layout_alignStart="@id/text_title"
android:ellipsize="marquee"
android:fadingEdge="horizontal"
android:marqueeRepeatLimit="marquee_forever"
android:paddingBottom="15dp" android:paddingBottom="15dp"
android:singleLine="true"
android:textAlignment="center" android:textAlignment="center"
android:textAppearance="?android:attr/textAppearanceListItemSecondary" android:textAppearance="?android:attr/textAppearanceListItemSecondary"
android:textColor="@android:color/tertiary_text_light" /> android:textColor="@android:color/tertiary_text_light" />

View File

@ -3,6 +3,7 @@
xmlns:tools="http://schemas.android.com/tools" xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="match_parent" android:layout_height="match_parent"
android:keepScreenOn="true"
tools:context=".EmulationActivity"> tools:context=".EmulationActivity">
<SurfaceView <SurfaceView

View File

@ -28,7 +28,6 @@
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:layout_marginBottom="8dp" android:layout_marginBottom="8dp"
android:padding="8dp"
app:maxImageSize="26dp" app:maxImageSize="26dp"
app:srcCompat="@drawable/ic_open" /> app:srcCompat="@drawable/ic_open" />
@ -37,7 +36,6 @@
style="@style/Widget.MaterialComponents.FloatingActionButton" style="@style/Widget.MaterialComponents.FloatingActionButton"
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:padding="8dp"
app:maxImageSize="26dp" app:maxImageSize="26dp"
app:srcCompat="@drawable/ic_log" /> app:srcCompat="@drawable/ic_log" />
</LinearLayout> </LinearLayout>

View File

@ -1,8 +1,10 @@
<?xml version="1.0" encoding="utf-8"?> <?xml version="1.0" encoding="utf-8"?>
<com.google.android.material.appbar.AppBarLayout xmlns:android="http://schemas.android.com/apk/res/android" <com.google.android.material.appbar.AppBarLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:app="http://schemas.android.com/apk/res-auto"
android:id="@+id/toolbar_layout"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:descendantFocusability="afterDescendants"
app:liftOnScroll="true"> app:liftOnScroll="true">
<com.google.android.material.appbar.MaterialToolbar <com.google.android.material.appbar.MaterialToolbar