src/video/mir/SDL_mirvideo.c
author Ryan C. Gordon <icculus@icculus.org>
Mon, 03 Feb 2014 11:52:54 -0500
changeset 8159 427e8fdf6f69
parent 8157 f5d262613ed2
child 8723 cfc134c9c369
permissions -rw-r--r--
Hooked up dynamic loading for Mir.
     1 /*
     2   Simple DirectMedia Layer
     3   Copyright (C) 1997-2014 Sam Lantinga <slouken@libsdl.org>
     4 
     5   This software is provided 'as-is', without any express or implied
     6   warranty.  In no event will the authors be held liable for any damages
     7   arising from the use of this software.
     8 
     9   Permission is granted to anyone to use this software for any purpose,
    10   including commercial applications, and to alter it and redistribute it
    11   freely, subject to the following restrictions:
    12 
    13   1. The origin of this software must not be misrepresented; you must not
    14      claim that you wrote the original software. If you use this software
    15      in a product, an acknowledgment in the product documentation would be
    16      appreciated but is not required.
    17   2. Altered source versions must be plainly marked as such, and must not be
    18      misrepresented as being the original software.
    19   3. This notice may not be removed or altered from any source distribution.
    20 */
    21 
    22 /*
    23   Contributed by Brandon Schaefer, <brandon.schaefer@canonical.com>
    24 */
    25 
    26 #include "../../SDL_internal.h"
    27 
    28 #if SDL_VIDEO_DRIVER_MIR
    29 
    30 #include "SDL_video.h"
    31 
    32 #include "SDL_mirframebuffer.h"
    33 #include "SDL_mirmouse.h"
    34 #include "SDL_miropengl.h"
    35 #include "SDL_mirvideo.h"
    36 #include "SDL_mirwindow.h"
    37 
    38 #include "SDL_mirdyn.h"
    39 
    40 #define MIR_DRIVER_NAME "mir"
    41 
    42 static int
    43 MIR_VideoInit(_THIS);
    44 
    45 static void
    46 MIR_VideoQuit(_THIS);
    47 
    48 static int
    49 MIR_GetDisplayBounds(_THIS, SDL_VideoDisplay* display, SDL_Rect* rect);
    50 
    51 static void
    52 MIR_GetDisplayModes(_THIS, SDL_VideoDisplay* sdl_display);
    53 
    54 static int
    55 MIR_SetDisplayMode(_THIS, SDL_VideoDisplay* sdl_display, SDL_DisplayMode* mode);
    56 
    57 static SDL_WindowShaper*
    58 MIR_CreateShaper(SDL_Window* window)
    59 {
    60     /* FIXME Im not sure if mir support this atm, will have to come back to this */
    61     return NULL;
    62 }
    63 
    64 static int
    65 MIR_SetWindowShape(SDL_WindowShaper* shaper, SDL_Surface* shape, SDL_WindowShapeMode* shape_mode)
    66 {
    67     return SDL_Unsupported();
    68 }
    69 
    70 static int
    71 MIR_ResizeWindowShape(SDL_Window* window)
    72 {
    73     return SDL_Unsupported();
    74 }
    75 
    76 static int
    77 MIR_Available()
    78 {
    79     int available = 0;
    80 
    81     if (SDL_MIR_LoadSymbols()) {
    82         /* !!! FIXME: try to make a MirConnection here. */
    83         available = 1;
    84         SDL_MIR_UnloadSymbols();
    85 
    86     }
    87 
    88     return available;
    89 }
    90 
    91 static void
    92 MIR_DeleteDevice(SDL_VideoDevice* device)
    93 {
    94     SDL_free(device);
    95     SDL_MIR_UnloadSymbols();
    96 }
    97 
    98 void
    99 MIR_PumpEvents(_THIS)
   100 {
   101 }
   102 
   103 static SDL_VideoDevice*
   104 MIR_CreateDevice(int device_index)
   105 {
   106     MIR_Data* mir_data;
   107     SDL_VideoDevice* device = NULL;
   108 
   109     if (!SDL_MIR_LoadSymbols()) {
   110         return NULL;
   111     }
   112 
   113     device = SDL_calloc(1, sizeof(SDL_VideoDevice));
   114     if (!device) {
   115         SDL_MIR_UnloadSymbols();
   116         SDL_OutOfMemory();
   117         return NULL;
   118     }
   119 
   120     mir_data = SDL_calloc(1, sizeof(MIR_Data));
   121     if (!mir_data) {
   122         SDL_free(device);
   123         SDL_MIR_UnloadSymbols();
   124         SDL_OutOfMemory();
   125         return NULL;
   126     }
   127 
   128     device->driverdata = mir_data;
   129 
   130     /* mirvideo */
   131     device->VideoInit        = MIR_VideoInit;
   132     device->VideoQuit        = MIR_VideoQuit;
   133     device->GetDisplayBounds = MIR_GetDisplayBounds;
   134     device->GetDisplayModes  = MIR_GetDisplayModes;
   135     device->SetDisplayMode   = MIR_SetDisplayMode;
   136     device->free             = MIR_DeleteDevice;
   137 
   138     /* miropengles */
   139     device->GL_SwapWindow      = MIR_GL_SwapWindow;
   140     device->GL_MakeCurrent     = MIR_GL_MakeCurrent;
   141     device->GL_CreateContext   = MIR_GL_CreateContext;
   142     device->GL_DeleteContext   = MIR_GL_DeleteContext;
   143     device->GL_LoadLibrary     = MIR_GL_LoadLibrary;
   144     device->GL_UnloadLibrary   = MIR_GL_UnloadLibrary;
   145     device->GL_GetSwapInterval = MIR_GL_GetSwapInterval;
   146     device->GL_SetSwapInterval = MIR_GL_SetSwapInterval;
   147     device->GL_GetProcAddress  = MIR_GL_GetProcAddress;
   148 
   149     /* mirwindow */
   150     device->CreateWindow        = MIR_CreateWindow;
   151     device->DestroyWindow       = MIR_DestroyWindow;
   152     device->GetWindowWMInfo     = MIR_GetWindowWMInfo;
   153     device->SetWindowFullscreen = MIR_SetWindowFullscreen;
   154     device->MaximizeWindow      = MIR_MaximizeWindow;
   155     device->MinimizeWindow      = MIR_MinimizeWindow;
   156     device->RestoreWindow       = MIR_RestoreWindow;
   157 
   158     device->CreateWindowFrom     = NULL;
   159     device->SetWindowTitle       = NULL;
   160     device->SetWindowIcon        = NULL;
   161     device->SetWindowPosition    = NULL;
   162     device->SetWindowSize        = NULL;
   163     device->SetWindowMinimumSize = NULL;
   164     device->SetWindowMaximumSize = NULL;
   165     device->ShowWindow           = NULL;
   166     device->HideWindow           = NULL;
   167     device->RaiseWindow          = NULL;
   168     device->SetWindowBordered    = NULL;
   169     device->SetWindowGammaRamp   = NULL;
   170     device->GetWindowGammaRamp   = NULL;
   171     device->SetWindowGrab        = NULL;
   172     device->OnWindowEnter        = NULL;
   173 
   174     /* mirframebuffer */
   175     device->CreateWindowFramebuffer  = MIR_CreateWindowFramebuffer;
   176     device->UpdateWindowFramebuffer  = MIR_UpdateWindowFramebuffer;
   177     device->DestroyWindowFramebuffer = MIR_DestroyWindowFramebuffer;
   178 
   179     device->shape_driver.CreateShaper      = MIR_CreateShaper;
   180     device->shape_driver.SetWindowShape    = MIR_SetWindowShape;
   181     device->shape_driver.ResizeWindowShape = MIR_ResizeWindowShape;
   182 
   183     device->PumpEvents = MIR_PumpEvents;
   184 
   185     device->SuspendScreenSaver = NULL;
   186 
   187     device->StartTextInput   = NULL;
   188     device->StopTextInput    = NULL;
   189     device->SetTextInputRect = NULL;
   190 
   191     device->HasScreenKeyboardSupport = NULL;
   192     device->ShowScreenKeyboard       = NULL;
   193     device->HideScreenKeyboard       = NULL;
   194     device->IsScreenKeyboardShown    = NULL;
   195 
   196     device->SetClipboardText = NULL;
   197     device->GetClipboardText = NULL;
   198     device->HasClipboardText = NULL;
   199 
   200     device->ShowMessageBox = NULL;
   201 
   202     return device;
   203 }
   204 
   205 VideoBootStrap MIR_bootstrap = {
   206     MIR_DRIVER_NAME, "SDL Mir video driver",
   207     MIR_Available, MIR_CreateDevice
   208 };
   209 
   210 static void
   211 MIR_SetCurrentDisplayMode(MirDisplayOutput const* out, SDL_VideoDisplay* display)
   212 {
   213     SDL_DisplayMode mode = {
   214         .format = SDL_PIXELFORMAT_RGB888,
   215         .w = out->modes[out->current_mode].horizontal_resolution,
   216         .h = out->modes[out->current_mode].vertical_resolution,
   217         .refresh_rate = out->modes[out->current_mode].refresh_rate,
   218         .driverdata = NULL
   219     };
   220 
   221     display->desktop_mode = mode;
   222     display->current_mode = mode;
   223 }
   224 
   225 static void
   226 MIR_AddAllModesFromDisplay(MirDisplayOutput const* out, SDL_VideoDisplay* display)
   227 {
   228     int n_mode;
   229     for (n_mode = 0; n_mode < out->num_modes; ++n_mode) {
   230         SDL_DisplayMode mode = {
   231             .format = SDL_PIXELFORMAT_RGB888,
   232             .w = out->modes[n_mode].horizontal_resolution,
   233             .h = out->modes[n_mode].vertical_resolution,
   234             .refresh_rate = out->modes[n_mode].refresh_rate,
   235             .driverdata = NULL
   236         };
   237 
   238         SDL_AddDisplayMode(display, &mode);
   239     }
   240 }
   241 
   242 static void
   243 MIR_InitDisplays(_THIS)
   244 {
   245     MIR_Data* mir_data = _this->driverdata;
   246     int d;
   247 
   248     MirDisplayConfiguration* display_config = MIR_mir_connection_create_display_config(mir_data->connection);
   249 
   250     for (d = 0; d < display_config->num_outputs; d++) {
   251         MirDisplayOutput const* out = display_config->outputs + d;
   252 
   253         SDL_VideoDisplay display;
   254         SDL_zero(display);
   255 
   256         if (out->used &&
   257             out->connected &&
   258             out->num_modes &&
   259             out->current_mode < out->num_modes) {
   260 
   261             MIR_SetCurrentDisplayMode(out, &display);
   262             MIR_AddAllModesFromDisplay(out, &display);
   263 
   264             SDL_AddVideoDisplay(&display);
   265         }
   266     }
   267 
   268     MIR_mir_display_config_destroy(display_config);
   269 }
   270 
   271 int
   272 MIR_VideoInit(_THIS)
   273 {
   274     MIR_Data* mir_data = _this->driverdata;
   275 
   276     mir_data->connection = MIR_mir_connect_sync(NULL, __PRETTY_FUNCTION__);
   277 
   278     if (!MIR_mir_connection_is_valid(mir_data->connection))
   279         return SDL_SetError("Failed to connect to the Mir Server");
   280 
   281     MIR_InitDisplays(_this);
   282     MIR_InitMouse();
   283 
   284     return 0;
   285 }
   286 
   287 void
   288 MIR_VideoQuit(_THIS)
   289 {
   290     MIR_Data* mir_data = _this->driverdata;
   291 
   292     MIR_FiniMouse();
   293 
   294     MIR_GL_DeleteContext(_this, NULL);
   295     MIR_GL_UnloadLibrary(_this);
   296 
   297     MIR_mir_connection_release(mir_data->connection);
   298 
   299     SDL_free(mir_data);
   300     _this->driverdata = NULL;
   301 }
   302 
   303 static int
   304 MIR_GetDisplayBounds(_THIS, SDL_VideoDisplay* display, SDL_Rect* rect)
   305 {
   306     MIR_Data* mir_data = _this->driverdata;
   307     int d;
   308 
   309     MirDisplayConfiguration* display_config = MIR_mir_connection_create_display_config(mir_data->connection);
   310 
   311     for (d = 0; d < display_config->num_outputs; d++) {
   312         MirDisplayOutput const* out = display_config->outputs + d;
   313 
   314         if (out->used &&
   315             out->connected &&
   316             out->num_modes &&
   317             out->current_mode < out->num_modes) {
   318 
   319             rect->x = out->position_x;
   320             rect->y = out->position_y;
   321             rect->w = out->modes->horizontal_resolution;
   322             rect->h = out->modes->vertical_resolution;
   323         }
   324     }
   325 
   326     MIR_mir_display_config_destroy(display_config);
   327 
   328     return 0;
   329 }
   330 
   331 static void
   332 MIR_GetDisplayModes(_THIS, SDL_VideoDisplay* sdl_display)
   333 {
   334 }
   335 
   336 static int
   337 MIR_SetDisplayMode(_THIS, SDL_VideoDisplay* sdl_display, SDL_DisplayMode* mode)
   338 {
   339     return 0;
   340 }
   341 
   342 #endif /* SDL_VIDEO_DRIVER_MIR */
   343 
   344 /* vi: set ts=4 sw=4 expandtab: */
   345