New bitmap method SetRGBConversionFunction which can be used to
[tangerine.git] / rom / graphics / bltmaskbitmaprastport.c
blob9094635e40f103630e4c963c7012958639088ab5
1 /*
2 Copyright © 1995-2001, The AROS Development Team. All rights reserved.
3 $Id$
5 Desc:
6 Lang: english
7 */
8 #include <aros/debug.h>
9 #include <proto/graphics.h>
10 #include <proto/oop.h>
11 #include "graphics_intern.h"
12 #include "gfxfuncsupport.h"
13 #include <hardware/blit.h>
15 struct bltmask_render_data
17 struct render_special_info rsi;
18 struct BitMap *srcbm;
19 OOP_Object *srcbm_obj;
20 OOP_Object *srcpf;
21 HIDDT_ColorModel src_colmod;
22 PLANEPTR mask;
23 ULONG mask_bpr;
24 ULONG minterm;
25 BOOL samebitmapformat;
28 static ULONG bltmask_render(APTR bltmask_rd, LONG srcx, LONG srcy,
29 OOP_Object *dstbm_obj, OOP_Object *dst_gc,
30 LONG x1, LONG y1, LONG x2, LONG y2, struct GfxBase *GfxBase);
32 /*****************************************************************************
34 NAME */
35 #include <clib/graphics_protos.h>
37 AROS_LH10(void, BltMaskBitMapRastPort,
39 /* SYNOPSIS */
40 AROS_LHA(struct BitMap *, srcBitMap, A0),
41 AROS_LHA(LONG , xSrc, D0),
42 AROS_LHA(LONG , ySrc, D1),
43 AROS_LHA(struct RastPort *, destRP, A1),
44 AROS_LHA(LONG , xDest, D2),
45 AROS_LHA(LONG , yDest, D3),
46 AROS_LHA(LONG , xSize, D4),
47 AROS_LHA(LONG , ySize, D5),
48 AROS_LHA(ULONG , minterm, D6),
49 AROS_LHA(PLANEPTR , bltMask, A2),
51 /* LOCATION */
52 struct GfxBase *, GfxBase, 106, Graphics)
54 /* FUNCTION
56 INPUTS
58 RESULT
60 NOTES
62 EXAMPLE
64 BUGS
66 SEE ALSO
68 INTERNALS
70 HISTORY
71 27-11-96 digulla automatically created from
72 graphics_lib.fd and clib/graphics_protos.h
74 *****************************************************************************/
76 AROS_LIBFUNC_INIT
77 AROS_LIBBASE_EXT_DECL(struct GfxBase *,GfxBase)
79 struct bltmask_render_data brd;
80 struct Rectangle rr;
81 HIDDT_DrawMode old_drmd;
82 OOP_Object *gc;
83 Point src;
85 struct TagItem gc_tags[] =
87 { aHidd_GC_DrawMode , 0UL },
88 { TAG_DONE }
91 EnterFunc(bug("BltMaskBitMapRastPort(%d %d %d, %d, %d, %d)\n"
92 , xSrc, ySrc, xDest, yDest, xSize, ySize));
94 FIX_GFXCOORD(xSrc);
95 FIX_GFXCOORD(ySrc);
96 FIX_GFXCOORD(xDest);
97 FIX_GFXCOORD(yDest);
99 if ((xSize < 1) || (ySize < 1)) return;
101 if (!OBTAIN_DRIVERDATA(destRP, GfxBase))
102 return;
104 brd.minterm = minterm;
105 brd.srcbm_obj = OBTAIN_HIDD_BM(srcBitMap);
106 if (NULL == brd.srcbm_obj)
108 RELEASE_DRIVERDATA(destRP, GfxBase);
109 return;
112 brd.srcbm = srcBitMap;
113 brd.mask = bltMask;
115 /* The mask has always the same size as the source bitmap */
116 brd.mask_bpr = 2 * WIDTH_TO_WORDS(GetBitMapAttr(srcBitMap, BMA_WIDTH));
118 OOP_GetAttr(brd.srcbm_obj, aHidd_BitMap_PixFmt, (IPTR *)&brd.srcpf);
120 IPTR attr;
122 OOP_GetAttr(brd.srcpf, aHidd_PixFmt_ColorModel, &attr);
123 brd.src_colmod = (HIDDT_ColorModel)attr;
126 gc = GetDriverData(destRP)->dd_GC;
127 OOP_GetAttr(gc, aHidd_GC_DrawMode, &old_drmd);
129 gc_tags[0].ti_Data = vHidd_GC_DrawMode_Copy;
130 OOP_SetAttrs(gc, gc_tags);
132 rr.MinX = xDest;
133 rr.MinY = yDest;
134 rr.MaxX = xDest + xSize - 1;
135 rr.MaxY = yDest + ySize - 1;
137 src.x = xSrc;
138 src.y = ySrc;
140 do_render_func(destRP, &src, &rr, bltmask_render, &brd, TRUE, GfxBase);
142 RELEASE_HIDD_BM(brd.srcbm_obj, srcBitMap);
144 gc_tags[0].ti_Data = old_drmd;
145 OOP_SetAttrs(gc, gc_tags);
147 RELEASE_DRIVERDATA(destRP, GfxBase);
149 ReturnVoid("BltBitMapRastPort");
151 AROS_LIBFUNC_EXIT
153 } /* BltMaskBitMapRastPort */
155 /****************************************************************************************/
157 static ULONG bltmask_render(APTR bltmask_rd, LONG srcx, LONG srcy,
158 OOP_Object *dstbm_obj, OOP_Object *dst_gc,
159 LONG x1, LONG y1, LONG x2, LONG y2, struct GfxBase *GfxBase)
161 struct bltmask_render_data *brd;
162 OOP_Object *dest_pf;
163 HIDDT_ColorModel dest_colmod;
164 HIDDT_Pixel *pixtab = NULL;
165 ULONG x, y, width, height;
166 LONG lines_done, lines_per_step, doing_lines;
167 BOOL pal_to_true = FALSE;
169 width = x2 - x1 + 1;
170 height = y2 - y1 + 1;
172 OOP_GetAttr(dstbm_obj, aHidd_BitMap_PixFmt, (IPTR *)&dest_pf);
174 IPTR attr;
176 OOP_GetAttr(dest_pf, aHidd_PixFmt_ColorModel, &attr);
177 dest_colmod = (HIDDT_ColorModel)attr;
180 brd = (struct bltmask_render_data *)bltmask_rd;
181 if ((brd->src_colmod == vHidd_ColorModel_Palette) && (dest_colmod == vHidd_ColorModel_Palette))
184 else if ((brd->src_colmod == vHidd_ColorModel_Palette) && (dest_colmod == vHidd_ColorModel_TrueColor))
186 pixtab = IS_HIDD_BM(brd->srcbm) ? HIDD_BM_PIXTAB(brd->srcbm) : NULL;
187 if (!pixtab) pixtab = IS_HIDD_BM(brd->rsi.curbm) ? HIDD_BM_PIXTAB(brd->rsi.curbm) : NULL;
189 if (!pixtab)
191 D(bug("BltMaskBitMapRastPort could not retrieve pixel table for blit from palette to truecolor bitmap"));
192 return width * height;
195 pal_to_true = TRUE;
197 else if ((brd->src_colmod == vHidd_ColorModel_TrueColor) && (dest_colmod == vHidd_ColorModel_TrueColor))
199 if (brd->srcpf != dest_pf)
201 D(bug("BltMaskBitMapRastPort not supporting blit between truecolor bitmaps of different formats yet"));
202 return width * height;
205 else if ((brd->src_colmod == vHidd_ColorModel_TrueColor) && (dest_colmod == vHidd_ColorModel_Palette))
207 D(bug("BltMaskBitMapRastPort from truecolor bitmap to palette bitmap not supported!"));
208 return width * height;
211 lines_per_step = (NUMPIX / (width * 2 * sizeof(HIDDT_Pixel)));
212 if (lines_per_step)
214 UBYTE *srcbuf, *destbuf;
216 LOCK_PIXBUF
218 srcbuf = (UBYTE *)PrivGBase(GfxBase)->pixel_buf;
219 destbuf = srcbuf;
220 destbuf += lines_per_step * width * sizeof(HIDDT_Pixel);
222 for(lines_done = 0; lines_done != height; lines_done += doing_lines)
224 HIDDT_Pixel *srcpixelbuf;
225 HIDDT_Pixel *destpixelbuf;
226 UBYTE *mask;
228 doing_lines = lines_per_step;
229 if (lines_done + doing_lines > height) doing_lines = height - lines_done;
231 HIDD_BM_GetImage(brd->srcbm_obj,
232 srcbuf,
233 width * sizeof(HIDDT_Pixel),
234 srcx, srcy + lines_done,
235 width, doing_lines,
236 vHidd_StdPixFmt_Native32);
238 HIDD_BM_GetImage(dstbm_obj,
239 destbuf,
240 width * sizeof(HIDDT_Pixel),
241 x1, y1 + lines_done,
242 width, doing_lines,
243 vHidd_StdPixFmt_Native32);
245 mask = &brd->mask[COORD_TO_BYTEIDX(0, srcy + lines_done, brd->mask_bpr)];
247 srcpixelbuf = (HIDDT_Pixel *)srcbuf;
248 destpixelbuf = (HIDDT_Pixel *)destbuf;
250 switch(brd->minterm)
252 case (ABC|ABNC|ANBC): /* (ABC|ABNC|ANBC) if copy source and blit thru mask */
253 if (pal_to_true)
255 for(y = 0; y < doing_lines; y++)
257 for(x = 0; x < width; x++)
259 if (mask[XCOORD_TO_BYTEIDX(srcx + x)] & XCOORD_TO_MASK(srcx + x))
261 *destpixelbuf = pixtab[*srcpixelbuf];
263 srcpixelbuf++;
264 destpixelbuf++;
266 mask += brd->mask_bpr;
269 else
271 for(y = 0; y < doing_lines; y++)
273 for(x = 0; x < width; x++)
275 if (mask[XCOORD_TO_BYTEIDX(srcx + x)] & XCOORD_TO_MASK(srcx + x))
277 *destpixelbuf = *srcpixelbuf;
279 srcpixelbuf++;
280 destpixelbuf++;
282 mask += brd->mask_bpr;
285 break;
287 case ANBC: /* (ANBC) if invert source and blit thru mask */
288 D(bug("BltMaskBitMapRastPort does not support ANBC minterm yet"));
289 break;
291 default:
292 D(bug("BltMaskBitMapRastPort: minterm 0x%x not handled.\n", brd->minterm));
293 break;
294 } /* switch(brd->minterm) */
296 HIDD_BM_PutImage(dstbm_obj,
297 dst_gc,
298 destbuf,
299 width * sizeof(HIDDT_Pixel),
300 x1, y1 + lines_done,
301 width, doing_lines,
302 vHidd_StdPixFmt_Native32);
304 } /* for(lines_done = 0; lines_done != height; lines_done += doing_lines) */
306 ULOCK_PIXBUF
308 } /* if (lines_per_step) */
309 else
311 /* urk :-( pixelbuffer too small to hold two lines) */
313 D(bug("BltMaskBitMapRastPort found pixelbuffer to be too small"));
316 return width * height;
319 /****************************************************************************************/