wing.c 9.41 KB
Newer Older
Alexandre Julliard's avatar
Alexandre Julliard committed
1
/*
Alexandre Julliard's avatar
Alexandre Julliard committed
2
 * WinG support
Alexandre Julliard's avatar
Alexandre Julliard committed
3
 *
4 5 6 7 8 9 10 11 12 13 14 15 16 17
 * Copyright (C) Robert Pouliot <krynos@clic.net>
 *
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
18
 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
Alexandre Julliard's avatar
Alexandre Julliard committed
19 20
 */

21 22
#include "config.h"

23 24
#include <stdarg.h>

25
#include "windef.h"
26 27
#include "winbase.h"
#include "wingdi.h"
Michael Stefaniuc's avatar
Michael Stefaniuc committed
28
#include "wownt32.h"
29
#include "wine/wingdi16.h"
30
#include "wine/list.h"
31
#include "wine/debug.h"
32

33
WINE_DEFAULT_DEBUG_CHANNEL(wing);
34

35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87
struct dib_segptr_bits
{
    struct list entry;
    HBITMAP   bmp;
    WORD      sel;
    WORD      count;
};

static struct list dib_segptr_list = LIST_INIT( dib_segptr_list );

/* remove saved bits for bitmaps that no longer exist */
static void cleanup_segptr_bits(void)
{
    unsigned int i;
    struct dib_segptr_bits *bits, *next;

    LIST_FOR_EACH_ENTRY_SAFE( bits, next, &dib_segptr_list, struct dib_segptr_bits, entry )
    {
        if (GetObjectType( bits->bmp ) == OBJ_BITMAP) continue;
        for (i = 0; i < bits->count; i++) FreeSelector16( bits->sel + (i << __AHSHIFT) );
        list_remove( &bits->entry );
        HeapFree( GetProcessHeap(), 0, bits );
    }
}

static SEGPTR alloc_segptr_bits( HBITMAP bmp, void *bits32 )
{
    DIBSECTION dib;
    unsigned int i, size;
    struct dib_segptr_bits *bits;

    cleanup_segptr_bits();

    if (!(bits = HeapAlloc( GetProcessHeap(), 0, sizeof(*bits) ))) return 0;

    GetObjectW( bmp, sizeof(dib), &dib );
    size = dib.dsBm.bmHeight * dib.dsBm.bmWidthBytes;

    /* calculate number of sel's needed for size with 64K steps */
    bits->bmp   = bmp;
    bits->count = (size + 0xffff) / 0x10000;
    bits->sel   = AllocSelectorArray16( bits->count );

    for (i = 0; i < bits->count; i++)
    {
        SetSelectorBase(bits->sel + (i << __AHSHIFT), (DWORD)bits32 + i * 0x10000);
        SetSelectorLimit16(bits->sel + (i << __AHSHIFT), size - 1); /* yep, limit is correct */
        size -= 0x10000;
    }
    list_add_head( &dib_segptr_list, &bits->entry );
    return MAKESEGPTR( bits->sel, 0 );
}

Jon Griffiths's avatar
Jon Griffiths committed
88 89 90 91 92 93 94 95 96 97
/*************************************************************************
 * WING {WING}
 *
 * The Windows Game dll provides a number of functions designed to allow
 * programmers to bypass Gdi and write directly to video memory. The intention
 * was to bolster the use of Windows as a gaming platform and remove the
 * need for Dos based games using 32 bit Dos extenders.
 *
 * This initial approach could not compete with the performance of Dos games
 * (such as Doom and Warcraft) at the time, and so this dll was eventually
Francois Gouget's avatar
Francois Gouget committed
98 99
 * superseded by DirectX. It should not be used by new applications, and is
 * provided only for compatibility with older Windows programs.
Jon Griffiths's avatar
Jon Griffiths committed
100
 */
Alexandre Julliard's avatar
Alexandre Julliard committed
101

Alexandre Julliard's avatar
Alexandre Julliard committed
102 103 104 105 106
typedef enum WING_DITHER_TYPE
{
  WING_DISPERSED_4x4, WING_DISPERSED_8x8, WING_CLUSTERED_4x4
} WING_DITHER_TYPE;

