Loading app/src/main/java/io/heckel/ntfy/db/Repository.kt +2 −2 Original line number Diff line number Diff line Loading @@ -353,7 +353,7 @@ class Repository(private val sharedPrefs: SharedPreferences, private val databas } fun addLastShareTopic(topic: String) { val topics = (getLastShareTopics() + topic).takeLast(LAST_TOPICS_COUNT) val topics = (getLastShareTopics().filterNot { it == topic } + topic).takeLast(LAST_TOPICS_COUNT) sharedPrefs.edit() .putString(SHARED_PREFS_LAST_TOPICS, topics.joinToString(separator = "\n")) .apply() Loading Loading @@ -437,7 +437,7 @@ class Repository(private val sharedPrefs: SharedPreferences, private val databas const val SHARED_PREFS_UNIFIED_PUSH_BASE_URL = "UnifiedPushBaseURL" const val SHARED_PREFS_LAST_TOPICS = "LastTopics" private const val LAST_TOPICS_COUNT = 5 private const val LAST_TOPICS_COUNT = 3 const val MUTED_UNTIL_SHOW_ALL = 0L const val MUTED_UNTIL_FOREVER = 1L Loading app/src/main/java/io/heckel/ntfy/ui/MainAdapter.kt +0 −1 Original line number Diff line number Diff line Loading @@ -13,7 +13,6 @@ import io.heckel.ntfy.R import io.heckel.ntfy.db.ConnectionState import io.heckel.ntfy.db.Repository import io.heckel.ntfy.db.Subscription import io.heckel.ntfy.util.isDarkThemeOn import io.heckel.ntfy.util.topicShortUrl import java.text.DateFormat import java.util.* Loading app/src/main/java/io/heckel/ntfy/ui/ShareActivity.kt +58 −9 Original line number Diff line number Diff line Loading @@ -7,15 +7,15 @@ import android.os.Bundle import android.os.Parcelable import android.text.Editable import android.text.TextWatcher import android.view.Menu import android.view.MenuItem import android.view.View import android.view.* import android.widget.* import androidx.appcompat.app.AppCompatActivity import androidx.lifecycle.lifecycleScope import androidx.recyclerview.widget.RecyclerView import com.google.android.material.textfield.TextInputLayout import io.heckel.ntfy.R import io.heckel.ntfy.app.Application import io.heckel.ntfy.db.Subscription import io.heckel.ntfy.msg.ApiService import io.heckel.ntfy.util.* import kotlinx.coroutines.Dispatchers Loading @@ -31,6 +31,9 @@ class ShareActivity : AppCompatActivity() { // Lazy-loaded things from Repository private lateinit var baseUrls: List<String> // Context-dependent things private lateinit var appBaseUrl: String // UI elements private lateinit var menu: Menu private lateinit var sendItem: MenuItem Loading @@ -43,6 +46,7 @@ class ShareActivity : AppCompatActivity() { private lateinit var baseUrlLayout: TextInputLayout private lateinit var baseUrlText: AutoCompleteTextView private lateinit var useAnotherServerCheckbox: CheckBox private lateinit var lastTopicsList: RecyclerView private lateinit var progress: ProgressBar private lateinit var errorText: TextView private lateinit var errorImage: ImageView Loading @@ -60,6 +64,9 @@ class ShareActivity : AppCompatActivity() { // Show 'Back' button supportActionBar?.setDisplayHomeAsUpEnabled(true) // Context-dependent things appBaseUrl = getString(R.string.app_base_url) // UI elements contentText = findViewById(R.id.share_content_text) contentImage = findViewById(R.id.share_content_image) Loading @@ -73,6 +80,7 @@ class ShareActivity : AppCompatActivity() { baseUrlText = findViewById(R.id.share_base_url_text) //baseUrlText.background = topicText.background useAnotherServerCheckbox = findViewById(R.id.share_use_another_server_checkbox) lastTopicsList = findViewById(R.id.share_last_topics) progress = findViewById(R.id.share_progress) progress.visibility = View.GONE errorText = findViewById(R.id.share_error_text) Loading @@ -93,6 +101,7 @@ class ShareActivity : AppCompatActivity() { } contentText.addTextChangedListener(textWatcher) topicText.addTextChangedListener(textWatcher) baseUrlText.addTextChangedListener(textWatcher) // Add behavior to "use another" checkbox useAnotherServerCheckbox.setOnCheckedChangeListener { _, isChecked -> Loading @@ -100,9 +109,25 @@ class ShareActivity : AppCompatActivity() { validateInput() } // Populate "last topics" val reversedLastTopics = repository.getLastShareTopics().reversed() lastTopicsList.adapter = TopicAdapter(reversedLastTopics) { topicUrl -> try { val (baseUrl, topic) = splitTopicUrl(topicUrl) topicText.text = topic if (baseUrl == appBaseUrl) { useAnotherServerCheckbox.isChecked = false } else { useAnotherServerCheckbox.isChecked = true baseUrlText.setText(baseUrl) } } catch (e: Exception) { Log.w(TAG, "Invalid topicUrl $topicUrl", e) } } // Add baseUrl auto-complete behavior lifecycleScope.launch(Dispatchers.IO) { val appBaseUrl = getString(R.string.app_base_url) baseUrls = repository.getSubscriptions() .groupBy { it.baseUrl } .map { it.key } Loading @@ -111,13 +136,19 @@ class ShareActivity : AppCompatActivity() { val activity = this@ShareActivity activity.runOnUiThread { initBaseUrlDropdown(baseUrls, baseUrlText, baseUrlLayout) useAnotherServerCheckbox.isChecked = baseUrls.count() == 1 useAnotherServerCheckbox.isChecked = if (reversedLastTopics.isNotEmpty()) { try { val (baseUrl, _) = splitTopicUrl(reversedLastTopics.first()) baseUrl != appBaseUrl } catch (_: Exception) { false } } else { baseUrls.count() == 1 } baseUrlLayout.visibility = if (useAnotherServerCheckbox.isChecked) View.VISIBLE else View.GONE } } // Populate "last topics" val lastTopics = repository.getLastShareTopics() Log.d(TAG, "last topics: $lastTopics") // Incoming intent val intent = intent ?: return Loading Loading @@ -284,6 +315,24 @@ class ShareActivity : AppCompatActivity() { } } class TopicAdapter(private val topicUrls: List<String>, val onClick: (String) -> Unit) : RecyclerView.Adapter<TopicAdapter.ViewHolder>() { override fun onCreateViewHolder(viewGroup: ViewGroup, viewType: Int): ViewHolder { val view = LayoutInflater.from(viewGroup.context).inflate(R.layout.fragment_share_item, viewGroup, false) return ViewHolder(view) } override fun onBindViewHolder(viewHolder: ViewHolder, position: Int) { viewHolder.topicName.text = shortUrl(topicUrls[position]) viewHolder.view.setOnClickListener { onClick(topicUrls[position]) } } override fun getItemCount() = topicUrls.size class ViewHolder(val view: View) : RecyclerView.ViewHolder(view) { val topicName: TextView = view.findViewById(R.id.share_item_text) } } companion object { const val TAG = "NtfyShareActivity" } Loading app/src/main/java/io/heckel/ntfy/util/Util.kt +5 −0 Original line number Diff line number Diff line Loading @@ -44,6 +44,11 @@ fun shortUrl(url: String) = url .replace("http://", "") .replace("https://", "") fun splitTopicUrl(topicUrl: String): Pair<String, String> { if (topicUrl.lastIndexOf("/") == -1) throw Exception("Invalid argument $topicUrl") return Pair(topicUrl.substringBeforeLast("/"), topicUrl.substringAfterLast("/")) } fun validTopic(topic: String): Boolean { return "[-_A-Za-z0-9]{1,64}".toRegex().matches(topic) // Must match server side! } Loading app/src/main/res/layout/activity_share.xml +150 −143 Original line number Diff line number Diff line <?xml version="1.0" encoding="utf-8"?> <androidx.constraintlayout.widget.ConstraintLayout <ScrollView xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_height="match_parent"> <androidx.constraintlayout.widget.ConstraintLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="horizontal" android:paddingStart="15dp" android:paddingEnd="15dp" android:paddingTop="10dp" android:paddingBottom="10dp"> <ProgressBar Loading @@ -21,9 +24,9 @@ android:paddingBottom="2dp" android:text="@string/share_content_title" android:textAlignment="viewStart" android:textAppearance="@style/TextAppearance.AppCompat.Large" android:textAppearance="@style/TextAppearance.AppCompat.Medium" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toTopOf="parent" android:paddingStart="2dp"/> app:layout_constraintTop_toTopOf="parent"/> <com.google.android.material.imageview.ShapeableImageView android:layout_width="wrap_content" android:layout_height="wrap_content" app:srcCompat="@drawable/ic_cancel_gray_24dp" Loading Loading @@ -75,24 +78,24 @@ android:paddingBottom="3dp" android:text="@string/share_topic_title" android:textAlignment="viewStart" android:textAppearance="@style/TextAppearance.AppCompat.Large" android:textAppearance="@style/TextAppearance.AppCompat.Medium" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/share_content_file_box" android:layout_marginTop="15dp" android:paddingStart="2dp"/> app:layout_constraintTop_toBottomOf="@id/share_content_file_box" android:layout_marginTop="15dp"/> <com.google.android.material.textfield.TextInputEditText android:id="@+id/share_topic_text" android:layout_width="match_parent" android:layout_height="wrap_content" android:hint="@string/add_dialog_topic_name_hint" android:importantForAutofill="no" android:maxLines="1" android:inputType="text" android:maxLength="64" android:maxLines="1" android:inputType="text|textNoSuggestions" android:maxLength="64" app:layout_constraintStart_toStartOf="parent" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintTop_toBottomOf="@id/share_topic_title"/> app:layout_constraintTop_toBottomOf="@id/share_topic_title" android:layout_marginStart="-3dp"/> <CheckBox android:text="@string/add_dialog_use_another_server" android:layout_width="match_parent" android:layout_height="wrap_content" android:id="@+id/share_use_another_server_checkbox" android:layout_marginStart="-3dp" app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintTop_toBottomOf="@id/share_topic_text"/> app:layout_constraintTop_toBottomOf="@id/share_topic_text" android:paddingTop="-5dp" android:layout_marginTop="-5dp" android:layout_marginStart="-5dp"/> <com.google.android.material.textfield.TextInputLayout style="@style/Widget.MaterialComponents.TextInputLayout.FilledBox.Dense.ExposedDropdownMenu" android:id="@+id/share_base_url_layout" Loading @@ -100,29 +103,26 @@ android:layout_height="wrap_content" android:layout_margin="0dp" android:padding="0dp" android:visibility="gone" android:visibility="visible" app:endIconMode="custom" app:hintEnabled="false" app:boxBackgroundColor="@null" app:layout_constraintStart_toStartOf="parent" app:boxBackgroundColor="@null" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintTop_toBottomOf="@id/share_use_another_server_checkbox"> app:layout_constraintTop_toBottomOf="@id/share_use_another_server_checkbox" app:layout_constraintStart_toStartOf="parent" android:layout_marginTop="-5dp"> <AutoCompleteTextView android:layout_width="match_parent" android:layout_height="wrap_content" android:id="@+id/share_base_url_text" android:hint="@string/app_base_url" android:maxLines="1" android:layout_marginTop="0dp" android:layout_marginTop="-5dp" android:layout_marginBottom="0dp" android:inputType="textNoSuggestions" android:inputType="textUri|textNoSuggestions" android:paddingStart="0dp" android:paddingEnd="0dp" android:paddingTop="5dp" android:paddingBottom="5dp" android:layout_marginStart="4dp" android:layout_marginEnd="4dp" android:textAppearance="?android:attr/textAppearanceMedium" /> android:layout_marginStart="4dp" android:textAppearance="@style/TextAppearance.AppCompat.Medium"/> </com.google.android.material.textfield.TextInputLayout> <TextView android:id="@+id/share_last_title" Loading @@ -132,13 +132,19 @@ android:paddingBottom="3dp" android:text="@string/share_previous_topics" android:textAlignment="viewStart" android:textAppearance="@style/TextAppearance.AppCompat.Large" android:paddingStart="2dp" app:layout_constraintTop_toBottomOf="@id/share_base_url_layout" app:layout_constraintStart_toStartOf="parent" android:layout_marginTop="15dp"/> <LinearLayout android:orientation="vertical" android:layout_width="0dp" android:layout_height="wrap_content" android:id="@+id/share_last_layout" app:layout_constraintTop_toBottomOf="@id/share_last_title" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintStart_toStartOf="parent" android:layout_marginTop="5dp"> </LinearLayout> android:textAppearance="@style/TextAppearance.AppCompat.Medium" app:layout_constraintTop_toBottomOf="@id/share_base_url_layout" app:layout_constraintStart_toStartOf="parent" android:layout_marginTop="15dp"/> <androidx.recyclerview.widget.RecyclerView android:layout_width="match_parent" android:layout_height="0dp" android:id="@+id/share_last_topics" app:layout_constraintTop_toBottomOf="@id/share_last_title" app:layout_constraintStart_toStartOf="parent" app:layout_constraintEnd_toEndOf="parent" android:clickable="true" android:focusable="true" android:background="?android:attr/selectableItemBackground" app:layoutManager="LinearLayoutManager"/> <TextView android:text="Unable to resolve host example.com" android:layout_width="0dp" Loading @@ -148,7 +154,7 @@ android:paddingEnd="4dp" android:textAppearance="@style/DangerText" app:layout_constraintStart_toEndOf="@id/share_error_image" android:layout_marginTop="10dp" app:layout_constraintTop_toBottomOf="@id/share_last_title"/> android:layout_marginTop="10dp" app:layout_constraintTop_toBottomOf="@id/share_last_topics"/> <ImageView android:layout_width="20dp" android:layout_height="20dp" app:srcCompat="@drawable/ic_error_red_24dp" Loading @@ -157,3 +163,4 @@ app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toTopOf="@+id/share_error_text" android:layout_marginTop="2dp"/> </androidx.constraintlayout.widget.ConstraintLayout> </ScrollView> Loading
app/src/main/java/io/heckel/ntfy/db/Repository.kt +2 −2 Original line number Diff line number Diff line Loading @@ -353,7 +353,7 @@ class Repository(private val sharedPrefs: SharedPreferences, private val databas } fun addLastShareTopic(topic: String) { val topics = (getLastShareTopics() + topic).takeLast(LAST_TOPICS_COUNT) val topics = (getLastShareTopics().filterNot { it == topic } + topic).takeLast(LAST_TOPICS_COUNT) sharedPrefs.edit() .putString(SHARED_PREFS_LAST_TOPICS, topics.joinToString(separator = "\n")) .apply() Loading Loading @@ -437,7 +437,7 @@ class Repository(private val sharedPrefs: SharedPreferences, private val databas const val SHARED_PREFS_UNIFIED_PUSH_BASE_URL = "UnifiedPushBaseURL" const val SHARED_PREFS_LAST_TOPICS = "LastTopics" private const val LAST_TOPICS_COUNT = 5 private const val LAST_TOPICS_COUNT = 3 const val MUTED_UNTIL_SHOW_ALL = 0L const val MUTED_UNTIL_FOREVER = 1L Loading
app/src/main/java/io/heckel/ntfy/ui/MainAdapter.kt +0 −1 Original line number Diff line number Diff line Loading @@ -13,7 +13,6 @@ import io.heckel.ntfy.R import io.heckel.ntfy.db.ConnectionState import io.heckel.ntfy.db.Repository import io.heckel.ntfy.db.Subscription import io.heckel.ntfy.util.isDarkThemeOn import io.heckel.ntfy.util.topicShortUrl import java.text.DateFormat import java.util.* Loading
app/src/main/java/io/heckel/ntfy/ui/ShareActivity.kt +58 −9 Original line number Diff line number Diff line Loading @@ -7,15 +7,15 @@ import android.os.Bundle import android.os.Parcelable import android.text.Editable import android.text.TextWatcher import android.view.Menu import android.view.MenuItem import android.view.View import android.view.* import android.widget.* import androidx.appcompat.app.AppCompatActivity import androidx.lifecycle.lifecycleScope import androidx.recyclerview.widget.RecyclerView import com.google.android.material.textfield.TextInputLayout import io.heckel.ntfy.R import io.heckel.ntfy.app.Application import io.heckel.ntfy.db.Subscription import io.heckel.ntfy.msg.ApiService import io.heckel.ntfy.util.* import kotlinx.coroutines.Dispatchers Loading @@ -31,6 +31,9 @@ class ShareActivity : AppCompatActivity() { // Lazy-loaded things from Repository private lateinit var baseUrls: List<String> // Context-dependent things private lateinit var appBaseUrl: String // UI elements private lateinit var menu: Menu private lateinit var sendItem: MenuItem Loading @@ -43,6 +46,7 @@ class ShareActivity : AppCompatActivity() { private lateinit var baseUrlLayout: TextInputLayout private lateinit var baseUrlText: AutoCompleteTextView private lateinit var useAnotherServerCheckbox: CheckBox private lateinit var lastTopicsList: RecyclerView private lateinit var progress: ProgressBar private lateinit var errorText: TextView private lateinit var errorImage: ImageView Loading @@ -60,6 +64,9 @@ class ShareActivity : AppCompatActivity() { // Show 'Back' button supportActionBar?.setDisplayHomeAsUpEnabled(true) // Context-dependent things appBaseUrl = getString(R.string.app_base_url) // UI elements contentText = findViewById(R.id.share_content_text) contentImage = findViewById(R.id.share_content_image) Loading @@ -73,6 +80,7 @@ class ShareActivity : AppCompatActivity() { baseUrlText = findViewById(R.id.share_base_url_text) //baseUrlText.background = topicText.background useAnotherServerCheckbox = findViewById(R.id.share_use_another_server_checkbox) lastTopicsList = findViewById(R.id.share_last_topics) progress = findViewById(R.id.share_progress) progress.visibility = View.GONE errorText = findViewById(R.id.share_error_text) Loading @@ -93,6 +101,7 @@ class ShareActivity : AppCompatActivity() { } contentText.addTextChangedListener(textWatcher) topicText.addTextChangedListener(textWatcher) baseUrlText.addTextChangedListener(textWatcher) // Add behavior to "use another" checkbox useAnotherServerCheckbox.setOnCheckedChangeListener { _, isChecked -> Loading @@ -100,9 +109,25 @@ class ShareActivity : AppCompatActivity() { validateInput() } // Populate "last topics" val reversedLastTopics = repository.getLastShareTopics().reversed() lastTopicsList.adapter = TopicAdapter(reversedLastTopics) { topicUrl -> try { val (baseUrl, topic) = splitTopicUrl(topicUrl) topicText.text = topic if (baseUrl == appBaseUrl) { useAnotherServerCheckbox.isChecked = false } else { useAnotherServerCheckbox.isChecked = true baseUrlText.setText(baseUrl) } } catch (e: Exception) { Log.w(TAG, "Invalid topicUrl $topicUrl", e) } } // Add baseUrl auto-complete behavior lifecycleScope.launch(Dispatchers.IO) { val appBaseUrl = getString(R.string.app_base_url) baseUrls = repository.getSubscriptions() .groupBy { it.baseUrl } .map { it.key } Loading @@ -111,13 +136,19 @@ class ShareActivity : AppCompatActivity() { val activity = this@ShareActivity activity.runOnUiThread { initBaseUrlDropdown(baseUrls, baseUrlText, baseUrlLayout) useAnotherServerCheckbox.isChecked = baseUrls.count() == 1 useAnotherServerCheckbox.isChecked = if (reversedLastTopics.isNotEmpty()) { try { val (baseUrl, _) = splitTopicUrl(reversedLastTopics.first()) baseUrl != appBaseUrl } catch (_: Exception) { false } } else { baseUrls.count() == 1 } baseUrlLayout.visibility = if (useAnotherServerCheckbox.isChecked) View.VISIBLE else View.GONE } } // Populate "last topics" val lastTopics = repository.getLastShareTopics() Log.d(TAG, "last topics: $lastTopics") // Incoming intent val intent = intent ?: return Loading Loading @@ -284,6 +315,24 @@ class ShareActivity : AppCompatActivity() { } } class TopicAdapter(private val topicUrls: List<String>, val onClick: (String) -> Unit) : RecyclerView.Adapter<TopicAdapter.ViewHolder>() { override fun onCreateViewHolder(viewGroup: ViewGroup, viewType: Int): ViewHolder { val view = LayoutInflater.from(viewGroup.context).inflate(R.layout.fragment_share_item, viewGroup, false) return ViewHolder(view) } override fun onBindViewHolder(viewHolder: ViewHolder, position: Int) { viewHolder.topicName.text = shortUrl(topicUrls[position]) viewHolder.view.setOnClickListener { onClick(topicUrls[position]) } } override fun getItemCount() = topicUrls.size class ViewHolder(val view: View) : RecyclerView.ViewHolder(view) { val topicName: TextView = view.findViewById(R.id.share_item_text) } } companion object { const val TAG = "NtfyShareActivity" } Loading
app/src/main/java/io/heckel/ntfy/util/Util.kt +5 −0 Original line number Diff line number Diff line Loading @@ -44,6 +44,11 @@ fun shortUrl(url: String) = url .replace("http://", "") .replace("https://", "") fun splitTopicUrl(topicUrl: String): Pair<String, String> { if (topicUrl.lastIndexOf("/") == -1) throw Exception("Invalid argument $topicUrl") return Pair(topicUrl.substringBeforeLast("/"), topicUrl.substringAfterLast("/")) } fun validTopic(topic: String): Boolean { return "[-_A-Za-z0-9]{1,64}".toRegex().matches(topic) // Must match server side! } Loading
app/src/main/res/layout/activity_share.xml +150 −143 Original line number Diff line number Diff line <?xml version="1.0" encoding="utf-8"?> <androidx.constraintlayout.widget.ConstraintLayout <ScrollView xmlns:android="http://schemas.android.com/apk/res/android" xmlns:app="http://schemas.android.com/apk/res-auto" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" android:layout_height="match_parent"> <androidx.constraintlayout.widget.ConstraintLayout android:layout_width="match_parent" android:layout_height="wrap_content" android:orientation="horizontal" android:paddingStart="15dp" android:paddingEnd="15dp" android:paddingTop="10dp" android:paddingBottom="10dp"> <ProgressBar Loading @@ -21,9 +24,9 @@ android:paddingBottom="2dp" android:text="@string/share_content_title" android:textAlignment="viewStart" android:textAppearance="@style/TextAppearance.AppCompat.Large" android:textAppearance="@style/TextAppearance.AppCompat.Medium" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toTopOf="parent" android:paddingStart="2dp"/> app:layout_constraintTop_toTopOf="parent"/> <com.google.android.material.imageview.ShapeableImageView android:layout_width="wrap_content" android:layout_height="wrap_content" app:srcCompat="@drawable/ic_cancel_gray_24dp" Loading Loading @@ -75,24 +78,24 @@ android:paddingBottom="3dp" android:text="@string/share_topic_title" android:textAlignment="viewStart" android:textAppearance="@style/TextAppearance.AppCompat.Large" android:textAppearance="@style/TextAppearance.AppCompat.Medium" app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toBottomOf="@id/share_content_file_box" android:layout_marginTop="15dp" android:paddingStart="2dp"/> app:layout_constraintTop_toBottomOf="@id/share_content_file_box" android:layout_marginTop="15dp"/> <com.google.android.material.textfield.TextInputEditText android:id="@+id/share_topic_text" android:layout_width="match_parent" android:layout_height="wrap_content" android:hint="@string/add_dialog_topic_name_hint" android:importantForAutofill="no" android:maxLines="1" android:inputType="text" android:maxLength="64" android:maxLines="1" android:inputType="text|textNoSuggestions" android:maxLength="64" app:layout_constraintStart_toStartOf="parent" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintTop_toBottomOf="@id/share_topic_title"/> app:layout_constraintTop_toBottomOf="@id/share_topic_title" android:layout_marginStart="-3dp"/> <CheckBox android:text="@string/add_dialog_use_another_server" android:layout_width="match_parent" android:layout_height="wrap_content" android:id="@+id/share_use_another_server_checkbox" android:layout_marginStart="-3dp" app:layout_constraintStart_toStartOf="parent" app:layout_constraintStart_toStartOf="parent" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintTop_toBottomOf="@id/share_topic_text"/> app:layout_constraintTop_toBottomOf="@id/share_topic_text" android:paddingTop="-5dp" android:layout_marginTop="-5dp" android:layout_marginStart="-5dp"/> <com.google.android.material.textfield.TextInputLayout style="@style/Widget.MaterialComponents.TextInputLayout.FilledBox.Dense.ExposedDropdownMenu" android:id="@+id/share_base_url_layout" Loading @@ -100,29 +103,26 @@ android:layout_height="wrap_content" android:layout_margin="0dp" android:padding="0dp" android:visibility="gone" android:visibility="visible" app:endIconMode="custom" app:hintEnabled="false" app:boxBackgroundColor="@null" app:layout_constraintStart_toStartOf="parent" app:boxBackgroundColor="@null" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintTop_toBottomOf="@id/share_use_another_server_checkbox"> app:layout_constraintTop_toBottomOf="@id/share_use_another_server_checkbox" app:layout_constraintStart_toStartOf="parent" android:layout_marginTop="-5dp"> <AutoCompleteTextView android:layout_width="match_parent" android:layout_height="wrap_content" android:id="@+id/share_base_url_text" android:hint="@string/app_base_url" android:maxLines="1" android:layout_marginTop="0dp" android:layout_marginTop="-5dp" android:layout_marginBottom="0dp" android:inputType="textNoSuggestions" android:inputType="textUri|textNoSuggestions" android:paddingStart="0dp" android:paddingEnd="0dp" android:paddingTop="5dp" android:paddingBottom="5dp" android:layout_marginStart="4dp" android:layout_marginEnd="4dp" android:textAppearance="?android:attr/textAppearanceMedium" /> android:layout_marginStart="4dp" android:textAppearance="@style/TextAppearance.AppCompat.Medium"/> </com.google.android.material.textfield.TextInputLayout> <TextView android:id="@+id/share_last_title" Loading @@ -132,13 +132,19 @@ android:paddingBottom="3dp" android:text="@string/share_previous_topics" android:textAlignment="viewStart" android:textAppearance="@style/TextAppearance.AppCompat.Large" android:paddingStart="2dp" app:layout_constraintTop_toBottomOf="@id/share_base_url_layout" app:layout_constraintStart_toStartOf="parent" android:layout_marginTop="15dp"/> <LinearLayout android:orientation="vertical" android:layout_width="0dp" android:layout_height="wrap_content" android:id="@+id/share_last_layout" app:layout_constraintTop_toBottomOf="@id/share_last_title" app:layout_constraintEnd_toEndOf="parent" app:layout_constraintStart_toStartOf="parent" android:layout_marginTop="5dp"> </LinearLayout> android:textAppearance="@style/TextAppearance.AppCompat.Medium" app:layout_constraintTop_toBottomOf="@id/share_base_url_layout" app:layout_constraintStart_toStartOf="parent" android:layout_marginTop="15dp"/> <androidx.recyclerview.widget.RecyclerView android:layout_width="match_parent" android:layout_height="0dp" android:id="@+id/share_last_topics" app:layout_constraintTop_toBottomOf="@id/share_last_title" app:layout_constraintStart_toStartOf="parent" app:layout_constraintEnd_toEndOf="parent" android:clickable="true" android:focusable="true" android:background="?android:attr/selectableItemBackground" app:layoutManager="LinearLayoutManager"/> <TextView android:text="Unable to resolve host example.com" android:layout_width="0dp" Loading @@ -148,7 +154,7 @@ android:paddingEnd="4dp" android:textAppearance="@style/DangerText" app:layout_constraintStart_toEndOf="@id/share_error_image" android:layout_marginTop="10dp" app:layout_constraintTop_toBottomOf="@id/share_last_title"/> android:layout_marginTop="10dp" app:layout_constraintTop_toBottomOf="@id/share_last_topics"/> <ImageView android:layout_width="20dp" android:layout_height="20dp" app:srcCompat="@drawable/ic_error_red_24dp" Loading @@ -157,3 +163,4 @@ app:layout_constraintStart_toStartOf="parent" app:layout_constraintTop_toTopOf="@+id/share_error_text" android:layout_marginTop="2dp"/> </androidx.constraintlayout.widget.ConstraintLayout> </ScrollView>