v1.0.0 - ShiftRing 정식 첫 릴리즈\
This commit is contained in:
@@ -0,0 +1,215 @@
|
||||
package com.example.shiftalarm
|
||||
|
||||
import android.app.Activity
|
||||
import android.content.Context
|
||||
import android.content.Intent
|
||||
import android.graphics.Color
|
||||
import android.graphics.drawable.ColorDrawable
|
||||
import android.net.Uri
|
||||
import android.os.Build
|
||||
import android.view.LayoutInflater
|
||||
import android.widget.Button
|
||||
import android.widget.ProgressBar
|
||||
import android.widget.TextView
|
||||
import android.widget.Toast
|
||||
import androidx.appcompat.app.AlertDialog
|
||||
import androidx.core.content.FileProvider
|
||||
import org.json.JSONObject
|
||||
import java.io.BufferedInputStream
|
||||
import java.io.File
|
||||
import java.io.FileOutputStream
|
||||
import java.net.HttpURLConnection
|
||||
import java.net.URL
|
||||
|
||||
object AppUpdateManager {
|
||||
|
||||
private const val VERSION_URL = "https://git.webpluss.net/sanjeok77/ShiftRing/raw/branch/main/version.json"
|
||||
|
||||
fun checkUpdate(activity: Activity, silent: Boolean = false) {
|
||||
val ctx = activity.applicationContext
|
||||
val versionCheckUrl = "$VERSION_URL?t=${System.currentTimeMillis()}"
|
||||
|
||||
Thread {
|
||||
try {
|
||||
val url = URL(versionCheckUrl)
|
||||
val connection = url.openConnection() as HttpURLConnection
|
||||
connection.connectTimeout = 5000
|
||||
connection.readTimeout = 5000
|
||||
connection.requestMethod = "GET"
|
||||
connection.useCaches = false
|
||||
|
||||
if (connection.responseCode == 200) {
|
||||
val reader = connection.inputStream.bufferedReader()
|
||||
val result = reader.readText()
|
||||
reader.close()
|
||||
|
||||
val json = JSONObject(result)
|
||||
val serverVersionCode = json.getInt("versionCode")
|
||||
val serverVersionName = json.getString("versionName")
|
||||
val apkUrl = json.getString("apkUrl")
|
||||
val changelog = json.optString("changelog", "버그 수정 및 성능 향상")
|
||||
|
||||
val pInfo = ctx.packageManager.getPackageInfo(ctx.packageName, 0)
|
||||
val currentVersionCode = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.P) {
|
||||
pInfo.longVersionCode.toInt()
|
||||
} else {
|
||||
@Suppress("DEPRECATION")
|
||||
pInfo.versionCode
|
||||
}
|
||||
val currentVersionName = pInfo.versionName ?: "0.0.0"
|
||||
|
||||
if (serverVersionCode > currentVersionCode) {
|
||||
activity.runOnUiThread {
|
||||
showUpdateDialog(activity, serverVersionName, changelog, apkUrl)
|
||||
}
|
||||
} else if (!silent && serverVersionCode == currentVersionCode) {
|
||||
activity.runOnUiThread {
|
||||
Toast.makeText(ctx, "현재 최신 버전을 사용 중입니다. ($currentVersionName)", Toast.LENGTH_SHORT).show()
|
||||
}
|
||||
}
|
||||
} else if (!silent) {
|
||||
activity.runOnUiThread {
|
||||
Toast.makeText(ctx, "서버 연결 실패", Toast.LENGTH_SHORT).show()
|
||||
}
|
||||
}
|
||||
} catch (e: Exception) {
|
||||
e.printStackTrace()
|
||||
if (!silent) {
|
||||
activity.runOnUiThread {
|
||||
Toast.makeText(ctx, "업데이트 확인 중 오류 발생", Toast.LENGTH_SHORT).show()
|
||||
}
|
||||
}
|
||||
}
|
||||
}.start()
|
||||
}
|
||||
|
||||
private fun showUpdateDialog(activity: Activity, version: String, changelog: String, apkUrl: String) {
|
||||
if (activity.isFinishing || activity.isDestroyed) return
|
||||
|
||||
val view = LayoutInflater.from(activity).inflate(R.layout.dialog_app_update_oneui, null)
|
||||
val tvVersion = view.findViewById<TextView>(R.id.tvUpdateVersion)
|
||||
val tvChangelog = view.findViewById<TextView>(R.id.tvChangelog)
|
||||
val btnLater = view.findViewById<Button>(R.id.btnUpdateLater)
|
||||
val btnNow = view.findViewById<Button>(R.id.btnUpdateNow)
|
||||
|
||||
tvVersion.text = "Version $version"
|
||||
tvChangelog.text = changelog
|
||||
|
||||
val dialog = AlertDialog.Builder(activity)
|
||||
.setView(view)
|
||||
.setCancelable(true)
|
||||
.create()
|
||||
|
||||
dialog.window?.setBackgroundDrawable(ColorDrawable(Color.TRANSPARENT))
|
||||
|
||||
btnLater.setOnClickListener {
|
||||
dialog.dismiss()
|
||||
}
|
||||
|
||||
btnNow.setOnClickListener {
|
||||
dialog.dismiss()
|
||||
downloadAndInstallApk(activity, apkUrl, version)
|
||||
}
|
||||
|
||||
dialog.show()
|
||||
|
||||
val width = (activity.resources.displayMetrics.widthPixels * 0.88).toInt()
|
||||
dialog.window?.setLayout(width, android.view.ViewGroup.LayoutParams.WRAP_CONTENT)
|
||||
}
|
||||
|
||||
private fun downloadAndInstallApk(activity: Activity, apkUrl: String, version: String) {
|
||||
if (activity.isFinishing || activity.isDestroyed) return
|
||||
|
||||
val view = LayoutInflater.from(activity).inflate(R.layout.dialog_update_progress_oneui, null)
|
||||
val tvSub = view.findViewById<TextView>(R.id.tvProgressSub)
|
||||
val progressBar = view.findViewById<ProgressBar>(R.id.downloadProgressBar)
|
||||
val tvPercent = view.findViewById<TextView>(R.id.tvProgressPercent)
|
||||
|
||||
tvSub.text = "v$version 다운로드 중..."
|
||||
|
||||
val progressDialog = AlertDialog.Builder(activity)
|
||||
.setView(view)
|
||||
.setCancelable(false)
|
||||
.create()
|
||||
|
||||
progressDialog.window?.setBackgroundDrawable(ColorDrawable(Color.TRANSPARENT))
|
||||
progressDialog.show()
|
||||
|
||||
val width = (activity.resources.displayMetrics.widthPixels * 0.88).toInt()
|
||||
progressDialog.window?.setLayout(width, android.view.ViewGroup.LayoutParams.WRAP_CONTENT)
|
||||
|
||||
Thread {
|
||||
try {
|
||||
val url = URL(apkUrl)
|
||||
val connection = url.openConnection() as HttpURLConnection
|
||||
connection.connectTimeout = 15000
|
||||
connection.readTimeout = 15000
|
||||
connection.requestMethod = "GET"
|
||||
connection.connect()
|
||||
|
||||
val fileLength = connection.contentLength
|
||||
val inputStream = BufferedInputStream(connection.inputStream)
|
||||
|
||||
val apkFile = File(activity.cacheDir, "update.apk")
|
||||
val outputStream = FileOutputStream(apkFile)
|
||||
|
||||
val buffer = ByteArray(8192)
|
||||
var total: Long = 0
|
||||
var count: Int
|
||||
|
||||
while (inputStream.read(buffer).also { count = it } != -1) {
|
||||
total += count
|
||||
outputStream.write(buffer, 0, count)
|
||||
|
||||
if (fileLength > 0) {
|
||||
val progress = (total * 100 / fileLength).toInt()
|
||||
activity.runOnUiThread {
|
||||
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
|
||||
progressBar.setProgress(progress, true)
|
||||
} else {
|
||||
progressBar.progress = progress
|
||||
}
|
||||
tvPercent.text = "$progress%"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
outputStream.flush()
|
||||
outputStream.close()
|
||||
inputStream.close()
|
||||
connection.disconnect()
|
||||
|
||||
activity.runOnUiThread {
|
||||
progressDialog.dismiss()
|
||||
installApk(activity, apkFile)
|
||||
}
|
||||
|
||||
} catch (e: Exception) {
|
||||
e.printStackTrace()
|
||||
activity.runOnUiThread {
|
||||
progressDialog.dismiss()
|
||||
Toast.makeText(activity, "다운로드 실패: ${e.message}", Toast.LENGTH_LONG).show()
|
||||
}
|
||||
}
|
||||
}.start()
|
||||
}
|
||||
|
||||
private fun installApk(activity: Activity, apkFile: File) {
|
||||
try {
|
||||
val apkUri = if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
|
||||
FileProvider.getUriForFile(activity, "${activity.packageName}.provider", apkFile)
|
||||
} else {
|
||||
Uri.fromFile(apkFile)
|
||||
}
|
||||
|
||||
val intent = Intent(Intent.ACTION_VIEW).apply {
|
||||
setDataAndType(apkUri, "application/vnd.android.package-archive")
|
||||
flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_GRANT_READ_URI_PERMISSION
|
||||
}
|
||||
activity.startActivity(intent)
|
||||
} catch (e: Exception) {
|
||||
e.printStackTrace()
|
||||
Toast.makeText(activity, "설치 실패: ${e.message}", Toast.LENGTH_LONG).show()
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user