Second Commit:

Version 1.5 [Partialy Optimized Version] [UI Fixes And Improvment]
Todo:
Optimized the Code
Add String Theolgy
This commit is contained in:
Diassdp
2025-02-02 00:12:52 +07:00
parent f299dfb3a0
commit b1f05c0d1c
29 changed files with 825 additions and 448 deletions

View File

@ -1,5 +1,8 @@
package com.healthjournal.ui.dashboard
import android.app.AlarmManager
import android.app.PendingIntent
import android.content.Context
import android.content.Intent
import android.os.Bundle
import android.util.Log
@ -7,6 +10,7 @@ import android.view.View
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
import androidx.recyclerview.widget.LinearLayoutManager
import com.google.android.material.bottomnavigation.BottomNavigationView
import com.google.firebase.Firebase
import com.google.firebase.auth.FirebaseAuth
import com.google.firebase.database.FirebaseDatabase
@ -14,46 +18,98 @@ import com.google.firebase.database.database
import com.healthjournal.R
import com.healthjournal.data.ResultData
import com.healthjournal.databinding.ActivityMainBinding
import com.healthjournal.receiver.ReminderReceiver
import com.healthjournal.ui.journal.input.JournalInputActivity
import com.healthjournal.ui.login.LoginActivity
import com.healthjournal.ui.profile.ProfileActivity
import com.healthjournal.ui.recommendation.RecommendationActivity
import com.healthjournal.utils.NotificationUtils
import java.text.SimpleDateFormat
import java.util.Calendar
import java.util.Locale
class MainActivity : AppCompatActivity() {
private lateinit var binding: ActivityMainBinding
private lateinit var user: FirebaseAuth
private lateinit var mainAdapter: MainAdapter
private lateinit var database: FirebaseDatabase
private val healthDataList: MutableList<ResultData> = mutableListOf()
private val database = Firebase.database
private var dailyReport = false
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
binding = ActivityMainBinding.inflate(layoutInflater)
// Create notification channel
NotificationUtils.createNotificationChannel(this)
// Schedule reminders
scheduleHealthReminders(this)
setContentView(binding.root)
user = FirebaseAuth.getInstance()
database = FirebaseDatabase.getInstance()
userCheck()
setupListener()
populateHistory()
navigationBottomBar()
}
private fun navigationBottomBar(){
binding.bottomNavigation.setOnItemSelectedListener {
when(it.itemId){
R.id.nav_add -> addJournal()
R.id.nav_home -> home()
R.id.nav_profile -> profile()
private fun scheduleHealthReminders(context: Context) {
val alarmManager = context.getSystemService(Context.ALARM_SERVICE) as AlarmManager
val daysOfWeek = listOf(Calendar.MONDAY, Calendar.WEDNESDAY, Calendar.FRIDAY)
for (day in daysOfWeek.shuffled().take(3)) {
val calendar = Calendar.getInstance().apply {
set(Calendar.DAY_OF_WEEK, day)
set(Calendar.HOUR_OF_DAY, 9) // Set reminder at 9 AM
set(Calendar.MINUTE, 0)
set(Calendar.SECOND, 0)
}
true
val intent = Intent(context, ReminderReceiver::class.java)
val pendingIntent = PendingIntent.getBroadcast(
context, day, intent, PendingIntent.FLAG_UPDATE_CURRENT or PendingIntent.FLAG_IMMUTABLE
)
alarmManager.setRepeating(
AlarmManager.RTC_WAKEUP,
calendar.timeInMillis,
AlarmManager.INTERVAL_DAY * 7, // Repeat every week
pendingIntent
)
}
}
private fun navigationBottomBar() {
val bottomNav = findViewById<BottomNavigationView>(R.id.nav_view)
bottomNav.setOnItemSelectedListener { item ->
when (item.itemId) {
R.id.nav_home -> {
finish()
startActivity(intent)
overridePendingTransition(0, 0)
true
}
R.id.nav_profile -> {
startActivity(Intent(this, ProfileActivity::class.java))
true
}
else -> false
}
}
binding.ivAdd.setOnClickListener {
if (dailyReport) {
Toast.makeText(this, "Daily Report Already Created", Toast.LENGTH_SHORT).show()
} else {
startActivity(Intent(this, JournalInputActivity::class.java))
}
}
}
private fun getWeekCount() {
val today = Calendar.getInstance()
val userID = user.currentUser!!.uid
@ -116,6 +172,7 @@ class MainActivity : AppCompatActivity() {
}
private fun dailycheck() {
getWeekCount()
val today = SimpleDateFormat("dd/MM/yyyy", Locale.getDefault()).format(android.icu.util.Calendar.getInstance().time).toString()
val userID = user.currentUser!!.uid
database.getReference("users").child(userID).child("journal").get().addOnCompleteListener { task ->
@ -124,7 +181,8 @@ class MainActivity : AppCompatActivity() {
if (it.child("date").value.toString() == today) {
dailyReport = true
switchLayout()
populateTodayReport()
val referencePath = it.key ?: return@forEach
populateTodayReport(referencePath)
}
}
} else {
@ -158,9 +216,12 @@ class MainActivity : AppCompatActivity() {
val user = FirebaseAuth.getInstance().currentUser
if (user == null) {
Toast.makeText(this, "Please Login to an account", Toast.LENGTH_SHORT).show()
// Redirect to LoginActivity
val intent = Intent(this, LoginActivity::class.java)
startActivity(intent)
finish()
} else {
Toast.makeText(this, "Welcome back!", Toast.LENGTH_SHORT).show()
dailycheck()
@ -183,14 +244,15 @@ class MainActivity : AppCompatActivity() {
if (task.isSuccessful) {
healthDataList.clear()
task.result.children.forEach { snapshot ->
val journalID = snapshot.child("date").value.toString()
val journalID = snapshot.key.toString()
val bloodSugar = snapshot.child("bloodSugar").value.toString().toFloatOrNull() ?: 0f
val diastolicBP = snapshot.child("bloodPressureDIA").value.toString().toIntOrNull() ?: 0
val systolicBP = snapshot.child("bloodPressureSYS").value.toString().toIntOrNull() ?: 0
val BMI = snapshot.child("bmi").value.toString().toFloatOrNull() ?: 0f
val date = snapshot.child("date").value.toString()
val task = snapshot.child("recommendation").child("task").value as? List<Map<String, Any>> ?: emptyList()
val resultData = ResultData(journalID, bloodSugar, diastolicBP, systolicBP, BMI, date)
val resultData = ResultData(journalID, bloodSugar, diastolicBP, systolicBP, BMI, date, task)
healthDataList.add(resultData)
}
mainAdapter.notifyDataSetChanged()
@ -202,24 +264,19 @@ class MainActivity : AppCompatActivity() {
}
private fun populateTodayReport(){
val today = SimpleDateFormat("dd/MM/yyyy", Locale.getDefault()).format(android.icu.util.Calendar.getInstance().time).toString()
private fun populateTodayReport(referencePath: String){
val userID = user.currentUser!!.uid
database.getReference("users").child(userID).child("journal").get().addOnCompleteListener { task ->
if (task.isSuccessful) {
task.result.children.forEach {
if (it.child("date").value.toString() == today) {
binding.tvBloodsugarLevel.text = it.child("bloodSugar").value.toString()+" mg/dL"
binding.tvBloodsugarDesc.text = it.child("recommendation").child("bloodSugarAnalysis").value.toString()
binding.tvBloodpressureLevel.text = it.child("bloodPressureDIA").value.toString()+"/"+it.child("bloodPressureSYS").value.toString()+" mm Hg"
binding.tvBloodpressureDesc.text = it.child("recommendation").child("bloodPressureAnalysis").value.toString()
binding.tvBmiLevel.text = it.child("BMI").value.toString() +" BMI"
binding.tvBmiDesc.text = it.child("recommendation").child("BMIAnalysis").value.toString()
}
}
database.getReference("users").child(userID).child("journal").child(referencePath).get().addOnCompleteListener {
if (it.isSuccessful) {
binding.tvBloodsugarLevel.text = it.result.child("bloodSugar").value.toString()+" mg/dL"
binding.tvBloodsugarDesc.text = it.result.child("recommendation").child("bloodSugarAnalysis").value.toString()
binding.tvBloodpressureLevel.text = it.result.child("bloodPressureDIA").value.toString()+"/"+it.result.child("bloodPressureSYS").value.toString()+" mm Hg"
binding.tvBloodpressureDesc.text = it.result.child("recommendation").child("bloodPressureAnalysis").value.toString()
binding.tvBmiLevel.text = it.result.child("BMI").value.toString() +" BMI"
binding.tvBmiDesc.text = it.result.child("recommendation").child("BMIAnalysis").value.toString()
} else {
Log.d("error", task.exception!!.message.toString())
Toast.makeText(this, task.exception!!.message, Toast.LENGTH_SHORT).show()
Log.d("error", it.exception!!.message.toString())
Toast.makeText(this, it.exception!!.message, Toast.LENGTH_SHORT).show()
}
}
}

View File

@ -19,6 +19,7 @@ class MainAdapter(private val healthDataList: MutableList<ResultData>) : Recycle
val tvDate: TextView = view.findViewById(R.id.tv_date)
val tvBloodSugar: TextView = view.findViewById(R.id.tv_BS_Level)
val tvBloodPressure: TextView = view.findViewById(R.id.tv_BP_Level)
val tvGoals: TextView = view.findViewById(R.id.tv_goals_count)
}
// Function to update the list and notify the adapter
@ -48,8 +49,19 @@ class MainAdapter(private val healthDataList: MutableList<ResultData>) : Recycle
}
}
private fun countGoals (){
private fun countGoals (list: List<Map<String, Any>>): String {
var completedGoals = 0
var goalsCount = 0
for (item in list) {
if (item["completed"] == true) {
completedGoals++
}
goalsCount++
}
if (completedGoals == 0) {
return "No goals completed"
}
return "$completedGoals/$goalsCount goals completed"
}
override fun onBindViewHolder(holder: HealthViewHolder, position: Int) {
@ -59,11 +71,11 @@ class MainAdapter(private val healthDataList: MutableList<ResultData>) : Recycle
holder.tvDate.text = healthData.date
holder.tvBloodSugar.text = "${healthData.bloodSugar} mg/dL"
holder.tvBloodPressure.text = "${healthData.diastolicBP}/${healthData.systolicBP} mm Hg"
holder.tvGoals.text = countGoals(healthData.task)
holder.itemView.setOnClickListener {
val context = holder.itemView.context
val intent = Intent(context, DetailJournalActivity::class.java).apply {
putExtra("HEALTH_DATA", healthData)
putExtra("JOURNAL_KEY", healthData.journalID)
}
context.startActivity(intent)
}

View File

@ -23,47 +23,70 @@ class DetailJournalActivity : AppCompatActivity() {
super.onCreate(savedInstanceState)
binding = ActivityDetailJournalBinding.inflate(layoutInflater)
setContentView(binding.root)
val healthData = intent.getSerializableExtra("HEALTH_DATA") as? ResultData
user = FirebaseAuth.getInstance()
setupListener()
populateDetailJournal()
}
private fun countGoals(taskList: List<Map<String, Any>>): String {
var completedGoals = 0
val totalGoals = taskList.size
for (task in taskList) {
val isCompleted = task["completed"] as? Boolean ?: false
if (isCompleted) {
completedGoals++
}
}
return when {
totalGoals == 0 -> "No goals available"
completedGoals == 0 -> "No goals completed"
else -> "$completedGoals/$totalGoals goals completed"
}
}
private fun populateDetailJournal() {
val userID = user.currentUser?.uid
val journalDate = intent.getStringExtra("JOURNAL_DATE")
if (userID != null && journalDate != null) {
database.getReference("users").child(userID).child("journal").child(journalDate).get()
.addOnCompleteListener(DetailJournalActivity()) {
if (it.isSuccessful) {
val data = it.result
if (data != null) {
/*
binding.tvBloodsugarLevel2.text = data.bloodSugarLevel
binding.tvBloodsugarDesc.text = data.bloodSugarDesc
binding.tvBloodpressureLevel2.text = data.bloodPressureLevel
binding.tvBloodpressureDesc.text = data.bloodPressureDesc
binding.tvBMILevel2.text = data.bmiLevel
binding.tvBMIDesc.text = data.bmiDesc
binding.tvGoals2.text = countGoalsCompleted(data.goalsCompleted)
binding.tvJournalNote.text = data.journalNote
*/
val journalID = intent.getStringExtra("JOURNAL_KEY")
if (userID != null && journalID != null) {
database.getReference("users").child(userID).child("journal").child(journalID).get()
.addOnCompleteListener(this) { task ->
if (task.isSuccessful) {
val result = task.result
if (result.exists()) {
binding.tvBloodsugarLevel2.text = "${result.child("bloodSugar").value ?: "N/A"} mg/dL"
binding.tvBloodsugarDesc.text = result.child("recommendation").child("bloodSugarAnalysis").value?.toString() ?: "No data"
binding.tvBloodpressureLevel2.text = "${result.child("bloodPressureDIA").value ?: "N/A"}/${result.child("bloodPressureSYS").value ?: "N/A"} mm Hg"
binding.tvBloodpressureDesc.text = result.child("recommendation").child("bloodPressureAnalysis").value?.toString() ?: "No data"
binding.tvBMILevel2.text = "${result.child("BMI").value ?: "N/A"} BMI"
binding.tvBMIDesc.text = result.child("recommendation").child("BMIAnalysis").value?.toString() ?: "No data"
binding.tvJournalNote.text = result.child("note").value?.toString() ?: "No notes available"
val taskListSnapshot = result.child("recommendation").child("tasks")
Log.d("debug", taskListSnapshot.toString())
val taskList = mutableListOf<Map<String, Any>>()
if (taskListSnapshot.exists()) {
for (taskSnapshot in taskListSnapshot.children) {
val taskMap = taskSnapshot.value as? Map<String, Any>
if (taskMap != null) {
taskList.add(taskMap)
}
}
}
binding.tvGoals2.text = countGoals(taskList)
} else {
Toast.makeText(this, "No journal entry found.", Toast.LENGTH_SHORT).show()
}
} else {
Toast.makeText(this, it.exception!!.message, Toast.LENGTH_SHORT).show()
Log.d("error", it.exception!!.message.toString())
Toast.makeText(this, task.exception?.message ?: "Error fetching data", Toast.LENGTH_SHORT).show()
Log.d("error", task.exception?.message.toString())
}
}
}
}
private fun countGoalsCompleted(goalsCompleted: List<Boolean>): String {
var count = 0
for (completed in goalsCompleted) {
if (completed) {
count++
}
}
return count.toString()
}
private fun deleteHistory() {
val userID = user.currentUser?.uid

View File

@ -24,10 +24,14 @@ class ProfileActivity : AppCompatActivity() {
super.onCreate(savedInstanceState)
binding = ActivityProfileBinding.inflate(layoutInflater)
setContentView(binding.root)
user = FirebaseAuth.getInstance()
setupListener()
populateData()
}
private fun setupListener() {
binding.btnLogout.setOnClickListener {
logout()
@ -47,13 +51,11 @@ class ProfileActivity : AppCompatActivity() {
private fun updateData(){
val userID = user.currentUser?.uid
val name = binding.edtName.text.toString()
val email = binding.edtEmail.text.toString()
val date = binding.edtDates.text.toString()
val date = binding.edtDate.text.toString()
val weight = binding.edtInputWeight.text.toString()
val height = binding.edtInputHeight.text.toString()
val userRef = database.getReference("users").child(userID!!)
userRef.child("name").setValue(name)
userRef.child("email").setValue(email)
userRef.child("date").setValue(date)
userRef.child("weight").setValue(weight)
userRef.child("height").setValue(height)
@ -61,13 +63,14 @@ class ProfileActivity : AppCompatActivity() {
populateData()
}
private fun populateData(){
val userID = user.currentUser?.uid
val userRef = database.getReference("users").child(userID!!)
userRef.get().addOnCompleteListener(ProfileActivity()){
if (it.isSuccessful){
private fun populateData() {
val userID = user.currentUser?.uid ?: return
val userRef = database.getReference("users").child(userID)
userRef.get().addOnCompleteListener(this) {
if (it.isSuccessful) {
binding.edtName.setText(it.result.child("name").value.toString())
binding.edtDates.setText(it.result.child("date").value.toString())
binding.edtDate.setText(it.result.child("date").value.toString())
binding.edtInputHeight.setText(it.result.child("height").value.toString())
binding.edtInputWeight.setText(it.result.child("weight").value.toString())
} else {
@ -78,4 +81,5 @@ class ProfileActivity : AppCompatActivity() {
}
}