Skip to content
This repository was archived by the owner on Dec 18, 2022. It is now read-only.

Commit 25c525a

Browse files
committed
implement recycler view in IsolationFlagsFragment
1 parent 131cd0a commit 25c525a

File tree

2 files changed

+183
-17
lines changed

2 files changed

+183
-17
lines changed

sampleapp/src/main/java/io/matthewnelson/sampleapp/ui/fragments/settings/tor/IsolationFlagsFragment.kt

Lines changed: 126 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -66,31 +66,37 @@
6666
* */
6767
package io.matthewnelson.sampleapp.ui.fragments.settings.tor
6868

69+
import android.content.Context
6970
import android.os.Bundle
7071
import android.view.LayoutInflater
7172
import android.view.View
7273
import android.view.ViewGroup
7374
import android.widget.Button
75+
import android.widget.CheckBox
7476
import android.widget.LinearLayout
77+
import android.widget.TextView
7578
import androidx.activity.OnBackPressedCallback
7679
import androidx.constraintlayout.widget.ConstraintLayout
7780
import androidx.core.view.marginTop
7881
import androidx.fragment.app.Fragment
82+
import androidx.recyclerview.widget.LinearLayoutManager
83+
import androidx.recyclerview.widget.RecyclerView
7984
import io.matthewnelson.sampleapp.R
80-
import io.matthewnelson.topl_service.service.components.onionproxy.ServiceTorSettings
81-
85+
import io.matthewnelson.topl_core_base.BaseConsts.IsolationFlag
86+
import io.matthewnelson.topl_core_base.TorSettings
8287

