SDL_nximage.c revision 9682c8870b8ff5e4ac2e4c70b759f791c6f38c1f
1/*
2    SDL - Simple DirectMedia Layer
3    Copyright (C) 1997-2012 Sam Lantinga
4    Copyright (C) 2001  Hsieh-Fu Tsai
5    Copyright (C) 2002  Greg Haerr <greg@censoft.com>
6
7    This library is free software; you can redistribute it and/or
8    modify it under the terms of the GNU Library General Public
9    License as published by the Free Software Foundation; either
10    version 2 of the License, or (at your option) any later version.
11
12    This library is distributed in the hope that it will be useful,
13    but WITHOUT ANY WARRANTY; without even the implied warranty of
14    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
15    Library General Public License for more details.
16
17    You should have received a copy of the GNU Library General Public
18    License along with this library; if not, write to the Free
19    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
20
21    Sam Lantinga
22    slouken@libsdl.org
23
24    Hsieh-Fu Tsai
25    clare@setabox.com
26*/
27#include "SDL_config.h"
28
29#include "SDL_nximage_c.h"
30
31void NX_NormalUpdate (_THIS, int numrects, SDL_Rect * rects)
32{
33    int           i, j, xinc, yinc, destinc, rowinc ;
34    int           x, y, w, h ;
35    unsigned char * src = NULL, * dest = NULL ;
36
37    Dprintf ("enter NX_NormalUpdate\n") ;
38
39    /* These are the values for the incoming image */
40    xinc = this -> screen -> format -> BytesPerPixel ;
41    yinc = this -> screen -> pitch ;
42
43    for (i = 0; i < numrects; ++ i) {
44        x = rects [i].x, y = rects [i].y ;
45        w = rects [i].w, h = rects [i].h ;
46        src = SDL_Image + y * yinc + x * xinc ;
47#ifdef ENABLE_NANOX_DIRECT_FB
48        if (Clientfb) {
49            if (currently_fullscreen)
50                dest = fbinfo.winpixels + (((y+OffsetY) * fbinfo.pitch) +
51                    ((x+OffsetX) * fbinfo.bytespp));
52            else
53                dest = fbinfo.winpixels + ((y * fbinfo.pitch) + (x * fbinfo.bytespp));
54            destinc = fbinfo.pitch;
55        }
56        else
57#endif
58        {
59            dest = Image_buff ;
60            destinc = w * xinc ;
61        }
62        rowinc = w * xinc;
63
64        // apply GammaRamp table
65        if ((pixel_type == MWPF_TRUECOLOR0888 || pixel_type == MWPF_TRUECOLOR888)
66          && GammaRamp_R && GammaRamp_G && GammaRamp_B) {
67            Uint8 * ptrsrc ;
68            Uint8 * ptrdst ;
69            int   k ;
70
71            for (j = h; j > 0; -- j, src += yinc, dest += destinc) {
72                ptrsrc = src ;
73                ptrdst = dest ;
74                for (k = w; k > 0; -- k) {
75                    *ptrdst++ = GammaRamp_B [*ptrsrc++] >> 8;
76                    *ptrdst++ = GammaRamp_G [*ptrsrc++] >> 8;
77                    *ptrdst++ = GammaRamp_R [*ptrsrc++] >> 8;
78                    *ptrdst++ = 0;
79                    ++ptrsrc;
80                }
81            }
82        }
83#if 1 /* This is needed for microwindows 0.90 or older */
84        else if (pixel_type == MWPF_TRUECOLOR0888 || pixel_type == MWPF_TRUECOLOR888) {
85            Uint8 * ptrsrc ;
86            Uint8 * ptrdst ;
87            int   k ;
88
89            for (j = h; j > 0; -- j, src += yinc, dest += destinc) {
90                ptrsrc = src ;
91                ptrdst = dest ;
92                for (k = w; k > 0; -- k) {
93                    *ptrdst++ = *ptrsrc++;
94                    *ptrdst++ = *ptrsrc++;
95                    *ptrdst++ = *ptrsrc++;
96                    *ptrdst++ = 0;
97                    ++ptrsrc;
98                }
99            }
100        }
101#endif
102        else
103        {
104            for (j = h; j > 0; -- j, src += yinc, dest += destinc)
105                SDL_memcpy (dest, src, rowinc) ;
106        }
107        if (!Clientfb) {
108            if (currently_fullscreen) {
109                GrArea (FSwindow, SDL_GC, x + OffsetX, y + OffsetY, w, h, Image_buff,
110                    pixel_type) ;
111            } else {
112                GrArea (SDL_Window, SDL_GC, x, y, w, h, Image_buff, pixel_type) ;
113            }
114        }
115    }
116    GrFlush();
117
118    Dprintf ("leave NX_NormalUpdate\n") ;
119}
120
121int NX_SetupImage (_THIS, SDL_Surface * screen)
122{
123    int size = screen -> h * screen -> pitch ;
124
125    Dprintf ("enter NX_SetupImage\n") ;
126
127    screen -> pixels = (void *) SDL_malloc (size) ;
128
129    if (!Clientfb) {
130        Image_buff = (unsigned char *) SDL_malloc (size) ;
131        if (screen -> pixels == NULL || Image_buff == NULL) {
132            SDL_free (screen -> pixels) ;
133            SDL_free (Image_buff) ;
134            SDL_OutOfMemory () ;
135            return -1 ;
136        }
137    }
138
139    SDL_Image = (unsigned char *) screen -> pixels ;
140
141    this -> UpdateRects = NX_NormalUpdate ;
142
143    Dprintf ("leave NX_SetupImage\n") ;
144    return 0 ;
145}
146
147void NX_DestroyImage (_THIS, SDL_Surface * screen)
148{
149    Dprintf ("enter NX_DestroyImage\n") ;
150
151    if (SDL_Image) SDL_free (SDL_Image) ;
152    if (Image_buff) SDL_free (Image_buff) ;
153    if (screen) screen -> pixels = NULL ;
154
155    Dprintf ("leave NX_DestroyImage\n") ;
156}
157
158int NX_ResizeImage (_THIS, SDL_Surface * screen, Uint32 flags)
159{
160    int            retval ;
161    GR_SCREEN_INFO si ;
162
163    Dprintf ("enter NX_ResizeImage\n") ;
164
165    NX_DestroyImage (this, screen) ;
166    retval = NX_SetupImage (this, screen) ;
167
168    GrGetScreenInfo (& si) ;
169    OffsetX = (si.cols - screen -> w) / 2 ;
170    OffsetY = (si.rows - screen -> h) / 2 ;
171
172#ifdef ENABLE_NANOX_DIRECT_FB
173    if (Clientfb) {
174        /* Get current window position and fb pointer*/
175        if (currently_fullscreen)
176            GrGetWindowFBInfo(FSwindow, &fbinfo);
177        else
178            GrGetWindowFBInfo(SDL_Window, &fbinfo);
179    }
180#endif
181    Dprintf ("leave NX_ResizeImage\n") ;
182    return retval ;
183}
184
185void NX_RefreshDisplay (_THIS)
186{
187    Dprintf ("enter NX_RefreshDisplay\n") ;
188
189    // Don't refresh a display that doesn't have an image (like GL)
190    if (! SDL_Image) {
191        return;
192    }
193
194#ifdef ENABLE_NANOX_DIRECT_FB
195    if (Clientfb) {
196        int j;
197        char *src, *dest = NULL;
198        int xinc, yinc, rowinc;
199
200        GrGetWindowFBInfo(SDL_Window, &fbinfo);
201
202        xinc = this -> screen -> format -> BytesPerPixel ;
203        yinc = this -> screen -> pitch ;
204
205        src = SDL_Image;
206        if (currently_fullscreen)
207            dest = fbinfo.winpixels + ((OffsetY * fbinfo.pitch) +
208                (OffsetX * fbinfo.bytespp));
209        else
210            dest = fbinfo.winpixels;
211        rowinc = xinc * this -> screen -> w;
212
213        for (j = this -> screen -> h; j > 0; -- j, src += yinc, dest += fbinfo.pitch)
214            SDL_memcpy (dest, src, rowinc) ;
215    }
216    else
217#endif
218    {
219        if (currently_fullscreen) {
220            GrArea (FSwindow, SDL_GC, OffsetX, OffsetY, this -> screen -> w,
221                this -> screen -> h, SDL_Image, pixel_type) ;
222        } else {
223            GrArea (SDL_Window, SDL_GC, 0, 0, this -> screen -> w,
224                this -> screen -> h, SDL_Image, pixel_type) ;
225        }
226    }
227    GrFlush();
228
229    Dprintf ("leave NX_RefreshDisplay\n") ;
230}
231