Added StretchDIBits for the PostScript driver.
This commit is contained in:
parent
3f89809d68
commit
44a79c4925
|
@ -8,22 +8,209 @@
|
|||
#include "gdi.h"
|
||||
#include "psdrv.h"
|
||||
#include "debug.h"
|
||||
#include "bitmap.h"
|
||||
#include "winbase.h"
|
||||
|
||||
|
||||
/***************************************************************************
|
||||
* PSDRV_WriteImageHeader
|
||||
*
|
||||
* Helper for PSDRV_StretchDIBits
|
||||
*
|
||||
* BUGS
|
||||
* Uses level 2 PostScript
|
||||
*/
|
||||
|
||||
static BOOL PSDRV_WriteImageHeader(DC *dc, const BITMAPINFO *info, INT xDst,
|
||||
INT yDst, INT widthDst, INT heightDst,
|
||||
INT widthSrc, INT heightSrc)
|
||||
{
|
||||
COLORREF map[256];
|
||||
int i;
|
||||
|
||||
switch(info->bmiHeader.biBitCount) {
|
||||
case 8:
|
||||
PSDRV_WriteIndexColorSpaceBegin(dc, 255);
|
||||
for(i = 0; i < 256; i++) {
|
||||
map[i] = info->bmiColors[i].rgbRed |
|
||||
info->bmiColors[i].rgbGreen << 8 |
|
||||
info->bmiColors[i].rgbBlue << 16;
|
||||
}
|
||||
PSDRV_WriteRGB(dc, map, 256);
|
||||
PSDRV_WriteIndexColorSpaceEnd(dc);
|
||||
break;
|
||||
|
||||
case 4:
|
||||
PSDRV_WriteIndexColorSpaceBegin(dc, 15);
|
||||
for(i = 0; i < 16; i++) {
|
||||
map[i] = info->bmiColors[i].rgbRed |
|
||||
info->bmiColors[i].rgbGreen << 8 |
|
||||
info->bmiColors[i].rgbBlue << 16;
|
||||
}
|
||||
PSDRV_WriteRGB(dc, map, 16);
|
||||
PSDRV_WriteIndexColorSpaceEnd(dc);
|
||||
break;
|
||||
|
||||
case 1:
|
||||
PSDRV_WriteIndexColorSpaceBegin(dc, 1);
|
||||
for(i = 0; i < 2; i++) {
|
||||
map[i] = info->bmiColors[i].rgbRed |
|
||||
info->bmiColors[i].rgbGreen << 8 |
|
||||
info->bmiColors[i].rgbBlue << 16;
|
||||
}
|
||||
PSDRV_WriteRGB(dc, map, 2);
|
||||
PSDRV_WriteIndexColorSpaceEnd(dc);
|
||||
break;
|
||||
|
||||
case 15:
|
||||
case 16:
|
||||
case 24:
|
||||
case 32:
|
||||
{
|
||||
PSCOLOR pscol;
|
||||
pscol.type = PSCOLOR_RGB;
|
||||
pscol.value.rgb.r = pscol.value.rgb.g = pscol.value.rgb.b = 0.0;
|
||||
PSDRV_WriteSetColor(dc, &pscol);
|
||||
break;
|
||||
}
|
||||
|
||||
default:
|
||||
FIXME(psdrv, "Not implemented yet\n");
|
||||
return FALSE;
|
||||
break;
|
||||
}
|
||||
|
||||
PSDRV_WriteImageDict(dc, info->bmiHeader.biBitCount, xDst, yDst,
|
||||
widthDst, heightDst, widthSrc, heightSrc);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************
|
||||
*
|
||||
* PSDRV_StretchDIBits
|
||||
*
|
||||
* BUGS
|
||||
* Doesn't work correctly if the DIB bits aren't byte aligned at the start of
|
||||
* a line - this affects 1 and 4 bit depths.
|
||||
* Compression not implemented.
|
||||
*/
|
||||
INT PSDRV_StretchDIBits( DC *dc, INT xDst, INT yDst, INT widthDst,
|
||||
INT heightDst, INT xSrc, INT ySrc,
|
||||
INT widthSrc, INT heightSrc, const void *bits,
|
||||
const BITMAPINFO *info, UINT wUsage, DWORD dwRop )
|
||||
INT heightDst, INT xSrc, INT ySrc,
|
||||
INT widthSrc, INT heightSrc, const void *bits,
|
||||
const BITMAPINFO *info, UINT wUsage, DWORD dwRop )
|
||||
{
|
||||
TRACE(psdrv, "(%d,%d %dx%d) -> (%d,%d %dx%d) on %08x. %d colour bits\n",
|
||||
xSrc, ySrc, widthSrc, heightSrc, xDst, yDst, widthDst, heightDst,
|
||||
dc->hSelf, info->bmiHeader.biBitCount);
|
||||
DWORD fullSrcWidth;
|
||||
INT widthbytes, fullSrcHeight;
|
||||
WORD bpp, compression;
|
||||
const char *ptr;
|
||||
INT line;
|
||||
|
||||
TRACE(psdrv, "%08x (%d,%d %dx%d) -> (%d,%d %dx%d)\n", dc->hSelf,
|
||||
xSrc, ySrc, widthSrc, heightSrc, xDst, yDst, widthDst, heightDst);
|
||||
|
||||
DIB_GetBitmapInfo((const BITMAPINFOHEADER *)info, &fullSrcWidth,
|
||||
&fullSrcHeight, &bpp, &compression);
|
||||
|
||||
widthbytes = DIB_GetDIBWidthBytes(fullSrcWidth, bpp);
|
||||
|
||||
TRACE(psdrv, "full size=%ldx%d bpp=%d compression=%d\n", fullSrcWidth,
|
||||
fullSrcHeight, bpp, compression);
|
||||
|
||||
|
||||
FIXME(psdrv, "stub\n");
|
||||
return FALSE;
|
||||
if(compression != BI_RGB) {
|
||||
FIXME(psdrv, "Compression not supported\n");
|
||||
return FALSE;
|
||||
}
|
||||
|
||||
|
||||
switch(bpp) {
|
||||
|
||||
case 1:
|
||||
PSDRV_WriteGSave(dc);
|
||||
PSDRV_WriteImageHeader(dc, info, xDst, yDst, widthDst, heightDst,
|
||||
widthSrc, heightSrc);
|
||||
ptr = bits;
|
||||
ptr += (ySrc * widthbytes);
|
||||
if(xSrc & 7 || widthSrc & 7)
|
||||
FIXME(psdrv, "This won't work...\n");
|
||||
for(line = 0; line < heightSrc; line++, ptr += widthbytes)
|
||||
PSDRV_WriteBytes(dc, ptr + xSrc/8, widthSrc/8);
|
||||
PSDRV_WriteGRestore(dc);
|
||||
break;
|
||||
|
||||
case 4:
|
||||
PSDRV_WriteGSave(dc);
|
||||
PSDRV_WriteImageHeader(dc, info, xDst, yDst, widthDst, heightDst,
|
||||
widthSrc, heightSrc);
|
||||
ptr = bits;
|
||||
ptr += (ySrc * widthbytes);
|
||||
if(xSrc & 1 || widthSrc & 1)
|
||||
FIXME(psdrv, "This won't work...\n");
|
||||
for(line = 0; line < heightSrc; line++, ptr += widthbytes)
|
||||
PSDRV_WriteBytes(dc, ptr + xSrc/2, widthSrc/2);
|
||||
PSDRV_WriteGRestore(dc);
|
||||
break;
|
||||
|
||||
case 8:
|
||||
PSDRV_WriteGSave(dc);
|
||||
PSDRV_WriteImageHeader(dc, info, xDst, yDst, widthDst, heightDst,
|
||||
widthSrc, heightSrc);
|
||||
ptr = bits;
|
||||
ptr += (ySrc * widthbytes);
|
||||
for(line = 0; line < heightSrc; line++, ptr += widthbytes)
|
||||
PSDRV_WriteBytes(dc, ptr + xSrc, widthSrc);
|
||||
PSDRV_WriteGRestore(dc);
|
||||
break;
|
||||
|
||||
case 15:
|
||||
case 16:
|
||||
PSDRV_WriteGSave(dc);
|
||||
PSDRV_WriteImageHeader(dc, info, xDst, yDst, widthDst, heightDst,
|
||||
widthSrc, heightSrc);
|
||||
|
||||
ptr = bits;
|
||||
ptr += (ySrc * widthbytes);
|
||||
for(line = 0; line < heightSrc; line++, ptr += widthbytes)
|
||||
PSDRV_WriteDIBits16(dc, (WORD *)ptr + xSrc, widthSrc);
|
||||
PSDRV_WriteGRestore(dc);
|
||||
break;
|
||||
|
||||
case 24:
|
||||
PSDRV_WriteGSave(dc);
|
||||
PSDRV_WriteImageHeader(dc, info, xDst, yDst, widthDst, heightDst,
|
||||
widthSrc, heightSrc);
|
||||
|
||||
ptr = bits;
|
||||
ptr += (ySrc * widthbytes);
|
||||
for(line = 0; line < heightSrc; line++, ptr += widthbytes)
|
||||
PSDRV_WriteDIBits24(dc, ptr + xSrc * 3, widthSrc);
|
||||
PSDRV_WriteGRestore(dc);
|
||||
break;
|
||||
|
||||
case 32:
|
||||
PSDRV_WriteGSave(dc);
|
||||
PSDRV_WriteImageHeader(dc, info, xDst, yDst, widthDst, heightDst,
|
||||
widthSrc, heightSrc);
|
||||
|
||||
ptr = bits;
|
||||
ptr += (ySrc * widthbytes);
|
||||
for(line = 0; line < heightSrc; line++, ptr += widthbytes)
|
||||
PSDRV_WriteDIBits32(dc, ptr + xSrc * 3, widthSrc);
|
||||
PSDRV_WriteGRestore(dc);
|
||||
break;
|
||||
|
||||
default:
|
||||
FIXME(psdrv, "Unsupported depth\n");
|
||||
return FALSE;
|
||||
|
||||
}
|
||||
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
|
|
@ -690,4 +690,167 @@ BOOL PSDRV_WriteRotate(DC *dc, float ang)
|
|||
return PSDRV_WriteSpool(dc, buf, strlen(buf));
|
||||
}
|
||||
|
||||
BOOL PSDRV_WriteIndexColorSpaceBegin(DC *dc, int size)
|
||||
{
|
||||
char buf[256];
|
||||
sprintf(buf, "[/Indexed /DeviceRGB %d\n<\n", size);
|
||||
return PSDRV_WriteSpool(dc, buf, strlen(buf));
|
||||
}
|
||||
|
||||
BOOL PSDRV_WriteIndexColorSpaceEnd(DC *dc)
|
||||
{
|
||||
char buf[] = ">\n] setcolorspace\n";
|
||||
return PSDRV_WriteSpool(dc, buf, sizeof(buf) - 1);
|
||||
}
|
||||
|
||||
BOOL PSDRV_WriteRGB(DC *dc, COLORREF *map, int number)
|
||||
{
|
||||
char *buf = HeapAlloc(PSDRV_Heap, 0, number * 7 + 1), *ptr;
|
||||
int i;
|
||||
|
||||
ptr = buf;
|
||||
for(i = 0; i < number; i++) {
|
||||
sprintf(ptr, "%02x%02x%02x%c", (int)GetRValue(map[i]),
|
||||
(int)GetGValue(map[i]), (int)GetBValue(map[i]),
|
||||
((i & 0x7) == 0x7) || (i == number - 1) ? '\n' : ' ');
|
||||
ptr += 7;
|
||||
}
|
||||
PSDRV_WriteSpool(dc, buf, number * 7);
|
||||
HeapFree(PSDRV_Heap, 0, buf);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
|
||||
BOOL PSDRV_WriteImageDict(DC *dc, WORD depth, INT xDst, INT yDst,
|
||||
INT widthDst, INT heightDst, INT widthSrc,
|
||||
INT heightSrc)
|
||||
{
|
||||
char start[] = "%d %d translate\n%d %d scale\n<<\n"
|
||||
" /ImageType 1\n /Width %d\n /Height %d\n /BitsPerComponent %d\n"
|
||||
" /ImageMatrix [%d 0 0 %d 0 %d]\n";
|
||||
|
||||
char decode1[] = " /Decode [0 %d]\n";
|
||||
char decode3[] = " /Decode [0 1 0 1 0 1]\n";
|
||||
|
||||
char end[] = " /DataSource currentfile /ASCIIHexDecode filter\n>> image\n";
|
||||
|
||||
char *buf = HeapAlloc(PSDRV_Heap, 0, 1000);
|
||||
|
||||
sprintf(buf, start, xDst, yDst, widthDst, heightDst, widthSrc, heightSrc,
|
||||
(depth < 8) ? depth : 8, widthSrc, -heightSrc, heightSrc);
|
||||
|
||||
PSDRV_WriteSpool(dc, buf, strlen(buf));
|
||||
|
||||
switch(depth) {
|
||||
case 8:
|
||||
sprintf(buf, decode1, 255);
|
||||
break;
|
||||
|
||||
case 4:
|
||||
sprintf(buf, decode1, 15);
|
||||
break;
|
||||
|
||||
case 1:
|
||||
sprintf(buf, decode1, 1);
|
||||
break;
|
||||
|
||||
default:
|
||||
strcpy(buf, decode3);
|
||||
break;
|
||||
}
|
||||
|
||||
PSDRV_WriteSpool(dc, buf, strlen(buf));
|
||||
|
||||
PSDRV_WriteSpool(dc, end, sizeof(end) - 1);
|
||||
|
||||
HeapFree(PSDRV_Heap, 0, buf);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL PSDRV_WriteBytes(DC *dc, const BYTE *bytes, int number)
|
||||
{
|
||||
char *buf = HeapAlloc(PSDRV_Heap, 0, number * 3 + 1);
|
||||
char *ptr;
|
||||
int i;
|
||||
|
||||
ptr = buf;
|
||||
|
||||
for(i = 0; i < number; i++) {
|
||||
sprintf(ptr, "%02x%c", bytes[i],
|
||||
((i & 0xf) == 0xf) || (i == number - 1) ? '\n' : ' ');
|
||||
ptr += 3;
|
||||
}
|
||||
PSDRV_WriteSpool(dc, buf, number * 3);
|
||||
|
||||
HeapFree(PSDRV_Heap, 0, buf);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL PSDRV_WriteDIBits16(DC *dc, const WORD *words, int number)
|
||||
{
|
||||
char *buf = HeapAlloc(PSDRV_Heap, 0, number * 7 + 1);
|
||||
char *ptr;
|
||||
int i;
|
||||
|
||||
ptr = buf;
|
||||
|
||||
for(i = 0; i < number; i++) {
|
||||
int r, g, b;
|
||||
|
||||
/* We want 0x0 -- 0x1f to map to 0x0 -- 0xff */
|
||||
|
||||
r = words[i] >> 10 & 0x1f;
|
||||
r = r << 3 | r >> 2;
|
||||
g = words[i] >> 5 & 0x1f;
|
||||
g = g << 3 | g >> 2;
|
||||
b = words[i] & 0x1f;
|
||||
b = b << 3 | b >> 2;
|
||||
sprintf(ptr, "%02x%02x%02x%c", r, g, b,
|
||||
((i & 0x7) == 0x7) || (i == number - 1) ? '\n' : ' ');
|
||||
ptr += 7;
|
||||
}
|
||||
PSDRV_WriteSpool(dc, buf, number * 7);
|
||||
|
||||
HeapFree(PSDRV_Heap, 0, buf);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL PSDRV_WriteDIBits24(DC *dc, const BYTE *bits, int number)
|
||||
{
|
||||
char *buf = HeapAlloc(PSDRV_Heap, 0, number * 7 + 1);
|
||||
char *ptr;
|
||||
int i;
|
||||
|
||||
ptr = buf;
|
||||
|
||||
for(i = 0; i < number; i++) {
|
||||
sprintf(ptr, "%02x%02x%02x%c", bits[i * 3 + 2], bits[i * 3 + 1],
|
||||
bits[i * 3],
|
||||
((i & 0x7) == 0x7) || (i == number - 1) ? '\n' : ' ');
|
||||
ptr += 7;
|
||||
}
|
||||
PSDRV_WriteSpool(dc, buf, number * 7);
|
||||
|
||||
HeapFree(PSDRV_Heap, 0, buf);
|
||||
return TRUE;
|
||||
}
|
||||
|
||||
BOOL PSDRV_WriteDIBits32(DC *dc, const BYTE *bits, int number)
|
||||
{
|
||||
char *buf = HeapAlloc(PSDRV_Heap, 0, number * 7 + 1);
|
||||
char *ptr;
|
||||
int i;
|
||||
|
||||
ptr = buf;
|
||||
|
||||
for(i = 0; i < number; i++) {
|
||||
sprintf(ptr, "%02x%02x%02x%c", bits[i * 4 + 2], bits[i * 4 + 1],
|
||||
bits[i * 4],
|
||||
((i & 0x7) == 0x7) || (i == number - 1) ? '\n' : ' ');
|
||||
ptr += 7;
|
||||
}
|
||||
PSDRV_WriteSpool(dc, buf, number * 7);
|
||||
|
||||
HeapFree(PSDRV_Heap, 0, buf);
|
||||
return TRUE;
|
||||
}
|
||||
|
|
|
@ -282,8 +282,16 @@ extern BOOL PSDRV_WriteClip(DC *dc);
|
|||
extern BOOL PSDRV_WriteEOClip(DC *dc);
|
||||
extern BOOL PSDRV_WriteHatch(DC *dc);
|
||||
extern BOOL PSDRV_WriteRotate(DC *dc, float ang);
|
||||
|
||||
|
||||
extern BOOL PSDRV_WriteIndexColorSpaceBegin(DC *dc, int size);
|
||||
extern BOOL PSDRV_WriteIndexColorSpaceEnd(DC *dc);
|
||||
extern BOOL PSDRV_WriteRGB(DC *dc, COLORREF *map, int number);
|
||||
extern BOOL PSDRV_WriteImageDict(DC *dc, WORD depth, INT xDst, INT yDst,
|
||||
INT widthDst, INT heightDst, INT widthSrc,
|
||||
INT heightSrc);
|
||||
extern BOOL PSDRV_WriteBytes(DC *dc, const BYTE *bytes, int number);
|
||||
extern BOOL PSDRV_WriteDIBits16(DC *dc, const WORD *words, int number);
|
||||
extern BOOL PSDRV_WriteDIBits24(DC *dc, const BYTE *bits, int number);
|
||||
extern BOOL PSDRV_WriteDIBits32(DC *dc, const BYTE *bits, int number);
|
||||
|
||||
|
||||
|
||||
|
|
Loading…
Reference in New Issue