Alexandre Julliard's avatar
Alexandre Julliard committed
107
/***********************************************************************
Patrik Stridvall's avatar
Patrik Stridvall committed
108
 *          WinGCreateDC	(WING.1001)
Jon Griffiths's avatar
Jon Griffiths committed
109 110 111 112 113 114 115 116 117
 *
 * Create a new WinG device context.
 *
 * PARAMS
 *  None.
 *
 * RETURNS
 *  Success: A handle to the created device context.
 *  Failure: A NULL handle.
Alexandre Julliard's avatar
Alexandre Julliard committed
118
 */
Alexandre Julliard's avatar
Alexandre Julliard committed
119
HDC16 WINAPI WinGCreateDC16(void)
Alexandre Julliard's avatar
Alexandre Julliard committed
120
{
121
    TRACE("(void)\n");
122
    return HDC_16( CreateCompatibleDC( 0 ));
Alexandre Julliard's avatar
Alexandre Julliard committed
123
}
Alexandre Julliard's avatar
Alexandre Julliard committed
124 125

/***********************************************************************
Patrik Stridvall's avatar
Patrik Stridvall committed
126
 *  WinGRecommendDIBFormat    (WING.1002)
Jon Griffiths's avatar
Jon Griffiths committed
127 128 129 130 131 132 133 134 135
 *
 * Get the recommended format of bitmaps for the current display.
 *
 * PARAMS
 *  bmpi [O] Destination for format information
 *
 * RETURNS
 *  Success: TRUE. bmpi is filled with the best (fastest) bitmap format
 *  Failure: FALSE, if bmpi is NULL.
Alexandre Julliard's avatar
Alexandre Julliard committed
136
 */
Brad Pepers's avatar
Brad Pepers committed
137
BOOL16 WINAPI WinGRecommendDIBFormat16(BITMAPINFO *bmpi)
Alexandre Julliard's avatar
Alexandre Julliard committed
138
{
139
    TRACE("(%p)\n", bmpi);
140

Brad Pepers's avatar
Brad Pepers committed
141 142 143 144 145 146
    if (!bmpi)
	return FALSE;

    bmpi->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
    bmpi->bmiHeader.biWidth = 320;
    bmpi->bmiHeader.biHeight = -1;
147 148
    bmpi->bmiHeader.biPlanes = 1;
    bmpi->bmiHeader.biBitCount = 8;
Brad Pepers's avatar
Brad Pepers committed
149 150 151 152 153 154
    bmpi->bmiHeader.biCompression = BI_RGB;
    bmpi->bmiHeader.biSizeImage = 0;
    bmpi->bmiHeader.biXPelsPerMeter = 0;
    bmpi->bmiHeader.biYPelsPerMeter = 0;
    bmpi->bmiHeader.biClrUsed = 0;
    bmpi->bmiHeader.biClrImportant = 0;
155

Alexandre Julliard's avatar
Alexandre Julliard committed
156
    return TRUE;
157
}
Alexandre Julliard's avatar
Alexandre Julliard committed
158 159

/***********************************************************************
Patrik Stridvall's avatar
Patrik Stridvall committed
160
 *        WinGCreateBitmap    (WING.1003)
Jon Griffiths's avatar
Jon Griffiths committed
161 162 163 164 165 166 167 168 169 170 171
 *
 * Create a new WinG bitmap.
 *
 * PARAMS
 *  hdc  [I] WinG device context
 *  bmpi [I] Information about the bitmap
 *  bits [I] Location of the bitmap image data
 *
 * RETURNS
 *  Success: A handle to the created bitmap.
 *  Failure: A NULL handle.
Alexandre Julliard's avatar
Alexandre Julliard committed
172
 */
173
HBITMAP16 WINAPI WinGCreateBitmap16(HDC16 hdc, BITMAPINFO *bmpi, SEGPTR *bits)
Alexandre Julliard's avatar
Alexandre Julliard committed
174
{
175 176 177 178 179 180
    LPVOID bits32;
    HBITMAP hbitmap;

    TRACE("(%d,%p,%p): create %dx%dx%d bitmap\n", hdc, bmpi, bits,
          bmpi->bmiHeader.biWidth, bmpi->bmiHeader.biHeight, bmpi->bmiHeader.biPlanes);

181
    hbitmap = CreateDIBSection( HDC_32(hdc), bmpi, DIB_RGB_COLORS, &bits32, 0, 0 );
182 183
    if (hbitmap)
    {
184 185
        SEGPTR segptr = alloc_segptr_bits( hbitmap, bits32 );
        if (bits) *bits = segptr;
186 187
    }
    return HBITMAP_16(hbitmap);
188
}
Alexandre Julliard's avatar
Alexandre Julliard committed
189

