summaryrefslogtreecommitdiff
path: root/main.c
diff options
context:
space:
mode:
Diffstat (limited to 'main.c')
-rw-r--r--main.c172
1 files changed, 172 insertions, 0 deletions
diff --git a/main.c b/main.c
new file mode 100644
index 0000000..e645b48
--- /dev/null
+++ b/main.c
@@ -0,0 +1,172 @@
1#include <stdarg.h>
2#include <stdio.h>
3#include <stdlib.h>
4#include <signal.h>
5#include <time.h>
6
7#include <cwiid.h>
8#include "gm.h"
9#include "display.h"
10
11/* Our wii's bluetooth and wii handles */
12static bdaddr_t g_bdaddr[4];
13static cwiid_wiimote_t *g_wiimotes[4];
14static int g_num_controls = 0;
15static int g_samples_received = 0;
16static uint32_t g_starttime;
17
18static volatile int g_redraw_lock = 0;
19
20static const int g_width = 400, g_height = 300;
21
22cwiid_mesg_callback_t cwiid_callback;
23cwiid_err_t err;
24void err(cwiid_wiimote_t *wiimote, const char *s, va_list ap)
25{
26 if (wiimote) printf("%d:", cwiid_get_id(wiimote)); else printf("-1:");
27 vprintf(s, ap);
28 printf("\n");
29}
30
31int main( int argc, char **argv ) {
32 int LEDs[4] = { CWIID_LED1_ON, CWIID_LED1_ON | CWIID_LED2_ON,
33 CWIID_LED1_ON | CWIID_LED2_ON | CWIID_LED3_ON,
34 CWIID_LED1_ON | CWIID_LED2_ON | CWIID_LED3_ON | CWIID_LED4_ON };
35 int i;
36 struct timeval now;
37
38 signal( SIGINT, exit );
39 display_init( g_width, g_height);
40
41 cwiid_set_err(err);
42
43 /* If no bdaddrs given on command line, just connect to
44 first visible wii */
45 if( argc <= 1 ) {
46 char bt_out[64];
47 g_bdaddr[0] = *BDADDR_ANY;
48
49 while( !(g_wiimotes[g_num_controls] = cwiid_open( &g_bdaddr[0], 0 )))
50 fprintf( stderr, "Unable to connect to wiimote\n" );
51
52 ba2str( &g_bdaddr[0], bt_out );
53 fprintf( stderr, "Connected to wiimote %i (BT-Addr: %s)\n", i, bt_out );
54 g_num_controls++;
55 }
56
57 /* ... else try to reach every single wii */
58 for( i=0; i<argc-1; ++i ) {
59 str2ba(argv[i+1], &g_bdaddr[i]);
60
61 while( !(g_wiimotes[g_num_controls] = cwiid_open( &g_bdaddr[i], 0 )))
62 fprintf( stderr, "Unable to connect to wiimote %i (BT-Addr: %s)\n", i, argv[i+1] );
63
64 g_num_controls++;
65 fprintf( stderr, "Connected to wiimote %i (BT-Addr: %s)\n", i, argv[i+1] );
66 }
67
68 for( i=0; i<g_num_controls; ++i ) {
69 if (cwiid_set_mesg_callback(g_wiimotes[i], cwiid_callback)) {
70 fprintf(stderr, "Unable to set message callback\n");
71 return -1;
72 }
73
74 /* Set report mode to IR */
75 cwiid_set_rpt_mode(g_wiimotes[i], CWIID_RPT_IR);
76
77 /* Enable call back */
78 cwiid_enable(g_wiimotes[i], CWIID_FLAG_MESG_IFC);
79
80 /* Reflect number in leds */
81 cwiid_set_led(g_wiimotes[i], LEDs[i]);
82 }
83
84 gettimeofday(&now, (struct timezone *)NULL);
85 g_starttime = now.tv_sec * 1000 + now.tv_usec / 1000; /* in ms */
86
87 /* Spin and let call back do all the work */
88 while( 1 ) {
89 if( ! (++i & 0xffff ) ) {
90 int wii_id, led;
91 while( g_redraw_lock );
92
93 for( wii_id=0; wii_id<4; ++wii_id )
94 for( led = 0; led<4; ++led )
95 display_rectangle( wii_id, led * g_width / 16, 0, g_width / 16, vubars_getinfo(wii_id, led)/2 );
96
97 display_redraw();
98 usleep( 1000 );
99 vubars_reduce();
100 display_rectangle( 2, g_width/2-10, 0, 20, -vubars_getweather()/2 );
101 display_rectangle( 2, g_width/2-15, -128, 30, 1 );
102 display_rectangle( 2, g_width/2-15, -64, 30, 1 );
103 }
104 }
105
106 return 0;
107}
108
109void cwiid_callback(cwiid_wiimote_t *wiimote, int mesg_count,
110 union cwiid_mesg mesg[], struct timespec *timestamp)
111{
112 int i, j, k, wii_id, ledmask;
113 int valid_sources;
114 struct timeval now;
115 uint32_t runtime;
116 wii_pt coords[4];
117
118 gettimeofday(&now, (struct timezone *)NULL);
119 runtime = now.tv_sec * 1000 + now.tv_usec / 1000 - g_starttime; /* in ms */
120
121 for( i=0; i<g_num_controls; ++i ) {
122 if( wiimote == g_wiimotes[i] )
123 wii_id = i;
124 }
125 g_redraw_lock = 1;
126 display_clear();
127 g_samples_received++;
128 for (i=0; i < mesg_count; i++) {
129 switch (mesg[i].type) {
130
131 case CWIID_MESG_IR:
132// printf("IR Report (%i): ", wii_id );
133// printf("(%ld Hz) ", ( g_samples_received * 1000 ) / runtime );
134
135 valid_sources = 0;
136 for (j = 0; j < CWIID_IR_SRC_COUNT; j++) {
137 if (mesg[i].ir_mesg.src[j].valid) {
138 coords[valid_sources].x = (double)mesg[i].ir_mesg.src[j].pos[CWIID_X];
139 coords[valid_sources].y = (double)mesg[i].ir_mesg.src[j].pos[CWIID_Y];
140
141 display_circle( wii_id, coords[valid_sources].x / 5.0, coords[valid_sources].y / 5.0, 6 );
142 valid_sources++;
143// printf("(%d,%d) ", mesg[i].ir_mesg.src[j].pos[CWIID_X],
144// mesg[i].ir_mesg.src[j].pos[CWIID_Y]);
145 }
146 }
147
148 if (!valid_sources) {
149// printf("no sources detected");
150 }
151
152 if( valid_sources == 4 ) {
153 wii_calibrate( wii_id, coords );
154 }
155
156 ledmask = 0;
157 for( j=0; j<valid_sources; ++j ) {
158 int led = wii_point_to_led( wii_id, coords+j );
159 ledmask |= 1<<led;
160 }
161 for( j=0; j<4; ++j ) {
162 vubars_peak( wii_id, j, ( ledmask >> j ) & 1 );
163 }
164
165 break;
166 default:
167 break;
168 }
169 }
170 g_redraw_lock = 0;
171}
172