35 |
|
* - Events processing is bound to the general emulation thread as SDL requires |
36 |
|
* to PumpEvents() within the same thread as the one that called SetVideoMode(). |
37 |
|
* Besides, there can't seem to be a way to call SetVideoMode() from a child thread. |
38 |
+ |
* - Refresh performance is still slow. Use SDL_CreateRGBSurface()? |
39 |
+ |
* - Backport hw cursor acceleration to Basilisk II? |
40 |
+ |
* - Move generic Native QuickDraw acceleration routines to gfxaccel.cpp |
41 |
|
*/ |
42 |
|
|
43 |
|
#include "sysdeps.h" |
99 |
|
static SDL_Thread *redraw_thread = NULL; // Redraw thread |
100 |
|
|
101 |
|
#ifdef ENABLE_VOSF |
102 |
< |
static bool use_vosf = true; // Flag: VOSF enabled |
102 |
> |
static bool use_vosf = false; // Flag: VOSF enabled |
103 |
|
#else |
104 |
|
static const bool use_vosf = false; // VOSF not possible |
105 |
|
#endif |
117 |
|
|
118 |
|
// SDL variables |
119 |
|
static int screen_depth; // Depth of current screen |
120 |
+ |
static SDL_Cursor *sdl_cursor; // Copy of Mac cursor |
121 |
+ |
static volatile bool cursor_changed = false; // Flag: cursor changed, redraw_func must update the cursor |
122 |
|
static SDL_Color sdl_palette[256]; // Color palette to be used as CLUT and gamma table |
123 |
|
static bool sdl_palette_changed = false; // Flag: Palette changed, redraw thread must set new colors |
124 |
|
static const int sdl_eventmask = SDL_MOUSEBUTTONDOWNMASK | SDL_MOUSEBUTTONUPMASK | SDL_MOUSEMOTIONMASK | SDL_KEYUPMASK | SDL_KEYDOWNMASK | SDL_VIDEOEXPOSEMASK | SDL_QUITMASK; |
260 |
|
{ |
261 |
|
ErrorAlert(GetString(error)); |
262 |
|
} |
263 |
+ |
|
264 |
+ |
// Display warning alert |
265 |
+ |
static void WarningAlert(int warning) |
266 |
+ |
{ |
267 |
+ |
WarningAlert(GetString(warning)); |
268 |
+ |
} |
269 |
|
#endif |
270 |
|
|
271 |
|
|
630 |
|
the_buffer = (uint8 *)vm_acquire(the_buffer_size); |
631 |
|
the_buffer_copy = (uint8 *)malloc(the_buffer_size); |
632 |
|
D(bug("the_buffer = %p, the_buffer_copy = %p, the_host_buffer = %p\n", the_buffer, the_buffer_copy, the_host_buffer)); |
633 |
+ |
|
634 |
+ |
// Check whether we can initialize the VOSF subsystem and it's profitable |
635 |
+ |
if (!video_vosf_init(m)) { |
636 |
+ |
WarningAlert(STR_VOSF_INIT_ERR); |
637 |
+ |
use_vosf = false; |
638 |
+ |
} |
639 |
+ |
else if (!video_vosf_profitable()) { |
640 |
+ |
video_vosf_exit(); |
641 |
+ |
printf("VOSF acceleration is not profitable on this platform, disabling it\n"); |
642 |
+ |
use_vosf = false; |
643 |
+ |
} |
644 |
+ |
if (!use_vosf) { |
645 |
+ |
free(the_buffer_copy); |
646 |
+ |
vm_release(the_buffer, the_buffer_size); |
647 |
+ |
the_host_buffer = NULL; |
648 |
+ |
} |
649 |
+ |
#endif |
650 |
+ |
if (!use_vosf) { |
651 |
+ |
// Allocate memory for frame buffer |
652 |
+ |
the_buffer_size = (aligned_height + 2) * s->pitch; |
653 |
+ |
the_buffer_copy = (uint8 *)calloc(1, the_buffer_size); |
654 |
+ |
the_buffer = (uint8 *)calloc(1, the_buffer_size); |
655 |
+ |
D(bug("the_buffer = %p, the_buffer_copy = %p\n", the_buffer, the_buffer_copy)); |
656 |
+ |
} |
657 |
+ |
|
658 |
+ |
#ifdef SHEEPSHAVER |
659 |
+ |
// Create cursor |
660 |
+ |
if ((sdl_cursor = SDL_CreateCursor(MacCursor + 4, MacCursor + 36, 16, 16, 0, 0)) != NULL) { |
661 |
+ |
SDL_SetCursor(sdl_cursor); |
662 |
+ |
cursor_changed = false; |
663 |
+ |
} |
664 |
|
#else |
665 |
< |
// Allocate memory for frame buffer |
666 |
< |
the_buffer_size = (aligned_height + 2) * s->pitch; |
625 |
< |
the_buffer_copy = (uint8 *)calloc(1, the_buffer_size); |
626 |
< |
the_buffer = (uint8 *)calloc(1, the_buffer_size); |
627 |
< |
D(bug("the_buffer = %p, the_buffer_copy = %p\n", the_buffer, the_buffer_copy)); |
665 |
> |
// Hide cursor |
666 |
> |
SDL_ShowCursor(0); |
667 |
|
#endif |
668 |
|
|
669 |
|
// Set window name/class |
670 |
|
set_window_name(STR_WINDOW_TITLE); |
671 |
|
|
633 |
– |
// Hide cursor |
634 |
– |
SDL_ShowCursor(0); |
635 |
– |
|
672 |
|
// Init blitting routines |
673 |
|
SDL_PixelFormat *f = s->format; |
674 |
|
VisualFormat visualFormat; |
787 |
|
|
788 |
|
if (video_driver_found) { |
789 |
|
// Skip aliases |
790 |
< |
static const char alias_str[] = "alias"; |
791 |
< |
if (strncmp(line, alias_str, sizeof(alias_str) - 1) == 0) |
790 |
> |
static const char sdl_str[] = "sdl"; |
791 |
> |
if (strncmp(line, sdl_str, sizeof(sdl_str) - 1) == 0) |
792 |
|
continue; |
793 |
|
|
794 |
|
// Read keycode |
799 |
|
break; |
800 |
|
} else { |
801 |
|
// Search for SDL video driver string |
802 |
< |
static const char alias_sdl_str[] = "alias SDL"; |
803 |
< |
if (strncmp(line, alias_sdl_str, sizeof(alias_sdl_str) - 1) == 0) { |
804 |
< |
char *p = line + sizeof(alias_sdl_str); |
802 |
> |
static const char sdl_str[] = "sdl"; |
803 |
> |
if (strncmp(line, sdl_str, sizeof(sdl_str) - 1) == 0) { |
804 |
> |
char *p = line + sizeof(sdl_str); |
805 |
|
if (strstr(video_driver, p) == video_driver) |
806 |
|
video_driver_found = true; |
807 |
|
} |
846 |
|
return false; |
847 |
|
} |
848 |
|
|
813 |
– |
#ifdef ENABLE_VOSF |
814 |
– |
if (use_vosf) { |
815 |
– |
// Initialize the VOSF system |
816 |
– |
if (!video_vosf_init(*this)) { |
817 |
– |
ErrorAlert(STR_VOSF_INIT_ERR); |
818 |
– |
return false; |
819 |
– |
} |
820 |
– |
} |
821 |
– |
#endif |
822 |
– |
|
849 |
|
// Initialize VideoRefresh function |
850 |
|
VideoRefreshInit(); |
851 |
|
|
1172 |
|
} |
1173 |
|
|
1174 |
|
#ifdef ENABLE_VOSF |
1175 |
< |
// We have to redraw everything because the interpretation of pixel values changed |
1176 |
< |
LOCK_VOSF; |
1177 |
< |
PFLAG_SET_ALL; |
1178 |
< |
UNLOCK_VOSF; |
1179 |
< |
memset(the_buffer_copy, 0, VIDEO_MODE_ROW_BYTES * VIDEO_MODE_Y); |
1175 |
> |
if (use_vosf) { |
1176 |
> |
// We have to redraw everything because the interpretation of pixel values changed |
1177 |
> |
LOCK_VOSF; |
1178 |
> |
PFLAG_SET_ALL; |
1179 |
> |
UNLOCK_VOSF; |
1180 |
> |
memset(the_buffer_copy, 0, VIDEO_MODE_ROW_BYTES * VIDEO_MODE_Y); |
1181 |
> |
} |
1182 |
|
#endif |
1183 |
|
} |
1184 |
|
|
1249 |
|
#ifdef SHEEPSHAVER |
1250 |
|
bool video_can_change_cursor(void) |
1251 |
|
{ |
1252 |
< |
// return hw_mac_cursor_accl && (display_type != DISPLAY_SCREEN); |
1225 |
< |
return false; |
1252 |
> |
return (display_type == DISPLAY_WINDOW); |
1253 |
|
} |
1254 |
|
#endif |
1255 |
|
|
1261 |
|
#ifdef SHEEPSHAVER |
1262 |
|
void video_set_cursor(void) |
1263 |
|
{ |
1264 |
< |
// cursor_changed = true; |
1264 |
> |
cursor_changed = true; |
1265 |
|
} |
1266 |
|
#endif |
1267 |
|
|
1629 |
|
|
1630 |
|
|
1631 |
|
/* |
1632 |
< |
* Translate key event to Mac keycode, returns -1 if no keycode was found |
1606 |
< |
* and -2 if the key was recognized as a hotkey |
1632 |
> |
* Keyboard-related utilify functions |
1633 |
|
*/ |
1634 |
|
|
1635 |
+ |
static bool is_modifier_key(SDL_KeyboardEvent const & e) |
1636 |
+ |
{ |
1637 |
+ |
switch (e.keysym.sym) { |
1638 |
+ |
case SDLK_NUMLOCK: |
1639 |
+ |
case SDLK_CAPSLOCK: |
1640 |
+ |
case SDLK_SCROLLOCK: |
1641 |
+ |
case SDLK_RSHIFT: |
1642 |
+ |
case SDLK_LSHIFT: |
1643 |
+ |
case SDLK_RCTRL: |
1644 |
+ |
case SDLK_LCTRL: |
1645 |
+ |
case SDLK_RALT: |
1646 |
+ |
case SDLK_LALT: |
1647 |
+ |
case SDLK_RMETA: |
1648 |
+ |
case SDLK_LMETA: |
1649 |
+ |
case SDLK_LSUPER: |
1650 |
+ |
case SDLK_RSUPER: |
1651 |
+ |
case SDLK_MODE: |
1652 |
+ |
case SDLK_COMPOSE: |
1653 |
+ |
return true; |
1654 |
+ |
} |
1655 |
+ |
return false; |
1656 |
+ |
} |
1657 |
+ |
|
1658 |
|
static bool is_ctrl_down(SDL_keysym const & ks) |
1659 |
|
{ |
1660 |
|
return ctrl_down || (ks.mod & KMOD_CTRL); |
1661 |
|
} |
1662 |
|
|
1663 |
+ |
|
1664 |
+ |
/* |
1665 |
+ |
* Translate key event to Mac keycode, returns -1 if no keycode was found |
1666 |
+ |
* and -2 if the key was recognized as a hotkey |
1667 |
+ |
*/ |
1668 |
+ |
|
1669 |
|
static int kc_decode(SDL_keysym const & ks, bool key_down) |
1670 |
|
{ |
1671 |
|
switch (ks.sym) { |
1735 |
|
case SDLK_RCTRL: return 0x36; |
1736 |
|
case SDLK_LSHIFT: return 0x38; |
1737 |
|
case SDLK_RSHIFT: return 0x38; |
1738 |
+ |
#if (defined(__APPLE__) && defined(__MACH__)) |
1739 |
+ |
case SDLK_LALT: return 0x3a; |
1740 |
+ |
case SDLK_RALT: return 0x3a; |
1741 |
+ |
case SDLK_LMETA: return 0x37; |
1742 |
+ |
case SDLK_RMETA: return 0x37; |
1743 |
+ |
#else |
1744 |
|
case SDLK_LALT: return 0x37; |
1745 |
|
case SDLK_RALT: return 0x37; |
1746 |
|
case SDLK_LMETA: return 0x3a; |
1747 |
|
case SDLK_RMETA: return 0x3a; |
1748 |
+ |
#endif |
1749 |
|
case SDLK_MENU: return 0x32; |
1750 |
|
case SDLK_CAPSLOCK: return 0x39; |
1751 |
|
case SDLK_NUMLOCK: return 0x47; |
1852 |
|
// Keyboard |
1853 |
|
case SDL_KEYDOWN: { |
1854 |
|
int code = -1; |
1855 |
< |
if (use_keycodes) { |
1855 |
> |
if (use_keycodes && !is_modifier_key(event.key)) { |
1856 |
|
if (event2keycode(event.key, true) != -2) // This is called to process the hotkeys |
1857 |
|
code = keycode_table[event.key.keysym.scancode & 0xff]; |
1858 |
|
} else |
1880 |
|
} |
1881 |
|
case SDL_KEYUP: { |
1882 |
|
int code = -1; |
1883 |
< |
if (use_keycodes) { |
1883 |
> |
if (use_keycodes && !is_modifier_key(event.key)) { |
1884 |
|
if (event2keycode(event.key, false) != -2) // This is called to process the hotkeys |
1885 |
|
code = keycode_table[event.key.keysym.scancode & 0xff]; |
1886 |
|
} else |
1887 |
|
code = event2keycode(event.key, false); |
1888 |
< |
if (code >= 0 && code != 0x39) { // Don't propagate Caps Lock releases |
1889 |
< |
ADBKeyUp(code); |
1888 |
> |
if (code >= 0) { |
1889 |
> |
if (code == 0x39) { // Caps Lock released |
1890 |
> |
if (caps_on) { |
1891 |
> |
ADBKeyUp(code); |
1892 |
> |
caps_on = false; |
1893 |
> |
} else { |
1894 |
> |
ADBKeyDown(code); |
1895 |
> |
caps_on = true; |
1896 |
> |
} |
1897 |
> |
} else |
1898 |
> |
ADBKeyUp(code); |
1899 |
|
if (code == 0x36) |
1900 |
|
ctrl_down = false; |
1901 |
|
} |
2229 |
|
// Refresh display |
2230 |
|
video_refresh(); |
2231 |
|
|
2232 |
+ |
#ifdef SHEEPSHAVER |
2233 |
+ |
// Set new cursor image if it was changed |
2234 |
+ |
if (cursor_changed && sdl_cursor) { |
2235 |
+ |
cursor_changed = false; |
2236 |
+ |
SDL_FreeCursor(sdl_cursor); |
2237 |
+ |
sdl_cursor = SDL_CreateCursor(MacCursor + 4, MacCursor + 36, 16, 16, MacCursor[2], MacCursor[3]); |
2238 |
+ |
if (sdl_cursor) |
2239 |
+ |
SDL_SetCursor(sdl_cursor); |
2240 |
+ |
} |
2241 |
+ |
#endif |
2242 |
+ |
|
2243 |
|
// Set new palette if it was changed |
2244 |
|
handle_palette_changes(); |
2245 |
|
} |