Skip to content

Commit af4b7f8

Browse files
committed
Implemented UI settings for password generator.
1 parent 07e14b7 commit af4b7f8

File tree

12 files changed

+515
-167
lines changed

12 files changed

+515
-167
lines changed

app/src/main/java/com/ladsers/passtable/android/activities/PasswordGeneratorActivity.kt

Lines changed: 188 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,14 +2,27 @@ package com.ladsers.passtable.android.activities
22

33
import android.content.Intent
44
import android.os.Bundle
5+
import android.view.KeyEvent
6+
import android.view.View
7+
import android.view.inputmethod.InputMethodManager
8+
import android.widget.EditText
9+
import android.widget.TextView
10+
import android.widget.Toast
511
import androidx.appcompat.app.AppCompatActivity
612
import androidx.core.content.ContextCompat
13+
import androidx.core.widget.doAfterTextChanged
714
import com.ladsers.passtable.android.R
815
import com.ladsers.passtable.android.components.PasswordGeneratorProcessor
16+
import com.ladsers.passtable.android.containers.Param
17+
import com.ladsers.passtable.android.containers.ParamStorage
918
import com.ladsers.passtable.android.databinding.ActivityPasswordGeneratorBinding
19+
import com.ladsers.passtable.android.databinding.PasswordGeneratorCollectionBinding
20+
import com.ladsers.passtable.android.widgets.EditTextParam
21+
import com.ladsers.passtable.lib.PasswordGenerator
1022

