]> git.street.me.uk Git - andy/viking.git/blame_incremental - src/vikgpsdlayer.c
Experimental VikGpsdLayer
[andy/viking.git] / src / vikgpsdlayer.c
... / ...
CommitLineData
1/*
2 * viking -- GPS Data and Topo Analyzer, Explorer, and Manager
3 *
4 * Copyright (C) 2003-2005, Evan Battaglia <gtoevan@gmx.net>
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; either version 2 of the License, or
9 * (at your option) any later version.
10 *
11 * This program is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 * GNU General Public License for more details.
15 *
16 * You should have received a copy of the GNU General Public License
17 * along with this program; if not, write to the Free Software
18 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
19 *
20 */
21#include <math.h>
22#include <gps.h>
23
24#include "vikgpsdlayer.h"
25#include "viklayer.h"
26#include "vikgpsdlayer_pixmap.h"
27
28static void gpsd_layer_marshall( VikGpsdLayer *vgl, guint8 **data, gint *len );
29static VikGpsdLayer *gpsd_layer_unmarshall( guint8 *data, gint len, VikViewport *vvp );
30static gboolean gpsd_layer_set_param ( VikGpsdLayer *vgl, guint16 id, VikLayerParamData data, VikViewport *vp );
31static VikLayerParamData gpsd_layer_get_param ( VikGpsdLayer *vgl, guint16 id );
32static VikGpsdLayer *vik_gpsd_layer_new ( VikViewport *vp );
33static void vik_gpsd_layer_free ( VikGpsdLayer *vgl );
34static void vik_gpsd_layer_draw ( VikGpsdLayer *vgl, gpointer data );
35
36
37static VikLayerParam gpsd_layer_params[] = {
38};
39
40
41enum { NUM_PARAMS=0 };
42
43VikLayerInterface vik_gpsd_layer_interface = {
44 "Gpsd",
45 &gpsdlayer_pixbuf,
46
47 NULL,
48 0,
49
50// gpsd_layer_params,
51 NULL,
52 NUM_PARAMS,
53 NULL,
54 0,
55
56 VIK_MENU_ITEM_ALL,
57
58 (VikLayerFuncCreate) vik_gpsd_layer_new,
59 (VikLayerFuncRealize) NULL,
60 NULL,
61 (VikLayerFuncFree) vik_gpsd_layer_free,
62
63 (VikLayerFuncProperties) NULL,
64 (VikLayerFuncDraw) vik_gpsd_layer_draw,
65 (VikLayerFuncChangeCoordMode) NULL,
66
67 (VikLayerFuncSetMenuItemsSelection) NULL,
68 (VikLayerFuncGetMenuItemsSelection) NULL,
69
70 (VikLayerFuncAddMenuItems) NULL,
71 (VikLayerFuncSublayerAddMenuItems) NULL,
72
73 (VikLayerFuncSublayerRenameRequest) NULL,
74 (VikLayerFuncSublayerToggleVisible) NULL,
75
76 (VikLayerFuncMarshall) gpsd_layer_marshall,
77 (VikLayerFuncUnmarshall) gpsd_layer_unmarshall,
78
79 (VikLayerFuncSetParam) gpsd_layer_set_param,
80 (VikLayerFuncGetParam) gpsd_layer_get_param,
81
82 (VikLayerFuncReadFileData) NULL,
83 (VikLayerFuncWriteFileData) NULL,
84
85 (VikLayerFuncDeleteItem) NULL,
86 (VikLayerFuncCopyItem) NULL,
87 (VikLayerFuncPasteItem) NULL,
88 (VikLayerFuncFreeCopiedItem) NULL,
89 (VikLayerFuncDragDropRequest) NULL,
90};
91
92typedef struct {
93 struct gps_data_t data;
94 VikGpsdLayer *vgl;
95} FakeGpsData;
96
97struct _VikGpsdLayer {
98 VikLayer vl;
99 GdkGC *gc;
100 struct LatLon ll;
101 gdouble course;
102 FakeGpsData fgd;
103 gint timeout;
104};
105
106GType vik_gpsd_layer_get_type ()
107{
108 static GType vgl_type = 0;
109
110 if (!vgl_type)
111 {
112 static const GTypeInfo vgl_info =
113 {
114 sizeof (VikGpsdLayerClass),
115 NULL, /* base_init */
116 NULL, /* base_finalize */
117 NULL, /* class init */
118 NULL, /* class_finalize */
119 NULL, /* class_data */
120 sizeof (VikGpsdLayer),
121 0,
122 NULL /* instance init */
123 };
124 vgl_type = g_type_register_static ( VIK_LAYER_TYPE, "VikGpsdLayer", &vgl_info, 0 );
125 }
126
127 return vgl_type;
128}
129
130static void gpsd_layer_marshall( VikGpsdLayer *vgl, guint8 **data, gint *len )
131{
132 vik_layer_marshall_params ( VIK_LAYER(vgl), data, len );
133}
134
135static VikGpsdLayer *gpsd_layer_unmarshall( guint8 *data, gint len, VikViewport *vvp )
136{
137 VikGpsdLayer *rv = vik_gpsd_layer_new ( vvp );
138 vik_layer_unmarshall_params ( VIK_LAYER(rv), data, len, vvp );
139 return rv;
140}
141
142gboolean gpsd_layer_set_param ( VikGpsdLayer *vgl, guint16 id, VikLayerParamData data, VikViewport *vp )
143{
144 switch ( id )
145 {
146
147 }
148 return TRUE;
149}
150
151static VikLayerParamData gpsd_layer_get_param ( VikGpsdLayer *vgl, guint16 id )
152{
153 VikLayerParamData rv;
154 switch ( id )
155 {
156// case PARAM_COLOR: rv.s = vgl->color ? vgl->color : ""; break;
157 }
158 return rv;
159}
160
161static void vik_gpsd_layer_draw ( VikGpsdLayer *vgl, gpointer data )
162{
163 VikViewport *vp = (VikViewport *) data;
164 VikCoord nw, se;
165 struct LatLon lnw, lse;
166 vik_viewport_screen_to_coord ( vp, -20, -20, &nw );
167 vik_viewport_screen_to_coord ( vp, vik_viewport_get_width(vp)+20, vik_viewport_get_width(vp)+20, &se );
168 vik_coord_to_latlon ( &nw, &lnw );
169 vik_coord_to_latlon ( &se, &lse );
170 if ( vgl->ll.lat > lse.lat &&
171 vgl->ll.lat < lnw.lat &&
172 vgl->ll.lon > lnw.lon &&
173 vgl->ll.lon < lse.lon ) {
174 VikCoord gps;
175 gint x, y;
176 gint pt_x, pt_y;
177
178 vik_coord_load_from_latlon ( &gps, vik_viewport_get_coord_mode(vp), &(vgl->ll) );
179 vik_viewport_coord_to_screen ( vp, &gps, &x, &y );
180 vik_viewport_draw_rectangle ( vp, vgl->gc, TRUE, x-2, y-2, 4, 4 );
181
182 pt_y = y-20*cos(M_PI/180*vgl->course);
183 pt_x = x+20*sin(M_PI/180*vgl->course);
184
185 g_print("%d %d %d %d\n", x, y, pt_x, pt_y);
186 vik_viewport_draw_line ( vp, vgl->gc, x, y, pt_x, pt_y );
187 }
188}
189
190static void vik_gpsd_layer_free ( VikGpsdLayer *vgl )
191{
192 if ( vgl->gc != NULL )
193 g_object_unref ( G_OBJECT(vgl->gc) );
194 gtk_timeout_remove ( vgl->timeout );
195}
196
197void gpsd_hook(FakeGpsData *fgd, gchar *data)
198{
199 gdouble lat, lon, alt, herror, verror, course, speed;
200 /* skip thru three spaces */
201 while (*data && *data != ' ') data++; if (*data) data++;
202 while (*data && *data != ' ') data++; if (*data) data++;
203 while (*data && *data != ' ') data++; if (*data) data++;
204 if ( sscanf(data, "%lf %lf %lf %lf %lf %lf %lf", &lat, &lon,
205 &alt, &herror, &verror, &course, &speed) ) {
206 VikGpsdLayer *vgl = fgd->vgl;
207 vgl->ll.lat = lat;
208 vgl->ll.lon = lon;
209 vgl->course = course;
210 /* could/should emit update here. */
211 }
212}
213
214static gboolean gpsd_timeout(VikGpsdLayer *vgl)
215{
216 gps_query(&(vgl->fgd), "o");
217 vik_layer_emit_update ( VIK_LAYER(vgl) );
218 return TRUE;
219}
220
221static VikGpsdLayer *vik_gpsd_layer_new ( VikViewport *vp )
222{
223 VikGpsdLayer *vgl = VIK_GPSD_LAYER ( g_object_new ( VIK_GPSD_LAYER_TYPE, NULL ) );
224
225 vik_layer_init ( VIK_LAYER(vgl), VIK_LAYER_GPSD );
226
227 struct gps_data_t *orig_data = gps_open ("localhost", DEFAULT_GPSD_PORT);
228 vgl->fgd.data = *orig_data;
229 vgl->fgd.vgl = vgl;
230 g_free ( orig_data );
231 gps_set_raw_hook(&(vgl->fgd), gpsd_hook); /* pass along vgl in fgd */
232
233 vgl->gc = vik_viewport_new_gc ( vp, "red", 2 );
234 vgl->ll.lat = vgl->ll.lon = vgl->course = 0;
235
236 gtk_timeout_add ( 1000, (GtkFunction)gpsd_timeout, vgl);
237
238 return vgl;
239}
240