Alexandre Julliard's avatar
Alexandre Julliard committed
190
/***********************************************************************
Alexandre Julliard's avatar
Alexandre Julliard committed
191
 *  WinGGetDIBPointer   (WING.1004)
Alexandre Julliard's avatar
Alexandre Julliard committed
192
 */
Alexandre Julliard's avatar
Alexandre Julliard committed
193
SEGPTR WINAPI WinGGetDIBPointer16(HBITMAP16 hWinGBitmap, BITMAPINFO* bmpi)
Alexandre Julliard's avatar
Alexandre Julliard committed
194
{
195 196 197 198 199 200 201
    struct dib_segptr_bits *bits;

    if (bmpi) FIXME( "%04x %p: setting BITMAPINFO not supported\n", hWinGBitmap, bmpi );

    LIST_FOR_EACH_ENTRY( bits, &dib_segptr_list, struct dib_segptr_bits, entry )
        if (HBITMAP_16(bits->bmp) == hWinGBitmap) return MAKESEGPTR( bits->sel, 0 );

202
    return 0;
Alexandre Julliard's avatar
Alexandre Julliard committed
203 204 205
}

/***********************************************************************
206
 *  WinGSetDIBColorTable   (WING.1006)
Jon Griffiths's avatar
Jon Griffiths committed
207 208 209 210 211 212 213 214 215 216 217
 *
 * Set all or part of the color table for a WinG device context.
 *
 * PARAMS
 *  hdc    [I] WinG device context
 *  start  [I] Start color
 *  num    [I] Number of entries to set
 *  colors [I] Array of color data
 *
 * RETURNS
 *  The number of entries set.
Alexandre Julliard's avatar
Alexandre Julliard committed
218
 */
219
UINT16 WINAPI WinGSetDIBColorTable16(HDC16 hdc, UINT16 start, UINT16 num, RGBQUAD *colors)
Alexandre Julliard's avatar
Alexandre Julliard committed
220
{
221
    TRACE("(%d,%d,%d,%p)\n", hdc, start, num, colors);
222
    return SetDIBColorTable( HDC_32(hdc), start, num, colors );
Alexandre Julliard's avatar
Alexandre Julliard committed
223 224 225
}

/***********************************************************************
Patrik Stridvall's avatar
Patrik Stridvall committed
226
 *  WinGGetDIBColorTable   (WING.1005)
Jon Griffiths's avatar
Jon Griffiths committed
227 228 229 230 231 232 233 234 235 236 237
 *
 * Get all or part of the color table for a WinG device context.
 *
 * PARAMS
 *  hdc    [I] WinG device context
 *  start  [I] Start color
 *  num    [I] Number of entries to set
 *  colors [O] Destination for the array of color data
 *
 * RETURNS
 *  The number of entries retrieved.
Alexandre Julliard's avatar
Alexandre Julliard committed
238
 */
239
UINT16 WINAPI WinGGetDIBColorTable16(HDC16 hdc, UINT16 start, UINT16 num, RGBQUAD *colors)
Alexandre Julliard's avatar
Alexandre Julliard committed
240
{
241
    TRACE("(%d,%d,%d,%p)\n", hdc, start, num, colors);
242
    return GetDIBColorTable( HDC_32(hdc), start, num, colors );
Alexandre Julliard's avatar
Alexandre Julliard committed
243 244
}

Alexandre Julliard's avatar
Alexandre Julliard committed
245
/***********************************************************************
Patrik Stridvall's avatar
Patrik Stridvall committed
246
 *  WinGCreateHalfTonePalette   (WING.1007)
Jon Griffiths's avatar
Jon Griffiths committed
247 248 249 250 251 252 253 254 255
 *
 * Create a half tone palette.
 *
 * PARAMS
 *  None.
 *
 * RETURNS
 *  Success: A handle to the created palette.
 *  Failure: A NULL handle.
Alexandre Julliard's avatar
Alexandre Julliard committed
256
 */
