Files
Pupil/app/src/main/java/xyz/quaver/pupil/ReaderActivity.kt
2019-05-18 23:20:06 +09:00

292 lines
10 KiB
Kotlin

package xyz.quaver.pupil
import android.graphics.drawable.Drawable
import android.os.Bundle
import android.util.Log
import android.view.*
import androidx.appcompat.app.AlertDialog
import androidx.appcompat.app.AppCompatActivity
import androidx.preference.PreferenceManager
import androidx.recyclerview.widget.LinearLayoutManager
import androidx.recyclerview.widget.LinearSmoothScroller
import androidx.recyclerview.widget.PagerSnapHelper
import androidx.recyclerview.widget.RecyclerView
import androidx.vectordrawable.graphics.drawable.Animatable2Compat
import androidx.vectordrawable.graphics.drawable.AnimatedVectorDrawableCompat
import kotlinx.android.synthetic.main.activity_reader.*
import kotlinx.android.synthetic.main.activity_reader.view.*
import kotlinx.android.synthetic.main.dialog_numberpicker.view.*
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.Dispatchers
import kotlinx.coroutines.launch
import kotlinx.serialization.json.Json
import kotlinx.serialization.json.JsonConfiguration
import xyz.quaver.hitomi.GalleryBlock
import xyz.quaver.pupil.adapters.ReaderAdapter
import xyz.quaver.pupil.util.GalleryDownloader
import xyz.quaver.pupil.util.ItemClickSupport
class ReaderActivity : AppCompatActivity() {
private val images = ArrayList<String>()
private lateinit var galleryBlock: GalleryBlock
private var gallerySize = 0
private var currentPage = 0
private var isScroll = true
private var isFullscreen = false
private lateinit var downloader: GalleryDownloader
private val snapHelper = PagerSnapHelper()
private var menu: Menu? = null
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
window.setFlags(
WindowManager.LayoutParams.FLAG_SECURE,
WindowManager.LayoutParams.FLAG_SECURE)
setContentView(R.layout.activity_reader)
galleryBlock = Json(JsonConfiguration.Stable).parse(
GalleryBlock.serializer(),
intent.getStringExtra("galleryblock")
)
supportActionBar?.title = galleryBlock.title
supportActionBar?.setDisplayHomeAsUpEnabled(false)
initDownloader()
initView()
if (!downloader.notify)
downloader.start()
}
override fun onResume() {
val preferences = PreferenceManager.getDefaultSharedPreferences(this)
if (preferences.getBoolean("security_mode", false))
window.setFlags(
WindowManager.LayoutParams.FLAG_SECURE,
WindowManager.LayoutParams.FLAG_SECURE)
else
window.clearFlags(WindowManager.LayoutParams.FLAG_SECURE)
super.onResume()
}
override fun onCreateOptionsMenu(menu: Menu?): Boolean {
menuInflater.inflate(R.menu.reader, menu)
this.menu = menu
return true
}
override fun onOptionsItemSelected(item: MenuItem?): Boolean {
when(item?.itemId) {
R.id.reader_menu_page_indicator -> {
val view = LayoutInflater.from(this).inflate(R.layout.dialog_numberpicker, findViewById(android.R.id.content), false)
with(view.reader_dialog_number_picker) {
minValue=1
maxValue=gallerySize
value=currentPage
}
val dialog = AlertDialog.Builder(this).apply {
setView(view)
}.create()
view.reader_dialog_ok.setOnClickListener {
(reader_recyclerview.layoutManager as LinearLayoutManager?)?.scrollToPositionWithOffset(view.reader_dialog_number_picker.value-1, 0)
dialog.dismiss()
}
dialog.show()
}
}
return true
}
override fun onDestroy() {
super.onDestroy()
if (!downloader.notify)
downloader.cancel()
}
override fun onBackPressed() {
if (isScroll and !isFullscreen)
super.onBackPressed()
if (isFullscreen) {
isFullscreen = false
fullscreen(false)
}
if (!isScroll) {
isScroll = true
scrollMode(true)
}
}
private fun initDownloader() {
var d: GalleryDownloader? = GalleryDownloader.get(galleryBlock.id)
if (d == null) {
d = GalleryDownloader(this, galleryBlock)
}
downloader = d.apply {
onReaderLoadedHandler = {
CoroutineScope(Dispatchers.Main).launch {
with(reader_progressbar) {
max = it.size
progress = 0
visibility = View.VISIBLE
}
gallerySize = it.size
menu?.findItem(R.id.reader_menu_page_indicator)?.title = "$currentPage/${it.size}"
}
}
onProgressHandler = {
CoroutineScope(Dispatchers.Main).launch {
reader_progressbar.progress = it
}
}
onDownloadedHandler = {
CoroutineScope(Dispatchers.Main).launch {
if (images.isEmpty()) {
images.addAll(it)
reader_recyclerview.adapter?.notifyDataSetChanged()
} else {
images.add(it.last())
reader_recyclerview.adapter?.notifyItemInserted(images.size-1)
}
}
}
onErrorHandler = {
downloader.notify = false
}
onCompleteHandler = {
CoroutineScope(Dispatchers.Main).launch {
reader_progressbar.visibility = View.GONE
}
}
onNotifyChangedHandler = { notify ->
val fab = reader_fab_download
if (notify) {
val icon = AnimatedVectorDrawableCompat.create(this, R.drawable.ic_downloading)
icon?.registerAnimationCallback(object: Animatable2Compat.AnimationCallback() {
override fun onAnimationEnd(drawable: Drawable?) {
if (downloader.notify)
fab.post {
icon.start()
fab.labelText = getString(R.string.reader_fab_download_cancel)
}
else
fab.post {
fab.setImageResource(R.drawable.ic_download)
fab.labelText = getString(R.string.reader_fab_download)
}
}
})
fab.setImageDrawable(icon)
icon?.start()
} else {
fab.setImageResource(R.drawable.ic_download)
}
}
}
if (downloader.notify) {
downloader.invokeOnReaderLoaded()
downloader.invokeOnNotifyChanged()
}
}
private fun initView() {
with(reader_recyclerview) {
adapter = ReaderAdapter(images)
addOnScrollListener(object: RecyclerView.OnScrollListener() {
override fun onScrolled(recyclerView: RecyclerView, dx: Int, dy: Int) {
super.onScrolled(recyclerView, dx, dy)
val layoutManager = recyclerView.layoutManager as LinearLayoutManager
if (layoutManager.findFirstVisibleItemPosition() == -1)
return
currentPage = layoutManager.findFirstVisibleItemPosition()+1
menu?.findItem(R.id.reader_menu_page_indicator)?.title = "$currentPage/$gallerySize"
}
})
ItemClickSupport.addTo(this)
.setOnItemClickListener { _, _, _ ->
if (isScroll) {
isScroll = false
isFullscreen = true
scrollMode(false)
fullscreen(true)
} else {
val smoothScroller = object : LinearSmoothScroller(context) {
override fun getVerticalSnapPreference() = SNAP_TO_START
}.apply {
targetPosition = currentPage
}
(reader_recyclerview.layoutManager as LinearLayoutManager?)?.startSmoothScroll(smoothScroller)
}
}
}
reader_fab_fullscreen.setOnClickListener {
isFullscreen = true
fullscreen(isFullscreen)
reader_fab.close(true)
}
reader_fab_download.setOnClickListener {
downloader.notify = !downloader.notify
if (!downloader.notify)
downloader.clearNotification()
}
}
private fun fullscreen(isFullscreen: Boolean) {
with(window.attributes) {
if (isFullscreen) {
flags = flags or WindowManager.LayoutParams.FLAG_FULLSCREEN
supportActionBar?.hide()
this@ReaderActivity.reader_fab.visibility = View.INVISIBLE
} else {
flags = flags and WindowManager.LayoutParams.FLAG_FULLSCREEN.inv()
supportActionBar?.show()
this@ReaderActivity.reader_fab.visibility = View.VISIBLE
}
window.attributes = this
}
}
private fun scrollMode(isScroll: Boolean) {
if (isScroll) {
snapHelper.attachToRecyclerView(null)
reader_recyclerview.layoutManager = LinearLayoutManager(this)
} else {
snapHelper.attachToRecyclerView(reader_recyclerview)
reader_recyclerview.layoutManager = LinearLayoutManager(this, LinearLayoutManager.HORIZONTAL, false)
}
(reader_recyclerview.layoutManager as LinearLayoutManager).scrollToPositionWithOffset(currentPage-1, 0)
}
}