1 /* AADL plugin for DIA
2 *
3 * Copyright (C) 2005 Laboratoire d'Informatique de Paris 6
4 * Author: Pierre Duquesne
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
22 /* AADL plugin for DIA
23 * Author: Pierre Duquesne
24 *
25 * This program is free software; you can redistribute it and/or modify
26 * it under the terms of the GNU General Public License as published by
27 * the Free Software Foundation; either version 2 of the License, or
28 * (at your option) any later version.
29 *
30 * This program is distributed in the hope that it will be useful,
31 * but WITHOUT ANY WARRANTY; without even the implied warranty of
32 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
33 * GNU General Public License for more details.
34 *
35 * You should have received a copy of the GNU General Public License
36 * along with this program; if not, write to the Free Software
37 * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
38 */
39
40 #include "aadl.h"
41
42 /***********************************************
43 ** PORT-RELATED FUNCTIONS **
44 ***********************************************/
45
46 void
rotate_around_origin(Point * p,real angle)47 rotate_around_origin (Point *p, real angle) /* FIXME: no namespace */
48 {
49 coord x = p->x;
50 coord y = p->y;
51
52 p->x = x * cos(angle) - y * sin(angle) ;
53 p->y = x * sin(angle) + y * cos(angle) ;
54
55 }
56
57
58
59
60 #define AADL_PORT_WIDTH_A 0.2
61 #define AADL_PORT_WIDTH_B 0.5
62 #define AADL_PORT_HEIGHT 0.6
63 #define AADL_PORT_LINEWIDTH 0.1
64 /* A| B C */
65 #define AADL_ACCESS_WIDTH_A 0.2 /* ---\ */
66 #define AADL_ACCESS_WIDTH_B 0.3 /* | + */
67 #define AADL_ACCESS_WIDTH_C 0.2 /* ---/ */
68 #define AADL_ACCESS_HEIGHT 0.9 /* | */
69
70 #define AADL_EVENT_DELTA_WIDTH 0.4
71 #define AADL_EVENT_DELTA_HEIGHT 0.3
72
73
74
75 #define draw_in_data_port() \
76 p[0].x = AADL_PORT_WIDTH_A; \
77 p[0].y = -AADL_PORT_HEIGHT/2; \
78 \
79 p[1].x = -AADL_PORT_WIDTH_B; \
80 p[1].y = 0; \
81 \
82 p[2].x = AADL_PORT_WIDTH_A; \
83 p[2].y = AADL_PORT_HEIGHT/2; \
84 \
85 rotate_around_origin(p, port->angle); \
86 rotate_around_origin(p+1, port->angle); \
87 rotate_around_origin(p+2, port->angle); \
88 \
89 point_add(p, &port->handle->pos); \
90 point_add(p+1, &port->handle->pos); \
91 point_add(p+2, &port->handle->pos); \
92 \
93 renderer_ops->set_linewidth(renderer, AADL_PORT_LINEWIDTH); \
94 renderer_ops->set_linejoin(renderer, LINEJOIN_MITER); \
95 renderer_ops->set_linestyle(renderer, LINESTYLE_SOLID); \
96 \
97 renderer_ops->fill_polygon(renderer, p, 3, &color_black); \
98 renderer_ops->draw_polygon(renderer, p, 3, &color_black);
99
100 #define draw_in_event_port() \
101 p[0].x = AADL_PORT_WIDTH_A; \
102 p[0].y = -AADL_PORT_HEIGHT/2 - AADL_EVENT_DELTA_HEIGHT; \
103 \
104 p[1].x = - AADL_PORT_WIDTH_B - AADL_EVENT_DELTA_WIDTH; \
105 p[1].y = 0; \
106 \
107 p[2].x = AADL_PORT_WIDTH_A; \
108 p[2].y = AADL_PORT_HEIGHT/2 + AADL_EVENT_DELTA_HEIGHT; \
109 \
110 rotate_around_origin(p, port->angle); \
111 rotate_around_origin(p+1, port->angle); \
112 rotate_around_origin(p+2, port->angle); \
113 \
114 point_add(p, &port->handle->pos); \
115 point_add(p+1, &port->handle->pos); \
116 point_add(p+2, &port->handle->pos); \
117 \
118 renderer_ops->set_linewidth(renderer, AADL_PORT_LINEWIDTH); \
119 renderer_ops->set_linejoin(renderer, LINEJOIN_MITER); \
120 renderer_ops->set_linestyle(renderer, LINESTYLE_SOLID); \
121 \
122 renderer_ops->draw_polyline(renderer, p, 3, &color_black);
123
124 #define draw_out_data_port() \
125 p[0].x = -AADL_PORT_WIDTH_A; \
126 p[0].y = -AADL_PORT_HEIGHT/2; \
127 \
128 p[1].x = AADL_PORT_WIDTH_B; \
129 p[1].y = 0; \
130 \
131 p[2].x = -AADL_PORT_WIDTH_A; \
132 p[2].y = AADL_PORT_HEIGHT/2; \
133 \
134 rotate_around_origin(p, port->angle); \
135 rotate_around_origin(p+1, port->angle); \
136 rotate_around_origin(p+2, port->angle); \
137 \
138 point_add(p, &port->handle->pos); \
139 point_add(p+1, &port->handle->pos); \
140 point_add(p+2, &port->handle->pos); \
141 \
142 renderer_ops->set_linewidth(renderer, AADL_PORT_LINEWIDTH); \
143 renderer_ops->set_linejoin(renderer, LINEJOIN_MITER); \
144 renderer_ops->set_linestyle(renderer, LINESTYLE_SOLID); \
145 \
146 renderer_ops->fill_polygon(renderer, p, 3, &color_black); \
147 renderer_ops->draw_polygon(renderer, p, 3, &color_black);
148
149 #define draw_out_event_port() \
150 p[0].x = - AADL_PORT_WIDTH_A; \
151 p[0].y = - AADL_PORT_HEIGHT/2 - AADL_EVENT_DELTA_HEIGHT; \
152 \
153 p[1].x = AADL_PORT_WIDTH_B + AADL_EVENT_DELTA_WIDTH; \
154 p[1].y = 0; \
155 \
156 p[2].x = - AADL_PORT_WIDTH_A; \
157 p[2].y = AADL_PORT_HEIGHT/2 + AADL_EVENT_DELTA_HEIGHT; \
158 \
159 rotate_around_origin(p, port->angle); \
160 rotate_around_origin(p+1, port->angle); \
161 rotate_around_origin(p+2, port->angle); \
162 \
163 point_add(p, &port->handle->pos); \
164 point_add(p+1, &port->handle->pos); \
165 point_add(p+2, &port->handle->pos); \
166 \
167 renderer_ops->set_linewidth(renderer, AADL_PORT_LINEWIDTH); \
168 renderer_ops->set_linejoin(renderer, LINEJOIN_MITER); \
169 renderer_ops->set_linestyle(renderer, LINESTYLE_SOLID); \
170 \
171 renderer_ops->draw_polyline(renderer, p, 3, &color_black);
172
173 #define draw_in_out_data_port() \
174 p[0].x = 0; \
175 p[0].y = -AADL_PORT_HEIGHT/2; \
176 \
177 p[1].x = AADL_PORT_WIDTH_B; \
178 p[1].y = 0; \
179 \
180 p[2].x = 0; \
181 p[2].y = AADL_PORT_HEIGHT/2; \
182 \
183 p[3].x = -AADL_PORT_WIDTH_B; \
184 p[3].y = 0; \
185 \
186 rotate_around_origin(p, port->angle); \
187 rotate_around_origin(p+1, port->angle); \
188 rotate_around_origin(p+2, port->angle); \
189 rotate_around_origin(p+3, port->angle); \
190 \
191 point_add(p, &port->handle->pos); \
192 point_add(p+1, &port->handle->pos); \
193 point_add(p+2, &port->handle->pos); \
194 point_add(p+3, &port->handle->pos); \
195 \
196 renderer_ops->set_linewidth(renderer, AADL_PORT_LINEWIDTH); \
197 renderer_ops->set_linejoin(renderer, LINEJOIN_MITER); \
198 renderer_ops->set_linestyle(renderer, LINESTYLE_SOLID); \
199 \
200 renderer_ops->fill_polygon(renderer, p, 4, &color_black); \
201 renderer_ops->draw_polygon(renderer, p, 4, &color_black);
202
203
204
205 #define draw_in_out_event_port() \
206 p[0].x = 0; \
207 p[0].y = -AADL_PORT_HEIGHT/2 - AADL_EVENT_DELTA_HEIGHT; \
208 \
209 p[1].x = AADL_PORT_WIDTH_B + AADL_EVENT_DELTA_WIDTH; \
210 p[1].y = 0; \
211 \
212 p[2].x = 0; \
213 p[2].y = AADL_PORT_HEIGHT/2 + AADL_EVENT_DELTA_HEIGHT; \
214 \
215 p[3].x = -AADL_PORT_WIDTH_B - AADL_EVENT_DELTA_WIDTH; \
216 p[3].y = 0; \
217 \
218 rotate_around_origin(p, port->angle); \
219 rotate_around_origin(p+1, port->angle); \
220 rotate_around_origin(p+2, port->angle); \
221 rotate_around_origin(p+3, port->angle); \
222 \
223 point_add(p, &port->handle->pos); \
224 point_add(p+1, &port->handle->pos); \
225 point_add(p+2, &port->handle->pos); \
226 point_add(p+3, &port->handle->pos); \
227 \
228 renderer_ops->set_linewidth(renderer, AADL_PORT_LINEWIDTH); \
229 renderer_ops->set_linejoin(renderer, LINEJOIN_MITER); \
230 renderer_ops->set_linestyle(renderer, LINESTYLE_SOLID); \
231 \
232 renderer_ops->draw_polygon(renderer, p, 4, &color_black);
233
234
235 /* FIXME: should i make methods from this function ? */
236
237 void
aadlbox_draw_port(Aadlport * port,DiaRenderer * renderer)238 aadlbox_draw_port(Aadlport *port, DiaRenderer *renderer)
239 {
240 DiaRendererClass *renderer_ops = DIA_RENDERER_GET_CLASS (renderer);
241 Point p[5];
242
243 assert(port!=NULL);
244 assert(renderer!=NULL);
245
246 switch(port->type) {
247
248 case ACCESS_PROVIDER:
249 p[0].x = - AADL_ACCESS_WIDTH_A;
250 p[0].y = - AADL_ACCESS_HEIGHT/2;
251
252 p[1].x = AADL_ACCESS_WIDTH_B;
253 p[1].y = - AADL_ACCESS_HEIGHT/2;
254
255 p[2].x = AADL_ACCESS_WIDTH_B + AADL_ACCESS_WIDTH_C ;
256 p[2].y = 0;
257
258 p[3].x = AADL_ACCESS_WIDTH_B;
259 p[3].y = AADL_ACCESS_HEIGHT/2;
260
261 p[4].x = - AADL_ACCESS_WIDTH_A;
262 p[4].y = AADL_ACCESS_HEIGHT/2;
263
264 rotate_around_origin(p, port->angle);
265 rotate_around_origin(p+1, port->angle);
266 rotate_around_origin(p+2, port->angle);
267 rotate_around_origin(p+3, port->angle);
268 rotate_around_origin(p+4, port->angle);
269
270 point_add(p, &port->handle->pos);
271 point_add(p+1, &port->handle->pos);
272 point_add(p+2, &port->handle->pos);
273 point_add(p+3, &port->handle->pos);
274 point_add(p+4, &port->handle->pos);
275
276 renderer_ops->set_linewidth(renderer, AADL_PORT_LINEWIDTH);
277 renderer_ops->set_linejoin(renderer, LINEJOIN_MITER);
278 renderer_ops->set_linestyle(renderer, LINESTYLE_SOLID);
279
280 renderer_ops->fill_polygon(renderer, p, 5, &color_white);
281 renderer_ops->draw_polygon(renderer, p, 5, &color_black);
282
283 break;
284
285 case ACCESS_REQUIRER:
286 p[0].x = AADL_ACCESS_WIDTH_A;
287 p[0].y = - AADL_ACCESS_HEIGHT/2;
288
289 p[1].x = - AADL_ACCESS_WIDTH_B;
290 p[1].y = - AADL_ACCESS_HEIGHT/2;
291
292 p[2].x = - AADL_ACCESS_WIDTH_B - AADL_ACCESS_WIDTH_C ;
293 p[2].y = 0;
294
295 p[3].x = - AADL_ACCESS_WIDTH_B;
296 p[3].y = AADL_ACCESS_HEIGHT/2;
297
298 p[4].x = AADL_ACCESS_WIDTH_A;
299 p[4].y = AADL_ACCESS_HEIGHT/2;
300
301 rotate_around_origin(p, port->angle);
302 rotate_around_origin(p+1, port->angle);
303 rotate_around_origin(p+2, port->angle);
304 rotate_around_origin(p+3, port->angle);
305 rotate_around_origin(p+4, port->angle);
306
307 point_add(p, &port->handle->pos);
308 point_add(p+1, &port->handle->pos);
309 point_add(p+2, &port->handle->pos);
310 point_add(p+3, &port->handle->pos);
311 point_add(p+4, &port->handle->pos);
312
313 renderer_ops->set_linewidth(renderer, AADL_PORT_LINEWIDTH);
314 renderer_ops->set_linejoin(renderer, LINEJOIN_MITER);
315 renderer_ops->set_linestyle(renderer, LINESTYLE_SOLID);
316
317 renderer_ops->fill_polygon(renderer, p, 5, &color_white);
318 renderer_ops->draw_polygon(renderer, p, 5, &color_black);
319
320 break;
321
322 case IN_DATA_PORT:
323 draw_in_data_port();
324 break;
325
326 case IN_EVENT_PORT:
327 draw_in_event_port()
328 break;
329
330 case IN_EVENT_DATA_PORT:
331 draw_in_data_port();
332 draw_in_event_port();
333 break;
334
335 case OUT_DATA_PORT:
336 draw_out_data_port();
337 break;
338
339 case OUT_EVENT_PORT:
340 draw_out_event_port();
341 break;
342
343 case OUT_EVENT_DATA_PORT:
344 draw_out_data_port();
345 draw_out_event_port();
346 break;
347
348 case IN_OUT_DATA_PORT:
349 draw_in_out_data_port();
350 break;
351
352 case IN_OUT_EVENT_PORT:
353 draw_in_out_event_port();
354 break;
355
356 case IN_OUT_EVENT_DATA_PORT:
357 draw_in_out_data_port();
358 draw_in_out_event_port();
359 break;
360
361 #define AADL_PORT_GROUP_SIZE 0.1
362
363 case PORT_GROUP: /* quick n dirty - should use macros*/
364 {
365 BezPoint b[5];
366 int i;
367
368 p[0].x = 0; p[0].y = 0;
369
370 rotate_around_origin(p, port->angle);
371 point_add(p, &port->handle->pos);
372
373 renderer_ops->set_linewidth(renderer, AADL_PORT_LINEWIDTH);
374 renderer_ops->set_linejoin(renderer, LINEJOIN_MITER);
375 renderer_ops->set_linestyle(renderer, LINESTYLE_SOLID);
376
377 renderer_ops->fill_ellipse(renderer, p,
378 6 * AADL_PORT_GROUP_SIZE,
379 6 * AADL_PORT_GROUP_SIZE,
380 &color_black);
381 renderer_ops->draw_ellipse(renderer, p,
382 6 * AADL_PORT_GROUP_SIZE,
383 6 * AADL_PORT_GROUP_SIZE,
384 &color_black);
385
386
387 b[0].type = BEZ_MOVE_TO;
388 b[1].type = BEZ_CURVE_TO;
389 b[2].type = BEZ_LINE_TO;
390 b[3].type = BEZ_CURVE_TO;
391 b[4].type = BEZ_LINE_TO;
392
393 b[0].p1.x = -2 * AADL_PORT_GROUP_SIZE;
394 b[0].p1.y = -6 * AADL_PORT_GROUP_SIZE;
395
396 b[1].p1.x = -6 * AADL_PORT_GROUP_SIZE;
397 b[1].p1.y = -4 * AADL_PORT_GROUP_SIZE;
398 b[1].p2.x = -6 * AADL_PORT_GROUP_SIZE;
399 b[1].p2.y = 4 * AADL_PORT_GROUP_SIZE;
400 b[1].p3.x = -2 * AADL_PORT_GROUP_SIZE;
401 b[1].p3.y = 6 * AADL_PORT_GROUP_SIZE;
402
403 b[2].p1.x = -2 * AADL_PORT_GROUP_SIZE;
404 b[2].p1.y = 9 * AADL_PORT_GROUP_SIZE;
405
406 b[3].p1.x = -9 * AADL_PORT_GROUP_SIZE;
407 b[3].p1.y = 7 * AADL_PORT_GROUP_SIZE;
408 b[3].p2.x = -9 * AADL_PORT_GROUP_SIZE;
409 b[3].p2.y = -7 * AADL_PORT_GROUP_SIZE;
410 b[3].p3.x = -2 * AADL_PORT_GROUP_SIZE;
411 b[3].p3.y = -9 * AADL_PORT_GROUP_SIZE;
412
413 b[4].p1.x = -2 * AADL_PORT_GROUP_SIZE;
414 b[4].p1.y = -6 * AADL_PORT_GROUP_SIZE;
415
416 for (i=0; i<5; i++) {
417 rotate_around_origin(&b[i].p1, port->angle);
418 point_add(&b[i].p1, &port->handle->pos);
419
420 if (b[i].type == BEZ_CURVE_TO) {
421 rotate_around_origin(&b[i].p2, port->angle);
422 rotate_around_origin(&b[i].p3, port->angle);
423
424 point_add(&b[i].p2, &port->handle->pos);
425 point_add(&b[i].p3, &port->handle->pos);
426 }
427 }
428
429 renderer_ops->fill_bezier(renderer, b, 5, &color_black);
430 renderer_ops->draw_bezier(renderer, b, 5, &color_black);
431
432 }
433 break;
434
435 default:
436 break;
437
438 }
439 }
440
441
442
aadlbox_update_port(Aadlbox * aadlbox,Aadlport * port)443 void aadlbox_update_port(Aadlbox *aadlbox, Aadlport *port)
444 {
445 /* Ports are always kept on the borders of the box */
446 aadlbox->specific->project_point_on_nearest_border(aadlbox,
447 &port->handle->pos, &port->angle);
448
449 /* reinit in & out connection point to default position */
450 /* FIXME: should i make methods ? */
451 switch (port->type) {
452
453 case ACCESS_PROVIDER:
454 port->in.pos.x = - AADL_ACCESS_WIDTH_A;
455 port->in.pos.y=0;
456
457 port->out.pos.x= AADL_ACCESS_WIDTH_B + AADL_ACCESS_WIDTH_C;
458 port->out.pos.y=0;
459 break;
460
461 case ACCESS_REQUIRER:
462 port->in.pos.x = AADL_ACCESS_WIDTH_A;
463 port->in.pos.y=0;
464
465 port->out.pos.x= - AADL_ACCESS_WIDTH_B - AADL_ACCESS_WIDTH_C;
466 port->out.pos.y=0;
467 break;
468
469 case IN_DATA_PORT:
470 port->in.pos.x = AADL_PORT_WIDTH_A; port->in.pos.y=0;
471 port->out.pos.x= -AADL_PORT_WIDTH_B; port->out.pos.y=0;
472 break;
473
474 case IN_EVENT_PORT:
475 case IN_EVENT_DATA_PORT:
476 port->in.pos.x = AADL_PORT_WIDTH_A;
477 port->in.pos.y=0;
478
479 port->out.pos.x= -AADL_PORT_WIDTH_B - AADL_EVENT_DELTA_WIDTH;
480 port->out.pos.y=0;
481 break;
482
483 case OUT_DATA_PORT:
484 port->in.pos.x = -AADL_PORT_WIDTH_A; port->in.pos.y=0;
485 port->out.pos.x= AADL_PORT_WIDTH_B; port->out.pos.y=0;
486 break;
487
488 case OUT_EVENT_PORT:
489 case OUT_EVENT_DATA_PORT:
490 port->in.pos.x = -AADL_PORT_WIDTH_A;
491 port->in.pos.y=0;
492
493 port->out.pos.x= AADL_PORT_WIDTH_B + AADL_EVENT_DELTA_WIDTH;
494 port->out.pos.y=0;
495 break;
496
497 case IN_OUT_DATA_PORT:
498 port->in.pos.x = -AADL_PORT_WIDTH_B; port->in.pos.y=0;
499 port->out.pos.x= AADL_PORT_WIDTH_B; port->out.pos.y=0;
500 break;
501
502 case IN_OUT_EVENT_PORT:
503 case IN_OUT_EVENT_DATA_PORT:
504 port->in.pos.x = -AADL_PORT_WIDTH_B - AADL_EVENT_DELTA_WIDTH;
505 port->in.pos.y=0;
506 port->out.pos.x= AADL_PORT_WIDTH_B + AADL_EVENT_DELTA_HEIGHT;
507 port->out.pos.y=0;
508 break;
509
510 case PORT_GROUP: /* quick n dirty */
511 port->in.pos.x = -9*AADL_PORT_GROUP_SIZE; port->in.pos.y=0;
512 port->out.pos.x = 3*AADL_PORT_GROUP_SIZE; port->out.pos.y=0;
513 break;
514
515 default:
516 break;
517
518
519 }
520
521 rotate_around_origin(&port->in.pos, port->angle);
522 rotate_around_origin(&port->out.pos, port->angle);
523
524 point_add(&port->in.pos, &port->handle->pos);
525 point_add(&port->out.pos, &port->handle->pos);
526
527 /* direction hints */
528 /*
529 if (port->angle >= M_PI/4.0 && port->angle < 3.0*M_PI/4.0)
530 port->out.directions = DIR_SOUTH;
531 else if (port->angle >= 3.0*M_PI/4.0 && port->angle < 5.0*M_PI/4.0)
532 port->out.directions = DIR_WEST;
533 else if (port->angle >= 5.0*M_PI/4.0 && port->angle < 7.0*M_PI/4.0)
534 port->out.directions = DIR_NORTH;
535 else
536 port->out.directions = DIR_EAST;
537 */
538 }
539
540
aadlbox_update_ports(Aadlbox * aadlbox)541 void aadlbox_update_ports(Aadlbox *aadlbox)
542 {
543 int i;
544
545 for (i=0;i<aadlbox->num_ports;i++)
546 aadlbox_update_port(aadlbox, aadlbox->ports[i]);
547 }
548
549
550