1123
class PasswordGeneratorActivity : AppCompatActivity() {
1224
private lateinit var binding: ActivityPasswordGeneratorBinding
25+
private lateinit var generator: PasswordGenerator
1326

1427
override fun onCreate(savedInstanceState: Bundle?) {
1528
super.onCreate(savedInstanceState)
@@ -27,10 +40,185 @@ class PasswordGeneratorActivity : AppCompatActivity() {
2740
if (y == 0) binding.toolbar.root.elevation = 0f
2841
}
2942

43+
generator = PasswordGenerator()
44+
45+
configureEditParamInt(
46+
binding.passwordLength.editText,
47+
binding.passwordLength.textView,
48+
Param.GENERATOR_PASSWORD_LENGTH
49+
)
50+
configureEditParamExclude()
51+
52+
configureCollection(
53+
binding.lowercaseLetters,
54+
R.string.ui_ct_lowercaseLetters,
55+
Param.GENERATOR_LOWERCASE_LETTERS_ALLOW,
56+
Param.GENERATOR_LOWERCASE_LETTERS_MINIMUM
57+
)
58+
configureCollection(
59+
binding.capitalLetters,
60+
R.string.ui_ct_capitalLetters,
61+
Param.GENERATOR_CAPITAL_LETTERS_ALLOW,
62+
Param.GENERATOR_CAPITAL_LETTERS_MINIMUM
63+
)
64+
configureCollection(
65+
binding.numbers,
66+
R.string.ui_ct_numbers,
67+
Param.GENERATOR_NUMBERS_ALLOW,
68+
Param.GENERATOR_NUMBERS_MINIMUM
69+
)
70+
configureCollection(
71+
binding.symbols,
72+
R.string.ui_ct_symbols,
73+
Param.GENERATOR_SYMBOLS_ALLOW,
74+
Param.GENERATOR_SYMBOLS_MINIMUM
75+
)
76+
3077
binding.btOk.setOnClickListener {
3178
val intent = Intent().putExtra(PasswordGeneratorProcessor.ResultKey, "some test string")
3279
setResult(RESULT_OK, intent)
3380
finish()
3481
}
3582
}
83+
84+
override fun onResume() {
85+
super.onResume()
86+
87+
val imm = getSystemService(INPUT_METHOD_SERVICE) as InputMethodManager
88+
89+
fun resetEditText(editText: EditText) {
90+
editText.clearFocus()
91+
imm.hideSoftInputFromWindow(editText.windowToken, 0)
92+
}
93+
94+
resetEditText(binding.passwordLength.editText)
95+
resetEditText(binding.exclude.editText)
96+
97+
resetEditText(binding.lowercaseLetters.etMinimumNumber)
98+
resetEditText(binding.capitalLetters.etMinimumNumber)
99+
resetEditText(binding.numbers.etMinimumNumber)
100+
resetEditText(binding.symbols.etMinimumNumber)
101+
}
102+
103+
private fun configureCollection(
104+
bin: PasswordGeneratorCollectionBinding,
105+
collectionNameResId: Int,
106+
paramAllow: Param,
107+
paramMinimum: Param
108+
) {
109+
bin.swCollectionAllow.text = getString(collectionNameResId)
110+
bin.swCollectionAllow.isChecked = ParamStorage.getBool(this, paramAllow)
111+
112+
bin.tvMinimumNumber.isClickable = bin.swCollectionAllow.isChecked
113+
bin.etMinimumNumber.isEnabled = bin.swCollectionAllow.isChecked
114+
115+
bin.swCollectionAllow.setOnCheckedChangeListener { _, isChecked ->
116+
ParamStorage.set(this, paramAllow, isChecked)
117+
bin.tvMinimumNumber.isClickable = isChecked
118+
bin.etMinimumNumber.isEnabled = isChecked
119+
120+
if (paramAllow == Param.GENERATOR_SYMBOLS_ALLOW) {
121+
bin.rbBasicSet.isEnabled = isChecked
122+
bin.rbFullSet.isEnabled = isChecked
123+
}
124+
125+
generate()
126+
}
127+
128+
configureEditParamInt(bin.etMinimumNumber, bin.tvMinimumNumber, paramMinimum)
129+
130+
if (paramAllow != Param.GENERATOR_SYMBOLS_ALLOW) return
131+
132+
bin.rbSymbolSet.visibility = View.VISIBLE
133+
bin.rbBasicSet.text = getString(
134+
R.string.ui_ct_basicSet,
135+
generator.easySymbolChars.joinToString(separator = " ")
136+
)
137+
bin.rbBasicSet.isEnabled = bin.swCollectionAllow.isChecked
138+
bin.rbFullSet.isEnabled = bin.swCollectionAllow.isChecked
139+
when (ParamStorage.getInt(this, Param.GENERATOR_SYMBOLS_SET)) {
140+
0 -> bin.rbBasicSet.isChecked = true
141+
1 -> bin.rbFullSet.isChecked = true
142+
}
143+
144+
bin.rbBasicSet.setOnCheckedChangeListener { _, isChecked ->
145+
if (!isChecked) return@setOnCheckedChangeListener
146+
ParamStorage.set(this, Param.GENERATOR_SYMBOLS_SET, 0)
147+
generate()
148+
}
149+
bin.rbFullSet.setOnCheckedChangeListener { _, isChecked ->
150+
if (!isChecked) return@setOnCheckedChangeListener
151+
ParamStorage.set(this, Param.GENERATOR_SYMBOLS_SET, 1)
152+
generate()
153+
}
154+
}
155+
156+
private fun configureEditParamInt(editText: EditTextParam, labelView: TextView, param: Param) {
157+
editText.setText(ParamStorage.getInt(this, param).toString())
158+
159+
val imm = getSystemService(INPUT_METHOD_SERVICE) as InputMethodManager
160+
161+
labelView.setOnClickListener {
162+
editText.requestFocus()
163+
imm.showSoftInput(editText, 0)
164+
}
165+
166+
editText.setOnKeyListener { v, keyCode, _ ->
167+
if (keyCode == KeyEvent.KEYCODE_ENTER) {
168+
imm.hideSoftInputFromWindow(v.windowToken, 0)
169+
170+
if (editText.text.toString().isNotEmpty()) {
171+
ParamStorage.set(this, param, editText.text.toString().toInt())
172+
generate()
173+
}
174+
v.clearFocus()
175+
return@setOnKeyListener true
176+
}
177+
return@setOnKeyListener false
178+
}
179+
editText.doAfterTextChanged { x ->
180+
if (x!!.length > 1 && x.toString().startsWith('0')) {
181+
editText.setText(x.toString().drop(1))
182+
editText.setSelection(1)
183+
}
184+
}
185+
editText.setOnFocusChangeListener { _, hasFocus ->
186+
if (hasFocus) return@setOnFocusChangeListener
187+
editText.setText(ParamStorage.getInt(this, param).toString())
188+
}
189+
}
190+
191+
private fun configureEditParamExclude() {
192+
val bin = binding.exclude
193+
bin.editText.setText(ParamStorage.getStr(this, Param.GENERATOR_EXCLUDE))
194+
val imm = getSystemService(INPUT_METHOD_SERVICE) as InputMethodManager
195+
196+
bin.textView.setOnClickListener {
197+
bin.editText.requestFocus()
198+
imm.showSoftInput(bin.editText, 0)
199+
}
200+
201+
bin.editText.setOnKeyListener { v, keyCode, _ ->
202+
if (keyCode == KeyEvent.KEYCODE_ENTER) {
203+
imm.hideSoftInputFromWindow(v.windowToken, 0)
204+
ParamStorage.set(this, Param.GENERATOR_EXCLUDE, bin.editText.text.toString())
205+
generate()
206+
v.clearFocus()
207+
return@setOnKeyListener true
208+
}
209+
return@setOnKeyListener false
210+
}
211+
bin.editText.setOnFocusChangeListener { _, hasFocus ->
212+
if (hasFocus) Toast.makeText(
213+
this,
214+
R.string.ui_msg_enterCharsInRowOrSpace,
215+
Toast.LENGTH_LONG
216+
).show()
217+
else bin.editText.setText(ParamStorage.getStr(this, Param.GENERATOR_EXCLUDE))
218+
}
219+
}
220+
221+
private fun generate() {
222+
223+
}
36224
}

