1 /* 2 * Copyright 2009, Ingo Weinhold, ingo_weinhold@gmx.de. 3 * Distributed under the terms of the MIT License. 4 */ 5 6 #include "chart/BigtimeChartAxisLegendSource.h" 7 8 #include <stdio.h> 9 10 #include "chart/ChartDataRange.h" 11 #include "chart/StringChartLegend.h" 12 13 14 struct decomposed_time { 15 bigtime_t hours; 16 int minutes; 17 int seconds; 18 int micros; 19 }; 20 21 22 static void 23 decompose_time(bigtime_t time, decomposed_time& decomposed) 24 { 25 // microsecs 26 decomposed.micros = time % 1000000; 27 time /= 1000000; 28 // secs 29 decomposed.seconds = time % 60; 30 time /= 60; 31 // mins 32 decomposed.minutes = time % 60; 33 time /= 60; 34 // hours 35 decomposed.hours = time; 36 } 37 38 39 int32 40 BigtimeChartAxisLegendSource::GetAxisLegends(const ChartDataRange& range, 41 ChartLegend** legends, double* values, int32 maxLegends) 42 { 43 // interpret range as time range 44 bigtime_t startTime = (bigtime_t)range.min; 45 bigtime_t endTime = (bigtime_t)range.max; 46 // TODO: Handle sub-microsecs ranges! 47 if (startTime >= endTime) 48 return 0; 49 50 bigtime_t positionFactors[4]; 51 positionFactors[3] = 1; 52 positionFactors[2] = 1000000; 53 positionFactors[1] = positionFactors[2] * 60; 54 positionFactors[0] = positionFactors[1] * 60; 55 56 // find the main position (h, m, s, us) we want to play with 57 int32 position = 0; 58 bigtime_t rangeTime = endTime - startTime; 59 while (rangeTime / positionFactors[position] + 1 < maxLegends / 2 60 && position < 3) { 61 position++; 62 } 63 64 // adjust the factor so that we get maxLegends / 2 to maxLegends legends 65 bigtime_t baseInterval = positionFactors[position]; 66 bigtime_t relativeFactor = 1; 67 while (rangeTime / (baseInterval * relativeFactor) >= maxLegends) { 68 if (relativeFactor == 1) { 69 relativeFactor = 2; 70 } else if (relativeFactor == 2) { 71 relativeFactor = 5; 72 } else if (relativeFactor == 5) { 73 baseInterval *= 10; 74 relativeFactor = 1; 75 } 76 } 77 78 // generate the legends 79 int32 count = 0; 80 bigtime_t interval = baseInterval * relativeFactor; 81 bigtime_t time = (startTime + interval - 1) / interval * interval; 82 for (; time <= endTime; time += interval) { 83 decomposed_time decomposed; 84 decompose_time(time, decomposed); 85 char buffer[128]; 86 snprintf(buffer, sizeof(buffer), "%02lld:%02d:%02d.%06d", 87 decomposed.hours, decomposed.minutes, decomposed.seconds, 88 decomposed.micros); 89 // TODO: Drop superfluous micro seconds digits, or even microseconds and seconds 90 // completely. 91 92 StringChartLegend* legend 93 = new(std::nothrow) StringChartLegend(buffer, 1); 94 if (legend == NULL) 95 return count; 96 97 legends[count] = legend; 98 values[count++] = (double)time; 99 } 100 101 return count; 102 } 103