diff --git a/app/Http/Controllers/PollController.php b/app/Http/Controllers/PollController.php index 17de12a..900236a 100644 --- a/app/Http/Controllers/PollController.php +++ b/app/Http/Controllers/PollController.php @@ -5,8 +5,9 @@ namespace App\Http\Controllers; use Illuminate\Http\Request; use Carbon\Carbon; use Validator; - use DB; +use Cache; + use App\Poll; use App\PollVote; use App\PollVotingCode; @@ -94,14 +95,79 @@ class PollController extends Controller { $voted = $request->session()->pull('voted', false); + $this->createPieChart($poll); + return view('view_poll_results') ->with('poll', $poll) ->with('voted', $voted); } - private static function createPieChart(Poll $poll) + private function createPieChart(Poll $poll) { - //TODO + $voteCount = $poll->votes->count(); + + if(Cache::has($poll->id) && Cache::get($poll->id)['vote_count'] == $voteCount) { + return; + } + + $baseColours = [[0xE8, 0x96, 0x3F], [0xAD, 0x3F, 0xE8], [0x3F, 0xE8, 0x6F], [0xE8, 0xE3, 0x3F], [0x3F, 0x64, 0xEB], [0xE8, 0x3F, 0x65], [0x3F, 0xE8, 0xDB]]; + shuffle($baseColours); + + $supersamplingFactor = 8; + + $width = 512 * $supersamplingFactor; + $height = 512 * $supersamplingFactor; + $padding = 16 * $supersamplingFactor; + + $chartWidth = $width - 2 * $padding; + $chartHeight = $height - 2 * $padding; + + $pieChart = imagecreatetruecolor($width, $height); + imagefill($pieChart, 0, 0, imagecolorallocate($pieChart, 0xFF, 0xFF, 0xFF)); + imageantialias($pieChart, true); + + $primary = imagecolorallocate($pieChart, 0xE8, 0x3F, 0xB8); + + $colours = []; + + $startDegrees = 0; + $sortedOptions = $poll->options->sortByDesc(function($option) use($poll) { return $poll->votes->where('poll_option_id', $option->id)->count(); }); + $nonZeroOptions = $sortedOptions->filter(function($option) use($poll) { return $poll->votes->where('poll_option_id', $option->id)->count() > 0; })->values(); + debug($nonZeroOptions); + for($i = 0; $i < $poll->options->count(); $i++) { + $option = $nonZeroOptions[$i]; + + //TODO: Fix gaps + $degrees = round($poll->votes->where('poll_option_id', $option->id)->count() / $voteCount * 360); + $endDegrees = min($startDegrees + $degrees, 360); + + $c = function($j) use($i, $baseColours, $nonZeroOptions) { + return $baseColours[$i % count($baseColours)][$j] + + (255 - $baseColours[$i % count($baseColours)][$j]) + * floor($i / count($baseColours)) / (floor($nonZeroOptions->count() / count($baseColours)) + 1); + }; + $colour = imagecolorallocate($pieChart, $c(0), $c(1), $c(2)); + $colours[$option->id] = '#' . dechex($c(0) << 16 | $c(1) << 8 | $c(2) << 0); + + debug([$option->text, [$startDegrees, $endDegrees], [$c(0), $c(1), $c(2)]]); + + imagefilledarc($pieChart, $width / 2, $height / 2, $chartWidth, $chartHeight, $startDegrees, $endDegrees, $colour, IMG_ARC_PIE); + + $startDegrees = $endDegrees; + } + + debug($colours); + + $resized = imagecreatetruecolor($width / $supersamplingFactor, $height / $supersamplingFactor); + imagecopyresampled($resized, $pieChart, 0, 0, 0, 0, $width / $supersamplingFactor, $height / $supersamplingFactor, $width, $height); + $pieChart = $resized; + + ob_start(); + imagepng($pieChart); + $dataUri = "data:image/png;base64," . base64_encode(ob_get_contents()); + ob_end_clean(); + + Cache::put($poll->id, ['vote_count' => $voteCount, 'pie_chart' => $dataUri, 'colours' => $colours], now()->addDays(1)); } public function hasVoted(Request $request, Poll $poll) diff --git a/resources/views/view_poll_results.blade.php b/resources/views/view_poll_results.blade.php index 9822127..2922987 100644 --- a/resources/views/view_poll_results.blade.php +++ b/resources/views/view_poll_results.blade.php @@ -10,12 +10,15 @@ @endif @if($poll->results_visible) + @php ($sortedOptions = $poll->options->sortByDesc(function($option) use($poll) { return $poll->votes->where('poll_option_id', $option->id)->count(); })) + @php ($nonZeroOptions = $sortedOptions->filter(function($option) use($poll) { return $poll->votes->where('poll_option_id', $option->id)->count() > 0; })) +
@php ($total = $poll->votes->count()) - @foreach ($poll->options->sortByDesc(function($option) use($poll) { return $poll->votes->where('poll_option_id', $option->id)->count(); }) as $option) + @foreach ($sortedOptions as $option) @php ($votes = $poll->votes->where('poll_option_id', $option->id)->count())
@@ -24,6 +27,7 @@ {{ $votes }} votes
+
@@ -36,8 +40,17 @@
+ @php ($cache = Cache::get($poll->id)) +
- TODO: Put a pie chart here. + +
+ @foreach ($nonZeroOptions as $option) + +
+ {{ $option->text }} +
+ @endforeach
diff --git a/resources/views/welcome.blade.php b/resources/views/welcome.blade.php deleted file mode 100644 index af5d4e5..0000000 --- a/resources/views/welcome.blade.php +++ /dev/null @@ -1,98 +0,0 @@ - - - - - - - Laravel - - - - - - - - -
- @if (Route::has('login')) - - @endif - -
-
- Laravel -
- - -
-
- -