8388
class IsolationFlagsFragment(
8489
private val bottomMarginAdjust: Int,
85-
private val flagType: String,
86-
private val serviceTorSettings: ServiceTorSettings
90+
private val portType: String,
91+
private val defaultTorSettings: TorSettings,
92+
private val enabledIsolationFlags: MutableSet<@IsolationFlag String>
8793
) : Fragment() {
8894

8995
companion object {
90-
const val SOCKS_FLAGS = "SOCKS_FLAGS"
91-
const val HTTP_FLAGS = "HTTP_FLAGS"
92-
const val DNS_FLAGS = "DNS_FLAGS"
93-
const val TRANS_FLAGS = "TRANS_FLAGS"
96+
const val SOCKS_FLAGS = "Socks Isolation Flags"
97+
const val HTTP_FLAGS = "HTTP Isolation Flags"
98+
const val DNS_FLAGS = "DNS Isolation Flags"
99+
const val TRANS_FLAGS = "Trans Isolation Flags"
94100
}
95101

96102
private val backPressHandler = BackPressHandler(true)
@@ -100,6 +106,9 @@ class IsolationFlagsFragment(
100106
private lateinit var layoutEnd: LinearLayout
101107
private lateinit var layoutStart: LinearLayout
102108
private lateinit var layoutConstraintInner: ConstraintLayout
109+
private lateinit var buttonReset: Button
110+
private lateinit var recyclerView: RecyclerView
111+
private lateinit var isolationFlagsAdapter: IsolationFlagsAdapter
103112

104113
override fun onCreateView(
105114
inflater: LayoutInflater,
@@ -115,7 +124,9 @@ class IsolationFlagsFragment(
115124
override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
116125
super.onViewCreated(view, savedInstanceState)
117126
findViews(view)
127+
setResetButtonText()
118128
setMargins()
129+
initRecyclerView(view.context)
119130
setClickListeners()
120131
enableParentViews(false)
121132
}
@@ -131,6 +142,23 @@ class IsolationFlagsFragment(
131142
layoutEnd = view.findViewById(R.id.isolation_flags_layout_end)
132143
layoutStart = view.findViewById(R.id.isolation_flags_layout_start)
133144
layoutConstraintInner = view.findViewById(R.id.isolation_flags_layout_constraint_inner)
145+
recyclerView = view.findViewById(R.id.recycler_view_isolation_flags)
146+
buttonReset = view.findViewById(R.id.isolation_flags_button_reset)
147+
}
148+
149+
private fun setResetButtonText() {
150+
when (portType) {
151+
// SOCKS_FLAGS is default string
152+
HTTP_FLAGS -> {
153+
buttonReset.text = getString(R.string.isolation_fragment_reset_http)
154+
}
155+
DNS_FLAGS -> {
156+
buttonReset.text = getString(R.string.isolation_fragment_reset_dns)
157+
}
158+
TRANS_FLAGS -> {
159+
buttonReset.text = getString(R.string.isolation_fragment_reset_trans)
160+
}
161+
}
134162
}
135163

136164
private fun setMargins() {
@@ -142,23 +170,38 @@ class IsolationFlagsFragment(
142170
}
143171
}
144172

173+
private fun initRecyclerView(context: Context) {
174+
isolationFlagsAdapter = IsolationFlagsAdapter()
175+
recyclerView.apply {
176+
setHasFixedSize(true)
177+
layoutManager = LinearLayoutManager(context)
178+
adapter = isolationFlagsAdapter
179+
}
180+
}
181+
145182
private fun setClickListeners() {
146183
layoutTop.setOnClickListener {
147-
removeFragment(true)
184+
removeFragment()
148185
}
149186
layoutBottom.setOnClickListener {
150-
removeFragment(true)
187+
removeFragment()
151188
}
152189
layoutEnd.setOnClickListener {
153-
removeFragment(true)
190+
removeFragment()
154191
}
155192
layoutStart.setOnClickListener {
156-
removeFragment(true)
193+
removeFragment()
194+
}
195+
buttonReset.setOnClickListener {
196+
isolationFlagsAdapter.resetToDefaults()
197+
isolationFlagsAdapter.notifyDataSetChanged()
157198
}
158199
}
159200

160-
private fun removeFragment(saveData: Boolean) {
161-
// TODO: Save Data
201+
private fun removeFragment() {
202+
parentFragment?.let {
203+
(it as SettingsTorFragment).setIsolationFlags(portType, enabledIsolationFlags.toList())
204+
}
162205
parentFragmentManager.beginTransaction().apply {
163206
remove(this@IsolationFlagsFragment)
164207
commit()
@@ -177,10 +220,77 @@ class IsolationFlagsFragment(
177220
}
178221

179222
private inner class BackPressHandler(enable: Boolean): OnBackPressedCallback(enable) {
180-
181223
override fun handleOnBackPressed() {
182-
removeFragment(false)
224+
removeFragment()
225+
}
226+
}
227+
228+
private inner class IsolationFlagsAdapter: RecyclerView.Adapter<IsolationFlagsAdapter.IsolationFlagHolder>() {
229+
230+
private val items = IsolationFlag.getAll()
231+
232+
fun resetToDefaults() {
233+
enabledIsolationFlags.clear()
234+
when (portType) {
235+
SOCKS_FLAGS -> {
236+
defaultTorSettings.socksPortIsolationFlags?.let {
237+
enabledIsolationFlags.addAll(it)
238+
}
239+
}
240+
HTTP_FLAGS -> {
241+
defaultTorSettings.httpTunnelPortIsolationFlags?.let {
242+
enabledIsolationFlags.addAll(it)
243+
}
244+
}
245+
DNS_FLAGS -> {
246+
defaultTorSettings.dnsPortIsolationFlags?.let {
247+
enabledIsolationFlags.addAll(it)
248+
}
249+
}
250+
TRANS_FLAGS -> {
251+
defaultTorSettings.transPortIsolationFlags?.let {
252+
enabledIsolationFlags.addAll(it)
253+
}
254+
}
255+
}
256+
}
257+
258+
inner class IsolationFlagHolder(view: View): RecyclerView.ViewHolder(view)
259+
260+
override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): IsolationFlagHolder {
261+
val view = LayoutInflater.from(parent.context).inflate(R.layout.holder_isolation_flag, parent, false)
262+
return IsolationFlagHolder(view)
263+
}
264+
265+
override fun getItemCount(): Int {
266+
return items.size
183267
}
184268

269+
override fun onBindViewHolder(holder: IsolationFlagHolder, position: Int) {
270+
val isolationFlag = items[position]
271+
val layout = holder.itemView.findViewById<ConstraintLayout>(R.id.holder_isolation_flag_layout_constraint)
272+
val textView = holder.itemView.findViewById<TextView>(R.id.holder_isolation_flag_text_view)
273+
val checkBox = holder.itemView.findViewById<CheckBox>(R.id.holder_isolation_flag_check_box)
274+
275+
textView.text = isolationFlag
276+
checkBox.isChecked = enabledIsolationFlags.contains(isolationFlag)
277+
278+
checkBox.setOnClickListener {
279+
clicked(isolationFlag, checkBox)
280+
}
281+
layout.setOnClickListener {
282+
clicked(isolationFlag, checkBox)
283+
}
284+
}
285+
286+
private fun clicked(@IsolationFlag isolationFlag: String, checkBox: CheckBox) {
287+
if (enabledIsolationFlags.contains(isolationFlag)) {
288+
enabledIsolationFlags.remove(isolationFlag)
289+
checkBox.isChecked = false
290+
} else {
291+
enabledIsolationFlags.add(isolationFlag)
292+
checkBox.isChecked = true
293+
}
294+
}
185295
}
186296
}

sampleapp/src/main/java/io/matthewnelson/sampleapp/ui/fragments/settings/tor/SettingsTorFragment.kt

Lines changed: 57 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -82,6 +82,8 @@ import io.matthewnelson.sampleapp.ui.fragments.settings.CloseKeyBoardNavListener
8282
import io.matthewnelson.sampleapp.ui.fragments.settings.tor.components.DnsPortOption
8383
import io.matthewnelson.sampleapp.ui.fragments.settings.tor.components.HttpPortOption
8484
import io.matthewnelson.sampleapp.ui.fragments.settings.tor.components.SocksPortOption
85+
import io.matthewnelson.sampleapp.ui.fragments.settings.tor.components.TransPortOption
86+
import io.matthewnelson.topl_core_base.BaseConsts.IsolationFlag
8587
import io.matthewnelson.topl_service.TorServiceController
8688
import io.matthewnelson.topl_service.service.components.onionproxy.ServiceTorSettings
8789

@@ -127,12 +129,54 @@ class SettingsTorFragment : Fragment() {
127129

128130
findViews(view)
129131
setButtonClickListener(view)
132+
initIsolationFlags()
130133
}
131134

132135
override fun onDestroyView() {
133136
super.onDestroyView()
134137
}
135138

139+
private val socksIsolationFlags = mutableListOf<@IsolationFlag String>()
140+
private val httpIsolationFlags = mutableListOf<@IsolationFlag String>()
141+
private val dnsIsolationFlags = mutableListOf<@IsolationFlag String>()
142+
// private val transIsolationFlags = mutableListOf<@IsolationFlag String>()
143+
144+
fun setIsolationFlags(portType: String, selectedList: List<@IsolationFlag String>) {
145+
when (portType) {
146+
IsolationFlagsFragment.SOCKS_FLAGS -> {
147+
socksIsolationFlags.clear()
148+
socksIsolationFlags.addAll(selectedList)
149+
}
150+
IsolationFlagsFragment.HTTP_FLAGS -> {
151+
httpIsolationFlags.clear()
152+
httpIsolationFlags.addAll(selectedList)
153+
}
154+
IsolationFlagsFragment.DNS_FLAGS -> {
155+
dnsIsolationFlags.clear()
156+
dnsIsolationFlags.addAll(selectedList)
157+
}
158+
// IsolationFlagsFragment.TRANS_FLAGS -> {
159+
// transIsolationFlags.clear()
160+
// transIsolationFlags.addAll(selectedList)
161+
// }
162+
}
163+
}
164+
165+
private fun initIsolationFlags() {
166+
serviceTorSettings.socksPortIsolationFlags?.let {
167+
setIsolationFlags(IsolationFlagsFragment.SOCKS_FLAGS, it)
168+
}
169+
serviceTorSettings.httpTunnelPortIsolationFlags?.let {
170+
setIsolationFlags(IsolationFlagsFragment.HTTP_FLAGS, it)
171+
}
172+
serviceTorSettings.dnsPortIsolationFlags?.let {
173+
setIsolationFlags(IsolationFlagsFragment.DNS_FLAGS, it)
174+
}
175+
// serviceTorSettings.transPortIsolationFlags?.let {
176+
// setIsolationFlags(IsolationFlagsFragment.TRANS_FLAGS, it)
177+
// }
178+
}
179+
136180
private fun findViews(view: View) {
137181
buttonSocksFlags = view.findViewById(R.id.settings_tor_button_socks_isolation_flags)
138182
buttonHttpFlags = view.findViewById(R.id.settings_tor_button_http_isolation_flags)
@@ -160,6 +204,11 @@ class SettingsTorFragment : Fragment() {
160204
dnsPortOption.saveDnsPort() ?: return@setOnClickListener
161205
// transPortOption.saveTransPort() ?: return@setOnClickListener
162206

207+
serviceTorSettings.socksPortIsolationFlagsSave(socksIsolationFlags)
208+
serviceTorSettings.httpPortIsolationFlagsSave(httpIsolationFlags)
209+
serviceTorSettings.dnsPortIsolationFlagsSave(dnsIsolationFlags)
210+
// serviceTorSettings.transPortIsolationFlagsSave(transIsolationFlags)
211+
163212
DashboardFragment.showMessage(
164213
DashMessage("Settings Saved\nTor may need to be restarted", R.drawable.dash_message_color_green, 4_000L)
165214
)
@@ -185,7 +234,14 @@ class SettingsTorFragment : Fragment() {
185234
IsolationFlagsFragment(
186235
saveButtonHeight,
187236
portType,
188-
serviceTorSettings
237+
serviceTorSettings.defaultTorSettings,
238+
when (portType) {
239+
IsolationFlagsFragment.SOCKS_FLAGS -> socksIsolationFlags.toMutableSet()
240+
IsolationFlagsFragment.HTTP_FLAGS -> httpIsolationFlags.toMutableSet()
241+
IsolationFlagsFragment.DNS_FLAGS -> dnsIsolationFlags.toMutableSet()
242+
// IsolationFlagsFragment.TRANS_FLAGS -> transIsolationFlags.toMutableSet()
243+
else -> return
244+
}
189245
)
190246
)
191247
commit()

0 commit comments

Comments
 (0)