Skip to content
This repository has been archived by the owner on Aug 7, 2024. It is now read-only.

Commit

Permalink
Merge pull request #283 from SuhasDissa/qs
Browse files Browse the repository at this point in the history
fix: QS tile related issues
  • Loading branch information
SuhasDissa authored Apr 8, 2024
2 parents c8e560f + 302b910 commit 3850194
Show file tree
Hide file tree
Showing 9 changed files with 87 additions and 52 deletions.
3 changes: 2 additions & 1 deletion app/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
<uses-permission android:name="android.permission.FOREGROUND_SERVICE_MEDIA_PROJECTION" />
<uses-permission android:name="android.permission.POST_NOTIFICATIONS" />

<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW"/>
<uses-permission android:name="android.permission.SYSTEM_ALERT_WINDOW" />

<!-- Opt out for network permissions that are optional for the ExoPlayer -->
<uses-permission
Expand All @@ -31,6 +31,7 @@
<activity
android:name=".ui.MainActivity"
android:exported="true"
android:launchMode="singleTop"
android:theme="@style/Theme.RecordYou">

<intent-filter>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -94,7 +94,7 @@ class CanvasOverlay(context: Context) {
y = 0
}

init {
fun show() {
hideCanvas()
try {
if (canvasView.windowToken == null && canvasView.parent == null) {
Expand Down
19 changes: 16 additions & 3 deletions app/src/main/java/com/bnyro/recorder/services/AudioRecorderTile.kt
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
package com.bnyro.recorder.services

import android.app.PendingIntent
import android.content.Intent
import android.content.Intent.FLAG_ACTIVITY_NEW_TASK
import android.os.Build
import android.service.quicksettings.TileService
import androidx.annotation.RequiresApi
Expand All @@ -11,12 +13,23 @@ import com.bnyro.recorder.ui.MainActivity
class AudioRecorderTile : TileService() {
override fun onClick() {
super.onClick()

val intent = Intent(this, MainActivity::class.java)
.putExtra(MainActivity.EXTRA_ACTION_KEY, RecorderType.AUDIO.name)
.apply {
flags = Intent.FLAG_ACTIVITY_NEW_TASK
flags = FLAG_ACTIVITY_NEW_TASK
}
startActivityAndCollapse(intent)
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.UPSIDE_DOWN_CAKE) {
startActivityAndCollapse(
PendingIntent.getActivity(
this, PENDING_INTENT_REQUEST_CODE, intent, PendingIntent.FLAG_IMMUTABLE
)
)
} else {
startActivityAndCollapse(intent)
}
}

companion object {
const val PENDING_INTENT_REQUEST_CODE = 20
}
}
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
package com.bnyro.recorder.services

import android.app.PendingIntent
import android.content.Intent
import android.os.Build
import android.service.quicksettings.TileService
Expand All @@ -11,12 +12,24 @@ import com.bnyro.recorder.ui.MainActivity
class ScreenRecorderTile : TileService() {
override fun onClick() {
super.onClick()

val intent = Intent(this, MainActivity::class.java)
.putExtra(MainActivity.EXTRA_ACTION_KEY, RecorderType.VIDEO.name)
.apply {
flags = Intent.FLAG_ACTIVITY_NEW_TASK
}
startActivityAndCollapse(intent)

if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.UPSIDE_DOWN_CAKE) {
startActivityAndCollapse(
PendingIntent.getActivity(
this, PENDING_INTENT_REQUEST_CODE, intent, PendingIntent.FLAG_IMMUTABLE
)
)
} else {
startActivityAndCollapse(intent)
}
}

companion object {
const val PENDING_INTENT_REQUEST_CODE = 21
}
}
47 changes: 41 additions & 6 deletions app/src/main/java/com/bnyro/recorder/ui/MainActivity.kt
Original file line number Diff line number Diff line change
@@ -1,8 +1,14 @@
package com.bnyro.recorder.ui

import android.app.Activity
import android.content.Context
import android.content.Intent
import android.media.projection.MediaProjectionManager
import android.os.Bundle
import androidx.activity.ComponentActivity
import androidx.activity.compose.setContent
import androidx.activity.result.ActivityResultLauncher
import androidx.activity.result.contract.ActivityResultContracts
import androidx.activity.viewModels
import androidx.compose.foundation.isSystemInDarkTheme
import androidx.compose.foundation.layout.fillMaxSize
Expand All @@ -12,21 +18,30 @@ import androidx.compose.ui.Modifier
import androidx.navigation.compose.rememberNavController
import com.bnyro.recorder.enums.RecorderType
import com.bnyro.recorder.enums.ThemeMode
import com.bnyro.recorder.ui.models.RecorderModel
import com.bnyro.recorder.ui.models.ThemeModel
import com.bnyro.recorder.ui.theme.RecordYouTheme

class MainActivity : ComponentActivity() {
private var initialRecorder = RecorderType.NONE
private var exitAfterRecordingStart = false
private lateinit var mProjectionManager: MediaProjectionManager
private val recorderModel: RecorderModel by viewModels()
private lateinit var launcher: ActivityResultLauncher<Intent>

override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
val themeModel: ThemeModel by viewModels()
launcher =
registerForActivityResult(ActivityResultContracts.StartActivityForResult()) { result ->
if (result.resultCode == Activity.RESULT_OK) {
recorderModel.startVideoRecorder(this, result)
}
}
mProjectionManager =
getSystemService(Context.MEDIA_PROJECTION_SERVICE) as MediaProjectionManager

initialRecorder = intent?.getStringExtra(EXTRA_ACTION_KEY)?.let {
RecorderType.valueOf(it)
} ?: RecorderType.NONE
intent?.putExtra(EXTRA_ACTION_KEY, "")
processIntent(intent)

setContent {
RecordYouTheme(
Expand All @@ -53,9 +68,29 @@ class MainActivity : ComponentActivity() {
}
}

override fun onNewIntent(intent: Intent) {
processIntent(intent)
super.onNewIntent(intent)
}

private fun processIntent(intent: Intent) {
val initialRecorderType = intent.getStringExtra(EXTRA_ACTION_KEY)?.let {
RecorderType.valueOf(it)
} ?: RecorderType.NONE
initialRecorder = initialRecorderType
if (initialRecorderType == RecorderType.AUDIO) {
recorderModel.startAudioRecorder(this)
} else if (initialRecorderType == RecorderType.VIDEO) {
if (recorderModel.hasScreenRecordingPermissions(this)) {
launcher.launch(mProjectionManager.createScreenCaptureIntent())
}
}
intent.removeExtra(EXTRA_ACTION_KEY)
}

override fun onPause() {
super.onPause()
if (initialRecorder != RecorderType.NONE) {
if (initialRecorder == RecorderType.VIDEO) {
exitAfterRecordingStart = true
initialRecorder = RecorderType.NONE
}
Expand All @@ -65,7 +100,7 @@ class MainActivity : ComponentActivity() {
super.onResume()
if (exitAfterRecordingStart) {
exitAfterRecordingStart = false
finish()
moveTaskToBack(true)
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,6 @@ import androidx.compose.material3.IconButton
import androidx.compose.material3.MaterialTheme
import androidx.compose.material3.Text
import androidx.compose.runtime.Composable
import androidx.compose.runtime.LaunchedEffect
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.clip
Expand All @@ -44,14 +43,12 @@ import androidx.compose.ui.unit.dp
import androidx.lifecycle.viewmodel.compose.viewModel
import com.bnyro.recorder.R
import com.bnyro.recorder.enums.RecorderState
import com.bnyro.recorder.enums.RecorderType
import com.bnyro.recorder.ui.common.ClickableIcon
import com.bnyro.recorder.ui.models.RecorderModel

@Composable
fun RecorderController(
recordScreenMode: Boolean,
initialRecorder: RecorderType
recordScreenMode: Boolean
) {
val recorderModel: RecorderModel = viewModel(LocalContext.current as ComponentActivity)
val context = LocalContext.current
Expand All @@ -71,19 +68,6 @@ fun RecorderController(
mProjectionManager.createScreenCaptureIntent()
)
}
LaunchedEffect(Unit) {
when (initialRecorder) {
RecorderType.AUDIO -> {
recorderModel.startAudioRecorder(context)
}

RecorderType.VIDEO -> {
requestScreenRecording()
}

RecorderType.NONE -> {}
}
}
Column(
modifier = Modifier.wrapContentSize(),
horizontalAlignment = Alignment.CenterHorizontally
Expand Down
24 changes: 7 additions & 17 deletions app/src/main/java/com/bnyro/recorder/ui/models/RecorderModel.kt
Original file line number Diff line number Diff line change
Expand Up @@ -6,12 +6,10 @@ import android.content.ComponentName
import android.content.Context
import android.content.Intent
import android.content.ServiceConnection
import android.net.Uri
import android.os.Build
import android.os.Handler
import android.os.IBinder
import android.os.Looper
import android.provider.Settings
import androidx.activity.result.ActivityResult
import androidx.annotation.RequiresApi
import androidx.compose.runtime.getValue
Expand All @@ -31,7 +29,6 @@ import com.bnyro.recorder.util.PermissionHelper
import com.bnyro.recorder.util.Preferences

class RecorderModel : ViewModel() {
private val audioPermission = arrayOf(Manifest.permission.RECORD_AUDIO)
private val supportsOverlay = Build.VERSION.SDK_INT >= Build.VERSION_CODES.O

var recorderState by mutableStateOf(RecorderState.IDLE)
Expand All @@ -52,6 +49,7 @@ class RecorderModel : ViewModel() {
recorderState = it
}
(recorderService as? ScreenRecorderService)?.prepare(activityResult!!)
if (supportsOverlay) canvasOverlay?.show()
recorderService?.start()
}

Expand All @@ -73,7 +71,12 @@ class RecorderModel : ViewModel() {

@SuppressLint("NewApi")
fun startAudioRecorder(context: Context) {
if (!PermissionHelper.checkPermissions(context, audioPermission)) return
val audioPermission = mutableListOf(Manifest.permission.RECORD_AUDIO)
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.TIRAMISU) {
audioPermission.add(Manifest.permission.POST_NOTIFICATIONS)
}

if (!PermissionHelper.checkPermissions(context, audioPermission.toTypedArray())) return

val serviceIntent =
if (Preferences.prefs.getBoolean(Preferences.losslessRecorderKey, false)) {
Expand Down Expand Up @@ -152,19 +155,6 @@ class RecorderModel : ViewModel() {

@SuppressLint("NewApi")
fun hasScreenRecordingPermissions(context: Context): Boolean {
val overlayEnabled = Preferences.prefs.getBoolean(
Preferences.showOverlayAnnotationToolKey,
false
)
if (supportsOverlay && overlayEnabled && !Settings.canDrawOverlays(context)) {
val intent = Intent(
Settings.ACTION_MANAGE_OVERLAY_PERMISSION,
Uri.parse("package:" + context.packageName)
)
context.startActivity(intent)
return false
}

val requiredPermissions = arrayListOf<String>()

val recordAudio =
Expand Down
5 changes: 3 additions & 2 deletions app/src/main/java/com/bnyro/recorder/ui/screens/HomeScreen.kt
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,8 @@ fun HomeScreen(
onNavigate: (Destination) -> Unit,
recorderModel: RecorderModel = viewModel(LocalContext.current as ComponentActivity)
) {
val pagerState = rememberPagerState { 2 }
val pagerState =
rememberPagerState(initialPage = if (initialRecorder == RecorderType.VIDEO) 1 else 0) { 2 }
val scope = rememberCoroutineScope()
val view = LocalView.current
Scaffold(modifier = Modifier.fillMaxSize(), topBar = {
Expand Down Expand Up @@ -114,7 +115,7 @@ fun HomeScreen(
state = pagerState,
modifier = Modifier.fillMaxSize()
) { index ->
RecorderView(initialRecorder = initialRecorder, recordScreenMode = (index == 1))
RecorderView(recordScreenMode = (index == 1))
}
}
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,15 +10,13 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.platform.LocalContext
import androidx.lifecycle.viewmodel.compose.viewModel
import com.bnyro.recorder.enums.RecorderState
import com.bnyro.recorder.enums.RecorderType
import com.bnyro.recorder.ui.common.ResponsiveRecordScreenLayout
import com.bnyro.recorder.ui.components.RecorderController
import com.bnyro.recorder.ui.components.RecorderPreview
import com.bnyro.recorder.ui.models.RecorderModel

@Composable
fun RecorderView(
initialRecorder: RecorderType,
recordScreenMode: Boolean
) {
val recorderModel: RecorderModel = viewModel(LocalContext.current as ComponentActivity)
Expand All @@ -39,7 +37,7 @@ fun RecorderView(
RecorderPreview(recordScreenMode)
},
PaneTwo = {
RecorderController(recordScreenMode, initialRecorder)
RecorderController(recordScreenMode)
}
)
}
Expand Down

0 comments on commit 3850194

Please sign in to comment.