diff --git a/app/build.gradle.kts b/app/build.gradle.kts index 0cb11ad6abb1668f5c6c8d4830f123c6b8f76d0c..2b493d6d0776c6e27a466dffc0854c719f7bc84e 100644 --- a/app/build.gradle.kts +++ b/app/build.gradle.kts @@ -21,6 +21,7 @@ android { } buildFeatures { viewBinding = true + dataBinding = true } buildTypes { @@ -73,5 +74,11 @@ dependencies { implementation("com.squareup.okhttp3:logging-interceptor:4.9.3") implementation("androidx.navigation:navigation-fragment-ktx:2.7.7") implementation("androidx.navigation:navigation-ui-ktx:2.7.7") + val roomVersion = "2.6.1" + + implementation("androidx.room:room-runtime:$roomVersion") + annotationProcessor("androidx.room:room-compiler:$roomVersion") + implementation("androidx.room:room-ktx:$roomVersion") + kapt("androidx.room:room-compiler:$roomVersion") } \ No newline at end of file diff --git a/app/src/main/java/com/pbd/psi/MainActivity.kt b/app/src/main/java/com/pbd/psi/MainActivity.kt index b7e2754f4277ad6b726b0e2fe2cc86027cd5a51b..927103875f6885593f077a46c0f3ccf10232d536 100644 --- a/app/src/main/java/com/pbd/psi/MainActivity.kt +++ b/app/src/main/java/com/pbd/psi/MainActivity.kt @@ -19,10 +19,6 @@ import android.content.res.ColorStateList import android.graphics.Color - - - - class MainActivity : AppCompatActivity() { companion object { const val SHARED_PREFS = "shared_prefs" @@ -48,13 +44,6 @@ class MainActivity : AppCompatActivity() { val navController = navHostFragment.navController bottomNavigationView.setupWithNavController(navController) -// setSupportActionBar(findViewById(R.id.toolbar)) -// supportActionBar?.setDisplayHomeAsUpEnabled(false) // Hide back button -// supportActionBar?.setDisplayShowHomeEnabled(false) // Hide logo -// supportActionBar?.setDisplayShowTitleEnabled(true) // Show title only -// val appBarConfiguration = AppBarConfiguration(navController.graph) -// binding.toolbar.setupWithNavController(navController, appBarConfiguration) - val serviceIntent = Intent(this, BackgroundService::class.java) startService(serviceIntent) diff --git a/app/src/main/java/com/pbd/psi/repository/TransactionRepository.kt b/app/src/main/java/com/pbd/psi/repository/TransactionRepository.kt new file mode 100644 index 0000000000000000000000000000000000000000..33f3c342ebaae0c80a9f1257296d7cf6e17a2ead --- /dev/null +++ b/app/src/main/java/com/pbd/psi/repository/TransactionRepository.kt @@ -0,0 +1,26 @@ +package com.pbd.psi.repository + +import androidx.lifecycle.LiveData +import com.pbd.psi.room.AppDatabase +import com.pbd.psi.room.TransactionEntity + +class TransactionRepository(private val database: AppDatabase) { + + val transactionList: LiveData<List<TransactionEntity>> = database.transactionDao().getAllTrans() + + fun getTransById(id: Int){ + database.transactionDao().getTransById(id) + } + + suspend fun addTransaction(transaction: TransactionEntity) { + database.transactionDao().addTransaction(transaction) + } + + suspend fun updateTransaction(transaction: TransactionEntity) { + database.transactionDao().updateTransaction(transaction) + } + + suspend fun deleteTransaction(transaction: TransactionEntity) { + database.transactionDao().deleteTransaction(transaction) + } +} \ No newline at end of file diff --git a/app/src/main/java/com/pbd/psi/room/AppDatabase.kt b/app/src/main/java/com/pbd/psi/room/AppDatabase.kt new file mode 100644 index 0000000000000000000000000000000000000000..04d804a612f177eccb6647906f9348cfc4b4b626 --- /dev/null +++ b/app/src/main/java/com/pbd/psi/room/AppDatabase.kt @@ -0,0 +1,36 @@ +package com.pbd.psi.room + +import androidx.room.Database +import androidx.room.Room +import androidx.room.RoomDatabase +import android.content.Context +import androidx.room.TypeConverters + +@Database(entities = [TransactionEntity::class], version = 1) +@TypeConverters(Converters::class) +abstract class AppDatabase() : RoomDatabase() { + + abstract fun transactionDao(): TransactionDao + + companion object { + @Volatile + private var Instance: AppDatabase? = null + + fun getDatabase(context: Context): AppDatabase{ + synchronized(this){ + var instance = Instance + + if (instance == null) { + instance = Room.databaseBuilder( + context.applicationContext, + AppDatabase::class.java, + "app_database" + ).build() + Instance = instance + } + + return instance + } + } + } +} diff --git a/app/src/main/java/com/pbd/psi/room/Converters.kt b/app/src/main/java/com/pbd/psi/room/Converters.kt new file mode 100644 index 0000000000000000000000000000000000000000..dee6eeb59ff0d2ab4d2c4c24d36001166e70fc86 --- /dev/null +++ b/app/src/main/java/com/pbd/psi/room/Converters.kt @@ -0,0 +1,19 @@ +package com.pbd.psi.room + +import androidx.room.TypeConverter +import java.text.SimpleDateFormat +import java.util.* + +class Converters { + private val dateFormat = SimpleDateFormat("yyyy-MM-dd", Locale.getDefault()) + + @TypeConverter + fun toDate(value: String?): Date? { + return value?.let { dateFormat.parse(it) } + } + + @TypeConverter + fun fromDate(date: Date?): String? { + return date?.let { dateFormat.format(it) } + } +} diff --git a/app/src/main/java/com/pbd/psi/room/TransactionDao.kt b/app/src/main/java/com/pbd/psi/room/TransactionDao.kt new file mode 100644 index 0000000000000000000000000000000000000000..f4e7024aa214c21e7ce583ba06f73be5039f2910 --- /dev/null +++ b/app/src/main/java/com/pbd/psi/room/TransactionDao.kt @@ -0,0 +1,21 @@ +package com.pbd.psi.room + +import androidx.lifecycle.LiveData +import androidx.room.* +@Dao +interface TransactionDao { + @Query("SELECT * FROM `transaction`") + fun getAllTrans(): LiveData<List<TransactionEntity>> + + @Query("SELECT * FROM `transaction` WHERE id=:id") + fun getTransById(id: Int): TransactionEntity + + @Insert(onConflict = OnConflictStrategy.ABORT) + suspend fun addTransaction(trans: TransactionEntity) + + @Update(onConflict = OnConflictStrategy.ABORT) + suspend fun updateTransaction(trans: TransactionEntity) + + @Delete + suspend fun deleteTransaction(trans: TransactionEntity) +} \ No newline at end of file diff --git a/app/src/main/java/com/pbd/psi/room/TransactionEntity.kt b/app/src/main/java/com/pbd/psi/room/TransactionEntity.kt new file mode 100644 index 0000000000000000000000000000000000000000..e7a721a54a9aa8db1df8d3fda0fbf90f21a389b9 --- /dev/null +++ b/app/src/main/java/com/pbd/psi/room/TransactionEntity.kt @@ -0,0 +1,17 @@ +package com.pbd.psi.room + +import androidx.room.Entity +import androidx.room.PrimaryKey +import java.util.Date + +@Entity(tableName = "transaction") +data class TransactionEntity( + @PrimaryKey(autoGenerate = true) + val id: Int = 0, + val name: String = "", + val category: Int = 0, + val price: Int = 0, + val date: Date = Date(), + val longitude: Double = 0.0, + val latitude: Double = 0.0, +) \ No newline at end of file diff --git a/app/src/main/java/com/pbd/psi/ui/add_transaction/AddTransFragment.kt b/app/src/main/java/com/pbd/psi/ui/add_transaction/AddTransFragment.kt new file mode 100644 index 0000000000000000000000000000000000000000..4ab80d9261917c4af65dcd0a31ec639fa1383499 --- /dev/null +++ b/app/src/main/java/com/pbd/psi/ui/add_transaction/AddTransFragment.kt @@ -0,0 +1,60 @@ +package com.pbd.psi.ui.add_transaction + +import android.os.Bundle +import androidx.fragment.app.Fragment +import android.view.LayoutInflater +import android.view.View +import android.view.ViewGroup +import com.pbd.psi.R + +// TODO: Rename parameter arguments, choose names that match +// the fragment initialization parameters, e.g. ARG_ITEM_NUMBER +private const val ARG_PARAM1 = "param1" +private const val ARG_PARAM2 = "param2" + +/** + * A simple [Fragment] subclass. + * Use the [AddTransFragment.newInstance] factory method to + * create an instance of this fragment. + */ +class AddTransFragment : Fragment() { + // TODO: Rename and change types of parameters + private var param1: String? = null + private var param2: String? = null + + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + arguments?.let { + param1 = it.getString(ARG_PARAM1) + param2 = it.getString(ARG_PARAM2) + } + } + + override fun onCreateView( + inflater: LayoutInflater, container: ViewGroup?, + savedInstanceState: Bundle? + ): View? { + // Inflate the layout for this fragment + return inflater.inflate(R.layout.fragment_add_trans, container, false) + } + + companion object { + /** + * Use this factory method to create a new instance of + * this fragment using the provided parameters. + * + * @param param1 Parameter 1. + * @param param2 Parameter 2. + * @return A new instance of fragment AddTransFragment. + */ + // TODO: Rename and change types and number of parameters + @JvmStatic + fun newInstance(param1: String, param2: String) = + AddTransFragment().apply { + arguments = Bundle().apply { + putString(ARG_PARAM1, param1) + putString(ARG_PARAM2, param2) + } + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/pbd/psi/ui/add_transaction/ExpenseFragment.kt b/app/src/main/java/com/pbd/psi/ui/add_transaction/ExpenseFragment.kt new file mode 100644 index 0000000000000000000000000000000000000000..f35255f9aa184292cff87344670661b0b5bf30af --- /dev/null +++ b/app/src/main/java/com/pbd/psi/ui/add_transaction/ExpenseFragment.kt @@ -0,0 +1,60 @@ +package com.pbd.psi.ui.add_transaction + +import android.os.Bundle +import androidx.fragment.app.Fragment +import android.view.LayoutInflater +import android.view.View +import android.view.ViewGroup +import com.pbd.psi.R + +// TODO: Rename parameter arguments, choose names that match +// the fragment initialization parameters, e.g. ARG_ITEM_NUMBER +private const val ARG_PARAM1 = "param1" +private const val ARG_PARAM2 = "param2" + +/** + * A simple [Fragment] subclass. + * Use the [ExpenseFragment.newInstance] factory method to + * create an instance of this fragment. + */ +class ExpenseFragment : Fragment() { + // TODO: Rename and change types of parameters + private var param1: String? = null + private var param2: String? = null + + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + arguments?.let { + param1 = it.getString(ARG_PARAM1) + param2 = it.getString(ARG_PARAM2) + } + } + + override fun onCreateView( + inflater: LayoutInflater, container: ViewGroup?, + savedInstanceState: Bundle? + ): View? { + // Inflate the layout for this fragment + return inflater.inflate(R.layout.fragment_expense, container, false) + } + + companion object { + /** + * Use this factory method to create a new instance of + * this fragment using the provided parameters. + * + * @param param1 Parameter 1. + * @param param2 Parameter 2. + * @return A new instance of fragment ExpenseFragment. + */ + // TODO: Rename and change types and number of parameters + @JvmStatic + fun newInstance(param1: String, param2: String) = + ExpenseFragment().apply { + arguments = Bundle().apply { + putString(ARG_PARAM1, param1) + putString(ARG_PARAM2, param2) + } + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/pbd/psi/ui/add_transaction/IncomeFragment.kt b/app/src/main/java/com/pbd/psi/ui/add_transaction/IncomeFragment.kt new file mode 100644 index 0000000000000000000000000000000000000000..7c0bf65a82c9b666ca592046a7bf6702bbca789a --- /dev/null +++ b/app/src/main/java/com/pbd/psi/ui/add_transaction/IncomeFragment.kt @@ -0,0 +1,60 @@ +package com.pbd.psi.ui.add_transaction + +import android.os.Bundle +import androidx.fragment.app.Fragment +import android.view.LayoutInflater +import android.view.View +import android.view.ViewGroup +import com.pbd.psi.R + +// TODO: Rename parameter arguments, choose names that match +// the fragment initialization parameters, e.g. ARG_ITEM_NUMBER +private const val ARG_PARAM1 = "param1" +private const val ARG_PARAM2 = "param2" + +/** + * A simple [Fragment] subclass. + * Use the [IncomeFragment.newInstance] factory method to + * create an instance of this fragment. + */ +class IncomeFragment : Fragment() { + // TODO: Rename and change types of parameters + private var param1: String? = null + private var param2: String? = null + + override fun onCreate(savedInstanceState: Bundle?) { + super.onCreate(savedInstanceState) + arguments?.let { + param1 = it.getString(ARG_PARAM1) + param2 = it.getString(ARG_PARAM2) + } + } + + override fun onCreateView( + inflater: LayoutInflater, container: ViewGroup?, + savedInstanceState: Bundle? + ): View? { + // Inflate the layout for this fragment + return inflater.inflate(R.layout.fragment_income, container, false) + } + + companion object { + /** + * Use this factory method to create a new instance of + * this fragment using the provided parameters. + * + * @param param1 Parameter 1. + * @param param2 Parameter 2. + * @return A new instance of fragment IncomeFragment. + */ + // TODO: Rename and change types and number of parameters + @JvmStatic + fun newInstance(param1: String, param2: String) = + IncomeFragment().apply { + arguments = Bundle().apply { + putString(ARG_PARAM1, param1) + putString(ARG_PARAM2, param2) + } + } + } +} \ No newline at end of file diff --git a/app/src/main/java/com/pbd/psi/ui/transaction/TransactionAdapter.kt b/app/src/main/java/com/pbd/psi/ui/transaction/TransactionAdapter.kt new file mode 100644 index 0000000000000000000000000000000000000000..8165a500d4e4f2104dede992a7f5251960896c5c --- /dev/null +++ b/app/src/main/java/com/pbd/psi/ui/transaction/TransactionAdapter.kt @@ -0,0 +1,21 @@ +package com.pbd.psi.ui.transaction + +import android.view.View +import android.view.ViewGroup +import androidx.recyclerview.widget.RecyclerView + +class TransactionAdapter: RecyclerView.Adapter<TransactionAdapter.ViewHolder>() { + class ViewHolder(val view:View): RecyclerView.ViewHolder(view) + + override fun onCreateViewHolder(parent: ViewGroup, viewType: Int): ViewHolder { + TODO("Not yet implemented") + } + + override fun getItemCount(): Int { + TODO("Not yet implemented") + } + + override fun onBindViewHolder(holder: ViewHolder, position: Int) { + TODO("Not yet implemented") + } +} \ No newline at end of file diff --git a/app/src/main/java/com/pbd/psi/ui/transaction/TransactionFragment.kt b/app/src/main/java/com/pbd/psi/ui/transaction/TransactionFragment.kt index b38f6ae30d2d82bf75a4d692bd64bfb0bf99d192..cc70303f4966c30279e4bc21c3397d43dbe4a935 100644 --- a/app/src/main/java/com/pbd/psi/ui/transaction/TransactionFragment.kt +++ b/app/src/main/java/com/pbd/psi/ui/transaction/TransactionFragment.kt @@ -6,55 +6,26 @@ import android.view.LayoutInflater import android.view.View import android.view.ViewGroup import com.pbd.psi.R +import com.pbd.psi.databinding.FragmentTransactionBinding +import com.pbd.psi.repository.TransactionRepository +import com.pbd.psi.room.AppDatabase -// TODO: Rename parameter arguments, choose names that match -// the fragment initialization parameters, e.g. ARG_ITEM_NUMBER -private const val ARG_PARAM1 = "param1" -private const val ARG_PARAM2 = "param2" - -/** - * A simple [Fragment] subclass. - * Use the [TransactionFragment.newInstance] factory method to - * create an instance of this fragment. - */ class TransactionFragment : Fragment() { - // TODO: Rename and change types of parameters - private var param1: String? = null - private var param2: String? = null - - override fun onCreate(savedInstanceState: Bundle?) { - super.onCreate(savedInstanceState) - arguments?.let { - param1 = it.getString(ARG_PARAM1) - param2 = it.getString(ARG_PARAM2) - } - } + private lateinit var binding: FragmentTransactionBinding override fun onCreateView( inflater: LayoutInflater, container: ViewGroup?, savedInstanceState: Bundle? - ): View? { - // Inflate the layout for this fragment - return inflater.inflate(R.layout.fragment_transaction, container, false) + ): View { + binding = FragmentTransactionBinding.inflate(inflater, container, false) + val appDatabase = AppDatabase.getDatabase(requireContext()) + val repository = TransactionRepository(appDatabase) + val viewModel = TransactionViewModel(repository) +// binding.transList.text = viewModel.transactionList + return binding.root } - companion object { - /** - * Use this factory method to create a new instance of - * this fragment using the provided parameters. - * - * @param param1 Parameter 1. - * @param param2 Parameter 2. - * @return A new instance of fragment TransactionFragment. - */ - // TODO: Rename and change types and number of parameters - @JvmStatic - fun newInstance(param1: String, param2: String) = - TransactionFragment().apply { - arguments = Bundle().apply { - putString(ARG_PARAM1, param1) - putString(ARG_PARAM2, param2) - } - } + override fun onViewCreated(view: View, savedInstanceState: Bundle?) { + super.onViewCreated(view, savedInstanceState) } } \ No newline at end of file diff --git a/app/src/main/java/com/pbd/psi/ui/transaction/TransactionViewModel.kt b/app/src/main/java/com/pbd/psi/ui/transaction/TransactionViewModel.kt new file mode 100644 index 0000000000000000000000000000000000000000..f92ec63319a7416d0f9de8c86180d3a7f207be09 --- /dev/null +++ b/app/src/main/java/com/pbd/psi/ui/transaction/TransactionViewModel.kt @@ -0,0 +1,34 @@ +package com.pbd.psi.ui.transaction + +import androidx.lifecycle.LiveData +import androidx.lifecycle.ViewModel +import androidx.lifecycle.viewModelScope +import com.pbd.psi.repository.TransactionRepository +import com.pbd.psi.room.TransactionEntity +import kotlinx.coroutines.launch + +class TransactionViewModel( + private val repository: TransactionRepository, +) : ViewModel() { + var transactionList: LiveData<List<TransactionEntity>> = repository.transactionList + + fun getTransById(id: Int) = viewModelScope.launch { + repository.getTransById(id) + } + + fun addTransaction(trans: TransactionEntity) = viewModelScope.launch { + repository.addTransaction(trans) + } + + fun updateTransaction(trans: TransactionEntity) = viewModelScope.launch { + repository.updateTransaction(trans) + } + + fun deleteTransaction(trans: TransactionEntity) = viewModelScope.launch { + repository.deleteTransaction(trans) + } + + companion object { + + } +} \ No newline at end of file diff --git a/app/src/main/res/layout/activity_main.xml b/app/src/main/res/layout/activity_main.xml index bae3daf6fdaa04487e18ca05ff81213fe836fba0..7b1048f6485ed6d165c3f4523e547f34c88d0109 100644 --- a/app/src/main/res/layout/activity_main.xml +++ b/app/src/main/res/layout/activity_main.xml @@ -5,18 +5,6 @@ android:layout_width="match_parent" android:layout_height="match_parent"> -<!-- <androidx.appcompat.widget.Toolbar--> -<!-- android:id="@+id/toolbar"--> -<!-- android:layout_width="match_parent"--> -<!-- android:layout_height="wrap_content"--> -<!-- android:background="?attr/colorPrimary"--> -<!-- android:minHeight="?attr/actionBarSize"--> -<!-- android:theme="?attr/actionBarTheme"--> -<!-- app:layout_constraintBottom_toTopOf="@+id/fragmentContainerView"--> -<!-- app:layout_constraintEnd_toEndOf="parent"--> -<!-- app:layout_constraintStart_toStartOf="parent"--> -<!-- app:layout_constraintTop_toTopOf="parent" />--> - <androidx.fragment.app.FragmentContainerView android:id="@+id/fragmentContainerView" android:name="androidx.navigation.fragment.NavHostFragment" diff --git a/app/src/main/res/layout/fragment_add_trans.xml b/app/src/main/res/layout/fragment_add_trans.xml new file mode 100644 index 0000000000000000000000000000000000000000..0027c7358abf40df4421f9b3fdb69e730c727c3e --- /dev/null +++ b/app/src/main/res/layout/fragment_add_trans.xml @@ -0,0 +1,97 @@ +<?xml version="1.0" encoding="utf-8"?> +<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" + xmlns:tools="http://schemas.android.com/tools" + android:layout_width="match_parent" + android:layout_height="match_parent" + android:orientation="vertical" + android:background="@color/primaryBlack" + xmlns:app="http://schemas.android.com/apk/res-auto" + tools:context=".ui.transaction.TransactionFragment"> + + <com.google.android.material.appbar.AppBarLayout + android:id="@+id/twibbon_header" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:background="@color/primaryBlack" + app:layout_constraintTop_toTopOf="parent"> + <androidx.constraintlayout.widget.ConstraintLayout + android:layout_width="match_parent" + android:layout_height="wrap_content"> + <TextView + android:id="@+id/twibbon_header_text" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:fontFamily="@font/montserrat" + android:text="@string/transaction_header" + android:textColor="@color/white" + android:textSize="20sp" + android:layout_marginVertical="8dp" + android:layout_gravity="center" + app:layout_constraintBottom_toBottomOf="parent" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintStart_toStartOf="parent" + app:layout_constraintTop_toTopOf="parent" /> + </androidx.constraintlayout.widget.ConstraintLayout> + </com.google.android.material.appbar.AppBarLayout> + + <LinearLayout + android:layout_width="match_parent" + android:layout_height="match_parent" + android:orientation="vertical" + android:gravity="center" + android:padding="15dp" + > + + <androidx.cardview.widget.CardView + android:id="@+id/cart_card_view" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_marginBottom="8dp" + app:cardBackgroundColor="@color/primaryDarker" + app:layout_constraintTop_toTopOf="parent" + app:cardCornerRadius="20dp"> + <androidx.constraintlayout.widget.ConstraintLayout + android:id="@+id/menu_data" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:paddingHorizontal="10dp" + android:paddingTop="15dp" + android:paddingBottom="35dp"> + + <LinearLayout + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:orientation="vertical" + app:layout_constraintBottom_toBottomOf="parent" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintStart_toStartOf="parent" + app:layout_constraintTop_toTopOf="parent"> + + <EditText + android:id="@+id/title_input" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:background="@color/white" + android:hint="@string/title_hint" + android:inputType="text" + android:padding="10dp" + app:layout_constraintBottom_toTopOf="@id/amount_input" + app:layout_constraintWidth="match_parent" + android:layout_marginBottom="20dp" + /> + + <EditText + android:id="@+id/amount_input" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:background="@color/white" + android:hint="@string/amount_hint" + android:inputType="number" + android:padding="10dp" + app:layout_constraintTop_toBottomOf="@+id/title_input" /> + </LinearLayout> + + </androidx.constraintlayout.widget.ConstraintLayout> + </androidx.cardview.widget.CardView> + </LinearLayout> +</LinearLayout> \ No newline at end of file diff --git a/app/src/main/res/layout/fragment_expense.xml b/app/src/main/res/layout/fragment_expense.xml new file mode 100644 index 0000000000000000000000000000000000000000..8cf66b24a54ff3dc48417323f6e31a58571a2007 --- /dev/null +++ b/app/src/main/res/layout/fragment_expense.xml @@ -0,0 +1,14 @@ +<?xml version="1.0" encoding="utf-8"?> +<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" + xmlns:tools="http://schemas.android.com/tools" + android:layout_width="match_parent" + android:layout_height="match_parent" + tools:context=".ui.add_transaction.ExpenseFragment"> + + <!-- TODO: Update blank fragment layout --> + <TextView + android:layout_width="match_parent" + android:layout_height="match_parent" + android:text="@string/hello_blank_fragment" /> + +</FrameLayout> \ No newline at end of file diff --git a/app/src/main/res/layout/fragment_income.xml b/app/src/main/res/layout/fragment_income.xml new file mode 100644 index 0000000000000000000000000000000000000000..04beaeb378c24fd5f0c5b70e02b0dd8130e003da --- /dev/null +++ b/app/src/main/res/layout/fragment_income.xml @@ -0,0 +1,64 @@ +<?xml version="1.0" encoding="utf-8"?> +<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" + xmlns:tools="http://schemas.android.com/tools" + android:layout_width="match_parent" + android:layout_height="match_parent" + tools:context=".ui.add_transaction.IncomeFragment" + android:background="@color/primaryDarker" + xmlns:app="http://schemas.android.com/apk/res-auto"> + + <androidx.cardview.widget.CardView + android:id="@+id/cart_card_view" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:layout_marginBottom="8dp" + app:cardBackgroundColor="@color/primaryDarker" + app:layout_constraintTop_toTopOf="parent" + app:cardCornerRadius="20dp"> + <androidx.constraintlayout.widget.ConstraintLayout + android:id="@+id/menu_data" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:paddingHorizontal="10dp" + android:paddingTop="15dp" + android:paddingBottom="35dp"> + + <LinearLayout + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:orientation="vertical" + app:layout_constraintBottom_toBottomOf="parent" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintStart_toStartOf="parent" + app:layout_constraintTop_toTopOf="parent"> + + <EditText + android:id="@+id/title_input" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:background="@color/white" + android:hint="@string/title_hint" + android:inputType="text" + android:padding="10dp" + app:layout_constraintBottom_toTopOf="@id/amount_input" + app:layout_constraintWidth="match_parent" + android:layout_marginBottom="20dp" + android:autofillHints="name" + /> + + <EditText + android:id="@+id/amount_input" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:background="@color/white" + android:hint="@string/amount_hint" + android:inputType="number" + android:padding="10dp" + android:autofillHints="postalCode" + app:layout_constraintTop_toBottomOf="@+id/title_input" /> + </LinearLayout> + + </androidx.constraintlayout.widget.ConstraintLayout> + </androidx.cardview.widget.CardView> + +</FrameLayout> \ No newline at end of file diff --git a/app/src/main/res/layout/fragment_transaction.xml b/app/src/main/res/layout/fragment_transaction.xml index 77b9867a1be170eb43d103ba0c3a40edfa43c414..793a68c847c10d61678d1b5d99af648bf520c4f1 100644 --- a/app/src/main/res/layout/fragment_transaction.xml +++ b/app/src/main/res/layout/fragment_transaction.xml @@ -1,14 +1,208 @@ <?xml version="1.0" encoding="utf-8"?> -<FrameLayout xmlns:android="http://schemas.android.com/apk/res/android" +<androidx.constraintlayout.widget.ConstraintLayout xmlns:android="http://schemas.android.com/apk/res/android" xmlns:tools="http://schemas.android.com/tools" android:layout_width="match_parent" android:layout_height="match_parent" + android:orientation="vertical" + android:background="@color/primaryBlack" + xmlns:app="http://schemas.android.com/apk/res-auto" tools:context=".ui.transaction.TransactionFragment"> - <!-- TODO: Update blank fragment layout --> - <TextView + <com.google.android.material.appbar.AppBarLayout + android:id="@+id/transaction_header" android:layout_width="match_parent" - android:layout_height="match_parent" - android:text="@string/transaction_fragment" /> + android:layout_height="wrap_content" + android:background="@color/primaryBlack" + app:layout_constraintTop_toTopOf="parent"> + <androidx.constraintlayout.widget.ConstraintLayout + android:layout_width="match_parent" + android:layout_height="wrap_content"> + <TextView + android:id="@+id/transaction_header_text" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:fontFamily="@font/montserrat" + android:text="@string/transaction_header" + android:textColor="@color/white" + android:textSize="20sp" + android:layout_marginVertical="8dp" + android:layout_gravity="center" + app:layout_constraintBottom_toBottomOf="parent" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintStart_toStartOf="parent" + app:layout_constraintTop_toTopOf="parent" /> + </androidx.constraintlayout.widget.ConstraintLayout> + </com.google.android.material.appbar.AppBarLayout> -</FrameLayout> \ No newline at end of file + <androidx.constraintlayout.widget.ConstraintLayout + android:id="@+id/transaction_info" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:orientation="horizontal" + android:layout_margin="20dp" + app:layout_constraintBottom_toTopOf="@+id/transaction_legend" + app:layout_constraintTop_toBottomOf="@+id/transaction_header"> + + <RelativeLayout + android:id="@+id/balance_info" + android:layout_width="wrap_content" + android:layout_height="match_parent" + android:orientation="vertical" + app:layout_constraintHorizontal_chainStyle="spread_inside" + app:layout_constraintEnd_toStartOf="@+id/add_button" + app:layout_constraintStart_toStartOf="@id/transaction_info" + app:layout_constraintTop_toTopOf="parent" + app:layout_constraintBottom_toBottomOf="parent" + > + <TextView + android:id="@+id/balance_label" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:text="@string/total_balance" /> + + <TextView + android:id="@+id/balance_nominal" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:text="@string/transaction_fragment" + android:textSize="20sp" + android:textColor="@color/white" + android:layout_below="@+id/balance_label"/> + + </RelativeLayout> + + <Button + android:id="@+id/add_button" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:text="@string/retake" + app:layout_constraintBottom_toBottomOf="@id/transaction_info" + app:layout_constraintEnd_toEndOf="@id/transaction_info" + app:layout_constraintStart_toEndOf="@+id/balance_info" + app:layout_constraintTop_toTopOf="@id/transaction_info" /> + + </androidx.constraintlayout.widget.ConstraintLayout> + + <androidx.constraintlayout.widget.ConstraintLayout + android:id="@+id/transaction_legend" + android:layout_width="match_parent" + android:layout_height="wrap_content" + android:orientation="horizontal" + app:layout_constraintHorizontal_chainStyle="spread" + app:layout_constraintBottom_toTopOf="@+id/transaction_list" + app:layout_constraintStart_toStartOf="parent" + app:layout_constraintTop_toBottomOf="@+id/transaction_info"> + + <RelativeLayout + android:id="@+id/income" + android:layout_width="wrap_content" + android:layout_height="match_parent" + android:orientation="vertical" + app:layout_constraintStart_toStartOf="@id/transaction_legend" + app:layout_constraintEnd_toStartOf="@+id/expense"> + + <ImageView + android:id="@+id/income_icon" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:contentDescription="@string/income" + android:src="@drawable/income_icon" + android:layout_centerHorizontal="true" + /> + + <TextView + android:id="@+id/income_text" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:text="@string/income" + android:layout_below="@id/income_icon" + android:layout_centerHorizontal="true" /> + + </RelativeLayout> + + <RelativeLayout + android:id="@+id/expense" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:orientation="vertical" + app:layout_constraintEnd_toStartOf="@id/all_flow" + app:layout_constraintStart_toEndOf="@id/income" + app:layout_constraintTop_toTopOf="parent"> + + <ImageView + android:id="@+id/expense_icon" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:contentDescription="@string/expense" + android:src="@drawable/outcome_icon" + android:layout_centerHorizontal="true" + /> + + <TextView + android:id="@+id/expense_text" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:text="@string/expense" + android:layout_below="@id/expense_icon" + android:layout_centerHorizontal="true" /> + + </RelativeLayout> + + <RelativeLayout + android:id="@+id/all_flow" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:orientation="vertical" + app:layout_constraintBottom_toBottomOf="@id/transaction_legend" + app:layout_constraintEnd_toEndOf="@id/transaction_legend" + app:layout_constraintStart_toEndOf="@id/expense" + app:layout_constraintTop_toTopOf="@id/transaction_legend"> + + <ImageView + android:id="@+id/all_flow_icon" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:contentDescription="@string/income" + android:src="@drawable/upload" + android:layout_centerHorizontal="true" + /> + + <TextView + android:id="@+id/all_flow_text" + android:layout_width="wrap_content" + android:layout_height="wrap_content" + android:text="@string/all" + android:layout_below="@id/all_flow_icon" + android:layout_centerHorizontal="true" /> + + </RelativeLayout> + + + </androidx.constraintlayout.widget.ConstraintLayout> + + <androidx.cardview.widget.CardView + android:id="@+id/transaction_list" + android:layout_width="match_parent" + android:layout_height="0dp" + android:layout_weight="1" + android:layout_margin="10dp" + app:cardCornerRadius="15dp" + app:cardBackgroundColor="@color/primaryDarker" + app:cardElevation="0dp" + app:cardUseCompatPadding="true" + app:layout_constraintBottom_toBottomOf="parent" + app:layout_constraintEnd_toEndOf="parent" + app:layout_constraintHorizontal_bias="0.0" + app:layout_constraintStart_toStartOf="parent" + app:layout_constraintTop_toBottomOf="@id/transaction_legend"> + + <androidx.recyclerview.widget.RecyclerView + android:layout_width="match_parent" + android:layout_height="match_parent" + android:layout_margin="10dp" + app:layoutManager="androidx.recyclerview.widget.LinearLayoutManager" /> + + </androidx.cardview.widget.CardView> + + +</androidx.constraintlayout.widget.ConstraintLayout> diff --git a/app/src/main/res/values/strings.xml b/app/src/main/res/values/strings.xml index 6ad7697436697663ef3a966628183c182e46f383..ecf7e71f56d22f5f398063aed142da7187f1cfdc 100644 --- a/app/src/main/res/values/strings.xml +++ b/app/src/main/res/values/strings.xml @@ -31,4 +31,17 @@ <string name="retake">Retake</string> <string name="change">Change</string> <string name="twibbon_command">Put your face inside the twibbon</string> + + <!-- Transaction--> + <string name="transaction_header">Transaksi</string> + <string name="title_hint">Title</string> + <string name="amount_hint">Amount</string> + <string name="total_balance">Total Balance</string> + <string name="income">Pemasukan</string> + <string name="expense">Pengeluaran</string> + <string name="all">Semua</string> + + + + </resources>