Forked from breadthe/app%Http%Livewire%Stats%DistanceByYear.php
Last active
February 3, 2021 17:05
-
-
Save rizkhal/5479de426dfad135631cc658d5825eed to your computer and use it in GitHub Desktop.
Laravel Livewire + Apexcharts
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
namespace App\Http\Livewire\Stats; | |
use Illuminate\Support\Facades\DB; | |
use Livewire\Component; | |
class DistanceByYear extends Component | |
{ | |
public $chartId; | |
public $athlete; | |
public $years; | |
public $distances; | |
public $total; | |
// Filters | |
public $bike; // aka bike_id; looks cleaner in the query string | |
public function render() | |
{ | |
$distancesByYear = $this->getDistancesByYear(); | |
$this->years = $distancesByYear->pluck('year'); | |
$this->distances = $distancesByYear | |
->pluck('total_distance') | |
->map(function ($distance) { | |
return session()->get('unit') === 'feet' | |
? metersToMiles($distance) | |
: metersToKm($distance); | |
}); | |
$this->total = $this->distances->sum(); | |
$this->emit("refreshChartData-{$this->chartId}", [ | |
'seriesData' => $this->distances, | |
'categories' => $this->years, | |
'seriesName' => 'Total distance this year', | |
]); | |
return view('livewire.stats.distance-by-year'); | |
} | |
public function resetFilter($filter) | |
{ | |
$this->{$filter} = null; | |
} | |
private function getDistancesByYear() | |
{ | |
$query = DB::table('activities') | |
->select( | |
DB::raw('YEAR(start_date_local) AS year'), | |
DB::raw('SUM(distance) AS total_distance'), | |
) | |
->where(['athlete_id' => $this->athlete->id]); | |
if ($this->bike > 0) { | |
$query->where('bike_id', $this->bike); | |
} | |
return $query | |
->groupByRaw('YEAR(start_date_local)') | |
->get(); | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<?php | |
namespace App\View\Components; | |
use Illuminate\View\Component; | |
class ApexCharts extends Component | |
{ | |
public string $chartId; | |
public $seriesData; | |
public $categories; | |
public $seriesName; | |
public function __construct($chartId, $seriesData, $categories, $seriesName = '') | |
{ | |
$this->chartId = $chartId; | |
$this->seriesData = $seriesData; | |
$this->categories = $categories; | |
$this->seriesName = $seriesName ?? 'Series'; | |
} | |
public function render() | |
{ | |
return view('components.apex-charts'); | |
} | |
} |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<div id="{!! $chartId !!}"></div> | |
@push('scripts') | |
<script> | |
(function () { | |
const options = { | |
chart: { | |
id: `{!! $chartId !!}`, | |
type: 'bar' | |
}, | |
plotOptions: { | |
bar: { | |
barHeight: '100%', | |
distributed: true, | |
dataLabels: { | |
// position: 'bottom' | |
}, | |
} | |
}, | |
xaxis: { | |
type: 'category', | |
categories: {!! $categories !!} | |
}, | |
series: [{ | |
name: `{!! $seriesName !!}`, | |
data: {!! $seriesData !!} | |
}], | |
// colors: ['#5c6ac4', '#007ace'], | |
} | |
const chart = new ApexCharts(document.getElementById(`{!! $chartId !!}`), options); | |
chart.render(); | |
document.addEventListener('livewire:load', () => { | |
@this.on(`refreshChartData-{!! $chartId !!}`, (chartData) => { | |
chart.updateOptions({ | |
xaxis: { | |
categories: chartData.categories | |
} | |
}); | |
chart.updateSeries([{ | |
data: chartData.seriesData, | |
name: chartData.seriesName, | |
}]); | |
}); | |
}); | |
}()); | |
</script> | |
@endpush |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
<div class="w-full"> | |
<div class="bg-white shadow-2xl rounded"> | |
<x-section-header> | |
Distance By Year | |
<x-slot name="content"> | |
<span class="text-xl font-normal"> | |
{{$total}} @include('partials.unit._distance') | |
</span> | |
</x-slot> | |
</x-section-header> | |
<section class="p-2"> | |
<!-- Filters --> | |
<!-- Bike --> | |
<div class="flex flex-col"> | |
<label for="bike" class="flex flex-col w-1/4 font-medium text-xs text-black tracking-tight uppercase"> | |
Bike | |
</label> | |
<div class="flex"> | |
<select name="bike" id="bike" class="border px-2 py-1 rounded shadow-inner text-sm" wire:model="bike"> | |
<option>All</option> | |
@foreach($athlete->bikes as $bikeFilter) | |
<option value="{{ $bikeFilter->id }}">{{ $bikeFilter->name }}</option> | |
@endforeach | |
</select> | |
@if(!empty($bike) && $bike !== 'All') | |
<button wire:click="resetFilter('bike')" class="px-2 text-xl" title="Remove Bike filter"> | |
<x-icon icon="teenyicons-x" width=15 height=15 viewBox="15 15" strokeWidth=1 /> | |
</button> | |
@endif | |
</div> | |
</div> | |
<x-apex-charts :chart-id="$chartId" :series-data="$distances" :categories="$years" series-name="Total distance this year"/> | |
</section> | |
</div> | |
</div> |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
@extends('layouts.connected') | |
@section('connected-content') | |
<div class="grid grid-cols-none xl:grid-cols-2 gap-4 w-full"> | |
<livewire:stats.distance-by-year :athlete="$athlete" chart-id="distance-by-year" key="distance-by-year"/> | |
<livewire:stats.distance-by-month :athlete="$athlete" chart-id="distance-by-month" key="distance-by-month"/> | |
</div> | |
@endsection | |
@prepend('scripts') | |
{{-- Push ApexCharts to the top of the scripts stack --}} | |
<script src="https://cdn.jsdelivr.net/npm/apexcharts"></script> | |
@endprepend |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment