OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [mw/] [src/] [engine/] [devopen.c] - Blame information for rev 1775

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 673 markom
/*
2
 * Copyright (c) 1999, 2000, 2001 Greg Haerr <greg@censoft.com>
3
 * Portions Copyright (c) 1991 David I. Bell
4
 * Permission is granted to use, distribute, or modify this source,
5
 * provided that this copyright notice remains intact.
6
 *
7
 * Device-independent mid level screen device init routines
8
 *
9
 * These routines implement the smallest Microwindows engine level
10
 * interface to the screen driver.  By setting the NOFONTSORCLIPPING
11
 * config option, only these routines will be included, which can
12
 * be used to generate a low-level interface to the screen drivers
13
 * without dragging in any other GdXXX routines.
14
 */
15
#include <stdio.h>
16
#include <stdlib.h>
17 716 simons
#include <string.h>
18 673 markom
#include "device.h"
19
#include "swap.h"
20
 
21
#if MSDOS | ELKS
22
#define NOSTDPAL8
23
#endif
24
 
25
/*
26
 * The following define can change depending on the window manager
27
 * usage of colors and layout of the 8bpp palette devpal8.c.
28
 * Color entries below this value won't be overwritten by user
29
 * programs or bitmap display conversion tables.
30
 */
31
#define FIRSTUSERPALENTRY       24  /* first writable pal entry over 16 color*/
32
 
33
       MWPIXELVAL gr_foreground;      /* current foreground color */
34
       MWPIXELVAL gr_background;      /* current background color */
35
       MWBOOL   gr_usebg;           /* TRUE if background drawn in pixmaps */
36
       int      gr_mode = MWMODE_COPY;      /* drawing mode */
37
/*static*/ MWPALENTRY   gr_palette[256];    /* current palette*/
38
/*static*/ int  gr_firstuserpalentry;/* first user-changable palette entry*/
39
/*static*/ int  gr_nextpalentry;    /* next available palette entry*/
40
static int      gr_pixtype;         /* screen pixel format*/
41
static long     gr_ncolors;         /* screen # colors*/
42
 
43
/*
44
 * Open low level graphics driver
45
 */
46
PSD
47
GdOpenScreen(void)
48
{
49
        PSD                     psd;
50
        MWPALENTRY *            stdpal;
51
        MWSCREENINFO            sinfo;
52
 
53
        psd = scrdev.Open(&scrdev);
54
        if (!psd)
55
                return NULL;
56
        GdGetScreenInfo(psd, &sinfo);
57
        gr_pixtype = sinfo.pixtype;
58
        gr_ncolors = sinfo.ncolors;
59
 
60
        /* assume no user changable palette entries*/
61
        gr_firstuserpalentry = (int)psd->ncolors;
62
 
63
        /* set palette according to system colors and devpalX.c*/
64
        switch((int)psd->ncolors) {
65
 
66
#if !defined(NOSTDPAL1) /* don't require stdpal1 if not needed */
67
        case 2:         /* 1bpp*/
68
        {
69
                extern MWPALENTRY       mwstdpal1[2];
70
                stdpal = mwstdpal1;
71
        }
72
        break;
73
#endif
74
 
75
#if !defined(NOSTDPAL2) /* don't require stdpal2 if not needed */
76
        case 4:         /* 2bpp*/
77
        {
78
                extern MWPALENTRY       mwstdpal2[4];
79
                stdpal = mwstdpal2;
80
        }
81
        break;
82
#endif
83
 
84
#if !defined(NOSTDPAL4)
85
        /* don't require stdpal4 if not needed */
86
        case 8:         /* 3bpp - not fully supported*/
87
        case 16:        /* 4bpp*/
88
        {
89
                extern MWPALENTRY       mwstdpal4[16];
90
                stdpal = mwstdpal4;
91
        }
92
        break;
93
#endif
94
 
95
#if !defined(NOSTDPAL8) /* don't require large stdpal8 if not needed */
96
        case 256:       /* 8bpp*/
97
        {
98
                extern MWPALENTRY       mwstdpal8[256];
99
#if xxxALPHABLEND
100
                /* don't change uniform palette if alpha blending*/
101
                gr_firstuserpalentry = 256;
102
#else
103
                /* start after last system-reserved color*/
104
                gr_firstuserpalentry = FIRSTUSERPALENTRY;
105
#endif
106
                stdpal = mwstdpal8;
107
        }
108
        break;
109
#endif  /* !defined(NOSTDPAL8)*/
110
 
111
        default:        /* truecolor*/
112
                /* no palette*/
113
                gr_firstuserpalentry = 0;
114
                stdpal = NULL;
115
        }
116
 
117
        /* reset next user palette entry, write hardware palette*/
118
        GdResetPalette();
119
        GdSetPalette(psd, 0, (int)psd->ncolors, stdpal);
120
#if xxxALPHABLEND
121
        /* one-time create alpha lookup table for 8bpp systems (takes ~1 sec)*/
122
        if(psd->ncolors == 256)
123
                init_alpha_lookup();
124
#endif
125
 
126
#if !NOFONTSORCLIPPING
127
        /* init local vars*/
128
        GdSetMode(MWMODE_COPY);
129
        GdSetForeground(GdFindColor(MWRGB(255, 255, 255)));     /* WHITE*/
130
        GdSetBackground(GdFindColor(MWRGB(0, 0, 0)));              /* BLACK*/
131
        GdSetUseBackground(TRUE);
132
        GdSetFont(GdCreateFont(psd, MWFONT_SYSTEM_VAR, 0, NULL));
133
#if DYNAMICREGIONS
134
        GdSetClipRegion(psd,
135
                GdAllocRectRegion(0, 0, psd->xvirtres, psd->yvirtres));
136
#else
137
        GdSetClipRects(psd, 0, NULL);
138
#endif /* DYNAMICREGIONS*/
139
#endif /* NOFONTSORCLIPPING*/
140
 
141
        /* fill black (actually fill to first palette entry or truecolor 0*/
142
        psd->FillRect(psd, 0, 0, psd->xvirtres-1, psd->yvirtres-1, 0);
143
        return psd;
144
}
145
 
