mirror of
https://github.com/libretro/scummvm.git
synced 2024-12-28 20:55:19 +00:00
Change the X11 driver to support various sizes (and no more hardcoded
to 320x200). svn-id: r4228
This commit is contained in:
parent
705f304004
commit
63ae2ad985
122
x11.cpp
122
x11.cpp
@ -130,6 +130,7 @@ private:
|
||||
unsigned char *local_fb;
|
||||
|
||||
int window_width, window_height;
|
||||
int fb_width, fb_height;
|
||||
int scumm_x, scumm_y;
|
||||
|
||||
#ifdef USE_XV_SCALING
|
||||
@ -301,7 +302,6 @@ OSystem *OSystem_X11::create(int gfx_mode, bool full_screen)
|
||||
OSystem_X11::OSystem_X11()
|
||||
{
|
||||
char buf[512];
|
||||
static XShmSegmentInfo shminfo;
|
||||
XWMHints *wm_hints;
|
||||
XGCValues values;
|
||||
XTextProperty window_name;
|
||||
@ -342,27 +342,13 @@ OSystem_X11::OSystem_X11()
|
||||
XSetWMProperties(display, window, &window_name, &window_name,
|
||||
NULL /* argv */ , 0 /* argc */ , NULL /* size hints */ ,
|
||||
wm_hints, NULL /* class hints */ );
|
||||
XFree(wm_hints);
|
||||
|
||||
XSelectInput(display, window,
|
||||
ExposureMask | KeyPressMask | KeyReleaseMask |
|
||||
PointerMotionMask | ButtonPressMask | ButtonReleaseMask |
|
||||
StructureNotifyMask);
|
||||
#ifdef USE_XV_SCALING
|
||||
image = XvShmCreateImage(display, 65, 0x03, 0, 320, 200, &shminfo);
|
||||
shminfo.shmid = shmget(IPC_PRIVATE, image->data_size, IPC_CREAT | 0700);
|
||||
#else
|
||||
image = XShmCreateImage(display, DefaultVisual(display, screen), 16, ZPixmap, NULL, &shminfo, 320, 200);
|
||||
shminfo.shmid = shmget(IPC_PRIVATE, 320 * 200 * 2, IPC_CREAT | 0700);
|
||||
#endif
|
||||
shminfo.shmaddr = (char *)shmat(shminfo.shmid, 0, 0);
|
||||
image->data = shminfo.shmaddr;
|
||||
shminfo.readOnly = False;
|
||||
if (XShmAttach(display, &shminfo) == 0) {
|
||||
error("Could not attach shared memory segment !\n");
|
||||
exit(1);
|
||||
}
|
||||
shmctl(shminfo.shmid, IPC_RMID, 0);
|
||||
|
||||
|
||||
values.foreground = BlackPixel(display, screen);
|
||||
black_gc = XCreateGC(display, window, GCForeground, &values);
|
||||
|
||||
@ -380,14 +366,6 @@ OSystem_X11::OSystem_X11()
|
||||
out_of_loop:
|
||||
create_empty_cursor();
|
||||
|
||||
/* Initialize the 'local' frame buffer and the palette */
|
||||
local_fb = (unsigned char *)calloc(320 * 200, sizeof(unsigned char));
|
||||
#ifdef USE_XV_SCALING
|
||||
palette = (unsigned int *)calloc(256, sizeof(unsigned int));
|
||||
#else
|
||||
palette = (unsigned short *)calloc(256, sizeof(unsigned short));
|
||||
#endif
|
||||
|
||||
/* And finally start the local timer */
|
||||
gettimeofday(&start_time, NULL);
|
||||
}
|
||||
@ -400,10 +378,44 @@ uint32 OSystem_X11::get_msecs() {
|
||||
}
|
||||
|
||||
void OSystem_X11::init_size(uint w, uint h) {
|
||||
if ((w != 320) || (h != 200))
|
||||
error("320x200 is the only game resolution supported");
|
||||
static XShmSegmentInfo shminfo;
|
||||
|
||||
/* Do nothing more for now... */
|
||||
fb_width = w;
|
||||
fb_height = h;
|
||||
|
||||
if ((fb_width != 320) || (fb_height != 200)) {
|
||||
/* We need to change the size of the X11 window */
|
||||
XWindowChanges new_values;
|
||||
|
||||
new_values.width = fb_width;
|
||||
new_values.height = fb_height;
|
||||
|
||||
XConfigureWindow(display, window, CWWidth | CWHeight, &new_values);
|
||||
}
|
||||
|
||||
#ifdef USE_XV_SCALING
|
||||
image = XvShmCreateImage(display, 65, 0x03, 0, fb_width, fb_height, &shminfo);
|
||||
shminfo.shmid = shmget(IPC_PRIVATE, image->data_size, IPC_CREAT | 0700);
|
||||
#else
|
||||
image = XShmCreateImage(display, DefaultVisual(display, screen), 16, ZPixmap, NULL, &shminfo, fb_width, fb_height);
|
||||
shminfo.shmid = shmget(IPC_PRIVATE, fb_width * fb_height * 2, IPC_CREAT | 0700);
|
||||
#endif
|
||||
shminfo.shmaddr = (char *)shmat(shminfo.shmid, 0, 0);
|
||||
image->data = shminfo.shmaddr;
|
||||
shminfo.readOnly = False;
|
||||
if (XShmAttach(display, &shminfo) == 0) {
|
||||
error("Could not attach shared memory segment !\n");
|
||||
exit(1);
|
||||
}
|
||||
shmctl(shminfo.shmid, IPC_RMID, 0);
|
||||
|
||||
/* Initialize the 'local' frame buffer and the palette */
|
||||
local_fb = (unsigned char *)calloc(fb_width * fb_height, sizeof(unsigned char));
|
||||
#ifdef USE_XV_SCALING
|
||||
palette = (unsigned int *)calloc(256, sizeof(unsigned int));
|
||||
#else
|
||||
palette = (unsigned short *)calloc(256, sizeof(unsigned short));
|
||||
#endif
|
||||
}
|
||||
|
||||
bool OSystem_X11::set_sound_proc(void *param, SoundProc *proc, byte format) {
|
||||
@ -460,11 +472,11 @@ void OSystem_X11::copy_rect(const byte *buf, int pitch, int x, int y, int w, int
|
||||
buf -= y * pitch;
|
||||
y = 0;
|
||||
}
|
||||
if (h > (200 - y)) {
|
||||
h = 200 - y;
|
||||
if (h > (fb_height - y)) {
|
||||
h = fb_height - y;
|
||||
}
|
||||
|
||||
dst = local_fb + 320 * y + x;
|
||||
dst = local_fb + fb_width * y + x;
|
||||
|
||||
if (h <= 0)
|
||||
return;
|
||||
@ -475,26 +487,26 @@ void OSystem_X11::copy_rect(const byte *buf, int pitch, int x, int y, int w, int
|
||||
AddDirtyRec(x, y, w, h);
|
||||
while (h-- > 0) {
|
||||
memcpy(dst, buf, w);
|
||||
dst += 320;
|
||||
dst += fb_width;
|
||||
buf += pitch;
|
||||
}
|
||||
}
|
||||
|
||||
void OSystem_X11::update_screen_helper(const dirty_square * d, dirty_square * dout) {
|
||||
int x, y;
|
||||
unsigned char *ptr_src = local_fb + (320 * d->y) + d->x;
|
||||
unsigned char *ptr_src = local_fb + (fb_width * d->y) + d->x;
|
||||
#ifdef USE_XV_SCALING
|
||||
unsigned int *ptr_dst = ((unsigned int *)image->data) + (320 * d->y) + d->x;
|
||||
unsigned int *ptr_dst = ((unsigned int *)image->data) + (fb_width * d->y) + d->x;
|
||||
#else
|
||||
unsigned short *ptr_dst = ((unsigned short *)image->data) + (320 * d->y) + d->x;
|
||||
unsigned short *ptr_dst = ((unsigned short *)image->data) + (fb_width * d->y) + d->x;
|
||||
#endif
|
||||
|
||||
for (y = 0; y < d->h; y++) {
|
||||
for (x = 0; x < d->w; x++) {
|
||||
*ptr_dst++ = palette[*ptr_src++];
|
||||
}
|
||||
ptr_dst += 320 - d->w;
|
||||
ptr_src += 320 - d->w;
|
||||
ptr_dst += fb_width - d->w;
|
||||
ptr_src += fb_width - d->w;
|
||||
}
|
||||
if (d->x < dout->x)
|
||||
dout->x = d->x;
|
||||
@ -509,8 +521,8 @@ void OSystem_X11::update_screen_helper(const dirty_square * d, dirty_square * do
|
||||
void OSystem_X11::update_screen() {
|
||||
bool full_redraw = false;
|
||||
bool need_redraw = false;
|
||||
static const dirty_square ds_full = { 0, 0, 320, 200 };
|
||||
dirty_square dout = { 320, 200, 0, 0 };
|
||||
static const dirty_square ds_full = { 0, 0, fb_width, fb_height };
|
||||
dirty_square dout = { fb_width, fb_height, 0, 0 };
|
||||
|
||||
/* First make sure the mouse is drawn, if it should be drawn. */
|
||||
draw_mouse();
|
||||
@ -545,13 +557,13 @@ void OSystem_X11::update_screen() {
|
||||
#ifndef USE_XV_SCALING
|
||||
XShmPutImage(display, window, DefaultGC(display, screen), image,
|
||||
0, 0, scumm_x, scumm_y + new_shake_pos,
|
||||
320, 200, 0);
|
||||
fb_width, fb_height, 0);
|
||||
#endif
|
||||
current_shake_pos = new_shake_pos;
|
||||
} else if (need_redraw == true) {
|
||||
#ifdef USE_XV_SCALING
|
||||
XvShmPutImage(display, 65, window, DefaultGC(display, screen), image,
|
||||
0, 0, 320, 200, 0, 0, window_width, window_height, 0);
|
||||
0, 0, fb_width, fb_height, 0, 0, window_width, window_height, 0);
|
||||
#else
|
||||
XShmPutImage(display, window, DefaultGC(display, screen), image,
|
||||
dout.x, dout.y, scumm_x + dout.x, scumm_y + dout.y + current_shake_pos,
|
||||
@ -605,17 +617,17 @@ void OSystem_X11::draw_mouse() {
|
||||
buf += (-ydraw) * w;
|
||||
ydraw = 0;
|
||||
} else {
|
||||
real_h = (ydraw + h) > 200 ? (200 - ydraw) : h;
|
||||
real_h = (ydraw + h) > fb_height ? (fb_height - ydraw) : h;
|
||||
}
|
||||
if (xdraw < 0) {
|
||||
real_w = w + xdraw;
|
||||
buf += (-xdraw);
|
||||
xdraw = 0;
|
||||
} else {
|
||||
real_w = (xdraw + w) > 320 ? (320 - xdraw) : w;
|
||||
real_w = (xdraw + w) > fb_width ? (fb_width - xdraw) : w;
|
||||
}
|
||||
|
||||
dst = local_fb + (ydraw * 320) + xdraw;
|
||||
dst = local_fb + (ydraw * fb_width) + xdraw;
|
||||
dst2 = dst;
|
||||
|
||||
if ((real_h == 0) || (real_w == 0)) {
|
||||
@ -633,7 +645,7 @@ void OSystem_X11::draw_mouse() {
|
||||
while (real_h_2 > 0) {
|
||||
memcpy(bak, dst, real_w);
|
||||
bak += BAK_WIDTH;
|
||||
dst += 320;
|
||||
dst += fb_width;
|
||||
real_h_2--;
|
||||
}
|
||||
while (real_h > 0) {
|
||||
@ -648,7 +660,7 @@ void OSystem_X11::draw_mouse() {
|
||||
width--;
|
||||
}
|
||||
buf += w - real_w;
|
||||
dst2 += 320 - real_w;
|
||||
dst2 += fb_width - real_w;
|
||||
real_h--;
|
||||
}
|
||||
}
|
||||
@ -662,13 +674,13 @@ void OSystem_X11::undraw_mouse() {
|
||||
|
||||
AddDirtyRec(old_state.x, old_state.y, old_state.w, old_state.h);
|
||||
|
||||
byte *dst = local_fb + (old_state.y * 320) + old_state.x;
|
||||
byte *dst = local_fb + (old_state.y * fb_width) + old_state.x;
|
||||
byte *bak = _ms_backup;
|
||||
|
||||
while (old_h > 0) {
|
||||
memcpy(dst, bak, old_state.w);
|
||||
bak += BAK_WIDTH;
|
||||
dst += 320;
|
||||
dst += fb_width;
|
||||
old_h--;
|
||||
}
|
||||
}
|
||||
@ -757,14 +769,14 @@ bool OSystem_X11::poll_event(Event *scumm_event) {
|
||||
}
|
||||
if ((real_h <= 0) || (real_w <= 0))
|
||||
break;
|
||||
if ((real_x >= 320) || (real_y >= 200))
|
||||
if ((real_x >= fb_width) || (real_y >= fb_height))
|
||||
break;
|
||||
|
||||
if ((real_x + real_w) >= 320) {
|
||||
real_w = 320 - real_x;
|
||||
if ((real_x + real_w) >= fb_width) {
|
||||
real_w = fb_width - real_x;
|
||||
}
|
||||
if ((real_y + real_h) >= 200) {
|
||||
real_h = 200 - real_y;
|
||||
if ((real_y + real_h) >= fb_height) {
|
||||
real_h = fb_height - real_y;
|
||||
}
|
||||
|
||||
/* Compute the intersection of the expose event with the real ScummVM display zone */
|
||||
@ -876,8 +888,8 @@ bool OSystem_X11::poll_event(Event *scumm_event) {
|
||||
(window_height != event.xconfigure.height)) {
|
||||
window_width = event.xconfigure.width;
|
||||
window_height = event.xconfigure.height;
|
||||
scumm_x = (window_width - 320) / 2;
|
||||
scumm_y = (window_height - 200) / 2;
|
||||
scumm_x = (window_width - fb_width) / 2;
|
||||
scumm_y = (window_height - fb_height) / 2;
|
||||
XFillRectangle(display, window, black_gc, 0, 0, window_width, window_height);
|
||||
}
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user