Add date goal handling for user journal

This commit is contained in:
Christopher C. Wells 2021-05-14 20:56:13 -07:00 committed by Christopher Charbonneau Wells
parent 153611e66d
commit 91fd85ef83
4 changed files with 41 additions and 29 deletions

View File

@ -42,25 +42,20 @@ class JournalEntryController extends Controller
}
// Get daily goals data for user.
$goals = Auth::user()->getGoalsByTime($date);
$dailyGoals = [];
foreach (Nutrients::all()->pluck('value') as $nutrient) {
$goal = $goals['present']
->where('frequency', 'daily')
->where('name', $nutrient)
->first();
if ($goal) {
$dailyGoals[$goal->name] = round($sums[$goal->name] / $goal->goal * 100);
if ($dailyGoals[$goal->name] > 0) {
$dailyGoals[$goal->name] .= '%';
}
$goal = Auth::user()->getGoalByDate($date);
$goalProgress = [];
if ($goal) {
foreach (Nutrients::all()->pluck('value') as $nutrient) {
$goalProgress[$nutrient] = round($sums[$nutrient] / $goal->{$nutrient} * 100);
$goalProgress[$nutrient] .= '%';
}
}
return view('journal-entries.index')
->with('entries', $entries)
->with('sums', $sums)
->with('dailyGoals', $dailyGoals)
->with('goal', $goal)
->with('goalProgress', $goalProgress)
->with('date', $date);
}

View File

@ -81,6 +81,7 @@ final class Goal extends Model
* Each entry has the following keys:
* - value: Day value (used for bitwise operations).
* - label: Human-readable name for the day.
* - dow: ISO-8601 numeric representation of the day of the week.
*/
public static function days(): Collection
{
@ -88,30 +89,37 @@ final class Goal extends Model
[
'value' => 1,
'label' => 'monday',
'dow' => 1,
],
[
'value' => 2,
'label' => 'tuesday',
'dow' => 2,
],
[
'value' => 4,
'label' => 'wednesday',
'dow' => 3,
],
[
'value' => 8,
'label' => 'thursday',
'dow' => 4,
],
[
'value' => 16,
'label' => 'friday',
'dow' => 5,
],
[
'value' => 32,
'label' => 'saturday',
'dow' => 6,
],
[
'value' => 64,
'label' => 'sunday',
'dow' => 7,
],
]);
}

View File

@ -106,14 +106,14 @@ final class User extends Authenticatable implements HasMedia
}
/**
* Get User's past, present, and future goals.
*
* @todo Refactor or remove as needed.
*
* @return \Illuminate\Support\Collection[]
* Get user's goal (if one exists) for a specific date.
*/
public function getGoalsByTime(?Carbon $date = null): array {
return ['past' => new Collection(), 'present' => new Collection(), 'future' => new Collection()];
public function getGoalByDate(Carbon $date): ?Goal {
$day = Goal::days()->firstWhere('dow', $date->format('N'));
if (!$day) {
throw new \BadMethodCallException("No day with `dow` value {$date->format('N')}.");
}
return $this->goals()->whereRaw("(days & {$day['value']}) != 0")->get()->first();
}
/**

View File

@ -51,7 +51,7 @@
<span class="text-lg">{{ number_format($sums['calories']) }}</span>
</div>
<div class="font-extrabold text-right text-lg">
{{ $dailyGoals['calories'] ?? 'N/A' }}
{{ $goalProgress['calories'] ?? 'N/A' }}
</div>
</div>
<div class="flex justify-between items-baseline border-b border-gray-300 text-sm">
@ -60,7 +60,7 @@
{{ number_format($sums['fat']) }}g
</div>
<div class="text-right">
{{ $dailyGoals['fat'] ?? 'N/A' }}
{{ $goalProgress['fat'] ?? 'N/A' }}
</div>
</div>
<div class="flex justify-between items-baseline border-b border-gray-300 text-sm">
@ -69,7 +69,7 @@
{{ number_format($sums['cholesterol']) }}mg
</div>
<div class="text-right">
{{ $dailyGoals['cholesterol'] ?? 'N/A' }}
{{ $goalProgress['cholesterol'] ?? 'N/A' }}
</div>
</div>
<div class="flex justify-between items-baseline border-b border-gray-300 text-sm">
@ -78,7 +78,7 @@
{{ number_format($sums['sodium']) }}mg
</div>
<div class="text-right">
{{ $dailyGoals['sodium'] ?? 'N/A' }}
{{ $goalProgress['sodium'] ?? 'N/A' }}
</div>
</div>
<div class="flex justify-between items-baseline border-b border-gray-300 text-sm">
@ -87,7 +87,7 @@
{{ number_format($sums['carbohydrates']) }}g
</div>
<div class="text-right">
{{ $dailyGoals['carbohydrates'] ?? 'N/A' }}
{{ $goalProgress['carbohydrates'] ?? 'N/A' }}
</div>
</div>
<div class="flex justify-between items-baseline text-sm">
@ -96,9 +96,18 @@
{{ number_format($sums['protein']) }}g
</div>
<div class="text-right">
{{ $dailyGoals['protein'] ?? 'N/A' }}
{{ $goalProgress['protein'] ?? 'N/A' }}
</div>
</div>
<h4 class="font-semibold text-lg pt-2">Goal</h4>
@empty($goal)
<div class="italic">No goal.</div>
@else
<a class="text-gray-500 hover:text-gray-700 hover:border-gray-300"
href="{{ route('goals.show', $goal) }}">
{{ $goal->name }}
</a>
@endempty
</div>
<div class="w-full sm:w-3/5 md:w-2/3 lg:w-3/4 flex flex-col space-y-4">
@foreach(['breakfast', 'lunch', 'dinner', 'snacks'] as $meal)
@ -110,9 +119,9 @@
</div>
<span class="text-sm text-gray-500">
@foreach(\App\Support\Nutrients::all()->sortBy('weight') as $nutrient)
{{ \App\Support\Nutrients::round($entries->where('meal', $meal)->sum($nutrient['value']), $nutrient['value']) }}{{ $nutrient['unit'] }}
{{ $nutrient['value'] }}@if(!$loop->last), @endif
@endforeach
{{ \App\Support\Nutrients::round($entries->where('meal', $meal)->sum($nutrient['value']), $nutrient['value']) }}{{ $nutrient['unit'] }}
{{ $nutrient['value'] }}@if(!$loop->last), @endif
@endforeach
</span>
</h3>
@forelse($entries->where('meal', $meal) as $entry)