146
/*
147
 * Close low level graphics driver
148
 */
149
void
150
GdCloseScreen(PSD psd)
151
{
152
        psd->Close(psd);
153
}
154
 
155
/* Set dynamic screen portrait mode, return new mode*/
156
int
157
GdSetPortraitMode(PSD psd, int portraitmode)
158
{
159
        /* set portrait mode if supported*/
160
        if (psd->SetPortrait)
161
                psd->SetPortrait(psd, portraitmode);
162
        return psd->portrait;
163
}
164
 
165
/*
166
 * Return about the screen.
167
 */
168
void
169
GdGetScreenInfo(PSD psd, PMWSCREENINFO psi)
170
{
171
        psd->GetScreenInfo(psd, psi);
172
        GdGetButtonInfo(&psi->buttons);
173
        GdGetModifierInfo(&psi->modifiers, NULL);
174
        GdGetCursorPos(&psi->xpos, &psi->ypos);
175
}
176
 
177
/* reset palette to empty except for system colors*/
178
void
179
GdResetPalette(void)
180
{
181
        /* note: when palette entries are changed, all
182
         * windows may need to be redrawn
183
         */
184
        gr_nextpalentry = gr_firstuserpalentry;
185
}
186
 
187
/* set the system palette section to the passed palette entries*/
188
void
189
GdSetPalette(PSD psd, int first, int count, MWPALENTRY *palette)
190
{
191
        int     i;
192
 
193
        /* no palette management needed if running truecolor*/
194
        if(psd->pixtype != MWPF_PALETTE)
195
                return;
196
 
197
        /* bounds check against # of device color entries*/
198
        if(first + count > (int)psd->ncolors)
199
                count = (int)psd->ncolors - first;
200
        if(count >= 0 && first < (int)psd->ncolors) {
201
                psd->SetPalette(psd, first, count, palette);
202
 
203
                /* copy palette for GdFind*Color*/
204
                for(i=0; i<count; ++i)
205
                        gr_palette[i+first] = palette[i];
206
        }
207
}
208
 
