diff --git a/app/src/main/java/com/example/notimanager/common/objects/DateFormatter.kt b/app/src/main/java/com/example/notimanager/common/objects/DateFormatter.kt index bafc1d9..ab5dc33 100644 --- a/app/src/main/java/com/example/notimanager/common/objects/DateFormatter.kt +++ b/app/src/main/java/com/example/notimanager/common/objects/DateFormatter.kt @@ -1,27 +1,29 @@ package com.example.notimanager.common.objects +import android.content.Context import android.graphics.Bitmap import android.graphics.drawable.Drawable import android.icu.text.SimpleDateFormat +import com.example.notimanager.R import java.util.Date import java.util.Locale import java.util.concurrent.TimeUnit object DateFormatter { - fun formatTimestamp(timestamp: Long, format: String = "relative"): String { + fun formatTimestamp(context: Context, timestamp: Long, format: String = "relative"): String { return if (format == "relative") { val currentTime = System.currentTimeMillis() val timeDifference = currentTime - timestamp return when { - timeDifference < TimeUnit.SECONDS.toMillis(1) -> "방금" - timeDifference < TimeUnit.MINUTES.toMillis(1) -> "${timeDifference / 1000}초 전" - timeDifference < TimeUnit.HOURS.toMillis(1) -> "${timeDifference / TimeUnit.MINUTES.toMillis(1)}분 전" - timeDifference < TimeUnit.DAYS.toMillis(1) -> "${timeDifference / TimeUnit.HOURS.toMillis(1)}시간 전" - timeDifference < TimeUnit.DAYS.toMillis(7) -> "${timeDifference / TimeUnit.DAYS.toMillis(1)}일 전" - timeDifference < TimeUnit.DAYS.toMillis(30) -> "${timeDifference / TimeUnit.DAYS.toMillis(7)}주 전" - timeDifference < TimeUnit.DAYS.toMillis(365) -> "${timeDifference / TimeUnit.DAYS.toMillis(30)}달 전" - else -> "${timeDifference / TimeUnit.DAYS.toMillis(365)}년 전" + timeDifference < TimeUnit.SECONDS.toMillis(1) -> context.getString(R.string.time_now) + timeDifference < TimeUnit.MINUTES.toMillis(1) -> context.getString(R.string.time_second, timeDifference / 1000) + timeDifference < TimeUnit.HOURS.toMillis(1) -> context.getString(R.string.time_minute, timeDifference / TimeUnit.MINUTES.toMillis(1)) + timeDifference < TimeUnit.DAYS.toMillis(1) -> context.getString(R.string.time_hour, timeDifference / TimeUnit.HOURS.toMillis(1)) + timeDifference < TimeUnit.DAYS.toMillis(7) -> context.getString(R.string.time_day, timeDifference / TimeUnit.DAYS.toMillis(1)) + timeDifference < TimeUnit.DAYS.toMillis(30) -> context.getString(R.string.time_week, timeDifference / TimeUnit.DAYS.toMillis(7)) + timeDifference < TimeUnit.DAYS.toMillis(365) -> context.getString(R.string.time_month, timeDifference / TimeUnit.DAYS.toMillis(30)) + else -> context.getString(R.string.time_year, timeDifference / TimeUnit.DAYS.toMillis(365)) } } else { SimpleDateFormat("HH:mm dd.MM.yyyy", Locale.getDefault()).format(Date(timestamp)) diff --git a/app/src/main/java/com/example/notimanager/domain/service/ForegroundNotiService.kt b/app/src/main/java/com/example/notimanager/domain/service/ForegroundNotiService.kt index 14b52ce..8289a5d 100644 --- a/app/src/main/java/com/example/notimanager/domain/service/ForegroundNotiService.kt +++ b/app/src/main/java/com/example/notimanager/domain/service/ForegroundNotiService.kt @@ -48,6 +48,8 @@ class ForegroundNotiService: Service() { appName: String, content: String, isGroupSummary: Boolean) { + val appContent = if (isGroupSummary) content else getString(R.string.status_app_content, content) + val notificationIntent = Intent(this, MainActivity::class.java).apply { putExtra("appName", appName) } @@ -60,7 +62,7 @@ class ForegroundNotiService: Service() { val notification = NotificationCompat.Builder(this, channelId) .setSmallIcon(R.mipmap.ic_launcher) .setContentTitle(appName) - .setContentText(content) + .setContentText(appContent) .setContentIntent(pendingIntent) .setPriority(NotificationCompat.PRIORITY_HIGH) .setGroup(groupId) diff --git a/app/src/main/java/com/example/notimanager/presentation/ui/activity/MainActivity.kt b/app/src/main/java/com/example/notimanager/presentation/ui/activity/MainActivity.kt index 9dd14d4..0f7e926 100644 --- a/app/src/main/java/com/example/notimanager/presentation/ui/activity/MainActivity.kt +++ b/app/src/main/java/com/example/notimanager/presentation/ui/activity/MainActivity.kt @@ -6,9 +6,11 @@ import android.util.Log import androidx.activity.ComponentActivity import androidx.activity.compose.setContent import androidx.activity.viewModels +import androidx.compose.ui.platform.LocalContext import androidx.navigation.NavController import androidx.navigation.NavHostController import androidx.navigation.compose.rememberNavController +import com.example.notimanager.R import com.example.notimanager.domain.service.ForegroundNotiService import com.example.notimanager.presentation.stateholder.viewmodel.NotificationPermissionViewModel import com.example.notimanager.presentation.stateholder.viewmodel.NotificationServicePermissionViewModel @@ -24,6 +26,10 @@ class MainActivity : ComponentActivity() { override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) + // 언어 변경에 따라 문자열 리소스를 가져오기 + val basicTitle = getString(R.string.status_basic_title) + val basicContent = getString(R.string.status_basic_content) + val appName = intent.extras?.getString("appName") ?: "" setContent { navController = rememberNavController() @@ -38,8 +44,8 @@ class MainActivity : ComponentActivity() { } val serviceIntent = Intent(this, ForegroundNotiService::class.java).apply { putExtra("clearGroup", true) - putExtra("appName", "NotiManager") - putExtra("content", "실행 중입니다.") + putExtra("appName", basicTitle) + putExtra("content", basicContent) putExtra("isGroupSummary", true) } startService(serviceIntent) @@ -49,11 +55,4 @@ class MainActivity : ComponentActivity() { super.onResume() serviceViewModel.checkNotificationServicePermission() } - - override fun onNewIntent(intent: Intent) { - super.onNewIntent(intent) - val appName = intent.extras?.getString("appName") ?: "" - if (appName != "" && appName != "NotiManager") navController.navigate("titleScreen/$appName") - - } } diff --git a/app/src/main/java/com/example/notimanager/presentation/ui/component/FilteredListView.kt b/app/src/main/java/com/example/notimanager/presentation/ui/component/FilteredListView.kt index 84abb73..88b4a38 100644 --- a/app/src/main/java/com/example/notimanager/presentation/ui/component/FilteredListView.kt +++ b/app/src/main/java/com/example/notimanager/presentation/ui/component/FilteredListView.kt @@ -22,8 +22,10 @@ import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.Color +import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.text.font.FontWeight import androidx.compose.ui.unit.dp +import com.example.notimanager.R import com.example.notimanager.domain.model.FilteredNotification import com.example.notimanager.presentation.stateholder.state.FilteredNotificationState import com.example.notimanager.presentation.stateholder.viewmodel.FilteredNotificationViewModel @@ -57,6 +59,11 @@ fun FilteredItemView( filteredItem: FilteredNotification, viewModel: FilteredNotificationViewModel, ) { + // 언어 변경에 따라 문자열 리소스를 가져오기 + val context = LocalContext.current + val removeFiltered = context.getString(R.string.modal_remove_filtered) + // 위의 문자열 리소스는 모달에서 사용할 텍스트 + var showModal by remember { mutableStateOf(false) } Row( @@ -95,7 +102,7 @@ fun FilteredItemView( color = Color.Gray ) - ClickableTextView(text = "제외 리스트에서 삭제", onClick = { + ClickableTextView(text = removeFiltered, onClick = { viewModel.deleteFilteredNoti(filteredItem.id){ viewModel.loadFilteredNoti() } diff --git a/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationAppListView.kt b/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationAppListView.kt index 0a856b1..c9ac139 100644 --- a/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationAppListView.kt +++ b/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationAppListView.kt @@ -27,12 +27,14 @@ import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.Color +import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.text.font.FontWeight import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.dp import androidx.hilt.navigation.compose.hiltViewModel import androidx.navigation.NavController +import com.example.notimanager.R import com.example.notimanager.common.objects.DateFormatter.formatTimestamp import com.example.notimanager.domain.model.NotificationApp import com.example.notimanager.presentation.stateholder.state.NotificationAppPriorityState @@ -109,6 +111,15 @@ fun NotificationAppItemView( priorityViewModel: NotificationAppPriorityViewModel, filteredNotificationViewModel: FilteredNotificationViewModel = hiltViewModel() ) { + // 언어 변경에 따라 문자열 리소스를 가져오기 + val context = LocalContext.current + val addFiltered = context.getString(R.string.modal_add_filtered) + val addPriority = context.getString(R.string.modal_add_priority) + val removeFiltered = context.getString(R.string.modal_remove_filtered) + val removePriority = context.getString(R.string.modal_remove_priority) + val delete = context.getString(R.string.modal_delete) + // 위의 문자열 리소스는 모달에서 사용할 텍스트 + var showModal by remember { mutableStateOf(false) } Row( @@ -138,16 +149,18 @@ fun NotificationAppItemView( overflow = TextOverflow.Ellipsis ) Text( - text = formatTimestamp(notification.timestamp), + text = formatTimestamp(context, notification.timestamp), style = MaterialTheme.typography.labelSmall, color = Color.LightGray ) } - + + // 더보기 IconButton(onClick = { showModal = true }) { Icon(Icons.Filled.MoreVert, contentDescription = "중요 표시 또는 삭제") } } + // 더보기 클릭 시 나오는 모달창 if (showModal) { BottomSheet(showModal, onDismiss = { showModal = false }){ Column( @@ -155,13 +168,16 @@ fun NotificationAppItemView( .fillMaxWidth() .padding(16.dp) ) { + // 알림 제목 Text( text = notification.appName, style = MaterialTheme.typography.labelLarge, color = Color.Gray ) + + // 상단 고정 여부 버튼 if (notification.priorityActive) { - ClickableTextView(text = "중요 알림 취소", onClick = { + ClickableTextView(text = removePriority, onClick = { priorityViewModel.removeAppPriority(notification.appName){ viewModel.loadNotificationApps() } @@ -169,19 +185,22 @@ fun NotificationAppItemView( }) } else{ - ClickableTextView(text = "중요 알림 설정", onClick = { + ClickableTextView(text = addPriority, onClick = { viewModel.setAppPriority(notification.appName, priorityViewModel.getLength()){ priorityViewModel.loadNotificationAppPriority() } showModal = false }) } - ClickableTextView(text = "삭제", onClick = { + + // 삭제 버튼 + ClickableTextView(text = delete, onClick = { viewModel.deleteNotificationApp(notification.appName) showModal = false }) - ClickableTextView(text = if (notification.filteredId == 0L) "알림 제외 리스트에 추가" else "알림 제외 리스트에서 제거", onClick = { + // 수집 여부 버튼 + ClickableTextView(text = if (notification.filteredId == 0L) addFiltered else removeFiltered, onClick = { if (notification.filteredId == 0L) filteredNotificationViewModel.insertFilteredNoti(notification.appName, ""){ viewModel.loadNotificationApps() priorityViewModel.loadNotificationAppPriority() diff --git a/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationListView.kt b/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationListView.kt index 60b0a7c..4001a45 100644 --- a/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationListView.kt +++ b/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationListView.kt @@ -23,6 +23,7 @@ import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.text.font.FontWeight import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.unit.dp +import com.example.notimanager.R import com.example.notimanager.common.objects.DateFormatter.formatTimestamp import com.example.notimanager.domain.model.Notification import com.example.notimanager.presentation.stateholder.state.NotificationState @@ -62,6 +63,12 @@ fun NotificationItemView( onClick: () -> Unit, onDelete: (Long) -> Unit ) { + // 언어 변경에 따라 문자열 리소스를 가져오기 + val context = LocalContext.current + val moveToApp = context.getString(R.string.modal_move_to_app) + val delete = context.getString(R.string.modal_delete) + // 위의 문자열 리소스는 모달에서 사용할 텍스트 + var showModal by remember { mutableStateOf(false) } Row( modifier = Modifier @@ -85,7 +92,7 @@ fun NotificationItemView( style = MaterialTheme.typography.bodySmall ) Text( - text = formatTimestamp(notification.timestamp), + text = formatTimestamp(context, notification.timestamp), style = MaterialTheme.typography.labelSmall, color = Color.LightGray ) @@ -110,12 +117,12 @@ fun NotificationItemView( overflow = TextOverflow.Ellipsis, color = Color.Gray ) - ClickableTextView(text = "앱으로 이동", onClick = { + ClickableTextView(text = moveToApp, onClick = { onClick() showModal = false }) - ClickableTextView(text = "삭제", onClick = { + ClickableTextView(text = delete, onClick = { onDelete(notification.id) showModal = false }) diff --git a/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationTitleListView.kt b/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationTitleListView.kt index 3457126..8e56239 100644 --- a/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationTitleListView.kt +++ b/app/src/main/java/com/example/notimanager/presentation/ui/component/NotificationTitleListView.kt @@ -28,12 +28,14 @@ import androidx.compose.runtime.setValue import androidx.compose.ui.Alignment import androidx.compose.ui.Modifier import androidx.compose.ui.graphics.Color +import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.text.font.FontWeight import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.tooling.preview.Preview import androidx.compose.ui.unit.dp import androidx.hilt.navigation.compose.hiltViewModel import androidx.navigation.NavController +import com.example.notimanager.R import com.example.notimanager.common.objects.DateFormatter.formatTimestamp import com.example.notimanager.common.objects.Encoder.getEncodedString import com.example.notimanager.domain.model.NotificationTitle @@ -120,6 +122,15 @@ fun NotificationTitleItemView( priorityViewModel: NotificationTitlePriorityViewModel, filteredNotificationViewModel: FilteredNotificationViewModel = hiltViewModel() ) { + // 언어 변경에 따라 문자열 리소스를 가져오기 + val context = LocalContext.current + val addFiltered = context.getString(R.string.modal_add_filtered) + val addPriority = context.getString(R.string.modal_add_priority) + val removeFiltered = context.getString(R.string.modal_remove_filtered) + val removePriority = context.getString(R.string.modal_remove_priority) + val delete = context.getString(R.string.modal_delete) + // 위의 문자열 리소스는 모달에서 사용할 텍스트 + var showModal by remember { mutableStateOf(false) } Row( modifier = Modifier @@ -144,7 +155,7 @@ fun NotificationTitleItemView( overflow = TextOverflow.Ellipsis ) Text( - text = formatTimestamp(notification.timestamp), + text = formatTimestamp(context, notification.timestamp), style = MaterialTheme.typography.labelSmall, color = Color.LightGray ) @@ -174,7 +185,7 @@ fun NotificationTitleItemView( ) if (notification.priorityActive) { - ClickableTextView(text = "중요 알림 취소", onClick = { + ClickableTextView(text = removePriority, onClick = { priorityViewModel.removeTitlePriority(notificationId = notification.id){ viewModel.loadNotificationTitles() } @@ -182,7 +193,7 @@ fun NotificationTitleItemView( }) } else{ - ClickableTextView(text = "중요 알림 설정", onClick = { + ClickableTextView(text = addPriority, onClick = { viewModel.setTitlePriority(notification.id, priorityViewModel.getLength()){ priorityViewModel.loadNotificationTitles() } @@ -190,7 +201,7 @@ fun NotificationTitleItemView( }) } - ClickableTextView(text = "삭제", onClick = { + ClickableTextView(text = delete, onClick = { if (notification.subText == "") viewModel.deleteByTitle(notification.title) { priorityViewModel.loadNotificationTitles() } else @@ -205,7 +216,7 @@ fun NotificationTitleItemView( if(notification.filteredId == 0L) { ClickableTextView( - text = "이 방 알림 무시하기", + text = addFiltered, onClick = { if (notification.subText == "") { filteredNotificationViewModel.insertFilteredNoti( @@ -226,7 +237,7 @@ fun NotificationTitleItemView( ) }else{ ClickableTextView( - text = "이 방 알림 계속 받기", + text = removeFiltered, onClick = { if (notification.subText == "") filteredNotificationViewModel.deleteFilteredNoti(notification.filteredId, onComplete) diff --git a/app/src/main/java/com/example/notimanager/presentation/ui/component/PermissionDialog.kt b/app/src/main/java/com/example/notimanager/presentation/ui/component/PermissionDialog.kt index f7dd5ff..33e1c16 100644 --- a/app/src/main/java/com/example/notimanager/presentation/ui/component/PermissionDialog.kt +++ b/app/src/main/java/com/example/notimanager/presentation/ui/component/PermissionDialog.kt @@ -9,18 +9,23 @@ import androidx.compose.runtime.getValue import androidx.compose.runtime.livedata.observeAsState import androidx.compose.runtime.mutableStateOf import androidx.compose.runtime.remember +import androidx.compose.ui.platform.LocalContext import androidx.hilt.navigation.compose.hiltViewModel -import com.example.notimanager.presentation.stateholder.viewmodel.NotificationPermissionViewModel +import com.example.notimanager.R import com.example.notimanager.presentation.stateholder.viewmodel.NotificationServicePermissionViewModel @Composable fun PermissionCheck(viewModel: NotificationServicePermissionViewModel = hiltViewModel()){ + val context = LocalContext.current + val title = context.getString(R.string.permission_title) + val message = context.getString(R.string.permission_message) + val isPermissionGranted by viewModel.isNotificationServiceEnabled.observeAsState() if (isPermissionGranted == false) { SimplePermissionDialog( - title = "알림 권한 필요", - message = "알림을 받기 위해 알림 권한이 필요합니다.", + title = title, + message = message, onAllow = { viewModel.requestServicePermission() }, ) } @@ -32,6 +37,9 @@ fun SimplePermissionDialog( message: String, onAllow: () -> Unit ) { + val context = LocalContext.current + val ok = context.getString(R.string.permission_ok) + val openDialog = remember { mutableStateOf(true) } if (openDialog.value) { @@ -48,7 +56,7 @@ fun SimplePermissionDialog( onAllow() }) { - Text("허용") + Text(ok) } } ) diff --git a/app/src/main/java/com/example/notimanager/presentation/ui/component/SettingView.kt b/app/src/main/java/com/example/notimanager/presentation/ui/component/SettingView.kt index ff888d0..4f2d933 100644 --- a/app/src/main/java/com/example/notimanager/presentation/ui/component/SettingView.kt +++ b/app/src/main/java/com/example/notimanager/presentation/ui/component/SettingView.kt @@ -5,18 +5,22 @@ import androidx.compose.foundation.layout.PaddingValues import androidx.compose.foundation.layout.padding import androidx.compose.runtime.Composable import androidx.compose.ui.Modifier +import androidx.compose.ui.platform.LocalContext import androidx.navigation.NavController +import com.example.notimanager.R @Composable fun SettingView( innerPadding: PaddingValues, navController: NavController ){ + val context = LocalContext.current + val name = context.getString(R.string.setting_filtered_list) Column( modifier = Modifier .padding(innerPadding) ) { - ClickableTextView("알림 제외 리스트") { + ClickableTextView(name) { navController.navigate("FilteredListScreen") } } diff --git a/app/src/main/java/com/example/notimanager/presentation/ui/component/TopAppBar.kt b/app/src/main/java/com/example/notimanager/presentation/ui/component/TopAppBar.kt index b244c71..01947e3 100644 --- a/app/src/main/java/com/example/notimanager/presentation/ui/component/TopAppBar.kt +++ b/app/src/main/java/com/example/notimanager/presentation/ui/component/TopAppBar.kt @@ -3,7 +3,6 @@ package com.example.notimanager.presentation.ui.component import androidx.compose.material.icons.Icons import androidx.compose.material.icons.automirrored.filled.ArrowBack import androidx.compose.material.icons.filled.Menu -import androidx.compose.material.icons.filled.MoreVert import androidx.compose.material3.ExperimentalMaterial3Api import androidx.compose.material3.Icon import androidx.compose.material3.IconButton @@ -11,26 +10,26 @@ import androidx.compose.material3.MaterialTheme import androidx.compose.material3.Text import androidx.compose.material3.TopAppBar import androidx.compose.runtime.Composable +import androidx.compose.ui.platform.LocalContext import androidx.compose.ui.text.style.TextOverflow import androidx.compose.ui.tooling.preview.Preview +import com.example.notimanager.R @OptIn(ExperimentalMaterial3Api::class) @Composable fun MainTopAppBar(settingOnClick: () -> Unit){ + val context = LocalContext.current + val appName = context.getString(R.string.app_name) TopAppBar( title = { - Text(text = "Notification Manager") + Text(text = appName) }, navigationIcon = { IconButton(onClick = settingOnClick) { Icon(Icons.Filled.Menu, contentDescription = "설정") } - }, - actions = { - IconButton(onClick = { /* TODO: 클릭 이벤트 처리 */ }) { - Icon(Icons.Filled.MoreVert, contentDescription = "더 보기") - } - }) + } + ) } @OptIn(ExperimentalMaterial3Api::class) @@ -74,9 +73,11 @@ fun NotificationTopAppBar(title: String, onBackClick: () -> Unit){ @OptIn(ExperimentalMaterial3Api::class) @Composable fun SettingTopAppBar(onBackClick: () -> Unit){ + val context = LocalContext.current + val name = context.getString(R.string.setting_name) TopAppBar( title = { - Text(text = "설정") + Text(text = name) }, navigationIcon = { IconButton(onClick = onBackClick) { @@ -89,9 +90,11 @@ fun SettingTopAppBar(onBackClick: () -> Unit){ @OptIn(ExperimentalMaterial3Api::class) @Composable fun FilteredTopAppBar(onBackClick: () -> Unit){ + val context = LocalContext.current + val name = context.getString(R.string.setting_filtered_list) TopAppBar( title = { - Text(text = "알림 제외 리스트") + Text(text = name) }, navigationIcon = { IconButton(onClick = onBackClick) { diff --git a/app/src/main/res/values-ko/strings.xml b/app/src/main/res/values-ko/strings.xml new file mode 100644 index 0000000..9c04881 --- /dev/null +++ b/app/src/main/res/values-ko/strings.xml @@ -0,0 +1,43 @@ + + NotiManager + + + 삭제 + 앱으로 이동하기 + + 더 이상 알림 받지 않기 + 상단에 고정하기 + + 읽음으로 표시하기 + 읽지 않음으로 표시하기 + + 다시 알림 받기"> + 고정 취소하기 + + + 설정 + 받지 않는 알림 목록 + 언어 설정하기 + + + 확인 + 거부 + 알림 권한이 필요해요 + 알림을 받기 위해 알림 권한이 필요해요 + + + NotiManager + 모든 알림을 읽었어요. + %1$s개의 읽지 않은 알림이 있어요. + + + 방금 + %1$d초 전 + %1$d분 전 + %1$d시간 전 + %1$d일 전 + %1$d주 전 + %1$d달 전 + %1$d년 전 + + \ No newline at end of file diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 15b4d85..73f45e2 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -1,3 +1,43 @@ NotiManager + + + Delete + Move to App + + Stop Receiving Notifications + Pin to Top + + Mark as Read + Mark as Unread + + Start Receiving Notifications Again + Unpin + + + Settings + List of Notifications Not Received + Change Language + + + OK + Deny + Notification Permission Required + Notification permission is required to receive notifications. + + + NotiManager + All notifications have been read. + %1$s unread notifications. + + + Just now + %1$d seconds ago + %1$d minutes ago + %1$d hours ago + %1$d days ago + %1$d weeks ago + %1$d months ago + %1$d years ago + \ No newline at end of file