Working on the Display API

This commit is contained in:
Joshua Granick
2015-07-31 12:10:57 -07:00
parent 0b9926a87a
commit fd376e6f99
9 changed files with 365 additions and 263 deletions

View File

@@ -18,6 +18,7 @@ namespace lime {
Rectangle (value rect);
void Contract (double x, double y, double width, double height);
value Value ();
double height;
double width;

View File

@@ -1,24 +1,24 @@
#ifndef LIME_SYSTEM_DISPLAY_H
#define LIME_SYSTEM_DISPLAY_H
#include <SDL.h>
#include <hx/CFFI.h>
namespace lime {
class Display {
public:
static value GetCurrentDisplayMode (int displayIndex);
static value GetDisplayMode (int displayIndex, int modeIndex);
static value GetDisplayBounds (int displayIndex);
static int GetNumDevices ();
static const char* GetDisplayName (int displayIndex);
static int GetNumDisplayModes (int displayIndex);
static value GetDetails ();
};
}

View File

@@ -161,6 +161,13 @@ namespace lime {
}
value lime_display_get_details () {
return Display::GetDetails ();
}
void lime_font_destroy (value handle) {
Font *font = (Font*)(intptr_t)val_float (handle);
@@ -391,41 +398,6 @@ namespace lime {
}
value lime_display_get_display_bounds (value displayIndex) {
return Display::GetDisplayBounds(val_int(displayIndex));
}
value lime_display_get_current_display_mode (value displayIndex) {
return Display::GetCurrentDisplayMode(val_int(displayIndex));
}
value lime_display_get_display_mode (value displayIndex, value modeIndex) {
return Display::GetDisplayMode(val_int(displayIndex), val_int(modeIndex));
}
value lime_display_get_name (value displayIndex) {
return alloc_string (Display::GetDisplayName (val_int (displayIndex)));
}
value lime_display_get_num_devices () {
return alloc_int (Display::GetNumDevices());
}
value lime_display_get_num_display_modes (value displayIndex) {
return alloc_int (Display::GetNumDisplayModes(val_int (displayIndex)));
}
value lime_gamepad_add_mappings (value mappings) {
@@ -1192,6 +1164,7 @@ namespace lime {
DEFINE_PRIM (lime_bytes_from_data_pointer, 2);
DEFINE_PRIM (lime_bytes_get_data_pointer, 1);
DEFINE_PRIM (lime_bytes_read_file, 1);
DEFINE_PRIM (lime_display_get_details, 0);
DEFINE_PRIM (lime_font_get_ascender, 1);
DEFINE_PRIM (lime_font_get_descender, 1);
DEFINE_PRIM (lime_font_get_family_name, 1);
@@ -1208,12 +1181,6 @@ namespace lime {
DEFINE_PRIM (lime_font_render_glyph, 3);
DEFINE_PRIM (lime_font_render_glyphs, 3);
DEFINE_PRIM (lime_font_set_size, 2);
DEFINE_PRIM (lime_display_get_display_bounds, 1);
DEFINE_PRIM (lime_display_get_current_display_mode, 1);
DEFINE_PRIM (lime_display_get_display_mode, 2);
DEFINE_PRIM (lime_display_get_name, 1);
DEFINE_PRIM (lime_display_get_num_devices, 0);
DEFINE_PRIM (lime_display_get_num_display_modes, 1);
DEFINE_PRIM (lime_gamepad_add_mappings, 1);
DEFINE_PRIM (lime_gamepad_event_manager_register, 2);
DEFINE_PRIM (lime_gamepad_get_device_guid, 1);

View File

@@ -1,67 +1,106 @@
#include <graphics/PixelFormat.h>
#include <math/Rectangle.h>
#include <system/Display.h>
#include <SDL.h>
namespace lime {
value Display::GetDisplayBounds (int displayIndex) {
static int id_bounds;
static int id_currentMode;
static int id_height;
static int id_name;
static int id_pixelFormat;
static int id_refreshRate;
static int id_supportedModes;
static int id_width;
static bool init = false;
value Display::GetDetails () {
SDL_Rect rect = { 0, 0, 0, 0};
SDL_GetDisplayBounds(displayIndex, &rect);
if (!init) {
id_bounds = val_id ("bounds");
id_currentMode = val_id ("currentMode");
id_height = val_id ("height");
id_name = val_id ("name");
id_pixelFormat = val_id ("pixelFormat");
id_refreshRate = val_id ("refreshRate");
id_supportedModes = val_id ("supportedModes");
id_width = val_id ("width");
init = true;
}
value mValue = alloc_empty_object ();
alloc_field (mValue, val_id("x"), alloc_int(rect.x));
alloc_field (mValue, val_id("y"), alloc_int(rect.y));
alloc_field (mValue, val_id("width"), alloc_int(rect.w));
alloc_field (mValue, val_id("height"), alloc_int(rect.h));
return mValue;
int numDevices = SDL_GetNumVideoDisplays ();
value devices = alloc_array (numDevices);
value display, supportedModes, mode;
int numDisplayModes;
SDL_Rect bounds = { 0, 0, 0, 0 };
SDL_DisplayMode currentDisplayMode = { SDL_PIXELFORMAT_UNKNOWN, 0, 0, 0, 0 };
SDL_DisplayMode displayMode = { SDL_PIXELFORMAT_UNKNOWN, 0, 0, 0, 0 };
for (int i = 0; i < numDevices; i++) {
display = alloc_empty_object ();
alloc_field (display, id_name, alloc_string (SDL_GetDisplayName (i)));
SDL_GetDisplayBounds (i, &bounds);
alloc_field (display, id_bounds, Rectangle (bounds.x, bounds.y, bounds.w, bounds.h).Value ());
SDL_GetCurrentDisplayMode (i, &currentDisplayMode);
numDisplayModes = SDL_GetNumDisplayModes (i);
supportedModes = alloc_array (numDisplayModes);
for (int j = 0; j < numDisplayModes; j++) {
SDL_GetDisplayMode (i, j, &displayMode);
if (displayMode.format == currentDisplayMode.format && displayMode.w == currentDisplayMode.w && displayMode.h == currentDisplayMode.h && displayMode.refresh_rate == currentDisplayMode.refresh_rate) {
alloc_field (display, id_currentMode, alloc_int (j));
}
mode = alloc_empty_object ();
alloc_field (mode, id_height, alloc_int (displayMode.h));
switch (displayMode.format) {
case SDL_PIXELFORMAT_ARGB8888:
alloc_field (mode, id_pixelFormat, alloc_int (ARGB32));
break;
case SDL_PIXELFORMAT_BGRA8888:
case SDL_PIXELFORMAT_BGRX8888:
alloc_field (mode, id_pixelFormat, alloc_int (BGRA32));
break;
default:
alloc_field (mode, id_pixelFormat, alloc_int (RGBA32));
}
alloc_field (mode, id_refreshRate, alloc_int (displayMode.refresh_rate));
alloc_field (mode, id_width, alloc_int (displayMode.w));
val_array_set_i (supportedModes, j, mode);
}
alloc_field (display, id_supportedModes, supportedModes);
val_array_set_i (devices, i, display);
}
return devices;
}
value Display::GetCurrentDisplayMode (int displayIndex) {
SDL_DisplayMode mode = { SDL_PIXELFORMAT_UNKNOWN, 0, 0, 0, 0 };
SDL_GetCurrentDisplayMode(displayIndex, &mode);
value mValue = alloc_empty_object ();
alloc_field (mValue, val_id("width"), alloc_int(mode.w));
alloc_field (mValue, val_id("height"), alloc_int(mode.h));
alloc_field (mValue, val_id("refresh_rate"), alloc_int(mode.refresh_rate));
alloc_field (mValue, val_id("format"), alloc_int(mode.format));
return mValue;
}
value Display::GetDisplayMode (int displayIndex, int modeIndex) {
SDL_DisplayMode mode = { SDL_PIXELFORMAT_UNKNOWN, 0, 0, 0, 0 };
SDL_GetDisplayMode(displayIndex, modeIndex, &mode);
value mValue = alloc_empty_object ();
alloc_field (mValue, val_id("width"), alloc_int(mode.w));
alloc_field (mValue, val_id("height"), alloc_int(mode.h));
alloc_field (mValue, val_id("refresh_rate"), alloc_int(mode.refresh_rate));
alloc_field (mValue, val_id("format"), alloc_int(mode.format));
return mValue;
}
int Display::GetNumDevices() {
return SDL_GetNumVideoDisplays();
}
const char* Display::GetDisplayName (int displayIndex) {
return SDL_GetDisplayName(displayIndex);
}
int Display::GetNumDisplayModes (int displayIndex) {
return SDL_GetNumDisplayModes(displayIndex);
}
}

View File

@@ -70,4 +70,26 @@ namespace lime {
}
value Rectangle::Value () {
if (!init) {
id_height = val_id ("height");
id_width = val_id ("width");
id_x = val_id ("x");
id_y = val_id ("y");
init = true;
}
value rect = alloc_empty_object ();
alloc_field (rect, id_height, alloc_float (height));
alloc_field (rect, id_width, alloc_float (width));
alloc_field (rect, id_x, alloc_float (x));
alloc_field (rect, id_y, alloc_float (y));
return rect;
}
}

View File

@@ -0,0 +1,144 @@
#include <graphics/ImageBuffer.h>
namespace lime {
static int id_bitsPerPixel;
static int id_buffer;
static int id_data;
static int id_format;
static int id_height;
static int id_premultiplied;
static int id_transparent;
static int id_width;
static bool init = false;
ImageBuffer::ImageBuffer () {
width = 0;
height = 0;
bitsPerPixel = 32;
format = RGBA32;
data = 0;
premultiplied = false;
transparent = false;
}
ImageBuffer::ImageBuffer (value imageBuffer) {
if (!init) {
id_bitsPerPixel = val_id ("bitsPerPixel");
id_transparent = val_id ("transparent");
id_buffer = val_id ("buffer");
id_width = val_id ("width");
id_height = val_id ("height");
id_data = val_id ("data");
id_format = val_id ("format");
id_premultiplied = val_id ("premultiplied");
init = true;
}
width = val_int (val_field (imageBuffer, id_width));
height = val_int (val_field (imageBuffer, id_height));
bitsPerPixel = val_int (val_field (imageBuffer, id_bitsPerPixel));
format = (PixelFormat)val_int (val_field (imageBuffer, id_format));
transparent = val_bool (val_field (imageBuffer, id_transparent));
value data_value = val_field (imageBuffer, id_data);
value buffer_value = val_field (data_value, id_buffer);
premultiplied = val_bool (val_field (imageBuffer, id_premultiplied));
data = new Bytes (buffer_value);
}
ImageBuffer::~ImageBuffer () {
delete data;
}
void ImageBuffer::Blit (const unsigned char *data, int x, int y, int width, int height) {
if (x < 0 || x + width > this->width || y < 0 || y + height > this->height) {
return;
}
int stride = Stride ();
unsigned char *bytes = this->data->Data ();
for (int i = 0; i < height; i++) {
memcpy (&bytes[(i + y) * this->width + x], &data[i * width], stride);
}
}
void ImageBuffer::Resize (int width, int height, int bitsPerPixel) {
this->bitsPerPixel = bitsPerPixel;
this->width = width;
this->height = height;
int stride = Stride ();
if (!this->data) {
this->data = new Bytes (height * stride);
} else {
this->data->Resize (height * stride);
}
}
int ImageBuffer::Stride () {
return width * (((bitsPerPixel + 3) & ~0x3) >> 3);
}
value ImageBuffer::Value () {
if (!init) {
id_bitsPerPixel = val_id ("bitsPerPixel");
id_transparent = val_id ("transparent");
id_buffer = val_id ("buffer");
id_width = val_id ("width");
id_height = val_id ("height");
id_data = val_id ("data");
id_format = val_id ("format");
id_premultiplied = val_id ("premultiplied");
init = true;
}
mValue = alloc_empty_object ();
alloc_field (mValue, id_width, alloc_int (width));
alloc_field (mValue, id_height, alloc_int (height));
alloc_field (mValue, id_bitsPerPixel, alloc_int (bitsPerPixel));
alloc_field (mValue, id_data, data ? data->Value () : alloc_null ());
alloc_field (mValue, id_transparent, alloc_bool (transparent));
alloc_field (mValue, id_format, alloc_int (format));
alloc_field (mValue, id_premultiplied, alloc_bool (premultiplied));
return mValue;
}
}