MOB-40 changed the settings view and fixed menu notifications

This commit is contained in:
Henrik Lepson 2021-11-25 16:13:35 +02:00
parent 1138abcb11
commit 762a8c8cc2
10 changed files with 124 additions and 80 deletions

View File

@ -38,6 +38,8 @@ class HomeFragment : Fragment() {
// The ID card reader mode is enabled on the home fragment when can is saved. // The ID card reader mode is enabled on the home fragment when can is saved.
private var canSaved: Boolean = false private var canSaved: Boolean = false
// Is the app used for authentication
private var auth: Boolean = false
override fun onCreateView( override fun onCreateView(
inflater: LayoutInflater, inflater: LayoutInflater,
@ -50,21 +52,37 @@ class HomeFragment : Fragment() {
return binding!!.root return binding!!.root
} }
// TODO: Split the contents of onViewCreated methods into smaller separate methods
override fun onViewCreated(view: View, savedInstanceState: Bundle?) { override fun onViewCreated(view: View, savedInstanceState: Bundle?) {
super.onViewCreated(view, savedInstanceState) super.onViewCreated(view, savedInstanceState)
initialChecks() initialChecks()
updateAction(canSaved) // Should be called later
var auth = false
if (requireActivity().intent.data?.getQueryParameter("action") != null) { if (requireActivity().intent.data?.getQueryParameter("action") != null) {
// Currently we only support authentication not signing. // Currently we only support authentication not signing.
auth = true auth = true
} }
val mobile = requireActivity().intent.getBooleanExtra("mobile", false) val mobile = requireActivity().intent.getBooleanExtra("mobile", false)
if (auth || mobile) { if (auth || mobile) {
startAuthentication(mobile)
} else {
updateAction(canSaved)
}
}
/**
* Starts the process of interacting with the ID card by sending user to the CAN fragment.
*/
private fun goToTheNextFragment(mobile: Boolean = false) {
(activity as MainActivity).menuAvailable = false
val action = HomeFragmentDirections.actionHomeFragmentToCanFragment(auth = true, mobile = mobile)
findNavController().navigate(action)
}
/**
* Method that starts the authentication use case.
*/
private fun startAuthentication(mobile: Boolean) {
try { try {
if (mobile) { if (mobile) {
// We use !! because we want an exception when something is not right. // We use !! to get extras because we want an exception to be thrown when something is missing.
intentParams.setChallenge(requireActivity().intent.getStringExtra("challenge")!!) intentParams.setChallenge(requireActivity().intent.getStringExtra("challenge")!!)
intentParams.setAuthUrl(requireActivity().intent.getStringExtra("authUrl")!!) intentParams.setAuthUrl(requireActivity().intent.getStringExtra("authUrl")!!)
intentParams.setOrigin(requireActivity().intent.getStringExtra("originUrl")!!) intentParams.setOrigin(requireActivity().intent.getStringExtra("originUrl")!!)
@ -78,29 +96,13 @@ class HomeFragment : Fragment() {
} }
} catch (e: Exception) { } catch (e: Exception) {
// There was a problem with parameters, which means that authentication is not possible. // There was a problem with parameters, which means that authentication is not possible.
// In that case we will cancel the authentication immediately as it would be waste of the user's time to carry on
// before eventual error.
val resultIntent = Intent() val resultIntent = Intent()
requireActivity().setResult(AppCompatActivity.RESULT_CANCELED, resultIntent) requireActivity().setResult(AppCompatActivity.RESULT_CANCELED, resultIntent)
requireActivity().finish() requireActivity().finish()
} }
goToTheNextFragment(mobile)
goToTheNextFragment(true, mobile)
}
}
/**
* Starts the process of interacting with the ID card by sending user to the CAN fragment.
*
* NOTE: This method should only be used for authentication flow in the future.
*/
private fun goToTheNextFragment(auth: Boolean = false, mobile: Boolean = false) {
(activity as MainActivity).menuAvailable = false
if (auth) {
val action = HomeFragmentDirections.actionHomeFragmentToCanFragment(reading = false, auth = true, mobile = mobile)
findNavController().navigate(action)
} else {
val action = HomeFragmentDirections.actionHomeFragmentToCanFragment(reading = true, auth = false, mobile = mobile)
findNavController().navigate(action)
}
} }
/** /**
@ -160,11 +162,22 @@ class HomeFragment : Fragment() {
} else { } else {
binding!!.detectionActionText.text = getString(R.string.action_detect_unavailable) binding!!.detectionActionText.text = getString(R.string.action_detect_unavailable)
} }
} }
// TODO: When error occurs it should be cleared within a reasonable timeframe and it should be possible to detect cards again /**
// TODO: Listen to system broadcasts to detect if NFC is turned on/off during when the app is working * Resets the error message and allows the user to try again
*/
private fun reset() {
binding!!.buttonAgain.setOnClickListener {
updateAction(canSaved)
binding!!.buttonAgain.visibility = View.GONE
}
binding!!.buttonAgain.visibility = View.VISIBLE
}
/**
* Method that enables the NFC reader mode, which allows the app to communicate with the ID card and retrieve information.
*/
private fun enableReaderMode() { private fun enableReaderMode() {
val adapter = NfcAdapter.getDefaultAdapter(activity) val adapter = NfcAdapter.getDefaultAdapter(activity)
if (adapter == null) { if (adapter == null) {
@ -192,8 +205,16 @@ class HomeFragment : Fragment() {
} }
} catch (e: Exception) { } catch (e: Exception) {
when(e) { when(e) {
is TagLostException -> requireActivity().runOnUiThread { binding!!.detectionActionText.text = getString(R.string.id_card_removed_early)} is TagLostException -> requireActivity().runOnUiThread {
else -> requireActivity().runOnUiThread { binding!!.detectionActionText.text = getString(R.string.nfc_reading_error) } binding!!.detectionActionText.text = getString(R.string.id_card_removed_early)
reset()
}
else -> requireActivity().runOnUiThread {
binding!!.detectionActionText.text = getString(R.string.nfc_reading_error)
viewModel.deleteCan(requireContext())
canState()
reset()
}
} }
} finally { } finally {
adapter.disableReaderMode(activity) adapter.disableReaderMode(activity)

View File

@ -20,6 +20,8 @@ class MainActivity : AppCompatActivity() {
// If true the settings menu can be accessed from the toolbar in the upper part of the screen. // If true the settings menu can be accessed from the toolbar in the upper part of the screen.
var menuAvailable: Boolean = true var menuAvailable: Boolean = true
var inMenu: Boolean = false
override fun onCreate(savedInstanceState: Bundle?) { override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState) super.onCreate(savedInstanceState)
val binding = ActivityMainBinding.inflate(layoutInflater) val binding = ActivityMainBinding.inflate(layoutInflater)
@ -41,9 +43,12 @@ class MainActivity : AppCompatActivity() {
if (menuAvailable) { if (menuAvailable) {
navigationController.navigate(R.id.action_homeFragment_to_settingsFragment) navigationController.navigate(R.id.action_homeFragment_to_settingsFragment)
menuAvailable = false menuAvailable = false
inMenu = true
true true
} else { } else {
if (!inMenu) {
Toast.makeText(this, getString(R.string.unavailable), Toast.LENGTH_SHORT).show() Toast.makeText(this, getString(R.string.unavailable), Toast.LENGTH_SHORT).show()
}
false false
} }
} }

View File

@ -8,6 +8,7 @@ import android.widget.Button
import androidx.fragment.app.Fragment import androidx.fragment.app.Fragment
import androidx.fragment.app.activityViewModels import androidx.fragment.app.activityViewModels
import androidx.navigation.fragment.findNavController import androidx.navigation.fragment.findNavController
import com.tarkvaraprojekt.mobileauthapp.MainActivity
import com.tarkvaraprojekt.mobileauthapp.R import com.tarkvaraprojekt.mobileauthapp.R
import com.tarkvaraprojekt.mobileauthapp.databinding.FragmentSettingsBinding import com.tarkvaraprojekt.mobileauthapp.databinding.FragmentSettingsBinding
import com.tarkvaraprojekt.mobileauthapp.model.SmartCardViewModel import com.tarkvaraprojekt.mobileauthapp.model.SmartCardViewModel
@ -67,6 +68,7 @@ class SettingsFragment : Fragment() {
viewModel.deleteCan(requireContext()) viewModel.deleteCan(requireContext())
showCanField() showCanField()
} else { } else {
(activity as MainActivity).inMenu = false
val action = SettingsFragmentDirections.actionSettingsFragmentToCanFragment(saving = true) val action = SettingsFragmentDirections.actionSettingsFragmentToCanFragment(saving = true)
findNavController().navigate(action) findNavController().navigate(action)
} }
@ -101,6 +103,7 @@ class SettingsFragment : Fragment() {
viewModel.deletePin(requireContext()) viewModel.deletePin(requireContext())
showPinField() showPinField()
} else { } else {
(activity as MainActivity).inMenu = false
val action = SettingsFragmentDirections.actionSettingsFragmentToPinFragment(saving = true) val action = SettingsFragmentDirections.actionSettingsFragmentToPinFragment(saving = true)
findNavController().navigate(action) findNavController().navigate(action)
} }
@ -130,6 +133,7 @@ class SettingsFragment : Fragment() {
* Navigates back to home fragment. * Navigates back to home fragment.
*/ */
private fun backToHome() { private fun backToHome() {
(activity as MainActivity).inMenu = false
findNavController().navigate(R.id.action_settingsFragment_to_homeFragment) findNavController().navigate(R.id.action_settingsFragment_to_homeFragment)
} }

View File

@ -100,4 +100,16 @@
android:layout_height="wrap_content" /> android:layout_height="wrap_content" />
</LinearLayout> </LinearLayout>
<Button
android:id="@+id/button_again"
android:textSize="@dimen/regular_text"
android:text="@string/try_again"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_marginTop="@dimen/margin_small"
android:layout_marginStart="@dimen/margin_huge"
android:visibility="gone"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/id_card_detection"/>
</androidx.constraintlayout.widget.ConstraintLayout> </androidx.constraintlayout.widget.ConstraintLayout>

View File

@ -89,20 +89,6 @@
</LinearLayout> </LinearLayout>
<Button
android:id="@+id/button_cancel"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="@dimen/margin_big"
android:fontFamily="sans-serif"
android:text="@string/button_cancel"
android:textSize="@dimen/regular_text"
app:layout_constraintEnd_toStartOf="@+id/button_continue"
app:layout_constraintHorizontal_bias="0.5"
app:layout_constraintHorizontal_chainStyle="spread"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/save_layout" />
<Button <Button
android:id="@+id/button_continue" android:id="@+id/button_continue"
android:layout_width="wrap_content" android:layout_width="wrap_content"
@ -111,9 +97,18 @@
android:fontFamily="sans-serif" android:fontFamily="sans-serif"
android:text="@string/continue_button" android:text="@string/continue_button"
android:textSize="@dimen/regular_text" android:textSize="@dimen/regular_text"
app:layout_constraintEnd_toEndOf="parent" app:layout_constraintStart_toStartOf="parent"
app:layout_constraintHorizontal_bias="0.5"
app:layout_constraintStart_toEndOf="@+id/button_cancel"
app:layout_constraintTop_toBottomOf="@id/save_layout" /> app:layout_constraintTop_toBottomOf="@id/save_layout" />
<Button
android:id="@+id/button_cancel"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_margin="@dimen/margin_big"
android:fontFamily="sans-serif"
android:text="@string/button_cancel"
android:textSize="@dimen/regular_text"
app:layout_constraintStart_toStartOf="parent"
app:layout_constraintTop_toBottomOf="@id/button_continue" />
</androidx.constraintlayout.widget.ConstraintLayout> </androidx.constraintlayout.widget.ConstraintLayout>

View File

@ -4,7 +4,7 @@
xmlns:tools="http://schemas.android.com/tools" xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="match_parent" android:layout_height="match_parent"
android:layout_margin="12dp" android:layout_margin="@dimen/padding"
tools:context=".menu.SettingsFragment"> tools:context=".menu.SettingsFragment">
<com.google.android.material.card.MaterialCardView <com.google.android.material.card.MaterialCardView
@ -22,44 +22,46 @@
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:orientation="vertical" android:orientation="vertical"
android:padding="12dp"> android:padding="@dimen/padding_small">
<TextView <TextView
android:id="@+id/can_saved" android:id="@+id/can_saved"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:textSize="20sp" android:textSize="@dimen/regular_text"
android:padding="12dp" android:padding="@dimen/margin_small"
android:text="@string/saved_can" /> android:text="@string/saved_can" />
<Button <Button
android:id="@+id/can_menu_action" android:id="@+id/can_menu_action"
android:layout_margin="12dp" android:layout_margin="@dimen/margin_small"
android:textSize="15sp" android:textSize="@dimen/regular_text"
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content"/> android:layout_height="wrap_content"/>
<TextView <TextView
android:id="@+id/pin_saved" android:id="@+id/pin_saved"
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:textSize="20sp" android:textSize="@dimen/regular_text"
android:padding="12dp" android:padding="@dimen/margin_small"
android:text="@string/saved_pin"/> android:text="@string/saved_pin"/>
<LinearLayout <LinearLayout
android:layout_width="match_parent" android:layout_width="match_parent"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:orientation="horizontal"> android:orientation="vertical">
<Button
android:id="@+id/pin_menu_action"
android:layout_margin="12dp"
android:textSize="15sp"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
<Button <Button
android:id="@+id/pin_menu_show" android:id="@+id/pin_menu_show"
android:layout_margin="12dp" android:layout_marginHorizontal="@dimen/margin"
android:textSize="15sp" android:layout_marginVertical="@dimen/margin_small"
android:textSize="@dimen/regular_text"
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:visibility="gone"/> android:visibility="gone"/>
<Button
android:id="@+id/pin_menu_action"
android:layout_marginHorizontal="@dimen/margin"
android:layout_marginVertical="@dimen/margin_small"
android:textSize="@dimen/regular_text"
android:layout_width="wrap_content"
android:layout_height="wrap_content" />
</LinearLayout> </LinearLayout>
</LinearLayout> </LinearLayout>
</com.google.android.material.card.MaterialCardView> </com.google.android.material.card.MaterialCardView>
@ -69,8 +71,9 @@
android:layout_width="wrap_content" android:layout_width="wrap_content"
android:layout_height="wrap_content" android:layout_height="wrap_content"
android:text="@string/return_text" android:text="@string/return_text"
android:layout_margin="24dp" android:layout_marginVertical="@dimen/margin"
android:textSize="15sp" android:layout_marginStart="@dimen/padding"
android:textSize="@dimen/regular_text"
app:layout_constraintTop_toBottomOf="@id/settings_card" app:layout_constraintTop_toBottomOf="@id/settings_card"
app:layout_constraintStart_toStartOf="parent" /> app:layout_constraintStart_toStartOf="parent" />

View File

@ -97,5 +97,6 @@
<string name="action_detect_unavailable">CAN must be added before ID card can be detected</string> <string name="action_detect_unavailable">CAN must be added before ID card can be detected</string>
<string name="nfc_not_available">NFC is not turned on or is not supported by the phone</string> <string name="nfc_not_available">NFC is not turned on or is not supported by the phone</string>
<string name="nfc_reading_error">The provided CAN does not match the ID card</string> <string name="nfc_reading_error">The provided CAN does not match the ID card</string>
<string name="id_card_removed_early">ID card was removed too eraly</string> <string name="id_card_removed_early">ID card was removed too early</string>
<string name="try_again">Try Again</string>
</resources> </resources>

View File

@ -95,5 +95,6 @@
<string name="action_detect_unavailable">CAN must be added before ID card can be detected</string> <string name="action_detect_unavailable">CAN must be added before ID card can be detected</string>
<string name="nfc_not_available">NFC is not turned on or is not supported by the phone</string> <string name="nfc_not_available">NFC is not turned on or is not supported by the phone</string>
<string name="nfc_reading_error">The provided CAN does not match the ID card</string> <string name="nfc_reading_error">The provided CAN does not match the ID card</string>
<string name="id_card_removed_early">ID card was removed too eraly</string> <string name="id_card_removed_early">ID card was removed too early</string>
<string name="try_again">Try Again</string>
</resources> </resources>

View File

@ -3,6 +3,7 @@
<dimen name="margin_small">4dp</dimen> <dimen name="margin_small">4dp</dimen>
<dimen name="margin">8dp</dimen> <dimen name="margin">8dp</dimen>
<dimen name="margin_big">16dp</dimen> <dimen name="margin_big">16dp</dimen>
<dimen name="margin_huge">32dp</dimen>
<dimen name="padding_tiny">8dp</dimen> <dimen name="padding_tiny">8dp</dimen>
<dimen name="padding_small">16dp</dimen> <dimen name="padding_small">16dp</dimen>
<dimen name="padding">24dp</dimen> <dimen name="padding">24dp</dimen>

View File

@ -95,5 +95,6 @@
<string name="action_detect_unavailable">CAN must be added before ID card can be detected</string> <string name="action_detect_unavailable">CAN must be added before ID card can be detected</string>
<string name="nfc_not_available">NFC is not turned on or is not supported by the phone</string> <string name="nfc_not_available">NFC is not turned on or is not supported by the phone</string>
<string name="nfc_reading_error">The provided CAN does not match the ID card</string> <string name="nfc_reading_error">The provided CAN does not match the ID card</string>
<string name="id_card_removed_early">ID card was removed too eraly</string> <string name="id_card_removed_early">ID card was removed too early</string>
<string name="try_again">Try Again</string>
</resources> </resources>