app/src/main/java/com/ladsers/passtable/android/components/settingsModules/LockFileSettingsModule.kt

Lines changed: 7 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -52,17 +52,11 @@ class LockFileSettingsModule(
5252
ParamStorage.set(activity, Param.LOCK_MODE, 1)
5353
binding.lockFile.swLockAllowWhenEditing.isEnabled = true
5454
binding.lockFile.etLockSecs.isEnabled = false
55-
binding.lockFile.etLockSecs.setText(
56-
ParamStorage.getInt(activity, Param.LOCK_SECS).toString()
57-
)
5855
}
5956
binding.lockFile.rbLockModeNever.setOnClickListener {
6057
ParamStorage.set(activity, Param.LOCK_MODE, 2)
6158
binding.lockFile.swLockAllowWhenEditing.isEnabled = false
6259
binding.lockFile.etLockSecs.isEnabled = false
63-
binding.lockFile.etLockSecs.setText(
64-
ParamStorage.getInt(activity, Param.LOCK_SECS).toString()
65-
)
6660
}
6761
binding.lockFile.swLockAllowWhenEditing.setOnCheckedChangeListener { _, isChecked ->
6862
ParamStorage.set(activity, Param.LOCK_ALLOW_WHEN_EDITING, isChecked)
@@ -76,7 +70,6 @@ class LockFileSettingsModule(
7670

7771
binding.lockFile.etLockSecs.setOnKeyListener { v, keyCode, _ ->
7872
if (keyCode == KeyEvent.KEYCODE_ENTER) {
79-
v.clearFocus()
8073
val imm =
8174
activity.getSystemService(AppCompatActivity.INPUT_METHOD_SERVICE) as InputMethodManager
8275
imm.hideSoftInputFromWindow(v.windowToken, 0)
@@ -86,23 +79,23 @@ class LockFileSettingsModule(
8679
Param.LOCK_SECS,
8780
binding.lockFile.etLockSecs.text.toString().toInt()
8881
)
89-
else binding.lockFile.etLockSecs.setText(
90-
ParamStorage.getInt(activity, Param.LOCK_SECS).toString()
91-
)
92-
82+
v.clearFocus()
9383
return@setOnKeyListener true
9484
}
9585
return@setOnKeyListener false
9686
}
9787
binding.lockFile.etLockSecs.doAfterTextChanged { x ->
9888
if (x.toString().startsWith('0')) binding.lockFile.etLockSecs.setText("")
9989
}
90+
binding.lockFile.etLockSecs.setOnFocusChangeListener { _, hasFocus ->
91+
if (hasFocus) return@setOnFocusChangeListener
92+
binding.lockFile.etLockSecs.setText(
93+
ParamStorage.getInt(activity, Param.LOCK_SECS).toString()
94+
)
95+
}
10096
}
10197

10298
override fun attachActionsOnResume() {
103-
binding.lockFile.etLockSecs.setText(
104-
ParamStorage.getInt(activity, Param.LOCK_SECS).toString()
105-
)
10699
binding.lockFile.etLockSecs.clearFocus()
107100
val imm =
108101
activity.getSystemService(AppCompatActivity.INPUT_METHOD_SERVICE) as InputMethodManager

app/src/main/java/com/ladsers/passtable/android/containers/Param.kt

Lines changed: 13 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,5 +21,17 @@ enum class Param(
2121
LOCK_ALLOW_WHEN_EDITING("lockAllowWhenEditing", defBool = true),
2222
REMEMBER_RECENT_FILES("rememberRecentFiles", defBool = true),
2323
THEME("theme", defInt = 0),
24-
PREVENT_SCREEN_CAPTURE("preventScreenCapture", defBool = true)
24+
PREVENT_SCREEN_CAPTURE("preventScreenCapture", defBool = true),
25+
26+
GENERATOR_PASSWORD_LENGTH("generatorPasswordLength", defInt = 8),
27+
GENERATOR_LOWERCASE_LETTERS_ALLOW("generatorLowercaseLettersAllow", defBool = true),
28+
GENERATOR_LOWERCASE_LETTERS_MINIMUM("generatorLowercaseLettersMinimum", defInt = 2),
29+
GENERATOR_CAPITAL_LETTERS_ALLOW("generatorCapitalLettersAllow", defBool = true),
30+
GENERATOR_CAPITAL_LETTERS_MINIMUM("generatorCapitalLettersMinimum", defInt = 2),
31+
GENERATOR_NUMBERS_ALLOW("generatorNumbersAllow", defBool = true),
32+
GENERATOR_NUMBERS_MINIMUM("generatorNumbersMinimum", defInt = 1),
33+
GENERATOR_SYMBOLS_ALLOW("generatorSymbolsAllow", defBool = true),
34+
GENERATOR_SYMBOLS_MINIMUM("generatorSymbolsMinimum", defInt = 1),
35+
GENERATOR_SYMBOLS_SET("generatorSymbolsSet", defInt = 0),
36+
GENERATOR_EXCLUDE("generatorExclude", defStr = "")
2537
}

app/src/main/java/com/ladsers/passtable/android/widgets/EditTextLockSecs.kt renamed to app/src/main/java/com/ladsers/passtable/android/widgets/EditTextParam.kt

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -5,18 +5,15 @@ import android.util.AttributeSet
55
import android.view.KeyEvent
66
import android.view.inputmethod.InputMethodManager
77
import androidx.appcompat.app.AppCompatActivity
8-
import com.ladsers.passtable.android.containers.Param
9-
import com.ladsers.passtable.android.containers.ParamStorage
108

11-
class EditTextLockSecs : androidx.appcompat.widget.AppCompatEditText {
9+
class EditTextParam : androidx.appcompat.widget.AppCompatEditText {
1210
constructor(context: Context) : super(context)
1311
constructor(context: Context, attrs: AttributeSet) : super(context, attrs)
1412
constructor(context: Context, attrs: AttributeSet, defStyleAttr: Int) :
1513
super(context, attrs, defStyleAttr)
1614

1715
override fun onKeyPreIme(keyCode: Int, event: KeyEvent?): Boolean {
1816
if (keyCode == KeyEvent.KEYCODE_BACK) {
19-
setText(ParamStorage.getInt(context, Param.LOCK_SECS).toString())
2017
clearFocus()
2118
val imm =
2219
context.getSystemService(AppCompatActivity.INPUT_METHOD_SERVICE) as InputMethodManager

app/src/main/res/layout/activity_password_generator.xml

Lines changed: 57 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -28,26 +28,78 @@
2828
android:layout_width="match_parent"
2929
android:layout_height="wrap_content"
3030
android:focusable="true"
31-
android:focusableInTouchMode="true">
32-
31+
android:focusableInTouchMode="true"
32+
android:paddingTop="8dp"
33+
android:paddingBottom="16dp">
3334

3435
<include
35-
android:id="@+id/chars"
36-
layout="@layout/password_generator_chars"
36+
android:id="@+id/passwordLength"
37+
layout="@layout/password_generator_length"
3738
android:layout_width="0dp"
3839
android:layout_height="wrap_content"
39-
android:layout_marginTop="8dp"
4040
app:layout_constraintEnd_toEndOf="parent"
4141
app:layout_constraintStart_toStartOf="parent"
4242
app:layout_constraintTop_toTopOf="parent" />
4343

44+
<include
45+
android:id="@+id/lowercaseLetters"
46+
layout="@layout/password_generator_collection"
47+
android:layout_width="0dp"
48+
android:layout_height="wrap_content"
49+
android:layout_marginTop="12dp"
50+
app:layout_constraintEnd_toEndOf="parent"
51+
app:layout_constraintStart_toStartOf="parent"
52+
app:layout_constraintTop_toBottomOf="@+id/passwordLength" />
53+
54+
<include
55+
android:id="@+id/capitalLetters"
56+
layout="@layout/password_generator_collection"
57+
android:layout_width="0dp"
58+
android:layout_height="wrap_content"
59+
android:layout_marginTop="12dp"
60+
app:layout_constraintEnd_toEndOf="parent"
61+
app:layout_constraintStart_toStartOf="parent"
62+
app:layout_constraintTop_toBottomOf="@+id/lowercaseLetters" />
63+
64+
<include
65+
android:id="@+id/numbers"
66+
layout="@layout/password_generator_collection"
67+
android:layout_width="0dp"
68+
android:layout_height="wrap_content"
69+
android:layout_marginTop="12dp"
70+
app:layout_constraintEnd_toEndOf="parent"
71+
app:layout_constraintStart_toStartOf="parent"
72+
app:layout_constraintTop_toBottomOf="@+id/capitalLetters" />
73+
74+
<include
75+
android:id="@+id/symbols"
76+
layout="@layout/password_generator_collection"
77+
android:layout_width="0dp"
78+
android:layout_height="wrap_content"
79+
android:layout_marginTop="12dp"
80+
app:layout_constraintEnd_toEndOf="parent"
81+
app:layout_constraintStart_toStartOf="parent"
82+
app:layout_constraintTop_toBottomOf="@+id/numbers" />
83+
84+
<include
85+
android:id="@+id/exclude"
86+
layout="@layout/password_generator_exclude"
87+
android:layout_width="0dp"
88+
android:layout_height="wrap_content"
89+
android:layout_marginTop="12dp"
90+
app:layout_constraintEnd_toEndOf="parent"
91+
app:layout_constraintStart_toStartOf="parent"
92+
app:layout_constraintTop_toBottomOf="@+id/symbols" />
93+
94+
4495
<Button
4596
android:id="@+id/btOk"
4697
style="@style/MainButton"
4798
android:layout_width="wrap_content"
4899
android:layout_marginBottom="24dp"
49100
android:elevation="2dp"
50101
android:text="@string/app_bt_save"
102+
android:visibility="gone"
51103
app:icon="@drawable/ic_save"
52104
app:layout_constraintBottom_toBottomOf="parent"
53105
app:layout_constraintEnd_toEndOf="parent"

0 commit comments

Comments
 (0)