Merge branch '#135_cursors' into develop. Closes #135.
This commit is contained in:
commit
90e17fbd16
727
src/Chart.vala
727
src/Chart.vala
File diff suppressed because it is too large
Load Diff
|
@ -7,11 +7,12 @@ namespace Gtk.CairoChart {
|
||||||
double dash_offset;
|
double dash_offset;
|
||||||
Color color;
|
Color color;
|
||||||
|
|
||||||
public LineStyle (double width = 1,
|
public LineStyle (Color color = Color(),
|
||||||
Cairo.LineJoin line_join = Cairo.LineJoin.MITER,
|
double width = 1,
|
||||||
Cairo.LineCap line_cap = Cairo.LineCap.ROUND,
|
|
||||||
double[]? dashes = null, double dash_offset = 0,
|
double[]? dashes = null, double dash_offset = 0,
|
||||||
Color color = Color()) {
|
Cairo.LineJoin line_join = Cairo.LineJoin.MITER,
|
||||||
|
Cairo.LineCap line_cap = Cairo.LineCap.ROUND
|
||||||
|
) {
|
||||||
this.width = width;
|
this.width = width;
|
||||||
this.line_join = line_join;
|
this.line_join = line_join;
|
||||||
this.line_cap = line_cap;
|
this.line_cap = line_cap;
|
||||||
|
|
|
@ -3,7 +3,7 @@ namespace Gtk.CairoChart {
|
||||||
Float128 x;
|
Float128 x;
|
||||||
Float128 y;
|
Float128 y;
|
||||||
|
|
||||||
public Point (Float128 x, Float128 y) {
|
public Point (Float128 x = 0.0, Float128 y = 0.0) {
|
||||||
this.x = x; this.y = y;
|
this.x = x; this.y = y;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -83,6 +83,9 @@ void plot_chart2 (Chart chart) {
|
||||||
s3.axis_x.title = new Text("All Series: Axis X.");
|
s3.axis_x.title = new Text("All Series: Axis X.");
|
||||||
s3.axis_y.title = new Text("Series 3: Axis Y.");
|
s3.axis_y.title = new Text("Series 3: Axis Y.");
|
||||||
|
|
||||||
|
//s1.axis_x.position = s2.axis_x.position = s3.axis_x.position = Axis.Position.HIGH;
|
||||||
|
//s1.axis_x.type = s2.axis_x.type = s3.axis_x.type = Axis.Type.DATE_TIME;
|
||||||
|
|
||||||
chart.series = { s1, s2, s3 };
|
chart.series = { s1, s2, s3 };
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -128,6 +131,8 @@ void plot_chart3 (Chart chart) {
|
||||||
s3.axis_x.title = new Text("Series 3: Axis X.");
|
s3.axis_x.title = new Text("Series 3: Axis X.");
|
||||||
s3.axis_y.title = new Text("Series 3: Axis Y.");
|
s3.axis_y.title = new Text("Series 3: Axis Y.");
|
||||||
|
|
||||||
|
//s1.axis_y.position = s2.axis_y.position = s3.axis_y.position = Axis.Position.LOW;
|
||||||
|
|
||||||
chart.series = { s1, s2, s3 };
|
chart.series = { s1, s2, s3 };
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -203,6 +208,13 @@ bool point_in_chart (Chart chart, double x, double y) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
enum MouseState {
|
||||||
|
FREE = 0, // default
|
||||||
|
DRAW_SELECTION,
|
||||||
|
MOVING_CHART,
|
||||||
|
CURSOR_SELECTION
|
||||||
|
}
|
||||||
|
|
||||||
int main (string[] args) {
|
int main (string[] args) {
|
||||||
init (ref args);
|
init (ref args);
|
||||||
|
|
||||||
|
@ -244,6 +256,8 @@ int main (string[] args) {
|
||||||
var radio_button2 = new RadioButton.with_label (radio_button1.get_group(), "Right Legend");
|
var radio_button2 = new RadioButton.with_label (radio_button1.get_group(), "Right Legend");
|
||||||
var radio_button3 = new RadioButton.with_label_from_widget (radio_button1, "Left Legend");
|
var radio_button3 = new RadioButton.with_label_from_widget (radio_button1, "Left Legend");
|
||||||
var radio_button4 = new RadioButton.with_label_from_widget (radio_button1, "Bottom Legend");
|
var radio_button4 = new RadioButton.with_label_from_widget (radio_button1, "Bottom Legend");
|
||||||
|
var radio_button7 = new RadioButton.with_label (null, "Vertical Cursors");
|
||||||
|
var radio_button8 = new RadioButton.with_label_from_widget (radio_button7, "Horizontal Cursors");
|
||||||
|
|
||||||
button1.clicked.connect (() => {
|
button1.clicked.connect (() => {
|
||||||
chart = chart1; da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
chart = chart1; da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
@ -252,7 +266,10 @@ int main (string[] args) {
|
||||||
case Legend.Position.RIGHT: radio_button2.set_active(true); break;
|
case Legend.Position.RIGHT: radio_button2.set_active(true); break;
|
||||||
case Legend.Position.LEFT: radio_button3.set_active(true); break;
|
case Legend.Position.LEFT: radio_button3.set_active(true); break;
|
||||||
case Legend.Position.BOTTOM: radio_button4.set_active(true); break;
|
case Legend.Position.BOTTOM: radio_button4.set_active(true); break;
|
||||||
default: break;
|
}
|
||||||
|
switch (chart.cursors_orientation) {
|
||||||
|
case Chart.CursorOrientation.VERTICAL: radio_button7.set_active(true); break;
|
||||||
|
case Chart.CursorOrientation.HORIZONTAL: radio_button8.set_active(true); break;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
button2.clicked.connect (() => {
|
button2.clicked.connect (() => {
|
||||||
|
@ -262,7 +279,10 @@ int main (string[] args) {
|
||||||
case Legend.Position.RIGHT: radio_button2.set_active(true); break;
|
case Legend.Position.RIGHT: radio_button2.set_active(true); break;
|
||||||
case Legend.Position.LEFT: radio_button3.set_active(true); break;
|
case Legend.Position.LEFT: radio_button3.set_active(true); break;
|
||||||
case Legend.Position.BOTTOM: radio_button4.set_active(true); break;
|
case Legend.Position.BOTTOM: radio_button4.set_active(true); break;
|
||||||
default: break;
|
}
|
||||||
|
switch (chart.cursors_orientation) {
|
||||||
|
case Chart.CursorOrientation.VERTICAL: radio_button7.set_active(true); break;
|
||||||
|
case Chart.CursorOrientation.HORIZONTAL: radio_button8.set_active(true); break;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
button3.clicked.connect (() => {
|
button3.clicked.connect (() => {
|
||||||
|
@ -272,7 +292,10 @@ int main (string[] args) {
|
||||||
case Legend.Position.RIGHT: radio_button2.set_active(true); break;
|
case Legend.Position.RIGHT: radio_button2.set_active(true); break;
|
||||||
case Legend.Position.LEFT: radio_button3.set_active(true); break;
|
case Legend.Position.LEFT: radio_button3.set_active(true); break;
|
||||||
case Legend.Position.BOTTOM: radio_button4.set_active(true); break;
|
case Legend.Position.BOTTOM: radio_button4.set_active(true); break;
|
||||||
default: break;
|
}
|
||||||
|
switch (chart.cursors_orientation) {
|
||||||
|
case Chart.CursorOrientation.VERTICAL: radio_button7.set_active(true); break;
|
||||||
|
case Chart.CursorOrientation.HORIZONTAL: radio_button8.set_active(true); break;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
button4.clicked.connect (() => {
|
button4.clicked.connect (() => {
|
||||||
|
@ -282,7 +305,10 @@ int main (string[] args) {
|
||||||
case Legend.Position.RIGHT: radio_button2.set_active(true); break;
|
case Legend.Position.RIGHT: radio_button2.set_active(true); break;
|
||||||
case Legend.Position.LEFT: radio_button4.set_active(true); break;
|
case Legend.Position.LEFT: radio_button4.set_active(true); break;
|
||||||
case Legend.Position.BOTTOM: radio_button4.set_active(true); break;
|
case Legend.Position.BOTTOM: radio_button4.set_active(true); break;
|
||||||
default: break;
|
}
|
||||||
|
switch (chart.cursors_orientation) {
|
||||||
|
case Chart.CursorOrientation.VERTICAL: radio_button7.set_active(true); break;
|
||||||
|
case Chart.CursorOrientation.HORIZONTAL: radio_button8.set_active(true); break;
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
button5.clicked.connect (() => {
|
button5.clicked.connect (() => {
|
||||||
|
@ -346,9 +372,38 @@ int main (string[] args) {
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
bool draw_selection = false;
|
|
||||||
|
/* var radio_button5 = new RadioButton.with_label (null, "Labels");
|
||||||
|
var radio_button6 = new RadioButton.with_label_from_widget (radio_button5, "Cursors");
|
||||||
|
radio_button5.toggled.connect ((button) => {
|
||||||
|
// TODO: set labels
|
||||||
|
if (button.get_active()) {
|
||||||
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
}
|
||||||
|
});
|
||||||
|
radio_button6.toggled.connect ((button) => {
|
||||||
|
// TODO: set cursors
|
||||||
|
if (button.get_active()) {
|
||||||
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
}
|
||||||
|
});*/
|
||||||
|
|
||||||
|
radio_button7.toggled.connect ((button) => {
|
||||||
|
if (button.get_active()) {
|
||||||
|
chart.cursors_orientation = Chart.CursorOrientation.VERTICAL;
|
||||||
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
}
|
||||||
|
});
|
||||||
|
radio_button8.toggled.connect ((button) => {
|
||||||
|
if (button.get_active()) {
|
||||||
|
chart.cursors_orientation = Chart.CursorOrientation.HORIZONTAL;
|
||||||
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
|
MouseState mouse_state = MouseState.FREE;
|
||||||
|
|
||||||
double sel_x0 = 0, sel_x1 = 0, sel_y0 = 0, sel_y1 = 0;
|
double sel_x0 = 0, sel_x1 = 0, sel_y0 = 0, sel_y1 = 0;
|
||||||
bool moving_chart = false;
|
|
||||||
double mov_x0 = 0, mov_y0 = 0;
|
double mov_x0 = 0, mov_y0 = 0;
|
||||||
|
|
||||||
da.draw.connect((context) => {
|
da.draw.connect((context) => {
|
||||||
|
@ -363,7 +418,7 @@ int main (string[] args) {
|
||||||
/*var ret = */chart.draw();
|
/*var ret = */chart.draw();
|
||||||
|
|
||||||
// user's post draw operations here...
|
// user's post draw operations here...
|
||||||
if (draw_selection) {
|
if (mouse_state == MouseState.DRAW_SELECTION) {
|
||||||
context.set_source_rgba (0.5, 0.5, 0.5, 0.7);
|
context.set_source_rgba (0.5, 0.5, 0.5, 0.7);
|
||||||
context.set_line_join(Cairo.LineJoin.MITER);
|
context.set_line_join(Cairo.LineJoin.MITER);
|
||||||
context.set_line_cap(Cairo.LineCap.ROUND);
|
context.set_line_cap(Cairo.LineCap.ROUND);
|
||||||
|
@ -381,18 +436,32 @@ int main (string[] args) {
|
||||||
da.button_press_event.connect((event) => {
|
da.button_press_event.connect((event) => {
|
||||||
if (!point_in_chart(chart, event.x, event.y)) return true;
|
if (!point_in_chart(chart, event.x, event.y)) return true;
|
||||||
|
|
||||||
if (event.button == 2) {
|
switch (event.button) {
|
||||||
draw_selection = true;
|
case 1: // start cursor position selection
|
||||||
|
if ((event.state & Gdk.ModifierType.SHIFT_MASK) != 0) { // remove cursor
|
||||||
|
chart.set_active_cursor (event.x, event.y, true);
|
||||||
|
chart.remove_active_cursor();
|
||||||
|
mouse_state = MouseState.FREE;
|
||||||
|
} else { // add cursor
|
||||||
|
chart.set_active_cursor (event.x, event.y);
|
||||||
|
mouse_state = MouseState.CURSOR_SELECTION;
|
||||||
|
}
|
||||||
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 2: // start zoom area selection
|
||||||
sel_x0 = sel_x1 = event.x;
|
sel_x0 = sel_x1 = event.x;
|
||||||
sel_y0 = sel_y1 = event.y;
|
sel_y0 = sel_y1 = event.y;
|
||||||
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
}
|
mouse_state = MouseState.DRAW_SELECTION;
|
||||||
|
break;
|
||||||
|
|
||||||
if (event.button == 3) {
|
case 3: // start moving
|
||||||
moving_chart = true;
|
|
||||||
mov_x0 = event.x;
|
mov_x0 = event.x;
|
||||||
mov_y0 = event.y;
|
mov_y0 = event.y;
|
||||||
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
mouse_state = MouseState.MOVING_CHART;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
return true; // return ret;
|
return true; // return ret;
|
||||||
|
@ -401,9 +470,20 @@ int main (string[] args) {
|
||||||
|
|
||||||
if (!point_in_chart(chart, event.x, event.y)) return true;
|
if (!point_in_chart(chart, event.x, event.y)) return true;
|
||||||
|
|
||||||
//var ret = chart.button_release_event(event);
|
switch (event.button) {
|
||||||
if (event.button == 2) {
|
case 1: // start cursor position selection
|
||||||
draw_selection = false;
|
if ((event.state & Gdk.ModifierType.SHIFT_MASK) != 0) { // remove cursor
|
||||||
|
//chart.remove_active_cursor ();
|
||||||
|
//da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
//mouse_state = MouseState.FREE;
|
||||||
|
} else { // add cursor
|
||||||
|
chart.add_active_cursor ();
|
||||||
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
mouse_state = MouseState.FREE;
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
|
case 2:
|
||||||
sel_x1 = event.x;
|
sel_x1 = event.x;
|
||||||
sel_y1 = event.y;
|
sel_y1 = event.y;
|
||||||
if (sel_x1 > sel_x0 && sel_y1 > sel_y0)
|
if (sel_x1 > sel_x0 && sel_y1 > sel_y0)
|
||||||
|
@ -411,11 +491,13 @@ int main (string[] args) {
|
||||||
else
|
else
|
||||||
chart.zoom_out ();
|
chart.zoom_out ();
|
||||||
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
}
|
mouse_state = MouseState.FREE;
|
||||||
|
break;
|
||||||
|
|
||||||
if (event.button == 3) {
|
case 3:
|
||||||
moving_chart = false;
|
|
||||||
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
mouse_state = MouseState.FREE;
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
return true; // return ret;
|
return true; // return ret;
|
||||||
|
@ -423,20 +505,25 @@ int main (string[] args) {
|
||||||
da.motion_notify_event.connect((event) => {
|
da.motion_notify_event.connect((event) => {
|
||||||
if (!point_in_chart(chart, event.x, event.y)) return true;
|
if (!point_in_chart(chart, event.x, event.y)) return true;
|
||||||
|
|
||||||
//var ret = chart.motion_notify_event(event);
|
switch (mouse_state) {
|
||||||
|
case MouseState.DRAW_SELECTION:
|
||||||
if (draw_selection) {
|
|
||||||
sel_x1 = event.x;
|
sel_x1 = event.x;
|
||||||
sel_y1 = event.y;
|
sel_y1 = event.y;
|
||||||
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
}
|
break;
|
||||||
|
|
||||||
if (moving_chart) {
|
case MouseState.MOVING_CHART:
|
||||||
var delta_x = event.x - mov_x0, delta_y = event.y - mov_y0;
|
var delta_x = event.x - mov_x0, delta_y = event.y - mov_y0;
|
||||||
chart.move (delta_x, delta_y);
|
chart.move (delta_x, delta_y);
|
||||||
mov_x0 = event.x;
|
mov_x0 = event.x;
|
||||||
mov_y0 = event.y;
|
mov_y0 = event.y;
|
||||||
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
break;
|
||||||
|
|
||||||
|
case MouseState.CURSOR_SELECTION:
|
||||||
|
chart.set_active_cursor (event.x, event.y);
|
||||||
|
da.queue_draw_area(0, 0, da.get_allocated_width(), da.get_allocated_height());
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
return true; // return ret;
|
return true; // return ret;
|
||||||
|
@ -462,6 +549,10 @@ int main (string[] args) {
|
||||||
vbox2.pack_start(radio_button2, false, false, 0);
|
vbox2.pack_start(radio_button2, false, false, 0);
|
||||||
vbox2.pack_start(radio_button3, false, false, 0);
|
vbox2.pack_start(radio_button3, false, false, 0);
|
||||||
vbox2.pack_start(radio_button4, false, false, 0);
|
vbox2.pack_start(radio_button4, false, false, 0);
|
||||||
|
//vbox2.pack_start(radio_button5, false, false, 0);
|
||||||
|
//vbox2.pack_start(radio_button6, false, false, 0);
|
||||||
|
vbox2.pack_start(radio_button7, false, false, 0);
|
||||||
|
vbox2.pack_start(radio_button8, false, false, 0);
|
||||||
|
|
||||||
var hbox = new Box(Orientation.HORIZONTAL, 0);
|
var hbox = new Box(Orientation.HORIZONTAL, 0);
|
||||||
hbox.pack_start(da, true, true, 0);
|
hbox.pack_start(da, true, true, 0);
|
||||||
|
|
Loading…
Reference in New Issue