[goffice] Axis: improve axis value rounding when axis is scaled.
- From: Morten Welinder <mortenw src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [goffice] Axis: improve axis value rounding when axis is scaled.
- Date: Mon, 4 May 2015 15:55:38 +0000 (UTC)
commit c6e227362abd6ed2cd38a1fc28309163f21e6381
Author: Morten Welinder <terra gnome org>
Date: Mon May 4 11:55:12 2015 -0400
Axis: improve axis value rounding when axis is scaled.
ChangeLog | 7 ++++++
goffice/graph/gog-axis.c | 47 ++++++++++++++++++++++++++++++++-------------
2 files changed, 40 insertions(+), 14 deletions(-)
---
diff --git a/ChangeLog b/ChangeLog
index 6764cf3..845bc5b 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,10 @@
+2015-05-04 Morten Welinder <terra gnome org>
+
+ * goffice/graph/gog-axis.c (axis_format_value): Allow caller to
+ handling scaling.
+ (map_linear_calc_ticks): Handling scaling so we can control
+ rounding errors in ticks.
+
2015-05-04 Jean Brefort <jean brefort normalesup org>
* goffice/graph/gog-axis.c (axis_format_value),
diff --git a/goffice/graph/gog-axis.c b/goffice/graph/gog-axis.c
index 260a7d6..30f7560 100644
--- a/goffice/graph/gog-axis.c
+++ b/goffice/graph/gog-axis.c
@@ -263,7 +263,8 @@ gog_axis_get_effective_format (GogAxis const *axis)
}
static void
-axis_format_value (GogAxis *axis, double val, GOString **str)
+axis_format_value (GogAxis *axis, double val, GOString **str,
+ gboolean do_scale)
{
GOFormat *fmt = gog_axis_get_effective_format (axis);
const GODateConventions *date_conv = axis->date_conv;
@@ -274,12 +275,20 @@ axis_format_value (GogAxis *axis, double val, GOString **str)
go_string_unref (*str);
+ if (do_scale)
+ val /= axis->display_factor;
+ else {
+ /* Caller handled scaling, except for sign. */
+ if (axis->display_factor < 0)
+ val = 0 - val;
+ }
+
err = go_format_value_gstring
(layout, NULL,
go_format_measure_strlen,
go_font_metrics_unit,
fmt,
- val / axis->display_factor, 'F', NULL, NULL,
+ val, 'F', NULL, NULL,
-1, date_conv, TRUE);
if (err)
*str = go_string_new ("#####");
@@ -497,7 +506,7 @@ map_discrete_calc_ticks (GogAxis *axis)
} else {
double val = go_data_get_vector_value (axis->labels, index);
if (go_finite (val))
- axis_format_value (axis, val, &ticks[j].str);
+ axis_format_value (axis, val, &ticks[j].str, TRUE);
else {
char *label = go_data_get_vector_string (axis->labels, index);
gog_axis_ticks_set_text (&ticks[j], label);
@@ -833,7 +842,8 @@ map_linear_auto_bound (GogAxis *axis, double minimum, double maximum, double *bo
static double
scale_step (double step, double *scale)
{
- double f, r, l10;
+ double f, r;
+ int l10;
if (step <= 0 || !go_finite (step)) {
*scale = 1;
@@ -847,9 +857,9 @@ scale_step (double step, double *scale)
return r;
}
- l10 = floor (log10 (f));
- *scale = pow (10, -l10 + 1);
- step *= *scale;
+ l10 = (int)floor (log10 (f));
+ *scale = go_pow10 (-l10 + 1);
+ step *=* scale; /* "*= *" isn't cute enough. */
r = go_fake_floor (step);
if (fabs (r - step) < 1e-10)
@@ -867,15 +877,21 @@ map_linear_calc_ticks (GogAxis *axis)
int t, N;
int maj_i, maj_N; /* Ticks for -1,....,maj_N */
int min_i, min_N; /* Ticks for 1,....,(min_N-1) */
+ double display_factor = fabs (axis->display_factor);
if (!gog_axis_get_bounds (axis, &minimum, &maximum)) {
gog_axis_set_ticks (axis, 2, create_invalid_axis_ticks (0.0, 1.0));
return;
}
+ maximum /= display_factor;
+ minimum /= display_factor;
range = maximum - minimum;
maj_step = gog_axis_get_entry (axis, GOG_AXIS_ELEM_MAJOR_TICK, NULL);
- if (maj_step <= 0.) maj_step = range;
+ if (maj_step <= 0.)
+ maj_step = range;
+ else
+ maj_step /= display_factor;
while (1) {
double ratio = go_fake_floor (range / maj_step);
double Nd = (ratio + 1); /* Correct if no minor */
@@ -890,7 +906,10 @@ map_linear_calc_ticks (GogAxis *axis)
}
min_step = gog_axis_get_entry (axis, GOG_AXIS_ELEM_MINOR_TICK, NULL);
- if (min_step <= 0.) min_step = maj_step;
+ if (min_step <= 0.)
+ min_step = maj_step;
+ else
+ min_step /= display_factor;
while (1) {
/* add 0.9 there because the ratio might not be an integer
* or there might be rounding errors, more than 0.9 would
@@ -948,9 +967,9 @@ map_linear_calc_ticks (GogAxis *axis)
if (maj_i >= 0) {
g_assert (t < N);
- ticks[t].position = maj_pos;
+ ticks[t].position = maj_pos * display_factor;
ticks[t].type = GOG_AXIS_TICK_MAJOR;
- axis_format_value (axis, maj_pos, &ticks[t].str);
+ axis_format_value (axis, maj_pos, &ticks[t].str, FALSE);
t++;
}
@@ -962,7 +981,7 @@ map_linear_calc_ticks (GogAxis *axis)
break;
g_assert (t < N);
- ticks[t].position = min_pos;
+ ticks[t].position = min_pos * display_factor;
ticks[t].type = GOG_AXIS_TICK_MINOR;
ticks[t].str = NULL;
t++;
@@ -1174,7 +1193,7 @@ map_date_calc_ticks (GogAxis *axis)
ticks[t].position = maj_pos;
ticks[t].type = GOG_AXIS_TICK_MAJOR;
- axis_format_value (axis, maj_pos, &ticks[t].str);
+ axis_format_value (axis, maj_pos, &ticks[t].str, TRUE);
t++;
/* Calculate next major so we know when to stop minors. */
@@ -1539,7 +1558,7 @@ map_log_calc_ticks (GogAxis *axis)
g_assert (t < N);
ticks[t].position = maj_pos;
ticks[t].type = GOG_AXIS_TICK_MAJOR;
- axis_format_value (axis, maj_pos, &ticks[t].str);
+ axis_format_value (axis, maj_pos, &ticks[t].str, TRUE);
t++;
}
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]