source: trunk/Modules/TimeMeasure/Graph.php

Last change on this file was 929, checked in by chronos, 3 years ago
  • Modified: Removed commended out print_r and echo commands used only for debugging.
File size: 10.3 KB
Line 
1<?php
2
3class PageGraph extends Page
4{
5 public int $FontSize;
6 public string $FontFileName;
7 public float $ValueToImageHeigthCoefficient;
8 public int $DefaultWidth;
9 public int $DefaultHeight;
10
11 function __construct(System $System)
12 {
13 parent::__construct($System);
14 $this->FontSize = 10;
15 $this->FontFileName = 'Arial.ttf';
16 $this->ValueToImageHeigthCoefficient = 0.9;
17 }
18
19 function Show(): string
20 {
21 $this->RawPage = true;
22 $this->Render();
23 return '';
24 }
25
26 function Render(): void
27 {
28 $PrefixMultiplier = new PrefixMultiplier();
29
30 if (array_key_exists('Debug', $_GET)) $Debug = $_GET['Debug'];
31 else $Debug = 0;
32
33 if (!array_key_exists('From', $_GET)) die('Musíte zadat čas počátku');
34 $StartTime = addslashes($_GET['From']);
35 if (!array_key_exists('To', $_GET)) die('Musíte zadat čas konce');
36 $EndTime = addslashes($_GET['To']);
37 if ($EndTime < $StartTime) $EndTime = $StartTime + 60;
38 $TimeDifference = $EndTime - $StartTime;
39 if (!array_key_exists('Measure', $_GET)) die('Musíte zadat měřenou veličinu');
40 $MeasureId = addslashes($_GET['Measure']);
41 if (!array_key_exists('Width', $_GET)) $Width = $this->DefaultWidth;
42 else $Width = addslashes($_GET['Width']);
43 if (!array_key_exists('Height', $_GET)) $Height = $this->DefaultHeight;
44 else $Height = addslashes($_GET['Height']);
45 if (!array_key_exists('Differential', $_GET)) $Differential = $this->Config['Application']['DefaultVariables']['Differential'];
46 else $Differential = addslashes($_GET['Differential']);
47 $VerticalLinesCount = round($Height / ($this->FontSize + 4));
48
49 $StopWatchStart = GetMicrotime();
50
51 $Measure = new Measure($this->System);
52 $Measure->Load($MeasureId);
53 //$Measure->LevelReducing = $this->LevelReducing;
54 //$Measure->ReferenceTime = $this->Config['Application']['ReferenceTime'];
55 //$Measure->MaxLevel = $this->Config['Application']['MaxLevel'];
56 //$Measure->DivisionCount = $this->Config['Application']['DivisionCount'];
57 //$Measure->Differential = $this->Config['Application']['DefaultVariables']['Differential'];
58 $Measure->Debug = $Debug;
59 $DbResult2 = $this->Database->select('MeasureMethod', '*', 'Id='.$Measure->Data['Method']);
60 $MeasureMethod = $DbResult2->fetch_assoc();
61
62 $FontSize = $this->FontSize;
63 $FontFile = dirname(__FILE__).'/../../style/'.$this->System->Config['Web']['Style'].'/'.$this->FontFileName;
64
65 $Level = floor(log(($EndTime - $StartTime) / $Measure->DivisionCount / 60) / log($Measure->LevelReducing)) - 1;
66 if ($Level < 0) $Level = 0;
67 if ($Level > $Measure->MaxLevel) $Level = $Measure->MaxLevel;
68 //$Level = 0;
69
70 $Points = $Measure->GetValues($StartTime, $EndTime, $Level);
71
72 if ($Debug) echo('Points count: '.count($Points).'<br/>');
73
74 // Calculate total max, avg, min value
75 $MaxValue = -1000000000000000000;
76 $AvgValue = 0;
77 $MinValue = 1000000000000000000;
78 foreach ($Points as $Index => $Item)
79 {
80 //$Points[$Index]['min'] = $Points[$Index]['min'] / $Measure['Divider'];
81 //$Points[$Index]['avg'] = $Points[$Index]['avg'] / $Measure['Divider'];
82 //$Points[$Index]['max'] = $Points[$Index]['max'] / $Measure['Divider'];
83 if ($Points[$Index]['Avg'] > $MaxValue) $MaxValue = $Points[$Index]['Avg'];
84 if ($Points[$Index]['Avg'] < $MinValue) $MinValue = $Points[$Index]['Avg'];
85 if ($Points[$Index]['Max'] > $MaxValue) $MaxValue = $Points[$Index]['Max'];
86 if ($Points[$Index]['Min'] < $MinValue) $MinValue = $Points[$Index]['Min'];
87 $AvgValue = $AvgValue + $Points[$Index]['Avg'];
88 }
89 //$MinValue = round($MinValue * $Measure['Divider']) / $Measure['Divider'];
90 //$MaxValue = round($MaxValue * $Measure['Divider']) / $Measure['Divider'];
91 $AvgValue = $AvgValue / count($Points); //round( * $Measure['Divider']) / $Measure['Divider'];
92
93 // Generate polygon and recalculate y values to fit graph height
94 $PointsMin = array(0, $Height - 1);
95 $PointsAvg = array(0, $Height - 1);
96 $PointsMax = array(0, $Height - 1);
97 if (($MaxValue - $MinValue) == 0) $MaxValue = $MinValue + 1;
98 {
99 foreach ($Points as $Index => $Item)
100 {
101 $PointsMin[] = $Index * $Width / $Measure->DivisionCount;
102 $PointsMin[] = $Height - 1 - ($Points[$Index]['Min'] - $MinValue) / ($MaxValue - $MinValue) * $Height * $this->ValueToImageHeigthCoefficient;
103 $PointsAvg[] = $Index * $Width / $Measure->DivisionCount;
104 $PointsAvg[] = $Height - 1 - ($Points[$Index]['Avg'] - $MinValue) / ($MaxValue - $MinValue) * $Height * $this->ValueToImageHeigthCoefficient;
105 $PointsMax[] = $Index * $Width / $Measure->DivisionCount;
106 $PointsMax[] = $Height - 1 - ($Points[$Index]['Max'] - $MinValue) / ($MaxValue - $MinValue) * $Height * $this->ValueToImageHeigthCoefficient;
107 }
108 }
109 $PointsMin[] = $Width - 1;
110 $PointsMin[] = $Height - 1;
111 $PointsAvg[] = $Width - 1;
112 $PointsAvg[] = $Height - 1;
113 $PointsMax[] = $Width - 1;
114 $PointsMax[] = $Height - 1;
115 $PointsMin[] = $Width - 1;
116 $PointsMin[] = $Height - 1;
117 $PointsAvg[] = $Width - 1;
118 $PointsAvg[] = $Height - 1;
119 $PointsMax[] = $Width - 1;
120 $PointsMax[] = $Height - 1;
121
122
123 //array_unshift($Points, $Height - 1);
124 //array_unshift($Points, 0);
125 //$Points[] = $Width - 1;
126 //$Points[] = $Height - 1;
127
128 // Generate image
129 if (!$Debug)
130 {
131 Header('Content-type: image/png');
132 Header('Cache-Control: no-cache'); // Dynamic graph - no cache
133 $Image = @imagecreate($Width, $Height);
134 $BackgroundColor = imagecolorallocate($Image, 255, 255, 255);
135 $Black = imagecolorallocate($Image, 0, 0, 0);
136 $White = imagecolorallocate($Image, 255, 255, 255);
137 $Gray = imagecolorallocate($Image, 200, 200, 200);
138 $DarkGray = imagecolorallocate($Image, 100, 100, 100);
139 $LightBlue = imagecolorallocate($Image, 150, 150, 255);
140 $Blue = imagecolorallocate($Image, 0, 0, 255);
141 $LightRed = imagecolorallocate($Image, 255, 150, 150);
142 $Red = imagecolorallocate($Image, 255, 0, 0);
143 $Green = imagecolorallocate($Image, 0, 200, 0);
144 $LightGreen = imagecolorallocate($Image, 150, 255, 150);
145
146 imagefilledpolygon($Image, $PointsMax, count($PointsMax) / 2, $LightRed);
147 imagefilledpolygon($Image, $PointsAvg, count($PointsAvg) / 2, $LightGreen);
148 imagefilledpolygon($Image, $PointsMin, count($PointsMin) / 2, $LightBlue);
149
150 $TimeMarks = array(1, 60, 60*60, 60*60*24, 60*60*24*7, 60*60*24*30, 60*60*24*365, 60*60*24*365*10);
151
152 $TimeRange = $EndTime - $StartTime;
153 $TimeMarksIndex = 0;
154 while (($TimeRange / $TimeMarks[$TimeMarksIndex]) > 1) $TimeMarksIndex += 1;
155 if ($TimeMarksIndex < 2) $TimeMarksIndex = 2;
156 $MajorTimeMarks = $TimeMarks[$TimeMarksIndex - 1];
157 $MinorTimeMarks = $TimeMarks[$TimeMarksIndex - 2];
158
159 $TimeShift = $Measure->AlignTime($StartTime, $MajorTimeMarks) - $StartTime;
160 //imagestring($Image, 10, 40, 50, $TimeShift, $Black);
161
162 // Zobraz měřítko Y
163 $VerticalLinesDistance = $Height / $VerticalLinesCount;
164 for ($I = 1; $I <= $VerticalLinesCount; $I++)
165 {
166 $Y = $Height - 1 - ($VerticalLinesDistance * $I);
167 for ($X = 1; $X < $Width; $X = $X + 3) imagesetpixel($Image, $X, $Y, $Gray);
168 //imageline($Image, 30, $Y, $Width-1, $Y, IMG_COLOR_STYLED);
169 }
170
171 $TimeShift = $Measure->AlignTime($StartTime, $MinorTimeMarks) - $StartTime;
172
173 // Zobraz měřítko X
174 $LastTextEnd = 0;
175 for ($Time = $StartTime; $Time < $EndTime; $Time += $MajorTimeMarks)
176 {
177 $X = round(($Time - $StartTime + $TimeShift) / $TimeRange * $Width) % $Width;
178 //imageline($Image, 30, $Y, $Width-1, $Y, IMG_COLOR_STYLED);
179 if (($MajorTimeMarks > 60 * 60 * 24)) $Text = date('j.n.Y', $Time + $TimeShift);
180 else $Text = date('j.n.Y G:i', $Time + $TimeShift);
181 $BoundBox = imagettfbbox($FontSize, 0, $FontFile, $Text);
182 if ($LastTextEnd < ($X - ($BoundBox[2] - $BoundBox[0] + 20) / 2))
183 {
184 for ($Y = 0; $Y < $Height; $Y = $Y + 1) imagesetpixel($Image, $X, $Y, $Gray);
185 imagettftext($Image, $FontSize, 0, $X - ($BoundBox[2] - $BoundBox[0]) / 2, $Height - 2, $Black, $FontFile, $Text);
186 $LastTextEnd = $X + ($BoundBox[2] - $BoundBox[0]) / 2;
187 }
188 else for ($Y = 0; $Y < $Height; $Y = $Y + 3) imagesetpixel($Image, $X, $Y, $Gray);
189 }
190
191 // Popisky osy Y
192 for ($I = 1; $I <= $VerticalLinesCount; $I++)
193 {
194 $Y = $Height - 1 - ($VerticalLinesDistance * $I);
195 //$Y = $Height - 1 - ($VerticalLinesDistance * $I / ($MaxValue - $MinValue) *
196 // $this->ValueToImageHeigthCoefficient * $Height);
197 $Text = $PrefixMultiplier->Add(round(($I * $VerticalLinesDistance / $Height /
198 $this->ValueToImageHeigthCoefficient * ($MaxValue - $MinValue) + $MinValue)), $MeasureMethod['Unit'], 3);
199 $BoundBox = imagettfbbox($FontSize, 0, $FontFile, $Text);
200 if (($Y - ($BoundBox[5] - $BoundBox[1]) / 2) > 10)
201 imagettftext($Image, $FontSize, 0, 2, $Y - ($BoundBox[5] - $BoundBox[1]) / 2, $Black, $FontFile, $Text);
202 }
203 $GenerationTime = floor((GetMicrotime() - $StopWatchStart) * 1000 ) / 1000;
204
205 $Left = $Width - 10;
206 $Text = ' Max. '.$PrefixMultiplier->Add($MaxValue, $MeasureMethod['Unit']);
207 $BoundingBox = imagettfbbox($FontSize, 0, $FontFile, $Text);
208 $Left -= ($BoundingBox[2] - $BoundingBox[0]);
209 imagettftext($Image, $FontSize, 0, $Left, 14, $Red, $FontFile, $Text);
210
211 $Text = ' Avg. '.$PrefixMultiplier->Add($AvgValue, $MeasureMethod['Unit']);
212 $BoundingBox = imagettfbbox($FontSize, 0, $FontFile, $Text);
213 $Left -= ($BoundingBox[2] - $BoundingBox[0]);
214 imagettftext($Image, $FontSize, 0, $Left, 14, $Green, $FontFile, $Text);
215
216 $Text = ' Min. '.$PrefixMultiplier->Add($MinValue, $MeasureMethod['Unit']);
217 $BoundingBox = imagettfbbox($FontSize, 0, $FontFile, $Text);
218 $Left -= ($BoundingBox[2] - $BoundingBox[0]);
219 imagettftext($Image, $FontSize, 0, $Left, 14, $Blue, $FontFile, $Text);
220 //imagestring($Image, 2, 70, 20, 'Vygenerováno za '.$GenerationTime.' sekund', $Black);
221 //imagestring($Image, 2, 50, 30, 'Level: '.$Level, $Black);
222
223 imagettftext($Image, $FontSize, 0, 70, 14, $Black, $FontFile, $Measure->Data['Description']);
224 imagerectangle($Image, 0, 0, $Width - 1, $Height - 1, $Black); // Frame border
225 imagepng($Image);
226 imagedestroy($Image);
227 }
228 }
229}
Note: See TracBrowser for help on using the repository browser.