209
/* get system palette entries, return count*/
210
int
211
GdGetPalette(PSD psd, int first, int count, MWPALENTRY *palette)
212
{
213
        int     i;
214
 
215
        /* no palette if running truecolor*/
216
        if(psd->pixtype != MWPF_PALETTE)
217
                return 0;
218
 
219
        /* bounds check against # of device color entries*/
220
        if(first + count > (int)psd->ncolors)
221
                if( (count = (int)psd->ncolors - first) <= 0)
222
                        return 0;
223
 
224
        for(i=0; i<count; ++i)
225
                *palette++ = gr_palette[i+first];
226
 
227
        return count;
228
}
229
 
230
/*
231
 * Convert a palette-independent value to a hardware color
232
 */
233
MWPIXELVAL
234
GdFindColor(MWCOLORVAL c)
235
{
236
        /*
237
         * Handle truecolor displays.  Note that the MWF_PALINDEX
238
         * bit is ignored when running truecolor drivers.
239
         */
240
        switch(gr_pixtype) {
241
        case MWPF_TRUECOLOR0888:
242
        case MWPF_TRUECOLOR888:
243
                /* create 24 bit 8/8/8 pixel (0x00RRGGBB) from RGB colorval*/
244
                /*RGB2PIXEL888(REDVALUE(c), GREENVALUE(c), BLUEVALUE(c))*/
245
                return COLOR2PIXEL888(c);
246
 
247
        case MWPF_TRUECOLOR565:
248
                /* create 16 bit 5/6/5 format pixel from RGB colorval*/
249
                /*RGB2PIXEL565(REDVALUE(c), GREENVALUE(c), BLUEVALUE(c))*/
250
                return COLOR2PIXEL565(c);
251
 
252
        case MWPF_TRUECOLOR555:
253
                /* create 16 bit 5/5/5 format pixel from RGB colorval*/
254
                /*RGB2PIXEL555(REDVALUE(c), GREENVALUE(c), BLUEVALUE(c))*/
255
                return COLOR2PIXEL555(c);
256
 
257
        case MWPF_TRUECOLOR332:
258
                /* create 8 bit 3/3/2 format pixel from RGB colorval*/
259
                /*RGB2PIXEL332(REDVALUE(c), GREENVALUE(c), BLUEVALUE(c))*/
260
                return COLOR2PIXEL332(c);
261
        }
262
 
263
        /* case MWPF_PALETTE: must be running 1, 2, 4 or 8 bit palette*/
264
 
265
        /*
266
         * Check if color is a palette index.  Note that the index
267
         * isn't error checked against the system palette, for speed.
268
         */
269
        if(c & MWF_PALINDEX)
270
                return (c & 0xff);
271
 
272
        /* search palette for closest match*/
273
        return GdFindNearestColor(gr_palette, (int)gr_ncolors, c);
274
}
275
 
276
/*
277
 * Search a palette to find the nearest color requested.
278
 * Uses a weighted squares comparison.
279
 */
280
MWPIXELVAL
281
GdFindNearestColor(MWPALENTRY *pal, int size, MWCOLORVAL cr)
282
{
283
        MWPALENTRY *    rgb;
284
        int             r, g, b;
285
        int             R, G, B;
286
        long            diff = 0x7fffffffL;
287
        long            sq;
288
        int             best = 0;
289
 
290
        r = REDVALUE(cr);
291
        g = GREENVALUE(cr);
292
        b = BLUEVALUE(cr);
293
        for(rgb=pal; diff && rgb < &pal[size]; ++rgb) {
294
                R = rgb->r - r;
295
                G = rgb->g - g;
296
                B = rgb->b - b;
297
#if 1
298
                /* speedy linear distance method*/
299
                sq = abs(R) + abs(G) + abs(B);
300
#else
301
                /* slower distance-cubed with luminance adjustment*/
302
                /* gray is .30R + .59G + .11B*/
303
                /* = (R*77 + G*151 + B*28)/256*/
304
                sq = (long)R*R*30*30 + (long)G*G*59*59 + (long)B*B*11*11;
305
#endif
306
 
307
                if(sq < diff) {
308
                        best = rgb - pal;
309
                        if((diff = sq) == 0)
310
                                return best;
311
                }
312
        }
313
        return best;
314
}
315
 