Alexandre Julliard's avatar
Alexandre Julliard committed
257
HPALETTE16 WINAPI WinGCreateHalfTonePalette16(void)
Alexandre Julliard's avatar
Alexandre Julliard committed
258
{
259 260
    HDC hdc = CreateCompatibleDC(0);
    HPALETTE16 ret = HPALETTE_16( CreateHalftonePalette( hdc ));
261
    TRACE("(void)\n");
262
    DeleteDC( hdc );
263
    return ret;
Alexandre Julliard's avatar
Alexandre Julliard committed
264 265 266
}

/***********************************************************************
Patrik Stridvall's avatar
Patrik Stridvall committed
267
 *  WinGCreateHalfToneBrush   (WING.1008)
Jon Griffiths's avatar
Jon Griffiths committed
268 269 270 271 272 273 274 275 276 277 278
 *
 * Create a half tone brush for a WinG device context.
 *
 * PARAMS
 *  winDC [I] WinG device context
 *  col   [I] Color
 *  type  [I] Desired dithering type.
 *
 * RETURNS
 *  Success: A handle to the created brush.
 *  Failure: A NULL handle.
Alexandre Julliard's avatar
Alexandre Julliard committed
279
 */
Brad Pepers's avatar
Brad Pepers committed
280
HBRUSH16 WINAPI WinGCreateHalfToneBrush16(HDC16 winDC, COLORREF col,
Alexandre Julliard's avatar
Alexandre Julliard committed
281
                                            WING_DITHER_TYPE type)
Alexandre Julliard's avatar
Alexandre Julliard committed
282
{
283
    TRACE("(%d,%d,%d)\n", winDC, col, type);
284
    return HBRUSH_16( CreateSolidBrush( col ));
Alexandre Julliard's avatar
Alexandre Julliard committed
285 286
}

Alexandre Julliard's avatar
Alexandre Julliard committed
287
/***********************************************************************
Patrik Stridvall's avatar
Patrik Stridvall committed
288
 *  WinGStretchBlt   (WING.1009)
Jon Griffiths's avatar
Jon Griffiths committed
289 290
 *
 * See StretchBlt16.
Alexandre Julliard's avatar
Alexandre Julliard committed
291
 */
Alexandre Julliard's avatar
Alexandre Julliard committed
292 293 294 295
BOOL16 WINAPI WinGStretchBlt16(HDC16 destDC, INT16 xDest, INT16 yDest,
                               INT16 widDest, INT16 heiDest,
                               HDC16 srcDC, INT16 xSrc, INT16 ySrc,
                               INT16 widSrc, INT16 heiSrc)
Alexandre Julliard's avatar
Alexandre Julliard committed
296
{
297
    BOOL retval;
298
    TRACE("(%d,%d,...)\n", destDC, srcDC);
299 300 301 302
    SetStretchBltMode( HDC_32(destDC), COLORONCOLOR );
    retval = StretchBlt( HDC_32(destDC), xDest, yDest, widDest, heiDest,
                         HDC_32(srcDC), xSrc, ySrc, widSrc, heiSrc, SRCCOPY );
    SetStretchBltMode( HDC_32(destDC), BLACKONWHITE );
Peter Ganten's avatar
Peter Ganten committed
303
    return retval;
Alexandre Julliard's avatar
Alexandre Julliard committed
304 305 306
}

/***********************************************************************
Patrik Stridvall's avatar
Patrik Stridvall committed
307
 *  WinGBitBlt   (WING.1010)
Jon Griffiths's avatar
Jon Griffiths committed
308 309
 *
 * See BitBlt16.
Alexandre Julliard's avatar
Alexandre Julliard committed
310
 */
Alexandre Julliard's avatar
Alexandre Julliard committed
311 312 313
BOOL16 WINAPI WinGBitBlt16(HDC16 destDC, INT16 xDest, INT16 yDest,
                           INT16 widDest, INT16 heiDest, HDC16 srcDC,
                           INT16 xSrc, INT16 ySrc)
Alexandre Julliard's avatar
Alexandre Julliard committed
314
{
315
    TRACE("(%d,%d,...)\n", destDC, srcDC);
316
    return BitBlt( HDC_32(destDC), xDest, yDest, widDest, heiDest, HDC_32(srcDC), xSrc, ySrc, SRCCOPY );
Alexandre Julliard's avatar
Alexandre Julliard committed
317
}