Commit c36b9f50 authored by SusanneFischer's avatar SusanneFischer
Browse files

some code cleanup, added proper error handling to new rental

parent 1cc2ee4d
Pipeline #3599 failed with stages
in 0 seconds
......@@ -14,14 +14,14 @@
android:name="com.google.android.wearable.standalone"
android:value="true" />
<activity android:name=".app.activity.SplashScreenActivity">
<activity android:name=".app.view.SplashScreenActivity">
<intent-filter>
<action android:name="android.intent.action.MAIN" />
<category android:name="android.intent.category.LAUNCHER" />
</intent-filter>
</activity>
<activity
android:name=".app.activity.MainActivity"
android:name=".app.view.MainActivity"
android:configChanges="uiMode"
android:launchMode="singleTop" />
<activity android:name=".signIn.activity.SignInActivity" />
......
package de.asta.hochschule.trier.verleih.admin.fragment
package de.asta.hochschule.trier.verleih.admin.view
import androidx.fragment.app.Fragment
import androidx.lifecycle.ViewModelProvider
import de.asta.hochschule.trier.verleih.R
import de.asta.hochschule.trier.verleih.admin.viewmodel.AdminMainViewModel
class AdminMainFragment : Fragment(R.layout.fragment_admin_main) {
private val viewModel: AdminMainViewModel by lazy {
ViewModelProvider(this).get(AdminMainViewModel::class.java)
}
}
\ No newline at end of file
class AdminMainFragment : Fragment(R.layout.fragment_admin_main)
\ No newline at end of file
package de.asta.hochschule.trier.verleih.admin.viewmodel
import androidx.lifecycle.ViewModel
class AdminMainViewModel : ViewModel() {
}
\ No newline at end of file
......@@ -13,8 +13,8 @@ class AppBarContent @JvmOverloads constructor(
context: Context, attrs: AttributeSet? = null, defStyleAttr: Int = 0
) : ConstraintLayout(context, attrs, defStyleAttr) {
var titleTextView: MaterialTextView
var profileImageView: CircleImageView
private var titleTextView: MaterialTextView
private var profileImageView: CircleImageView
init {
val styledAttributes = context.obtainStyledAttributes(
......@@ -33,19 +33,14 @@ class AppBarContent @JvmOverloads constructor(
profileImageView = (getChildAt(0) as ViewGroup).getChildAt(0) as CircleImageView
profileImageView.setImageDrawable(ContextCompat.getDrawable(context, image))
profileImageView.setOnClickListener { Log.d("AppBarContent", "onClick") }
profileImageView.setOnClickListener {
Log.d(TAG, "on profile image click")
// TODO: show user profile
}
}
fun setTitle(title: String) {
titleTextView.text = title
}
fun setProfileImage(drawableId: Int) {
profileImageView.setImageDrawable(ContextCompat.getDrawable(context, drawableId))
}
fun setProfileImageClick(listener: OnClickListener) {
profileImageView.setOnClickListener(listener)
companion object {
private const val TAG = "AppBarContent"
}
}
\ No newline at end of file
package de.asta.hochschule.trier.verleih.app.activity
package de.asta.hochschule.trier.verleih.app.view
import android.content.Intent
import android.os.Bundle
......@@ -6,7 +6,6 @@ import androidx.activity.viewModels
import androidx.appcompat.app.AppCompatActivity
import androidx.navigation.fragment.findNavController
import androidx.navigation.ui.NavigationUI
import com.google.android.material.bottomnavigation.BottomNavigationView
import com.google.android.material.snackbar.Snackbar
import com.google.gson.Gson
import de.asta.hochschule.trier.verleih.R
......@@ -26,39 +25,41 @@ class MainActivity : AppCompatActivity() {
binding = ActivityMainBinding.inflate(layoutInflater)
setContentView(binding.root)
val bottomNavigationView: BottomNavigationView = findViewById(R.id.bottom_navigation)
val navController =
supportFragmentManager.findFragmentById(R.id.main_nav_host)?.findNavController()
if (navController != null) {
NavigationUI.setupWithNavController(bottomNavigationView, navController)
}
setupBottomNavigation()
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if (requestCode == EditRentalActivity.DELETE_RENTAL_REQUEST_CODE) {
if (resultCode == EditRentalActivity.DELETE_RENTAL_REQUEST_CODE && data != null) {
if (data != null) {
val rental = Gson().fromJson(
data.getStringExtra(EditRentalActivity.INTENT_EXTRA_DELETE_RENTAL),
Rental::class.java
)
viewModel.deleteRental(rental)
val snackBar = Snackbar.make(
binding.root,
"${rental.eventname} ${getString(R.string.deleted)}",
Snackbar.LENGTH_LONG
)
snackBar.setAction(R.string.undo) {
viewModel.reAddRental(rental)
}
snackBar.show()
showUndoSnackBar(rental)
}
}
}
companion object {
private const val TAG = "MainActivty"
private fun setupBottomNavigation() {
val navController =
supportFragmentManager.findFragmentById(R.id.main_nav_host)?.findNavController()
if (navController != null) {
NavigationUI.setupWithNavController(binding.bottomNavigation, navController)
}
}
private fun showUndoSnackBar(rental: Rental) {
val snackBar = Snackbar.make(
binding.bottomNavigation,
"${rental.eventname} ${getString(R.string.deleted)}",
Snackbar.LENGTH_LONG
)
snackBar.setAction(R.string.undo) {
viewModel.reAddRental(rental)
}
snackBar.show()
}
}
\ No newline at end of file
package de.asta.hochschule.trier.verleih.app.activity
package de.asta.hochschule.trier.verleih.app.view
import android.content.Intent
import android.os.*
......@@ -33,7 +33,6 @@ class SplashScreenActivity : AppCompatActivity() {
startActivity(intent)
finish()
}, SPLASH_TIME.toLong())
}
companion object {
......
package de.asta.hochschule.trier.verleih.app
package de.asta.hochschule.trier.verleih.app.view
import androidx.fragment.app.Fragment
import de.asta.hochschule.trier.verleih.R
class TestFragment : Fragment(R.layout.fragment_example) {
}
\ No newline at end of file
class TestFragment : Fragment(R.layout.fragment_example)
\ No newline at end of file
......@@ -3,19 +3,21 @@ package de.asta.hochschule.trier.verleih.app.viewmodel
import androidx.lifecycle.ViewModel
import com.google.firebase.database.FirebaseDatabase
import de.asta.hochschule.trier.verleih.rental.model.Rental
import de.asta.hochschule.trier.verleih.util.Constants
class MainViewModel : ViewModel() {
fun deleteRental(rental: Rental) {
rental.id?.let {
FirebaseDatabase.getInstance().reference.child("rentals").child(it).removeValue()
FirebaseDatabase.getInstance().reference.child(Constants.RENTALS.childName)
.child(it).removeValue()
}
}
fun reAddRental(rental: Rental) {
rental.id = null
val firebaseRef = FirebaseDatabase.getInstance().reference.child("rentals")
firebaseRef.push().setValue(rental)
FirebaseDatabase.getInstance().reference.child(Constants.RENTALS.childName)
.push().setValue(rental)
}
}
\ No newline at end of file
package de.asta.hochschule.trier.verleih.event.fragment
package de.asta.hochschule.trier.verleih.event.view
import androidx.fragment.app.Fragment
import androidx.lifecycle.ViewModelProvider
import de.asta.hochschule.trier.verleih.R
import de.asta.hochschule.trier.verleih.event.viewmodel.EventMainViewModel
class EventMainFragment : Fragment(R.layout.fragment_event_main) {
private val viewModel: EventMainViewModel by lazy {
ViewModelProvider(this).get(EventMainViewModel::class.java)
}
}
\ No newline at end of file
class EventMainFragment : Fragment(R.layout.fragment_event_main)
\ No newline at end of file
package de.asta.hochschule.trier.verleih.event.viewmodel
import androidx.lifecycle.ViewModel
class EventMainViewModel : ViewModel() {
}
\ No newline at end of file
package de.asta.hochschule.trier.verleih.news.fragment
import androidx.fragment.app.Fragment
import androidx.lifecycle.ViewModelProvider
import de.asta.hochschule.trier.verleih.R
import de.asta.hochschule.trier.verleih.news.viewmodel.NewsMainViewModel
class NewsMainFragment : Fragment(R.layout.fragment_news_main) {
private val viewModel: NewsMainViewModel by lazy {
ViewModelProvider(this).get(NewsMainViewModel::class.java)
}
}
\ No newline at end of file
package de.asta.hochschule.trier.verleih.news.view
import androidx.fragment.app.Fragment
import de.asta.hochschule.trier.verleih.R
class NewsMainFragment : Fragment(R.layout.fragment_news_main)
\ No newline at end of file
package de.asta.hochschule.trier.verleih.news.viewmodel
import androidx.lifecycle.ViewModel
class NewsMainViewModel : ViewModel() {
}
\ No newline at end of file
......@@ -3,7 +3,7 @@ package de.asta.hochschule.trier.verleih.rental.adapter
import android.view.*
import androidx.recyclerview.widget.RecyclerView
import de.asta.hochschule.trier.verleih.databinding.RowNoteOverviewBinding
import de.asta.hochschule.trier.verleih.helper.DateHelper
import de.asta.hochschule.trier.verleih.util.DateHelper
class EditRentalNotesAdapter(private var notes: MutableMap<String, String>?) :
RecyclerView.Adapter<EditRentalNotesAdapter.ViewHolder>() {
......
......@@ -2,7 +2,7 @@ package de.asta.hochschule.trier.verleih.rental.adapter
import androidx.fragment.app.Fragment
import androidx.viewpager2.adapter.FragmentStateAdapter
import de.asta.hochschule.trier.verleih.app.TestFragment
import de.asta.hochschule.trier.verleih.app.view.TestFragment
import de.asta.hochschule.trier.verleih.rental.view.*
class NewRentalPagerAdapter(private val activity: NewRentalActivity) :
......
......@@ -8,9 +8,9 @@ import androidx.recyclerview.widget.RecyclerView
import com.firebase.ui.database.*
import com.google.gson.Gson
import de.asta.hochschule.trier.verleih.databinding.RowRentalListBinding
import de.asta.hochschule.trier.verleih.helper.DateHelper
import de.asta.hochschule.trier.verleih.rental.model.Rental
import de.asta.hochschule.trier.verleih.rental.view.EditRentalActivity
import de.asta.hochschule.trier.verleih.util.DateHelper
import org.joda.time.DateTime
import java.util.*
......
package de.asta.hochschule.trier.verleih.rental.model
class RentalObject() {
var id: String? = null
var name: String? = null
var description: String? = null
var picture_name: String? = null
......
......@@ -4,16 +4,17 @@ import android.content.Intent
import android.os.Bundle
import android.view.*
import androidx.activity.viewModels
import androidx.appcompat.widget.Toolbar
import androidx.fragment.app.FragmentActivity
import androidx.recyclerview.widget.LinearLayoutManager
import com.google.android.material.snackbar.*
import com.google.gson.Gson
import de.asta.hochschule.trier.verleih.R
import de.asta.hochschule.trier.verleih.databinding.ActivityEditRentalBinding
import de.asta.hochschule.trier.verleih.helper.DateHelper
import de.asta.hochschule.trier.verleih.rental.adapter.*
import de.asta.hochschule.trier.verleih.rental.model.*
import de.asta.hochschule.trier.verleih.rental.viewmodel.EditRentalViewModel
import de.asta.hochschule.trier.verleih.util.DateHelper
class EditRentalActivity : FragmentActivity() {
......@@ -21,23 +22,50 @@ class EditRentalActivity : FragmentActivity() {
private val viewModel: EditRentalViewModel by viewModels()
private var rental: Rental? = null
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = ActivityEditRentalBinding.inflate(layoutInflater)
setContentView(binding.root)
val rental = Gson().fromJson(intent.getStringExtra(INTENT_EXTRA_RENTAL), Rental::class.java)
rental = Gson().fromJson(intent.getStringExtra(INTENT_EXTRA_RENTAL), Rental::class.java)
val isEditable = rental?.pickupdate?.let { DateHelper.getDateTime(it).isAfterNow }
setupAppBar(isEditable)
setupRecyclerViews(isEditable)
setViewsVisibility()
setTexts()
}
private fun setupRecyclerViews(showMenuItems: Boolean?) {
binding.rentalContainer.itemsRecyclerview.layoutManager = LinearLayoutManager(this)
viewModel.receiveRentalObjects(rental) { objects ->
binding.rentalContainer.itemsRecyclerview.adapter =
RentalItemOverviewAdapter(objects, rental?.objects)
if (showMenuItems == true) {
binding.appbar.setOnMenuItemClickListener(getOnMenuItemClickListener(objects))
}
}
binding.rentalContainer.notesRecyclerView.layoutManager = LinearLayoutManager(this)
binding.rentalContainer.notesRecyclerView.adapter = EditRentalNotesAdapter(rental?.notes)
}
private fun setupAppBar(showMenuItems: Boolean?) {
binding.appbar.setNavigationOnClickListener {
onBackPressed()
}
binding.rentalContainer.overviewDescription.visibility = View.GONE
binding.rentalContainer.statusText.visibility = View.VISIBLE
binding.rentalContainer.statusDescription.visibility = View.VISIBLE
if (showMenuItems == true) {
binding.appbar.inflateMenu(R.menu.appbar_edit_delete)
}
}
private fun setTexts() {
binding.rentalContainer.eventTitleText.text = rental?.eventname
binding.rentalContainer.statusText.text = rental?.status
binding.rentalContainer.noteTitleText.text = getString(R.string.notes)
binding.rentalContainer.noteTextInputLayout.hint = getString(R.string.add_note)
binding.rentalContainer.eventPickupText.text =
rental?.pickupdate?.let {
DateHelper.getDateTime(it).toString(DateHelper.LONG_DATE_TIME_FORMAT)
......@@ -46,44 +74,34 @@ class EditRentalActivity : FragmentActivity() {
rental?.returndate?.let {
DateHelper.getDateTime(it).toString(DateHelper.LONG_DATE_TIME_FORMAT)
}
val isEditable = rental?.pickupdate?.let { DateHelper.getDateTime(it).isAfterNow }
if (isEditable == true) {
binding.appbar.inflateMenu(R.menu.appbar_edit_delete)
}
binding.rentalContainer.itemsRecyclerview.layoutManager = LinearLayoutManager(this)
viewModel.receiveRentalObjects(rental) {
binding.rentalContainer.itemsRecyclerview.adapter =
RentalItemOverviewAdapter(it, rental?.objects)
if (isEditable == true) {
binding.appbar.setOnMenuItemClickListener { item ->
when (item.itemId) {
R.id.appbar_edit -> {
editRental(rental, it)
return@setOnMenuItemClickListener true
}
R.id.appbar_delete -> {
deleteRental(rental)
return@setOnMenuItemClickListener true
}
else -> return@setOnMenuItemClickListener false
}
}
}
}
binding.rentalContainer.noteTitleText.text = getString(R.string.notes)
}
private fun setViewsVisibility() {
binding.rentalContainer.overviewDescription.visibility = View.GONE
binding.rentalContainer.statusText.visibility = View.VISIBLE
binding.rentalContainer.statusDescription.visibility = View.VISIBLE
binding.rentalContainer.noteDescription.visibility = View.GONE
binding.rentalContainer.notesRecyclerView.visibility = View.VISIBLE
binding.rentalContainer.notesRecyclerView.layoutManager = LinearLayoutManager(this)
binding.rentalContainer.notesRecyclerView.adapter = EditRentalNotesAdapter(rental?.notes)
binding.rentalContainer.noteTextInputLayout.hint = getString(R.string.add_note)
binding.rentalContainer.editItemsButton.visibility = View.INVISIBLE
binding.rentalContainer.editInformationButton.visibility = View.INVISIBLE
}
private fun getOnMenuItemClickListener(rentalObjects: ArrayList<RentalObject>): Toolbar.OnMenuItemClickListener {
return Toolbar.OnMenuItemClickListener { item ->
when (item.itemId) {
R.id.appbar_edit -> {
rental?.let { editRental(it, rentalObjects) }
return@OnMenuItemClickListener true
}
R.id.appbar_delete -> {
rental?.let { deleteRental(it) }
return@OnMenuItemClickListener true
}
else -> return@OnMenuItemClickListener false
}
}
}
private fun editRental(rental: Rental, rentalObjects: ArrayList<RentalObject>) {
val intent = Intent(this, NewRentalActivity::class.java)
intent.putExtra(INTENT_EXTRA_RENTAL, Gson().toJson(rental))
......@@ -102,8 +120,8 @@ class EditRentalActivity : FragmentActivity() {
const val INTENT_EXTRA_RENTAL = "Rental"
const val INTENT_EXTRA_RENTAL_OBJECTS = "Rental_Objects"
const val INTENT_EXTRA_DELETE_RENTAL = "Delete_Rental"
private const val TAG = "EditRentalActivity"
private const val EDIT_RENTAL_REQUEST_CODE = 1
const val DELETE_RENTAL_REQUEST_CODE = 2
}
}
\ No newline at end of file
package de.asta.hochschule.trier.verleih.rental.view
import android.os.Bundle
import android.util.Log
import android.widget.Toast
import androidx.activity.viewModels
import androidx.fragment.app.FragmentActivity
import androidx.viewpager2.widget.ViewPager2
import com.google.android.material.tabs.TabLayoutMediator
import com.google.firebase.database.FirebaseDatabase
import com.google.gson.Gson
import com.google.gson.reflect.TypeToken
import de.asta.hochschule.trier.verleih.R
......@@ -31,24 +28,27 @@ class NewRentalActivity : FragmentActivity() {
onBackPressed()
}
val rentalExtra = Gson().fromJson(
intent.getStringExtra(EditRentalActivity.INTENT_EXTRA_RENTAL),
Rental::class.java
)
val rentalObjectType = object : TypeToken<ArrayList<RentalObject>>() {}.type
val rentalObjectsExtra = Gson().fromJson<ArrayList<RentalObject>>(
intent.getStringExtra(EditRentalActivity.INTENT_EXTRA_RENTAL_OBJECTS),
rentalObjectType
)
if (rentalExtra != null && rentalObjectsExtra != null) {
viewModel.setupViewModel(rentalExtra, rentalObjectsExtra)
binding.appbar.setTitle(R.string.edit_rental)
setupEditRental()
setupViewPager()
}
override fun onBackPressed() {
if (binding.newRentalPager.currentItem == 0) {
super.onBackPressed()
} else {
binding.newRentalPager.currentItem = binding.newRentalPager.currentItem - 1
}
val pagerAdapter = NewRentalPagerAdapter(this)
binding.newRentalPager.adapter = pagerAdapter
}
fun goToPage(page: Int) {
if (page in PAGE_DATE_TIME..PAGE_OVERVIEW) {
binding.newRentalPager.currentItem = page
}
}
private fun setupViewPager() {
binding.newRentalPager.adapter = NewRentalPagerAdapter(this)
TabLayoutMediator(binding.newRentalPagerTabs, binding.newRentalPager) { _, _ -> }.attach()
binding.newRentalPager.isUserInputEnabled = false
binding.newRentalPager.registerOnPageChangeCallback(object :
ViewPager2.OnPageChangeCallback() {
......@@ -60,127 +60,39 @@ class NewRentalActivity : FragmentActivity() {
}
}
})
binding.pagerBackButton.setOnClickListener {
onBackPressed()
}
binding.pagerNextButton.setOnClickListener {
if (!isValidInput(
binding.newRentalPager.currentItem,
viewModel.rentalLiveData.value,
viewModel.objectsLiveData.value,
viewModel.rentalObjectsLiveData.value
)
) {
Toast.makeText(this, "Input invalid", Toast.LENGTH_SHORT).show()
} else {
if (viewModel.validateInput(binding.newRentalPager.currentItem)) {
if (binding.newRentalPager.currentItem == PAGE_OVERVIEW) {
Log.d(TAG, "save")
val rental = viewModel.buildRental()
val firebaseRef = FirebaseDatabase.getInstance().reference.child("rentals")
firebaseRef.push().setValue(rental)
viewModel.saveRentalToDatabase()
finish()
} else {
binding.newRentalPager.currentItem = binding.newRentalPager.currentItem + 1
}
}
}
viewModel.rentalLiveData.observe(this, { rental ->
if (isValidInput(
binding.newRentalPager.currentItem,
rental,
viewModel.objectsLiveData.value,
viewModel.rentalObjectsLiveData.value
)
) {
Log.d(TAG, "Valid input")
}
})
viewModel.objectsLiveData.observe(this, { objects ->
if (isValidInput(
binding.newRentalPager.currentItem,