316
#if !VXWORKS
317
#include <unistd.h>
318
#include <fcntl.h>
319
/*
320
 * Create .bmp file from framebuffer data
321
 *
322
 * 1, 4, 8, 16, 24 and 32 bpp supported
323
 */
324
#define BI_RGB          0L
325
#define BI_RLE8         1L
326
#define BI_RLE4         2L
327
#define BI_BITFIELDS    3L
328
 
329
typedef unsigned char   BYTE;
330
typedef unsigned short  WORD;
331
typedef unsigned long   DWORD;
332
typedef long            LONG;
333
 
334
#pragma pack(1)
335
/* windows style bmp*/
336
typedef struct {
337
        /* BITMAPFILEHEADER*/
338
        BYTE    bfType[2];
339
        DWORD   bfSize;
340
        WORD    bfReserved1;
341
        WORD    bfReserved2;
342
        DWORD   bfOffBits;
343
        /* BITMAPINFOHEADER*/
344
        DWORD   BiSize;
345
        LONG    BiWidth;
346
        LONG    BiHeight;
347
        WORD    BiPlanes;
348
        WORD    BiBitCount;
349
        DWORD   BiCompression;
350
        DWORD   BiSizeImage;
351
        LONG    BiXpelsPerMeter;
352
        LONG    BiYpelsPerMeter;
353
        DWORD   BiClrUsed;
354
        DWORD   BiClrImportant;
355
} BMPHEAD;
356
#pragma pack()
357
 
358
/* r/g/b masks for non-palette bitmaps*/
359
#define RMASK332        0xe0
360
#define GMASK332        0x1c
361
#define BMASK332        0x03
362
#define RMASK555        0x7c00
363
#define GMASK555        0x03e0
364
#define BMASK555        0x001f
365
#define RMASK565        0xf800
366
#define GMASK565        0x07e0
367
#define BMASK565        0x001f
368
#define RMASK888        0xff0000
369
#define GMASK888        0x00ff00
370
#define BMASK888        0x0000ff
371
 
372
#if defined(HAVE_FILEIO)
373
static void
374
putsw(unsigned long dw, FILE *ofp)
375
{
376
        /* little-endian storage of shortword*/
377
        putc((unsigned char)dw, ofp);
378
        dw >>= 8;
379
        putc((unsigned char)dw, ofp);
380
}
381
 
382
static void
383
putdw(unsigned long dw, FILE *ofp)
384
{
385
        /* little-endian storage of longword*/
386
        putc((unsigned char)dw, ofp);
387
        dw >>= 8;
388
        putc((unsigned char)dw, ofp);
389
        dw >>= 8;
390
        putc((unsigned char)dw, ofp);
391
        dw >>= 8;
392
        putc((unsigned char)dw, ofp);
393
}
394
#endif /* HAVE_FILEIO*/
395
 
