Deleted old fragment + xml

Added string res
Fixed bug with embedded date picker boundaries, animated size change

Signed-off-by: rapterjet2004 <juliuslinus1@gmail.com>
This commit is contained in:
rapterjet2004 2024-12-19 09:24:57 -06:00 committed by Marcel Hibbe
parent eae4e43ab2
commit 63cb98ece7
No known key found for this signature in database
GPG Key ID: C793F8B59F43CE7B
4 changed files with 21 additions and 549 deletions

View File

@ -3504,8 +3504,6 @@ class ChatActivity :
val chatApiVersion = ApiUtils.getChatApiVersion(spreedCapabilities, intArrayOf(ApiUtils.API_V1, 1))
// val newFragment: DialogFragment = DateTimePickerFragment.newInstance(roomToken, message!!.id, chatApiVersion)
// newFragment.show(supportFragmentManager, DateTimePickerFragment.TAG)
val bundle = bundleOf()
bundle.putString(KEY_ROOM_TOKEN, roomToken)
bundle.putString(BundleKeys.KEY_MESSAGE_ID, message!!.id)

View File

@ -9,6 +9,7 @@ package com.nextcloud.talk.ui.dialog
import android.content.Context
import android.os.Bundle
import androidx.compose.animation.animateContentSize
import androidx.compose.foundation.clickable
import androidx.compose.foundation.layout.Arrangement
import androidx.compose.foundation.layout.Column
@ -37,20 +38,19 @@ import androidx.compose.material3.rememberTimePickerState
import androidx.compose.runtime.Composable
import androidx.compose.runtime.MutableState
import androidx.compose.runtime.collectAsState
import androidx.compose.runtime.getValue
import androidx.compose.runtime.mutableStateOf
import androidx.compose.runtime.remember
import androidx.compose.runtime.setValue
import androidx.compose.ui.Alignment
import androidx.compose.ui.Modifier
import androidx.compose.ui.draw.scale
import androidx.compose.ui.graphics.Color
import androidx.compose.ui.graphics.vector.ImageVector
import androidx.compose.ui.res.stringResource
import androidx.compose.ui.unit.dp
import androidx.compose.ui.window.Dialog
import androidx.compose.ui.window.DialogProperties
import androidx.lifecycle.asFlow
import autodagger.AutoInjector
import com.nextcloud.talk.R
import com.nextcloud.talk.application.NextcloudTalkApplication
import com.nextcloud.talk.chat.viewmodels.ChatViewModel
import com.nextcloud.talk.ui.theme.ViewThemeUtils
@ -95,6 +95,7 @@ class DateTimeCompose(val bundle: Bundle) {
}
val colorScheme = viewThemeUtils.getColorScheme(context)
val isCollapsed = remember { mutableStateOf(true) }
MaterialTheme(colorScheme = colorScheme) {
Dialog(
@ -103,11 +104,13 @@ class DateTimeCompose(val bundle: Bundle) {
},
properties = DialogProperties(
dismissOnBackPress = true,
dismissOnClickOutside = true
dismissOnClickOutside = true,
usePlatformDefaultWidth = isCollapsed.value
)
) {
Surface(
shape = RoundedCornerShape(8.dp),
modifier = Modifier.animateContentSize()
) {
Column(
modifier = Modifier
@ -116,7 +119,7 @@ class DateTimeCompose(val bundle: Bundle) {
) {
Header()
Body()
CollapsableDateTime(shouldDismiss)
CollapsableDateTime(shouldDismiss, isCollapsed)
}
}
}
@ -206,7 +209,7 @@ class DateTimeCompose(val bundle: Bundle) {
if (currTime < laterToday) {
TimeOption(
label = "Later Today",
label = stringResource(R.string.later_today),
timeString = laterTodayStr
) {
timeState.value = laterToday
@ -215,7 +218,7 @@ class DateTimeCompose(val bundle: Bundle) {
if (tomorrow.dayOfWeek < DayOfWeek.SATURDAY) {
TimeOption(
label = "Tomorrow",
label = stringResource(R.string.tomorrow),
timeString = tomorrowStr
) {
timeState.value = tomorrow
@ -224,7 +227,7 @@ class DateTimeCompose(val bundle: Bundle) {
if (currTime.dayOfWeek < DayOfWeek.SATURDAY) {
TimeOption(
label = "This weekend",
label = stringResource(R.string.this_weekend),
timeString = thisWeekendStr
) {
timeState.value = thisWeekend
@ -232,7 +235,7 @@ class DateTimeCompose(val bundle: Bundle) {
}
TimeOption(
label = "Next weekend",
label = stringResource(R.string.next_week),
timeString = nextWeekStr
) {
timeState.value = nextWeek
@ -247,8 +250,8 @@ class DateTimeCompose(val bundle: Bundle) {
modifier = Modifier
.padding(8.dp)
) {
Text("Remind Me Later")
Spacer(modifier = Modifier.width(32.dp))
Text("Remind Me Later", modifier = Modifier.weight(1f))
// Spacer(modifier = Modifier.width(32.dp))
val reminderState = chatViewModel.getReminderExistState
.asFlow()
@ -271,30 +274,28 @@ class DateTimeCompose(val bundle: Bundle) {
@OptIn(ExperimentalMaterial3Api::class)
@Composable
private fun CollapsableDateTime(shouldDismiss: MutableState<Boolean>) {
var isCollapsed by remember { mutableStateOf(true) }
GeneralIconButton(icon = Icons.Filled.DateRange, label = "Custom") { isCollapsed = !isCollapsed }
private fun CollapsableDateTime(shouldDismiss: MutableState<Boolean>, isCollapsed: MutableState<Boolean>) {
GeneralIconButton(icon = Icons.Filled.DateRange, label = "Custom") { isCollapsed.value = !isCollapsed.value }
val scrollState = rememberScrollState()
Column(
horizontalAlignment = Alignment.CenterHorizontally,
modifier = Modifier.verticalScroll(scrollState)
) {
if (!isCollapsed) {
if (!isCollapsed.value) {
val datePickerState = rememberDatePickerState()
val timePickerState = rememberTimePickerState()
DatePicker(
state = datePickerState,
modifier = Modifier.scale(0.9f)
)
TimePicker(
state = timePickerState,
modifier = Modifier.scale(0.9f)
)
val date = datePickerState.selectedDateMillis?.let {
// FIXME check out the offset logic here
// it works, i think. Need to test it out. I'm not sure if I'm missing something
LocalDateTime.ofEpochSecond(it / 1000, 0, ZoneOffset.ofTotalSeconds(0))
val instant = Instant.ofEpochMilli(it)
LocalDateTime.ofInstant(instant, ZoneOffset.UTC) // Google sends time in UTC
}
if (date != null) {
val year = date.year

View File

@ -1,315 +0,0 @@
/*
* Nextcloud Talk - Android Client
*
* SPDX-FileCopyrightText: 2023 Julius Linus <julius.linus@nextcloud.com>
* SPDX-License-Identifier: GPL-3.0-or-later
*/
package com.nextcloud.talk.ui.dialog
import android.app.Dialog
import android.os.Bundle
import android.text.format.DateFormat
import android.text.format.DateUtils
import android.view.LayoutInflater
import android.view.View
import android.view.ViewGroup
import androidx.fragment.app.DialogFragment
import autodagger.AutoInjector
import com.google.android.material.datepicker.CalendarConstraints
import com.google.android.material.datepicker.DateValidatorPointForward
import com.google.android.material.datepicker.MaterialDatePicker
import com.google.android.material.dialog.MaterialAlertDialogBuilder
import com.google.android.material.timepicker.MaterialTimePicker
import com.google.android.material.timepicker.TimeFormat
import com.nextcloud.android.common.ui.theme.utils.ColorRole
import com.nextcloud.talk.R
import com.nextcloud.talk.application.NextcloudTalkApplication
import com.nextcloud.talk.chat.ChatActivity
import com.nextcloud.talk.chat.viewmodels.ChatViewModel
import com.nextcloud.talk.databinding.DialogDateTimePickerBinding
import com.nextcloud.talk.ui.theme.ViewThemeUtils
import com.nextcloud.talk.users.UserManager
import java.util.Calendar
import java.util.TimeZone
import javax.inject.Inject
@Suppress("TooManyFunctions")
@AutoInjector(NextcloudTalkApplication::class)
class DateTimePickerFragment : DialogFragment() {
lateinit var binding: DialogDateTimePickerBinding
private var dialogView: View? = null
private lateinit var viewModel: ChatViewModel
private var currentTimeStamp: Long? = null
private lateinit var roomToken: String
private lateinit var messageId: String
private var chatApiVersion: Int = -1
private var laterTodayTimeStamp = 0L
private var tomorrowTimeStamp = 0L
private var weekendTimeStamp = 0L
private var nextWeekTimeStamp = 0L
@Inject
lateinit var userManager: UserManager
@Inject
lateinit var viewThemeUtils: ViewThemeUtils
override fun onCreateDialog(savedInstanceState: Bundle?): Dialog {
binding = DialogDateTimePickerBinding.inflate(layoutInflater)
dialogView = binding.root
viewModel = (requireActivity() as ChatActivity).chatViewModel
arguments?.let {
roomToken = it.getString(TOKEN_ARG, "")
messageId = it.getString(ID_ARG, "")
chatApiVersion = it.getInt(CHAT_API_VERSION_ARG)
}
return MaterialAlertDialogBuilder(requireContext()).setView(dialogView).create()
}
override fun onCreateView(inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle?): View? {
NextcloudTalkApplication.sharedApplication!!.componentApplication.inject(this)
setUpDefaults()
setUpColors()
setListeners()
getReminder()
viewModel.getReminderExistState.observe(this) { state ->
when (state) {
is ChatViewModel.GetReminderExistState -> {
val timeStamp = state.reminder.timestamp?.toLong()?.times(ONE_SEC)
showDelete(true)
setTimeStamp(getTimeFromTimeStamp(timeStamp!!))
}
else -> {
showDelete(false)
binding.dateTimePickerTimestamp.text = ""
}
}
}
return inflater.inflate(R.layout.dialog_date_time_picker, container, false)
}
private fun setUpDefaults() {
val currTime = getTimeFromCalendar()
val currentWeekInYear = Calendar.getInstance().get(Calendar.WEEK_OF_YEAR)
laterTodayTimeStamp = getTimeFromCalendar(hour = HOUR_SIX_PM, minute = 0)
binding.dateTimePickerLaterTodayTextview.text = getTimeFromTimeStamp(laterTodayTimeStamp)
if (Calendar.getInstance().get(Calendar.DAY_OF_WEEK) == Calendar.SATURDAY) {
tomorrowTimeStamp = getTimeFromCalendar(
hour = HOUR_EIGHT_AM,
minute = 0,
daysToAdd = 1
)
binding.dateTimePickerWeekend.visibility = View.GONE // because today is the weekend
} else {
tomorrowTimeStamp = getTimeFromCalendar(hour = HOUR_EIGHT_AM, minute = 0, daysToAdd = 1)
weekendTimeStamp = getTimeFromCalendar(hour = HOUR_EIGHT_AM, weekDay = Calendar.SATURDAY, minute = 0)
}
binding.dateTimePickerTomorrowTextview.text = getTimeFromTimeStamp(tomorrowTimeStamp)
binding.dateTimePickerWeekendTextview.text = getTimeFromTimeStamp(weekendTimeStamp)
nextWeekTimeStamp = getTimeFromCalendar(
hour = HOUR_EIGHT_AM,
weekDay = Calendar.MONDAY,
minute = 0,
weekInYear =
currentWeekInYear + 1
) // this should only pick mondays from next week only
binding.dateTimePickerNextWeekTextview.text = getTimeFromTimeStamp(nextWeekTimeStamp)
// This is to hide the later today option, if it's past 6pm
if (currTime > laterTodayTimeStamp) {
binding.dateTimePickerLaterToday.visibility = View.GONE
}
// This is to hide the tomorrow option, if that's also the weekend
if (binding.dateTimePickerTomorrowTextview.text == binding.dateTimePickerWeekendTextview.text) {
binding.dateTimePickerTomorrow.visibility = View.GONE
}
}
private fun getReminder() {
viewModel.getReminder(userManager.currentUser.blockingGet(), roomToken, messageId, chatApiVersion)
}
private fun showDelete(value: Boolean) {
if (value) {
binding.buttonDelete.visibility = View.VISIBLE
} else {
binding.buttonDelete.visibility = View.GONE
}
}
private fun setUpColors() {
binding.root.let {
viewThemeUtils.platform.colorViewBackground(it)
}
binding.dateTimePickerCustomIcon.let {
viewThemeUtils.platform.colorImageView(it, ColorRole.PRIMARY)
}
binding.dateTimePickerTimestamp.let {
viewThemeUtils.material.themeSearchBarText(it)
}
binding.run {
listOf(
binding.buttonClose,
binding.buttonSet
)
}.forEach(viewThemeUtils.material::colorMaterialButtonPrimaryBorderless)
}
private fun setListeners() {
binding.dateTimePickerLaterToday.setOnClickListener {
currentTimeStamp = laterTodayTimeStamp / ONE_SEC
setTimeStamp(getTimeFromTimeStamp(laterTodayTimeStamp))
}
binding.dateTimePickerTomorrow.setOnClickListener {
currentTimeStamp = tomorrowTimeStamp / ONE_SEC
setTimeStamp(getTimeFromTimeStamp(tomorrowTimeStamp))
}
binding.dateTimePickerWeekend.setOnClickListener {
currentTimeStamp = weekendTimeStamp / ONE_SEC
setTimeStamp(getTimeFromTimeStamp(weekendTimeStamp))
}
binding.dateTimePickerNextWeek.setOnClickListener {
currentTimeStamp = nextWeekTimeStamp / ONE_SEC
setTimeStamp(getTimeFromTimeStamp(nextWeekTimeStamp))
}
binding.dateTimePickerCustom.setOnClickListener {
val constraintsBuilder = CalendarConstraints.Builder()
.setValidator(DateValidatorPointForward.now())
.build()
val time = System.currentTimeMillis()
val datePicker = MaterialDatePicker.Builder.datePicker()
.setTitleText(R.string.nc_remind)
.setSelection(time + TimeZone.getDefault().getOffset(time))
.setCalendarConstraints(constraintsBuilder).build()
datePicker.addOnPositiveButtonClickListener { selection ->
val localTimeInMillis = selection - TimeZone.getDefault().getOffset(selection)
val calendar = Calendar.getInstance()
calendar.timeInMillis = localTimeInMillis
val year = calendar.get(Calendar.YEAR)
val month = calendar.get(Calendar.MONTH)
val day = calendar.get(Calendar.DAY_OF_YEAR)
setUpTimePicker(year, month, day)
}
datePicker.show(this.parentFragmentManager, TAG)
}
binding.buttonClose.setOnClickListener { dismiss() }
binding.buttonSet.setOnClickListener {
currentTimeStamp?.let { time ->
viewModel.setReminder(
userManager.currentUser.blockingGet(),
roomToken,
messageId,
time.toInt(),
chatApiVersion
)
}
dismiss()
}
binding.buttonDelete.setOnClickListener {
viewModel.deleteReminder(userManager.currentUser.blockingGet(), roomToken, messageId, chatApiVersion)
}
}
private fun setUpTimePicker(year: Int, month: Int, day: Int) {
val locale = if (DateFormat.is24HourFormat(requireContext())) TimeFormat.CLOCK_24H else TimeFormat.CLOCK_12H
val timePicker = MaterialTimePicker.Builder()
.setTitleText(R.string.nc_remind)
.setTimeFormat(locale)
.build()
timePicker.addOnPositiveButtonClickListener {
val timestamp = getTimeFromCalendar(
year,
month,
day,
timePicker.hour,
timePicker.minute
)
setTimeStamp(getTimeFromTimeStamp(timestamp))
currentTimeStamp = timestamp / ONE_SEC
}
timePicker.show(this.parentFragmentManager, TAG)
}
/**
* You can use `weekDay` or `daysToAdd` or neither but don't use both b/c it messes up the calendar
*/
@Suppress("LongParameterList")
private fun getTimeFromCalendar(
year: Int = Calendar.getInstance().get(Calendar.YEAR),
month: Int = Calendar.getInstance().get(Calendar.MONTH),
day: Int = Calendar.getInstance().get(Calendar.DAY_OF_YEAR),
hour: Int = Calendar.getInstance().get(Calendar.HOUR_OF_DAY),
minute: Int = Calendar.getInstance().get(Calendar.MINUTE),
daysToAdd: Int = 0,
weekInYear: Int = -1,
weekDay: Int = -1
): Long {
val calendar: Calendar = Calendar.getInstance().apply {
set(Calendar.YEAR, year)
set(Calendar.MONTH, month)
set(Calendar.DAY_OF_YEAR, day)
if (weekDay > -1) set(Calendar.DAY_OF_WEEK, weekDay)
if (daysToAdd > 0) add(Calendar.DAY_OF_YEAR, daysToAdd)
if (weekInYear != -1) set(Calendar.WEEK_OF_YEAR, weekInYear)
set(Calendar.HOUR_OF_DAY, hour)
set(Calendar.MINUTE, minute)
set(Calendar.SECOND, 0)
}
return calendar.timeInMillis
}
private fun setTimeStamp(date: String) {
binding.dateTimePickerTimestamp.text = date
}
private fun getTimeFromTimeStamp(time: Long): String {
return DateUtils.formatDateTime(
requireContext(),
time,
DateUtils.FORMAT_SHOW_DATE
) + ", " + DateUtils.formatDateTime(
requireContext(),
time,
DateUtils.FORMAT_SHOW_TIME
)
}
companion object {
val TAG = DateTimePickerFragment::class.simpleName
private const val ONE_SEC = 1000
private const val HOUR_EIGHT_AM = 8
private const val HOUR_SIX_PM = 18
private const val TOKEN_ARG = "TOKEN_ARG"
private const val ID_ARG = "ID_ARG"
private const val CHAT_API_VERSION_ARG = "CHAT_API_VERSION_ARG"
@JvmStatic
fun newInstance(token: String, id: String, chatApiVersion: Int): DateTimePickerFragment {
val args = Bundle()
args.putString(TOKEN_ARG, token)
args.putString(ID_ARG, id)
args.putInt(CHAT_API_VERSION_ARG, chatApiVersion)
val dateTimePickerFragment = DateTimePickerFragment()
dateTimePickerFragment.arguments = args
return dateTimePickerFragment
}
}
}

View File

@ -1,212 +0,0 @@
<?xml version="1.0" encoding="utf-8"?>
<!--
~ Nextcloud Talk - Android Client
~
~ SPDX-FileCopyrightText: 2023 Julius Linus <julius.linus@nextcloud.com>
~ SPDX-License-Identifier: GPL-3.0-or-later
-->
<ScrollView xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:orientation="vertical"
tools:background="@color/white">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="vertical">
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:layout_margin="@dimen/standard_margin"
android:orientation="horizontal">
<com.google.android.material.textview.MaterialTextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="@string/nc_remind"
android:textSize="@dimen/md_title_textsize" />
<com.google.android.material.textview.MaterialTextView
android:id="@+id/date_time_picker_timestamp"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:textSize="@dimen/supporting_text_text_size"
android:textStyle="bold"
tools:text="Apr 15th, 8:00 AM" />
</LinearLayout>
<com.google.android.material.divider.MaterialDivider
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<LinearLayout
android:id="@+id/date_time_picker_later_today"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?android:attr/selectableItemBackground"
android:orientation="horizontal"
android:padding="@dimen/standard_padding">
<com.google.android.material.textview.MaterialTextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="@string/later_today"
android:textSize="@dimen/headline_text_size" />
<com.google.android.material.textview.MaterialTextView
android:id="@+id/date_time_picker_later_today_textview"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text=""
android:textSize="@dimen/headline_text_size" />
</LinearLayout>
<LinearLayout
android:id="@+id/date_time_picker_tomorrow"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?android:attr/selectableItemBackground"
android:orientation="horizontal"
android:padding="@dimen/standard_padding">
<com.google.android.material.textview.MaterialTextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="@string/tomorrow"
android:textSize="@dimen/headline_text_size" />
<com.google.android.material.textview.MaterialTextView
android:id="@+id/date_time_picker_tomorrow_textview"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text=""
android:textSize="@dimen/headline_text_size" />
</LinearLayout>
<LinearLayout
android:id="@+id/date_time_picker_weekend"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?android:attr/selectableItemBackground"
android:orientation="horizontal"
android:padding="@dimen/standard_padding">
<com.google.android.material.textview.MaterialTextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="@string/this_weekend"
android:textSize="@dimen/headline_text_size" />
<com.google.android.material.textview.MaterialTextView
android:id="@+id/date_time_picker_weekend_textview"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text=""
android:textSize="@dimen/headline_text_size" />
</LinearLayout>
<LinearLayout
android:id="@+id/date_time_picker_next_week"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?android:attr/selectableItemBackground"
android:orientation="horizontal"
android:padding="@dimen/standard_padding">
<com.google.android.material.textview.MaterialTextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="@string/next_week"
android:textSize="@dimen/headline_text_size" />
<com.google.android.material.textview.MaterialTextView
android:id="@+id/date_time_picker_next_week_textview"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text=""
android:textSize="@dimen/headline_text_size" />
</LinearLayout>
<com.google.android.material.divider.MaterialDivider
android:layout_width="match_parent"
android:layout_height="wrap_content" />
<LinearLayout
android:id="@+id/date_time_picker_custom"
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:background="?android:attr/selectableItemBackground"
android:orientation="horizontal"
android:padding="@dimen/standard_padding">
<ImageView
android:id="@+id/date_time_picker_custom_icon"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:contentDescription="@string/calendar"
android:paddingEnd="@dimen/standard_double_padding"
android:src="@drawable/baseline_calendar_month_24"
tools:ignore="RtlSymmetry" />
<com.google.android.material.textview.MaterialTextView
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:text="@string/custom"
android:textSize="@dimen/headline_text_size" />
</LinearLayout>
<LinearLayout
android:layout_width="match_parent"
android:layout_height="wrap_content"
android:orientation="horizontal">
<LinearLayout
android:layout_width="0dp"
android:layout_height="wrap_content"
android:layout_weight="1"
android:orientation="vertical">
<com.google.android.material.button.MaterialButton
android:id="@+id/button_delete"
style="@style/Button.Borderless"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:minHeight="@dimen/min_size_clickable_area"
android:text="@string/nc_delete"
android:textColor="@color/design_default_color_error" />
</LinearLayout>
<com.google.android.material.button.MaterialButton
android:id="@+id/button_set"
style="@style/Button.Borderless"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:minHeight="@dimen/min_size_clickable_area"
android:text="@string/set" />
<com.google.android.material.button.MaterialButton
android:id="@+id/button_close"
style="@style/Button.Borderless"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_gravity="end"
android:minHeight="@dimen/min_size_clickable_area"
android:text="@string/close" />
</LinearLayout>
</LinearLayout>
</ScrollView>