Tscope5
display.c
Go to the documentation of this file.
1 ////////////////////////////////////////////////////////////////////////////////
2 //
3 // __ ______
4 // / /_______________ ____ ___ / ____/
5 // / __/ ___/ ___/ __ \/ __ \/ _ \ /___ )
6 // / /_(__ ) /__/ /_/ / /_/ / __/ ____/ /
7 // \__/____/\___/\____/ .___/\___/ /_____/
8 // /_/
9 //
10 /// \file display.c
11 /// Definitions of display functions.
12 /// \example display01.c
13 /// \example display01.cpp
14 /// \example display02.c
15 /// \example display03.c
16 /// \example display04.c
17 /// \example display05.c
18 ////////////////////////////////////////////////////////////////////////////////
19 
20 
21 #include "../include/tscope5/display.h"
22 #include "../include/tscope5/graphics.h"
23 #include "../include/tscope5/bitmaps.h"
24 #include "../include/tscope5/display_internal.h"
25 #include "../include/tscope5/system_internal.h"
26 #include "../include/tscope5/graphics_internal.h"
27 
28 #include <math.h>
29 
30 
31 ////////////////////////////////////////////////////////////////////////////////
32 /// @name Basic operations
33 /// A display can either be a window or a fullscreen display.
34 /// There are three basic display operations:
35 /// - You will need to install a display with ts5_install_display()
36 /// before anything can be drawn.
37 /// - The contents of a display can be cleared with ts5_clear_display().
38 /// - Anything that is drawn on a display only becomes visible
39 /// after a call to ts5_flip_display().
40 //@{
41 ////////////////////////////////////////////////////////////////////////////////
42 
43 
44 ////////////////////////////////////////////////////////////////////////////////
45 /// Open a new display.
46 ///
47 /// \return The index of the new display.
48 ///
49 /// TS5_FULLSCREEN_WINDOW mode:
50 /// - A fullscreen display will be opened using the same
51 /// display size and refreshrate as the desktop.
52 /// - In this mode, the display size, position and refreshrate
53 /// cannot be set by the user. These parameters will be ignored.
54 /// - Tscope5 will check whether the new display is the first
55 /// display on the adapter. If not, the program is aborted.
56 ///
57 /// TS5_FULLSCREEN mode:
58 /// - A fullscreen display will be opened.
59 /// The user can specify the display size and refreshrate.
60 /// - In this mode, the display position cannot be set by the user.
61 /// This parameter will be ignored.
62 /// - Tscope5 will check whether the new display is the
63 /// first display on the adapter. If not, the program is aborted.
64 /// - Tscope5 will check whether the display size and refreshrate is
65 /// supported by the adapter. If not, the program is aborted.
66 /// - A call to ts5_print_status() will list all combinations of
67 /// size and refreshrate that are supported by the adapter.
68 ///
69 /// TS5_WINDOWED mode:
70 /// - Opens a window. The user can specifiy the display size and position.
71 /// - In this mode, the refreshrate cannot be set by the user.
72 /// This parameter will be ignored.
73 /// - Tscope5 will check whether the adapter is already in use by
74 /// a TS5_FULLSCREEN_WINDOW or TS5_FULLSCREEN display.
75 /// If so, the program is aborted.
76 /// - Tscope5 will check whether the window will fit on the display.
77 /// If not, the dimensions of the display are reduced.
78 /// - Tscope5 will check whether the window will be visible on the screen.
79 /// If not, the window position is changed.
80 ///
81 /// The new display is the drawing target for future drawing operations.
82 ////////////////////////////////////////////////////////////////////////////////
84 {
85  ts5_check_display("ts5_install_display");
86 
87  TS5_DISPLAY_STATUS request = ts5_nextdisplay;
88 
89  // TS5_FULLSCREEN_WINDOW
90  if (ts5_nextdisplay.display_mode == TS5_FULLSCREEN_WINDOW) {
91 
92  // the adapter cannot be in use by another tscope5 display
93  int i;
94  for (i = 0; i < _ts5_status.num_displays; i++) {
95 
96  if (_ts5_status.display[i].adapter
97  == ts5_nextdisplay.adapter) {
98  ts5_fatal ("%s: %s, %s (%d)\n", "ts5_install_display",
99  "cannot open fullscreen display",
100  "adapter already in use by another display", i);
101  }
102  }
103 
104  // copy relevant settings
105  request.w = 320;
106  request.h = 240;
107  request.x = -1;
108  request.y = -1;
109  request.refreshrate = -1;
110  request.display_mode = TS5_FULLSCREEN_WINDOW;
111  request.vsync_mode = ts5_nextdisplay.vsync_mode;
112 
113  #ifdef TS5_RASPBERRYPI
114 
115  request.display_mode = TS5_FULLSCREEN;
116  request.w = ts5_get_display_adapter_width(1);
117  request.h = ts5_get_display_adapter_height(1);
118 
119 
120  #endif
121  }
122 
123 
124  // TS5_FULLSCREEN
125  if (ts5_nextdisplay.display_mode == TS5_FULLSCREEN) {
126 
127  // the adapter cannot be in use by another tscope5 display
128  int i;
129  for (i = 0; i < _ts5_status.num_displays; i++) {
130 
131  if (_ts5_status.display[i].adapter
132  == ts5_nextdisplay.adapter) {
133  ts5_fatal ("%s: %s, %s (%d)\n", "ts5_install_display",
134  "cannot open fullscreen display",
135  " adapter already in use by another display", i);
136  }
137  }
138 
139  // is the combination of display size and refresh rate supported by
140  // the adapter?
141  ALLEGRO_DISPLAY_MODE *mode;
142  mode = (ALLEGRO_DISPLAY_MODE *)al_malloc(sizeof(ALLEGRO_DISPLAY_MODE));
143  int nmodes = al_get_num_display_modes();
144  int found=0;
145 
146  for (i=0; i<nmodes; i++) {
147 
148  mode = al_get_display_mode(i, mode);
149 
150  if (mode->width==ts5_nextdisplay.w
151  && mode->height==ts5_nextdisplay.h
152  && (mode->refresh_rate==ts5_nextdisplay.refreshrate
153  || mode->refresh_rate==0)) {
154  found=1;
155  }
156  }
157 
158  al_free(mode);
159 
160  if (!found) {
161  ts5_fatal ("%s: %s (%d, %d) %s (%d) %s %d\n",
162  "ts5_install_display",
163  "the requested combination of size",
165  "and refreshate", ts5_nextdisplay.refreshrate,
166  "is not supported by display adapter",
167  ts5_nextdisplay.adapter);
168  }
169 
170  // copy relevant settings
171  request.w = ts5_nextdisplay.w;
172  request.h = ts5_nextdisplay.h;
173  request.x = -1;
174  request.y = -1;
175  request.refreshrate = ts5_nextdisplay.refreshrate;
176  request.display_mode = TS5_FULLSCREEN;
177  request.vsync_mode = ts5_nextdisplay.vsync_mode;
178  }
179 
180  // TS5_WINDOWED
181  if (ts5_nextdisplay.display_mode == TS5_WINDOWED) {
182 
183  // the adapter cannot be in used by a
184  // TS5_FULLSCREEN_WINDOW or TS5_FULLSCREEN display
185  int i;
186  for (i = 0; i < _ts5_status.num_displays; i++) {
187 
188  if (_ts5_status.display[i].adapter
189  == ts5_nextdisplay.adapter
190  && (_ts5_status.display[i].display_mode
191  == TS5_FULLSCREEN
192  || _ts5_status.display[i].display_mode
193  == TS5_FULLSCREEN_WINDOW)) {
194 
195  ts5_fatal ("%s: %s, %s (%d)\n", "ts5_install_display",
196  "cannot open display",
197  " adapter already in use by a fullscreen display",
198  i);
199  }
200  }
201 
202  // window should be at least 320 pixels wide
203  // and smaller than the width of the monitor
204  if (ts5_nextdisplay.w < 320 ) {
205  request.w = 320;
206  ts5_log(TS5_LOGLEVEL_1, "%s: %s %d (was %d)\n",
207  "ts5_install_display", "adjusting display width to",
208  request.w, ts5_nextdisplay.w);
209  }
210  else if (ts5_nextdisplay.w
211  > _ts5_status.display_adapter
212  [ts5_nextdisplay.adapter].w) {
213 
214  request.w = _ts5_status.display_adapter[ts5_nextdisplay.adapter].w;
215 
216  ts5_log(TS5_LOGLEVEL_1, "%s: %s %d (was %d)\n",
217  "ts5_install_display", "adjusting display width to",
218  request.w, ts5_nextdisplay.w);
219  }
220  else {
221  request.w = ts5_nextdisplay.w;
222  }
223 
224  // window should be at least 240 pixels high
225  // and smaller than the height of the monitor
226  if (ts5_nextdisplay.h < 240 ) {
227  request.h = 240;
228  ts5_log(TS5_LOGLEVEL_1, "%s: %s %d (was %d)\n",
229  "ts5_install_display", "adjusting display height to",
230  request.h, ts5_nextdisplay.h);
231  }
232  else if (ts5_nextdisplay.h
233  > _ts5_status.display_adapter
234  [ts5_nextdisplay.adapter].h) {
235 
236  request.h = _ts5_status.display_adapter
237  [ts5_nextdisplay.adapter].h;
238 
239  ts5_log(TS5_LOGLEVEL_1, "%s: %s %d (was %d)\n",
240  "ts5_install_display", "adjusting display height to",
241  request.h, ts5_nextdisplay.h);
242  }
243  else {
244  request.h = ts5_nextdisplay.h;
245  }
246 
247  request.x = ts5_nextdisplay.x;
248  request.y = ts5_nextdisplay.y;
249 
250  if (request.x == -1) {
251 
252  if (_ts5_status.graphics.coordinate_system
253  == TS5_CARTESIAN_COORDINATES) {
254 
255  request.x = (_ts5_status.display_adapter
256  [request.adapter].w - request.w)/2;
257  }
258  else {
259  request.x = 0;
260  }
261 
262  request.x += _ts5_status.display_adapter[request.adapter].x1;
263  }
264 
265  if (request.y == -1) {
266 
267  if (_ts5_status.graphics.coordinate_system
268  == TS5_CARTESIAN_COORDINATES) {
269 
270  request.y = (_ts5_status.display_adapter
271  [request.adapter].h - request.h)/2;
272  }
273  else {
274  request.y = 0;
275  }
276 
277  request.y += _ts5_status.display_adapter[request.adapter].y1;
278  }
279 
280  // copy relevant settings
281  request.refreshrate = -1;
282  request.display_mode = TS5_WINDOWED;
283  request.vsync_mode = ts5_nextdisplay.vsync_mode;
284  }
285 
286 
287  // pass on display parameters to Allegro
288  al_set_new_display_adapter(request.adapter);
289  al_set_new_display_refresh_rate(request.refreshrate);
290 
291  al_set_new_display_option(ALLEGRO_VSYNC, (int)request.vsync_mode,
292  ALLEGRO_SUGGEST);
293 
294  if (request.display_mode == TS5_WINDOWED) {
295  al_set_new_window_position(request.x, request.y);
296  }
297 
298  if (request.display_mode == TS5_FULLSCREEN_WINDOW) {
299  al_set_new_window_position(INT_MAX, INT_MAX);
300  }
301 
302  al_set_new_display_flags(request.display_mode);
303 
304  // update counters
305  _ts5_status.num_displays++;
306  _ts5_status.active_display = _ts5_status.num_displays - 1;
307 
308  // try top open display
309  ts5_log(TS5_LOGLEVEL_1, "ts5_install_display: Opening display\n");
310 
311  TS5_DISPLAY **display;
312  display = al_realloc(_ts5_data.display,
313  _ts5_status.num_displays * sizeof(TS5_DISPLAY *));
314 
315  if (display == NULL) {
316  ts5_fatal("%s: %s\n", "ts5_install_display",
317  "failed to allocate memory for display pointer");
318  }
319 
320  _ts5_data.display = (TS5_DISPLAY **) display;
321 
322  _ts5_data.display[_ts5_status.active_display] =
323  al_create_display(request.w, request.h);
324 
325  if (!_ts5_data.display[_ts5_status.active_display]) {
326  ts5_fatal("ts5_install_display: could not open display\n");
327  }
328 
329  if (ts5_nextdisplay.display_mode == TS5_FULLSCREEN_WINDOW) {
330  request.w = _ts5_status.display_adapter[request.adapter].w;
331  request.h = _ts5_status.display_adapter[request.adapter].h;
332  }
333 
334  // make a display buffer
335  TS5_BITMAP **display_buffer;
336 
337  display_buffer = al_realloc(_ts5_data.display_buffer,
338  _ts5_status.num_displays * sizeof(TS5_BITMAP *));
339 
340  if (display_buffer == NULL) {
341  ts5_fatal("%s: %s\n", "ts5_install_display",
342  "failed to allocate memory for display buffer pointer");
343  }
344 
345  _ts5_data.display_buffer = (TS5_BITMAP **) display_buffer;
346 
347  _ts5_data.display_buffer[_ts5_status.active_display] =
348  al_create_bitmap(request.w, request.h);
349 
350  if (!_ts5_data.display_buffer[_ts5_status.active_display]) {
351  ts5_fatal("ts5_install_display: could not open display buffer\n");
352  }
353 
354 
355  // make a backup of the display buffer
356  TS5_BITMAP **display_backup;
357 
358  display_backup = al_realloc(_ts5_data.display_backup,
359  _ts5_status.num_displays * sizeof(TS5_BITMAP *));
360 
361  if (display_backup == NULL) {
362  ts5_fatal("%s: %s\n", "ts5_install_display",
363  "failed to allocate memory for display backup pointer");
364  }
365 
366  _ts5_data.display_backup = (TS5_BITMAP **) display_backup;
367 
368  _ts5_data.display_backup[_ts5_status.active_display] =
369  al_create_bitmap(request.w, request.h);
370 
371  if (!_ts5_data.display_backup[_ts5_status.active_display]) {
372  ts5_fatal("ts5_install_display: could not open display backup\n");
373  }
374 
375 
376  // copy the settings in the structure
377  TS5_DISPLAY_STATUS *display_status;
378  display_status = al_realloc(_ts5_status.display,
379  _ts5_status.num_displays * sizeof(TS5_DISPLAY_STATUS));
380 
381  if (display_status == NULL) {
382  ts5_fatal("%s: %s\n", "ts5_install_display",
383  "failed to allocate memory for display settings");
384  }
385 
386  _ts5_status.display = (TS5_DISPLAY_STATUS *) display_status;
387 
388  _ts5_status.display[_ts5_status.active_display].adapter =
389  request.adapter;
390 
391  if (request.display_mode==TS5_WINDOWED) {
392 
393  al_get_window_position(_ts5_data.display[_ts5_status.active_display],
394  &request.x, &request.y);
395 
396  if (request.x + request.w
397  > _ts5_status.display_adapter[ts5_nextdisplay.adapter].x2) {
398 
399  int oldw = request.w;
400 
401  request.w = _ts5_status.display_adapter
402  [ts5_nextdisplay.adapter].x2 - request.x;
403 
404  al_resize_display(_ts5_data.display[_ts5_status.active_display],
405  request.w, request.h);
406 
407  ts5_log(TS5_LOGLEVEL_1, "%s: %s %d (was %d)\n",
408  "ts5_install_display", "adjusting display width to",
409  request.w, oldw);
410  }
411 
412  if (request.y + request.h > _ts5_status.display_adapter
413  [ts5_nextdisplay.adapter].y2) {
414 
415  int oldh = request.h;
416 
417  request.h = _ts5_status.display_adapter
418  [ts5_nextdisplay.adapter].y2 - request.y;
419 
420  al_resize_display(_ts5_data.display[_ts5_status.active_display],
421  request.w, request.h);
422 
423  al_set_window_position(_ts5_data.display
424  [_ts5_status.active_display],
425  request.x, request.y + (request.h-oldh));
426 
427  ts5_log(TS5_LOGLEVEL_1, "%s: %s %d (was %d)\n",
428  "ts5_install_display", "adjusting display height to",
429  request.h, oldh);
430 
431  al_get_window_position(
432  _ts5_data.display[_ts5_status.active_display],
433  &request.x, &request.y);
434  }
435 
436  request.x -= _ts5_status.display_adapter[request.adapter].x1;
437  request.y -= _ts5_status.display_adapter[request.adapter].y1;
438 
439  if (_ts5_status.graphics.coordinate_system
440  == TS5_CARTESIAN_COORDINATES) {
441 
442  request.x =
443  request.x
444  - (_ts5_status.display_adapter[request.adapter].w
445  - request.w)/2.0;
446 
447  request.y =
448  (_ts5_status.display_adapter[request.adapter].h
449  - request.h)/2.0
450  - request.y;
451  }
452  }
453 
454  _ts5_status.display[_ts5_status.active_display].x = request.x;
455  _ts5_status.display[_ts5_status.active_display].y = request.y;
456  _ts5_status.display[_ts5_status.active_display].w = request.w;
457  _ts5_status.display[_ts5_status.active_display].h = request.h;
458 
459  _ts5_status.display[_ts5_status.active_display].refreshrate =
460  ts5_nextdisplay.refreshrate;
461 
462  _ts5_status.display[_ts5_status.active_display].display_mode =
463  request.display_mode;
464 
465  _ts5_status.display[_ts5_status.active_display].vsync_mode =
466  request.vsync_mode;
467 
468  // set the new display as the drawing target and clear the display
469  ts5_set_drawing_target(_ts5_data.display_backup
470  [_ts5_status.active_display]);
471  al_clear_to_color(_ts5_status.graphics.background_color);
472 
473  ts5_set_drawing_target(_ts5_data.display_buffer
474  [_ts5_status.active_display]);
475 
476 
477  // clear and flip
478  int i;
479  for(i=0; i<4; i++) {
480  al_flip_display();
481  }
482  _ts5_status.display[_ts5_status.active_display].last_sync = al_get_time();
485 
486  // set atexit and return
487  atexit(ts5_uninstall_displays);
488 
489  return _ts5_status.active_display;
490 }
491 
492 
493 ////////////////////////////////////////////////////////////////////////////////
494 /// Clear the current drawing target.
495 ///
496 /// The drawing target can either be a display or a bitmap (to clear a bitmap:
497 /// set it as drawing target and call ts5_clear_display()).
498 ///
499 /// The background color is controlled by ts5_set_background_color().
500 ////////////////////////////////////////////////////////////////////////////////
502 {
503  ts5_check_display("ts5_clear_display");
504  ts5_log(TS5_LOGLEVEL_5, "ts5_clear_display()\n");
505 
506  if (_ts5_data.target == NULL) {
507  ts5_fatal("ts5_clear_display: target is a NULL pointer\n");
508  }
509 
510  al_clear_to_color(_ts5_status.graphics.background_color);
511 }
512 
513 
514 ////////////////////////////////////////////////////////////////////////////////
515 /// Make what has been drawn visible on the screen.
516 ///
517 /// \return The time when the display flip occurs.
518 ///
519 /// All drawing operations (primitives, text, bitmaps, ...)
520 /// are performed on a back buffer.
521 /// Once you have finished drawing you should call this function
522 /// to make your drawings visible on the screen.
523 /// After a call to this function the back buffer is not cleared.
524 ////////////////////////////////////////////////////////////////////////////////
526 {
527  ts5_check_display("ts5_flip_display");
528  ts5_log(TS5_LOGLEVEL_5, "ts5_flip_display()\n");
529 
530 
531  // if we do not synchronize with _every_ vsync
532  // we need to call al_wait_for_vsync to get in sync again
533  #ifdef TS5_WINDOWS
534  if (al_get_time() - _ts5_status.display[_ts5_status.active_display].last_sync >
535  1.0 / _ts5_status.display[_ts5_status.active_display].refreshrate + 0.003) {
536  al_wait_for_vsync();
537  }
538  #endif
539 
540  // on mac we need another trick for this:
541  // blit the backup of the buffer
542  // then make a new backup of the buffer
543  #ifdef TS5_MACOSX
544  if (al_get_time() - _ts5_status.display[_ts5_status.active_display].last_sync >
545  1.0 / _ts5_status.display[_ts5_status.active_display].refreshrate + 0.003) {
546 
547  al_set_target_backbuffer(_ts5_data.display[_ts5_status.active_display]);
548  al_draw_bitmap(_ts5_data.display_backup[_ts5_status.active_display], 0.0, 0.0, 0);
549  al_flip_display();
550  }
551 
552  al_set_target_bitmap(_ts5_data.display_backup[_ts5_status.active_display]);
553  al_clear_to_color(_ts5_status.graphics.background_color);
554  al_draw_bitmap(_ts5_data.display_buffer[_ts5_status.active_display], 0.0, 0.0, 0);
555  #endif
556 
557 
558  al_set_target_backbuffer(_ts5_data.display[_ts5_status.active_display]);
559  al_draw_bitmap(_ts5_data.display_buffer[_ts5_status.active_display], 0.0, 0.0, 0);
560  al_flip_display();
561 
562  _ts5_status.display[_ts5_status.active_display].last_sync = al_get_time();
563 
564  al_clear_to_color(_ts5_status.graphics.background_color);
565 
566  al_set_target_bitmap(_ts5_data.display_buffer
567  [_ts5_status.active_display]);
568 
569  return _ts5_status.display[_ts5_status.active_display].last_sync;
570 }
571 
572 
573 ////////////////////////////////////////////////////////////////////////////////
574 //@}
575 ////////////////////////////////////////////////////////////////////////////////
576 
577 
578 ////////////////////////////////////////////////////////////////////////////////
579 /// @name Setting the display target
580 /// Tscope5 supports multiple displays
581 /// (each call to ts5_install_display() opens a new display).
582 /// - By default everything is drawn on the display that was opened last.
583 /// - With ts5_set_active_display() you can change the target display.
584 ///
585 /// You can also redirect drawing to memory bitmaps (see bitmaps.c)
586 /// using ts5_set_drawing_target().
587 //@{
588 ////////////////////////////////////////////////////////////////////////////////
589 
590 
591 ////////////////////////////////////////////////////////////////////////////////
592 /// Set the active display.
593 ///
594 /// \param display Index of the display.
595 ///
596 /// \return The index of the previous active display.
597 ///
598 /// The 'active' display is the display that will be used
599 /// for drawing operations.
600 ////////////////////////////////////////////////////////////////////////////////
601 int ts5_set_active_display(const int display)
602 {
603  ts5_check_display2("ts5_set_active_display", display);
604  ts5_log(TS5_LOGLEVEL_4, "ts5_set_active_display(%d)\n", display);
605 
606  int retval = _ts5_status.active_display + 1;
607  _ts5_status.active_display = display - 1;
608  _ts5_data.target = _ts5_data.display_buffer[_ts5_status.active_display];
609  al_set_target_bitmap(_ts5_data.target);
610 
611  _ts5_status.graphics.target_width =
612  al_get_bitmap_width(_ts5_data.target);
613 
614  _ts5_status.graphics.target_height =
615  al_get_bitmap_height(_ts5_data.target);
616 
617  return retval;
618 }
619 
620 
621 ////////////////////////////////////////////////////////////////////////////////
622 /// Get the active display.
623 ///
624 /// \return The index of the active display.
625 ///
626 /// The 'active' display is the display that will be used
627 /// for drawing operations.
628 ////////////////////////////////////////////////////////////////////////////////
630 {
631  ts5_check_display("ts5_get_active_display");
632  ts5_log(TS5_LOGLEVEL_4, "ts5_get_active_display()\n");
633 
634  return _ts5_status.active_display + 1;
635 }
636 
637 
638 ////////////////////////////////////////////////////////////////////////////////
639 //@}
640 ////////////////////////////////////////////////////////////////////////////////
641 
642 
643 ////////////////////////////////////////////////////////////////////////////////
644 /// @name Display adapter settings
645 /// A display adapter is a physical monitor that is attached to the computer.
646 /// Tscope5 supports multiple display adapters.
647 /// Functions are available to query the number and dimensions of
648 /// each display adapter.
649 //@{
650 ////////////////////////////////////////////////////////////////////////////////
651 
652 
653 ////////////////////////////////////////////////////////////////////////////////
654 /// Get the number of display adapters that are connected to the system.
655 ///
656 /// \return The number of display adapters that are connected to the system.
657 ////////////////////////////////////////////////////////////////////////////////
659 {
660  ts5_check_display("ts5_get_num_display_adapters");
661  ts5_log(TS5_LOGLEVEL_4, "ts5_get_num_display_adapters()\n");
662 
663  return _ts5_status.num_display_adapters;
664 }
665 
666 
667 ////////////////////////////////////////////////////////////////////////////////
668 /// Get the size of the monitor attached to a display adapter.
669 ///
670 /// \param adapter Index of the display adapter.
671 /// \param w Variable that will store the width.
672 /// \param h Variable that will store the height.
673 ///
674 /// w and h are the maximum size of a window that can be opened on that adapter.
675 ///
676 /// Pass 0 to get the size of the display adapter for the next display.
677 ///
678 /// You can pass NULL for values you are not interested in.
679 ////////////////////////////////////////////////////////////////////////////////
680 void ts5_get_display_adapter_size(const int adapter, double *w, double *h)
681 {
682  ts5_check_display("ts5_get_display_adapter_size");
683  ts5_log(TS5_LOGLEVEL_4, "ts5_get_display_adapter_size(%d,%f,%f)\n",
684  adapter, w, h);
685 
686  double ww, hh;
687 
688  if (adapter < 0) {
689  ts5_fatal("ts5_get_display_adapter_size: adapter index not valid\n");
690  }
691  else if (adapter == 0) {
692  ww = _ts5_status.display_adapter[ts5_nextdisplay.adapter].w;
693  hh = _ts5_status.display_adapter[ts5_nextdisplay.adapter].h;
694  }
695  else if (adapter <= _ts5_status.num_display_adapters) {
696  ww = _ts5_status.display_adapter[adapter-1].w;
697  hh = _ts5_status.display_adapter[adapter-1].h;
698  }
699  else {
700  ts5_fatal("ts5_get_display_adapter_size: adapter index not valid\n");
701  }
702 
703  if (w) {
704  *w = ww;
705  }
706 
707  if (h) {
708  *h = hh;
709  }
710 }
711 
712 
713 ////////////////////////////////////////////////////////////////////////////////
714 /// Get the width of the monitor attached to a display adapter.
715 ///
716 /// \param adapter Index of the display adapter.
717 ///
718 /// \return the width of the display adapter.
719 ///
720 /// Pass 0 to get the width of the display adapter for the next display.
721 ////////////////////////////////////////////////////////////////////////////////
722 double ts5_get_display_adapter_width(const int adapter)
723 {
724  ts5_check_display("ts5_get_display_adapter_width");
725  ts5_log(TS5_LOGLEVEL_4, "ts5_get_display_adapter_width(%d)\n", adapter);
726 
727  double w;
728  ts5_get_display_adapter_size(adapter, &w, NULL);
729 
730  return w;
731 }
732 
733 
734 ////////////////////////////////////////////////////////////////////////////////
735 /// Get the heigth of the monitor attached to a display adapter.
736 ///
737 /// \param adapter Index of the display adapter.
738 ///
739 /// \return the height of the display adapter.
740 ///
741 /// Pass 0 to get the height of the display adapter for the next display.
742 ////////////////////////////////////////////////////////////////////////////////
743 double ts5_get_display_adapter_height(const int adapter)
744 {
745  ts5_check_display("ts5_get_display_adapter_height");
746  ts5_log(TS5_LOGLEVEL_4, "ts5_get_display_adapter_height(%d)\n", adapter);
747 
748  double h;
749  ts5_get_display_adapter_size(adapter, NULL, &h);
750 
751  return h;
752 }
753 
754 
755 ////////////////////////////////////////////////////////////////////////////////
756 //@}
757 ////////////////////////////////////////////////////////////////////////////////
758 
759 
760 ////////////////////////////////////////////////////////////////////////////////
761 /// @name Display settings
762 /// Before opening a display various settings can be requested
763 /// using the functions below.
764 /// Once a display is opened the settings remain until the end of the program.
765 //@{
766 ////////////////////////////////////////////////////////////////////////////////
767 
768 
769 ////////////////////////////////////////////////////////////////////////////////
770 /// Set the display adapter for the next display that will be opened.
771 ///
772 /// \param adapter Index of the active display adapter.
773 ///
774 /// \return The index of the previous active display adapter.
775 ///
776 /// A display adapter corresponds to a physical display that is
777 /// attached to the computer.
778 /// The first adapter has index 1, etc.
779 ///
780 /// The display is attached to adapter 1 by default.
781 ////////////////////////////////////////////////////////////////////////////////
782 int ts5_set_display_adapter(const int adapter)
783 {
784  ts5_check_display("ts5_set_display_adapter");
785  ts5_log(TS5_LOGLEVEL_4, "ts5_set_display_adapter(%d)\n", adapter);
786 
787  int retval = ts5_nextdisplay.adapter + 1;
788 
789  if (adapter > 0 && adapter <= _ts5_status.num_display_adapters) {
790  ts5_nextdisplay.adapter = adapter - 1;
791  ts5_log(TS5_LOGLEVEL_4, "%s: %s %d (was %d)\n",
792  "ts5_set_display_adapter",
793  "set display adapter for next display to",
794  retval-1, ts5_nextdisplay.adapter+1);
795  }
796  else {
797  ts5_fatal ("ts5_set_display_adapter: adapter index not valid\n");
798  }
799 
800  return retval;
801 }
802 
803 
804 ////////////////////////////////////////////////////////////////////////////////
805 /// Get the index of the display adapter of a display.
806 ///
807 /// \param display Index of the display.
808 ///
809 /// \return The index of the adapter that the display is attached to.
810 ///
811 /// Pass 0 to get the index of the display adapter for the next display.
812 ////////////////////////////////////////////////////////////////////////////////
813 int ts5_get_display_adapter(const int display)
814 {
815  ts5_check_display2("ts5_get_display_adapter", display);
816  ts5_log(TS5_LOGLEVEL_4, "ts5_get_display_adapter(%d)\n", display);
817 
818  int retval;
819 
820  if (display == 0) {
821  retval = ts5_nextdisplay.adapter + 1;
822  }
823  else {
824  retval = _ts5_status.display[display-1].adapter + 1;
825  }
826 
827  return retval;
828 }
829 
830 
831 ////////////////////////////////////////////////////////////////////////////////
832 /// Set the size of the next display.
833 ///
834 /// \param w Width of the next display in pixels.
835 /// \param h Height of the next display in pixels.
836 ///
837 /// The default width and height is 320 x 240. This is also the minimum.
838 ////////////////////////////////////////////////////////////////////////////////
839 void ts5_set_display_size(double w, double h)
840 {
841  ts5_check_display("ts5_set_display_size");
842  ts5_log(TS5_LOGLEVEL_4, "ts5_set_display_size(%f,%f)\n", w, h);
843 
844  int oldw = ts5_nextdisplay.w;
845  int oldh = ts5_nextdisplay.h;
846 
847  if (_ts5_status.graphics.coordinate_scale
848  == TS5_RELATIVE_COORDINATES) {
849  w *= _ts5_status.display_adapter[ts5_nextdisplay.adapter].w;
850  h *= _ts5_status.display_adapter[ts5_nextdisplay.adapter].h;
851  }
852 
853  ts5_nextdisplay.w = w;
854  ts5_nextdisplay.h = h;
855 
856  ts5_log(TS5_LOGLEVEL_4, "%s: %s %d x %d (was %d x %d)\n",
857  "ts5_set_display_size",
858  "set display size for next display to",
859  ts5_nextdisplay.w, ts5_nextdisplay.h, oldw, oldh);
860 }
861 
862 
863 ////////////////////////////////////////////////////////////////////////////////
864 /// Get the size of a display.
865 ///
866 /// \param display Index of the display.
867 /// \param w Variable that will store the width.
868 /// \param h Variable that will store the height.
869 ///
870 /// Set display to 0 to get the width of the next display.
871 ///
872 /// You can pass NULL for values you are not interested in.
873 ////////////////////////////////////////////////////////////////////////////////
874 void ts5_get_display_size(const int display, double *w, double *h)
875 {
876  ts5_check_display2("ts5_get_display_size", display);
877  ts5_log(TS5_LOGLEVEL_4, "ts5_get_display_size(%d,%p,%p)\n", display, w, h);
878 
879  double ww, hh;
880 
881  if (display == 0) {
882  ww = ts5_nextdisplay.w;
883  hh = ts5_nextdisplay.h;
884  }
885  else {
886  ww = _ts5_status.display[display-1].w;
887  hh = _ts5_status.display[display-1].h;
888  }
889 
890  if (w) {
891  *w = ww;
892  }
893 
894  if (h) {
895  *h = hh;
896  }
897 }
898 
899 
900 ////////////////////////////////////////////////////////////////////////////////
901 /// Get the width of a display.
902 ///
903 /// \param display Index of the display.
904 ///
905 /// \return the width of the display.
906 ///
907 /// Set display to 0 to get the width of the next display.
908 ////////////////////////////////////////////////////////////////////////////////
909 double ts5_get_display_width(const int display)
910 {
911  ts5_check_display2("ts5_get_display_width", display);
912  ts5_log(TS5_LOGLEVEL_4, "ts5_get_display_width(%d)\n", display);
913 
914  double w;
915  ts5_get_display_size(display, &w, NULL);
916 
917  return w;
918 }
919 
920 
921 ////////////////////////////////////////////////////////////////////////////////
922 /// Get the height of a display.
923 ///
924 /// \param display Index of the display.
925 ///
926 /// \return the height of the display.
927 ///
928 /// Set display to 0 to get the height of the next display.
929 ////////////////////////////////////////////////////////////////////////////////
930 double ts5_get_display_height(const int display)
931 {
932  ts5_check_display2("ts5_get_display_height", display);
933  ts5_log(TS5_LOGLEVEL_4, "ts5_get_display_height(%d)\n", display);
934 
935  double h;
936  ts5_get_display_size(display, NULL, &h);
937 
938  return h;
939 }
940 
941 
942 ////////////////////////////////////////////////////////////////////////////////
943 /// Set the position of the next display.
944 ///
945 /// \param x Horizontal position of the display on the desktop.
946 /// \param y Vertical position of the display on the desktop.
947 ///
948 /// Only meaningful for non-fullscreen displays.
949 ///
950 /// CARTESIAN coordinates: Center of the display is the origin,
951 /// default position is the center of the display.
952 ///
953 /// COMPUTER coordinates: The upper left corner of the display is the origin,
954 /// default position is top left corner of the display.
955 ////////////////////////////////////////////////////////////////////////////////
956 void ts5_set_display_position(double x, double y)
957 {
958  ts5_check_display("ts5_set_display_position");
959  ts5_log(TS5_LOGLEVEL_4, "ts5_set_display_position(%f,%f)\n", x, y);
960 
961  int oldx = ts5_nextdisplay.x;
962  int oldy = ts5_nextdisplay.y;
963 
964  if (_ts5_status.graphics.coordinate_scale
965  == TS5_RELATIVE_COORDINATES) {
966 
967  if (_ts5_status.graphics.coordinate_system
968  == TS5_CARTESIAN_COORDINATES) {
969 
970  x *= _ts5_status.display_adapter[ts5_nextdisplay.adapter].w
971  / 2.0;
972 
973  y *= _ts5_status.display_adapter[ts5_nextdisplay.adapter].h
974  / 2.0;
975  }
976  else {
977  x *= _ts5_status.display_adapter[ts5_nextdisplay.adapter].w;
978  y *= _ts5_status.display_adapter[ts5_nextdisplay.adapter].h;
979  }
980  }
981 
982  if (_ts5_status.graphics.coordinate_system
983  == TS5_CARTESIAN_COORDINATES) {
984 
985  x += _ts5_status.display_adapter[ts5_nextdisplay.adapter].w/2.0;
986  x -= ts5_nextdisplay.w/2.0;
987  y = -y;
988  y += _ts5_status.display_adapter[ts5_nextdisplay.adapter].h/2.0;
989  y -= ts5_nextdisplay.h/2.0;
990  }
991 
992  x += _ts5_status.display_adapter[ts5_nextdisplay.adapter].x1;
993  y += _ts5_status.display_adapter[ts5_nextdisplay.adapter].y1;
994 
995  ts5_nextdisplay.x = x;
996  ts5_nextdisplay.y = y;
997 
998  ts5_log(TS5_LOGLEVEL_4, "%s: %s (%d,%d) (was (%d,%d))\n",
999  "ts5_set_display_position",
1000  "set display position for next display to",
1002  oldx, oldy);
1003 }
1004 
1005 
1006 ////////////////////////////////////////////////////////////////////////////////
1007 /// Get the position of a display.
1008 ///
1009 /// \param display Index of the display.
1010 /// \param x Variable that will store the horizontal position.
1011 /// \param y Variable that will store the vertical position.
1012 ///
1013 /// Only meaningful for non-fullscreen displays.
1014 ///
1015 /// Set display to 0 to get the x position of the next display.
1016 ///
1017 /// You can pass NULL for values you are not interested in.
1018 ////////////////////////////////////////////////////////////////////////////////
1019 void ts5_get_display_position(const int display, double *x, double *y)
1020 {
1021  ts5_check_display2("ts5_get_display_position", display);
1022  ts5_log(TS5_LOGLEVEL_4, "ts5_get_display_position(%d,%p,%p)\n",
1023  display, x, y);
1024 
1025  double xx, yy;
1026  double dw, dh, aw, ah;
1027 
1028  // get the values we need
1029  if (display != 0) {
1030 
1031  int adapter = ts5_get_display_adapter(display);
1032  al_get_window_position(_ts5_data.display[display-1],
1033  &_ts5_status.display[display-1].x,
1034  &_ts5_status.display[display-1].y);
1035 
1036  xx = _ts5_status.display[display-1].x;
1037  yy = _ts5_status.display[display-1].y;
1038 
1039  xx -= _ts5_status.display_adapter[adapter-1].x1;
1040  yy -= _ts5_status.display_adapter[adapter-1].y1;
1041 
1042  dw = _ts5_status.display[display-1].w;
1043  dh = _ts5_status.display[display-1].h;
1044 
1045  aw = _ts5_status.display_adapter[adapter-1].w;
1046  ah = _ts5_status.display_adapter[adapter-1].h;
1047  }
1048  else {
1049 
1050  xx = ts5_nextdisplay.x;
1051  yy = ts5_nextdisplay.y;
1052 
1053  dw = ts5_nextdisplay.w;
1054  dh = ts5_nextdisplay.h;
1055 
1056  aw = _ts5_status.display_adapter[ts5_nextdisplay.adapter].w;
1057  ah = _ts5_status.display_adapter[ts5_nextdisplay.adapter].h;
1058  }
1059 
1060  // if the settings are not default, compute xx and yy
1061  if (xx!=-1 && yy!=-1) {
1062 
1063 
1064  // convert to cartesian if necessary
1065  if (_ts5_status.graphics.coordinate_system
1066  == TS5_CARTESIAN_COORDINATES) {
1067  xx = xx + dw/2.0 - aw/2.0;
1068  yy = ah/2.0 - yy - dh/2.0;
1069  }
1070 
1071  // convert to relative if necessary
1072  if (_ts5_status.graphics.coordinate_scale
1073  == TS5_RELATIVE_COORDINATES) {
1074 
1075  if (_ts5_status.graphics.coordinate_system
1076  == TS5_CARTESIAN_COORDINATES) {
1077  xx /= aw/2.0;
1078  yy /= ah/2.0;
1079  }
1080  else {
1081  xx /= aw;
1082  yy /= ah;
1083  }
1084  }
1085  }
1086 
1087  if (x) {
1088  *x = xx;
1089  }
1090 
1091  if (y) {
1092  *y = yy;
1093  }
1094 
1095 
1096 }
1097 
1098 
1099 ////////////////////////////////////////////////////////////////////////////////
1100 /// Get the horizontal position of a display.
1101 ///
1102 /// \param display Index of the display.
1103 ///
1104 /// \return
1105 /// The horizontal position of the display.
1106 ////////////////////////////////////////////////////////////////////////////////
1107 double ts5_get_display_x(const int display)
1108 {
1109  ts5_check_display2("ts5_get_display_x", display);
1110  ts5_log(TS5_LOGLEVEL_4, "ts5_get_display_x(%d)\n", display);
1111 
1112  double x;
1113  ts5_get_display_position(display, &x, NULL);
1114 
1115  return x;
1116 }
1117 
1118 
1119 ////////////////////////////////////////////////////////////////////////////////
1120 /// Get the vertical position of a display.
1121 ///
1122 /// \param display Index of the display.
1123 ///
1124 /// \return
1125 /// The vertical position of the display.
1126 ////////////////////////////////////////////////////////////////////////////////
1127 double ts5_get_display_y(const int display)
1128 {
1129  ts5_check_display2("ts5_get_display_y", display);
1130  ts5_log(TS5_LOGLEVEL_4, "ts5_get_display_y(%d)\n", display);
1131 
1132  double y;
1133  ts5_get_display_position(display, NULL, &y);
1134 
1135  return y;
1136 }
1137 
1138 
1139 
1140 
1141 ////////////////////////////////////////////////////////////////////////////////
1142 /// Set the requested refreshrate for the next display.
1143 ///
1144 /// \param rate Refreshrate in cycles per second.
1145 ///
1146 /// \return The previous refresh rate.
1147 ///
1148 /// The refreshrate can only be changed for real fullscreen displays.
1149 ///
1150 /// Even then this is only a request.
1151 ///
1152 /// The default value 0 (let the system choose).
1153 ////////////////////////////////////////////////////////////////////////////////
1154 int ts5_set_refreshrate(const int rate)
1155 {
1156  ts5_check_display("ts5_set_refreshrate");
1157  ts5_log(TS5_LOGLEVEL_4, "ts5_set_refreshrate(%d)\n", rate);
1158 
1159  int retval = ts5_nextdisplay.refreshrate;
1160 
1161  ts5_nextdisplay.refreshrate = rate;
1162 
1163  ts5_log(TS5_LOGLEVEL_4, "%s: %s %d (was %d)\n", "ts5_set_refreshrate",
1164  "set refreshrate for next display to",
1165  ts5_nextdisplay.refreshrate, retval);
1166 
1167  return retval;
1168 }
1169 
1170 
1171 ////////////////////////////////////////////////////////////////////////////////
1172 /// Get the refreshrate of a display.
1173 ///
1174 /// \param display Index of the display.
1175 ///
1176 /// \return The refresh rate of the display.
1177 ///
1178 /// Set display to 0 to get the refreshrate of the next display.
1179 ////////////////////////////////////////////////////////////////////////////////
1180 int ts5_get_refreshrate(const int display)
1181 {
1182  ts5_check_display2("ts5_get_refreshrate", display);
1183  ts5_log(TS5_LOGLEVEL_4, "ts5_get_refreshrate(%d)\n", display);
1184 
1185  int retval;
1186 
1187  if (display == 0) {
1188  retval = ts5_nextdisplay.refreshrate;
1189  }
1190  else {
1191  retval = _ts5_status.display[display-1].refreshrate;
1192  }
1193 
1194  return retval;
1195 }
1196 
1197 
1198 ////////////////////////////////////////////////////////////////////////////////
1199 /// Set the display mode for the next display.
1200 ///
1201 /// \param mode Window mode.
1202 /// Can be TS5_WINDOWED, TS5_FULLSCREEN or TS5_FULLSCREEN_WINDOW.
1203 ///
1204 /// \return The previous display mode.
1205 ///
1206 /// In TS5_WINDOWED mode the window can have any dimension that
1207 /// will fit on the physical display
1208 /// and the position of the window on the display can be adjusted.
1209 /// Multiple TS5_WINDOWED displays can be combined on one physical display.
1210 /// The refreshrate is always the refreshrate of the physical display.
1211 ///
1212 /// In TS5_FULLSCREEN_WINDOW mode the display always has the dimension
1213 /// of the desktop.
1214 /// The refreshrate is always the refreshrate of the physical display.
1215 /// Only one TS5_FULLSCREEN_WINDOW display can be used
1216 /// per physical display.
1217 ///
1218 /// TS5_FULLSCREEN modes are the most flexible:
1219 /// any combination of display dimension and refreshrate
1220 /// that is supported by the monitor can be set.
1221 /// Does not seem to work on Mac OS X.
1222 ///
1223 /// The default window mode is TS5_WINDOWED.
1224 ////////////////////////////////////////////////////////////////////////////////
1225 int ts5_set_display_mode(const int mode)
1226 {
1227  ts5_check_display("ts5_set_display_mode");
1228  ts5_log(TS5_LOGLEVEL_4, "ts5_set_display_mode(%d)\n", mode);
1229 
1230  int retval = ts5_nextdisplay.display_mode;
1231 
1232  if (mode != TS5_WINDOWED
1233  && mode != TS5_FULLSCREEN
1234  && mode != TS5_FULLSCREEN_WINDOW) {
1235  ts5_fatal ("%s: %s (%d)\n", "ts5_set_display_mode",
1236  "requested display mode not available", mode);
1237  }
1238 
1239  ts5_nextdisplay.display_mode = mode;
1240 
1241  ts5_log(TS5_LOGLEVEL_4, "%s: %s %d (was %d)\n", "ts5_set_display_mode",
1242  "set display mode for next display to",
1243  ts5_nextdisplay.display_mode, retval);
1244 
1245  return retval;
1246 }
1247 
1248 
1249 ////////////////////////////////////////////////////////////////////////////////
1250 /// Get the display mode of a display.
1251 ///
1252 /// \param display Index of the display.
1253 ///
1254 /// \return The window mode of the display.
1255 ///
1256 /// Set display to 0 to get the display mode of the next display.
1257 ////////////////////////////////////////////////////////////////////////////////
1258 int ts5_get_display_mode(const int display)
1259 {
1260  ts5_check_display2("ts5_get_display_mode", display);
1261  ts5_log(TS5_LOGLEVEL_4, "ts5_get_display_mode(%d)\n", display);
1262 
1263  int retval;
1264 
1265  if (display == 0) {
1266  retval = ts5_nextdisplay.display_mode;
1267  }
1268  else {
1269  retval = _ts5_status.display[display-1].display_mode;
1270  }
1271 
1272  return retval;
1273 }
1274 
1275 
1276 ////////////////////////////////////////////////////////////////////////////////
1277 /// Set the vsync mode for the next display.
1278 ///
1279 /// \param mode Vsync mode.
1280 /// Can be TS5_VSYNC_WHATEVER, TS5_VSYNC_ON or TS5_VSYNC_OFF.
1281 ///
1282 /// \return The previous vsync mode.
1283 ///
1284 /// The default vsync mode is TS5_VSYNC_ON.
1285 ////////////////////////////////////////////////////////////////////////////////
1286 int ts5_set_vsync_mode(const int mode)
1287 {
1288  ts5_check_display("ts5_set_vsync_mode");
1289  ts5_log(TS5_LOGLEVEL_4, "ts5_set_vsync_mode(%d)\n", mode);
1290 
1291  int retval = ts5_nextdisplay.vsync_mode;
1292 
1293  if (mode < TS5_VSYNC_WHATEVER || mode > TS5_VSYNC_OFF) {
1294  ts5_fatal("ts5_set_vsync_mode: mode should be 0, 1 or 2 (is %d)\n",
1295  mode);
1296  }
1297 
1298  ts5_nextdisplay.vsync_mode = mode;
1299 
1300  ts5_log(TS5_LOGLEVEL_4, "%s: %s %d (was %d)\n", "ts5_set_vsync_mode",
1301  "set vsync mode for next display to",
1302  ts5_nextdisplay.vsync_mode, retval);
1303 
1304  return retval;
1305 }
1306 
1307 
1308 ////////////////////////////////////////////////////////////////////////////////
1309 /// Get the vsync mode of a display.
1310 ///
1311 /// \param display Index of the display.
1312 ///
1313 /// \return The vsync mode of the display.
1314 ///
1315 /// Set display to 0 to get the requested vsync mode for the next display.
1316 ////////////////////////////////////////////////////////////////////////////////
1317 int ts5_get_vsync_mode(const int display)
1318 {
1319  ts5_check_display2("ts5_get_vsync_mode", display);
1320  ts5_log(TS5_LOGLEVEL_4, "ts5_get_vsync_mode(%d)\n", display);
1321 
1322  int retval;
1323 
1324  if (display == 0) {
1325  retval = ts5_nextdisplay.vsync_mode;
1326  }
1327  else {
1328  retval = _ts5_status.display[display-1].vsync_mode;
1329  }
1330 
1331  return retval;
1332 }
1333 
1334 
1335 ////////////////////////////////////////////////////////////////////////////////
1336 //@}
1337 ////////////////////////////////////////////////////////////////////////////////
double ts5_get_display_adapter_width(const int adapter)
Get the width of the monitor attached to a display adapter.
Definition: display.c:722
int ts5_get_vsync_mode(const int display)
Get the vsync mode of a display.
Definition: display.c:1317
void ts5_check_display(char *calling_function)
Do some checks at the start of each display function.
int ts5_set_display_mode(const int mode)
Set the display mode for the next display.
Definition: display.c:1225
TS5_DISPLAY_STATUS ts5_nextdisplay
Settings for the next display that will be opened.
void ts5_check_display2(char *calling_function, const int display)
Do some checks at the start of each display function.
int ts5_get_num_display_adapters()
Get the number of display adapters that are connected to the system.
Definition: display.c:658
double ts5_flip_display()
Make what has been drawn visible on the screen.
Definition: display.c:525
int ts5_set_active_display(const int display)
Set the active display.
Definition: display.c:601
int ts5_set_vsync_mode(const int mode)
Set the vsync mode for the next display.
Definition: display.c:1286
void ts5_get_display_adapter_size(const int adapter, double *w, double *h)
Get the size of the monitor attached to a display adapter.
Definition: display.c:680
TS5_BITMAP * ts5_set_drawing_target(TS5_BITMAP *target)
Set the active drawing target.
Definition: bitmaps.c:243
void ts5_get_display_position(const int display, double *x, double *y)
Get the position of a display.
Definition: display.c:1019
int ts5_get_display_mode(const int display)
Get the display mode of a display.
Definition: display.c:1258
int ts5_install_display()
Open a new display.
Definition: display.c:83
void ts5_uninstall_displays()
Close all open displays.
double ts5_get_display_x(const int display)
Get the horizontal position of a display.
Definition: display.c:1107
void ts5_set_display_size(double w, double h)
Set the size of the next display.
Definition: display.c:839
int ts5_get_active_display()
Get the active display.
Definition: display.c:629
double ts5_get_display_adapter_height(const int adapter)
Get the heigth of the monitor attached to a display adapter.
Definition: display.c:743
void ts5_log(const unsigned int level, const char *format,...)
Send info to a logging window.
Definition: system.c:45
int ts5_get_refreshrate(const int display)
Get the refreshrate of a display.
Definition: display.c:1180
void ts5_clear_display()
Clear the current drawing target.
Definition: display.c:501
double ts5_get_display_width(const int display)
Get the width of a display.
Definition: display.c:909
void ts5_set_display_position(double x, double y)
Set the position of the next display.
Definition: display.c:956
int ts5_set_refreshrate(const int rate)
Set the requested refreshrate for the next display.
Definition: display.c:1154
double ts5_get_display_height(const int display)
Get the height of a display.
Definition: display.c:930
void ts5_fatal(const char *format,...)
Exit safely with an error message.
Definition: system.c:529
void ts5_get_display_size(const int display, double *w, double *h)
Get the size of a display.
Definition: display.c:874
double ts5_get_display_y(const int display)
Get the vertical position of a display.
Definition: display.c:1127
int ts5_set_display_adapter(const int adapter)
Set the display adapter for the next display that will be opened.
Definition: display.c:782
int ts5_get_display_adapter(const int display)
Get the index of the display adapter of a display.
Definition: display.c:813