396
/* create .bmp file from framebuffer data*/
397
int
398
GdCaptureScreen(char *path)
399
{
400
#if defined(HAVE_FILEIO)
401
        int     ifd, i, j;
402
        FILE *  ofp;
403
        int     cx, cy, extra, bpp, bytespp, ncolors, sizecolortable;
404
        unsigned long rmask, gmask, bmask;
405
        unsigned char *cptr;
406
        unsigned short *sptr;
407
        unsigned long *lptr;
408
        BMPHEAD bmp;
409
        unsigned char buf[2048*4];
410
 
411
        ofp = fopen(path, "wb");
412
        if (!ofp)
413
                return 1;
414
        ifd = open("/dev/fb0", 0);
415
 
416
        cx = scrdev.xvirtres;
417
        cy = scrdev.yvirtres;
418
        bpp = scrdev.bpp;
419
        bytespp = (bpp+7)/8;
420
 
421
        /* dword right padded*/
422
        extra = (cx*bytespp) & 3;
423
        if (extra)
424
                extra = 4 - extra;
425
        ncolors = (bpp <= 8)? (1<<bpp): 0;
426
        /* color table is either palette or 3 longword r/g/b masks*/
427
        sizecolortable = ncolors? ncolors*4: 3*4;
428
        if (bpp == 24)
429
                sizecolortable = 0;      /* special case 24bpp has no table*/
430
 
431
        /* fill out bmp header*/
432
        memset(&bmp, 0, sizeof(bmp));
433
        bmp.bfType[0] = 'B';
434
        bmp.bfType[1] = 'M';
435
        bmp.bfSize = dwswap(sizeof(bmp) + sizecolortable + (long)(cx+extra)*cy*bytespp);
436
        bmp.bfOffBits = dwswap(sizeof(bmp) + sizecolortable);
437
        bmp.BiSize = dwswap(40);
438
        bmp.BiWidth = dwswap(cx);
439
        bmp.BiHeight = dwswap(cy);
440
        bmp.BiPlanes = wswap(1);
441
        bmp.BiBitCount = wswap(bpp);
442
        bmp.BiCompression = dwswap((bpp==16 || bpp==32)? BI_BITFIELDS: BI_RGB);
443
        bmp.BiSizeImage = dwswap((long)(cx+extra)*cy*bytespp);
444
        bmp.BiClrUsed = dwswap((bpp <= 8)? ncolors: 0);
445
        /*bmp.BiClrImportant = 0;*/
446
 
447
        /* write header*/
448
        fwrite(&bmp, sizeof(bmp), 1, ofp);
449
 
450
        /* write colortable*/
451
        if (sizecolortable) {
452
                if(bpp <= 8) {
453
                        /* write palette*/
454
                        for(i=0; i<ncolors; i++) {
455
                                putc(gr_palette[i].b, ofp);
456
                                putc(gr_palette[i].g, ofp);
457
                                putc(gr_palette[i].r, ofp);
458
                                putc(0, ofp);
459
                        }
460
                } else {
461
                        /* write 3 r/g/b masks*/
462
                        switch (gr_pixtype) {
463
                        case MWPF_TRUECOLOR0888:
464
                        default:
465
                                rmask = RMASK888;
466
                                gmask = GMASK888;
467
                                bmask = BMASK888;
468
                                break;
469
                        case MWPF_TRUECOLOR565:
470
                                rmask = RMASK565;
471
                                gmask = GMASK565;
472
                                bmask = BMASK565;
473
                                break;
474
                        case MWPF_TRUECOLOR555:
475
                                rmask = RMASK555;
476
                                gmask = GMASK555;
477
                                bmask = BMASK555;
478
                                break;
479
                        case MWPF_TRUECOLOR332:
480
                                rmask = RMASK332;
481
                                gmask = GMASK332;
482
                                bmask = BMASK332;
483
                                break;
484
                        }
485
                        putdw(rmask, ofp);
486
                        putdw(gmask, ofp);
487
                        putdw(bmask, ofp);
488
                }
489
        }
490
 
491
        /* write image data, upside down ;)*/
492
        for(i=cy-1; i>=0; --i) {
493
                long base = sizeof(bmp) + sizecolortable + (long)i*cx*bytespp;
494
                fseek(ofp, base, SEEK_SET);
495
                read(ifd, buf, cx*bytespp);
496
                switch (bpp) {
497
                case 32:
498
                        lptr = (unsigned long *)buf;
499
                        for(j=0; j<cx; ++j)
500
                                putdw(*lptr++, ofp);
501
                        break;
502
                case 24:
503
                        cptr = (unsigned char *)buf;
504
                        for(j=0; j<cx; ++j) {
505
                                putc(*cptr++, ofp);
506
                                putc(*cptr++, ofp);
507
                                putc(*cptr++, ofp);
508
                        }
509
                        break;
510
                case 16:
511
                        sptr = (unsigned short *)buf;
512
                        for(j=0; j<cx; ++j)
513
                                putsw(*sptr++, ofp);
514
                        break;
515
                default:
516
                        cptr = (unsigned char *)buf;
517
                        for(j=0; j<cx; ++j)
518
                                putc(*cptr++, ofp);
519
                        break;
520
                }
521
                for(j=0; j<extra; ++j)
522
                        putc(0, ofp);            /* DWORD pad each line*/
523
        }
524
 
525
        fclose(ofp);
526
        close(ifd);
527
#endif /* HAVE_FILEIO*/
528
        return 0;
529
}
530
#endif /* !VXWORKS*/

powered by: WebSVN 2.1.0

© copyright 1999-2025 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.