implemented more drawing modes, refactored a little, still work left to do...

git-svn-id: file:///srv/svn/repos/haiku/trunk/current@10918 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Stephan Aßmus 2005-01-20 23:07:07 +00:00
parent 95ff0e4fe8
commit f71ffba994
5 changed files with 878 additions and 0 deletions

View File

@ -0,0 +1,215 @@
// DrawingModeBlend.h
#ifndef DRAWING_MODE_BLEND_H
#define DRAWING_MODE_BLEND_H
#include <SupportDefs.h>
#include "DrawingMode.h"
#include "PatternHandler.h"
inline void
blend_blend(uint8* d1, uint8* d2, uint8* d3, uint8* da,
uint8 s1, uint8 s2, uint8 s3, uint8 a)
{
s1 = (*d1 + s1) >> 1;
s2 = (*d2 + s2) >> 1;
s3 = (*d3 + s3) >> 1;
blend(d1, d2, d3, da, s1, s2, s3, a);
}
inline void
assign_blend(uint8* d1, uint8* d2, uint8* d3, uint8* da,
uint8 s1, uint8 s2, uint8 s3)
{
*d1 = (*d1 + s1) >> 1;
*d2 = (*d2 + s2) >> 1;
*d3 = (*d3 + s3) >> 1;
}
namespace agg
{
//====================================================DrawingModeBlend
template<class Order>
class DrawingModeBlend : public DrawingMode
{
public:
typedef Order order_type;
//--------------------------------------------------------------------
DrawingModeBlend()
: DrawingMode()
{
}
//--------------------------------------------------------------------
virtual void blend_pixel(int x, int y, const color_type& c, int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(cover)
{
assign_blend(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_blend(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, cover);
}
}
//--------------------------------------------------------------------
virtual void blend_hline(int x, int y, unsigned len,
const color_type& c, int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
if(cover == 255)
{
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
assign_blend(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
p += 4;
x++;
}
while(--len);
}
else
{
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
blend_blend(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, cover);
x++;
p += 4;
}
while(--len);
}
}
//--------------------------------------------------------------------
virtual void blend_vline(int x, int y, unsigned len,
const color_type& c, int8u cover)
{
printf("DrawingModeBlend::blend_vline()\n");
}
//--------------------------------------------------------------------
virtual void blend_solid_hspan(int x, int y, unsigned len,
const color_type& c, const int8u* covers)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(*covers)
{
if(*covers == 255)
{
assign_blend(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_blend(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, *covers);
}
}
covers++;
p += 4;
x++;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_solid_vspan(int x, int y, unsigned len,
const color_type& c, const int8u* covers)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(*covers)
{
if(*covers == 255)
{
assign_blend(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_blend(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, *covers);
}
}
covers++;
p += m_rbuf->stride();
y++;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_color_hspan(int x, int y, unsigned len,
const color_type* colors,
const int8u* covers,
int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
uint8 alpha = covers ? *covers++ : cover;
if(alpha)
{
if(alpha == 255)
{
assign_blend(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
colors->r, colors->g, colors->b);
}
else
{
blend_blend(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
colors->r, colors->g, colors->b, alpha);
}
}
p += 4;
++colors;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_color_vspan(int x, int y, unsigned len,
const color_type* colors,
const int8u* covers,
int8u cover)
{
printf("DrawingModeBlend::blend_color_vspan()\n");
}
};
typedef DrawingModeBlend<order_rgba32> DrawingModeRGBA32Blend; //----DrawingModeRGBA32Blend
typedef DrawingModeBlend<order_argb32> DrawingModeARGB32Blend; //----DrawingModeARGB32Blend
typedef DrawingModeBlend<order_abgr32> DrawingModeABGR32Blend; //----DrawingModeABGR32Blend
typedef DrawingModeBlend<order_bgra32> DrawingModeBGRA32Blend; //----DrawingModeBGRA32Blend
}
#endif // DRAWING_MODE_BLEND_H

View File

@ -2,9 +2,13 @@
#include "DrawingModeAdd.h"
#include "DrawingModeBlend.h"
#include "DrawingModeCopy.h"
#include "DrawingModeInvert.h"
#include "DrawingModeMax.h"
#include "DrawingModeMin.h"
#include "DrawingModeOver.h"
#include "DrawingModeSubtract.h"
#include "DrawingModeFactory.h"
@ -22,9 +26,23 @@ DrawingModeFactory::DrawingModeFor(drawing_mode mode)
case B_OP_OVER:
return new agg::DrawingModeBGRA32Over();
break;
case B_OP_ADD:
return new agg::DrawingModeBGRA32Add();
break;
case B_OP_SUBTRACT:
return new agg::DrawingModeBGRA32Subtract();
break;
case B_OP_BLEND:
return new agg::DrawingModeBGRA32Blend();
break;
case B_OP_MIN:
return new agg::DrawingModeBGRA32Min();
break;
case B_OP_MAX:
return new agg::DrawingModeBGRA32Max();
break;
default:
return new agg::DrawingModeBGRA32Copy();

View File

@ -0,0 +1,215 @@
// DrawingModeMax.h
#ifndef DRAWING_MODE_MAX_H
#define DRAWING_MODE_MAX_H
#include <SupportDefs.h>
#include "DrawingMode.h"
#include "PatternHandler.h"
inline void
blend_max(uint8* d1, uint8* d2, uint8* d3, uint8* da,
uint8 s1, uint8 s2, uint8 s3, uint8 a)
{
s1 = max_c(*d1, s1);
s2 = max_c(*d2, s2);
s3 = max_c(*d3, s3);
blend(d1, d2, d3, da, s1, s2, s3, a);
}
inline void
assign_max(uint8* d1, uint8* d2, uint8* d3, uint8* da,
uint8 s1, uint8 s2, uint8 s3)
{
*d1 = max_c(*d1, s1);
*d2 = max_c(*d2, s2);
*d3 = max_c(*d3, s3);
}
namespace agg
{
//====================================================DrawingModeMax
template<class Order>
class DrawingModeMax : public DrawingMode
{
public:
typedef Order order_type;
//--------------------------------------------------------------------
DrawingModeMax()
: DrawingMode()
{
}
//--------------------------------------------------------------------
virtual void blend_pixel(int x, int y, const color_type& c, int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(cover)
{
assign_max(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_max(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, cover);
}
}
//--------------------------------------------------------------------
virtual void blend_hline(int x, int y, unsigned len,
const color_type& c, int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
if(cover == 255)
{
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
assign_max(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
p += 4;
x++;
}
while(--len);
}
else
{
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
blend_max(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, cover);
x++;
p += 4;
}
while(--len);
}
}
//--------------------------------------------------------------------
virtual void blend_vline(int x, int y, unsigned len,
const color_type& c, int8u cover)
{
printf("DrawingModeMax::blend_vline()\n");
}
//--------------------------------------------------------------------
virtual void blend_solid_hspan(int x, int y, unsigned len,
const color_type& c, const int8u* covers)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(*covers)
{
if(*covers == 255)
{
assign_max(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_max(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, *covers);
}
}
covers++;
p += 4;
x++;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_solid_vspan(int x, int y, unsigned len,
const color_type& c, const int8u* covers)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(*covers)
{
if(*covers == 255)
{
assign_max(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_max(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, *covers);
}
}
covers++;
p += m_rbuf->stride();
y++;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_color_hspan(int x, int y, unsigned len,
const color_type* colors,
const int8u* covers,
int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
uint8 alpha = covers ? *covers++ : cover;
if(alpha)
{
if(alpha == 255)
{
assign_max(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
colors->r, colors->g, colors->b);
}
else
{
blend_max(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
colors->r, colors->g, colors->b, alpha);
}
}
p += 4;
++colors;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_color_vspan(int x, int y, unsigned len,
const color_type* colors,
const int8u* covers,
int8u cover)
{
printf("DrawingModeMax::blend_color_vspan()\n");
}
};
typedef DrawingModeMax<order_rgba32> DrawingModeRGBA32Max; //----DrawingModeRGBA32Max
typedef DrawingModeMax<order_argb32> DrawingModeARGB32Max; //----DrawingModeARGB32Max
typedef DrawingModeMax<order_abgr32> DrawingModeABGR32Max; //----DrawingModeABGR32Max
typedef DrawingModeMax<order_bgra32> DrawingModeBGRA32Max; //----DrawingModeBGRA32Max
}
#endif // DRAWING_MODE_MAX_H

View File

@ -0,0 +1,215 @@
// DrawingModeMin.h
#ifndef DRAWING_MODE_MIN_H
#define DRAWING_MODE_MIN_H
#include <SupportDefs.h>
#include "DrawingMode.h"
#include "PatternHandler.h"
inline void
blend_min(uint8* d1, uint8* d2, uint8* d3, uint8* da,
uint8 s1, uint8 s2, uint8 s3, uint8 a)
{
s1 = min_c(*d1, s1);
s2 = min_c(*d2, s2);
s3 = min_c(*d3, s3);
blend(d1, d2, d3, da, s1, s2, s3, a);
}
inline void
assign_min(uint8* d1, uint8* d2, uint8* d3, uint8* da,
uint8 s1, uint8 s2, uint8 s3)
{
*d1 = min_c(*d1, s1);
*d2 = min_c(*d2, s2);
*d3 = min_c(*d3, s3);
}
namespace agg
{
//====================================================DrawingModeMin
template<class Order>
class DrawingModeMin : public DrawingMode
{
public:
typedef Order order_type;
//--------------------------------------------------------------------
DrawingModeMin()
: DrawingMode()
{
}
//--------------------------------------------------------------------
virtual void blend_pixel(int x, int y, const color_type& c, int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(cover)
{
assign_min(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_min(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, cover);
}
}
//--------------------------------------------------------------------
virtual void blend_hline(int x, int y, unsigned len,
const color_type& c, int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
if(cover == 255)
{
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
assign_min(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
p += 4;
x++;
}
while(--len);
}
else
{
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
blend_min(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, cover);
x++;
p += 4;
}
while(--len);
}
}
//--------------------------------------------------------------------
virtual void blend_vline(int x, int y, unsigned len,
const color_type& c, int8u cover)
{
printf("DrawingModeMin::blend_vline()\n");
}
//--------------------------------------------------------------------
virtual void blend_solid_hspan(int x, int y, unsigned len,
const color_type& c, const int8u* covers)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(*covers)
{
if(*covers == 255)
{
assign_min(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_min(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, *covers);
}
}
covers++;
p += 4;
x++;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_solid_vspan(int x, int y, unsigned len,
const color_type& c, const int8u* covers)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(*covers)
{
if(*covers == 255)
{
assign_min(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_min(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, *covers);
}
}
covers++;
p += m_rbuf->stride();
y++;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_color_hspan(int x, int y, unsigned len,
const color_type* colors,
const int8u* covers,
int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
uint8 alpha = covers ? *covers++ : cover;
if(alpha)
{
if(alpha == 255)
{
assign_min(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
colors->r, colors->g, colors->b);
}
else
{
blend_min(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
colors->r, colors->g, colors->b, alpha);
}
}
p += 4;
++colors;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_color_vspan(int x, int y, unsigned len,
const color_type* colors,
const int8u* covers,
int8u cover)
{
printf("DrawingModeMin::blend_color_vspan()\n");
}
};
typedef DrawingModeMin<order_rgba32> DrawingModeRGBA32Min; //----DrawingModeRGBA32Min
typedef DrawingModeMin<order_argb32> DrawingModeARGB32Min; //----DrawingModeARGB32Min
typedef DrawingModeMin<order_abgr32> DrawingModeABGR32Min; //----DrawingModeABGR32Min
typedef DrawingModeMin<order_bgra32> DrawingModeBGRA32Min; //----DrawingModeBGRA32Min
}
#endif // DRAWING_MODE_MIN_H

View File

@ -0,0 +1,215 @@
// DrawingModeSubtract.h
#ifndef DRAWING_MODE_SUBTRACT_H
#define DRAWING_MODE_SUBTRACT_H
#include <SupportDefs.h>
#include "DrawingMode.h"
#include "PatternHandler.h"
inline void
blend_subtract(uint8* d1, uint8* d2, uint8* d3, uint8* da,
uint8 s1, uint8 s2, uint8 s3, uint8 a)
{
s1 = max_c(0, *d1 - s1);
s2 = max_c(0, *d2 - s2);
s3 = max_c(0, *d3 - s3);
blend(d1, d2, d3, da, s1, s2, s3, a);
}
inline void
assign_subtract(uint8* d1, uint8* d2, uint8* d3, uint8* da,
uint8 s1, uint8 s2, uint8 s3)
{
*d1 = max_c(0, *d1 - s1);
*d2 = max_c(0, *d2 - s2);
*d3 = max_c(0, *d3 - s3);
}
namespace agg
{
//====================================================DrawingModeSubtract
template<class Order>
class DrawingModeSubtract : public DrawingMode
{
public:
typedef Order order_type;
//--------------------------------------------------------------------
DrawingModeSubtract()
: DrawingMode()
{
}
//--------------------------------------------------------------------
virtual void blend_pixel(int x, int y, const color_type& c, int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(cover)
{
assign_subtract(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_subtract(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, cover);
}
}
//--------------------------------------------------------------------
virtual void blend_hline(int x, int y, unsigned len,
const color_type& c, int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
if(cover == 255)
{
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
assign_subtract(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
p += 4;
x++;
}
while(--len);
}
else
{
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
blend_subtract(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, cover);
x++;
p += 4;
}
while(--len);
}
}
//--------------------------------------------------------------------
virtual void blend_vline(int x, int y, unsigned len,
const color_type& c, int8u cover)
{
printf("DrawingModeSubtract::blend_vline()\n");
}
//--------------------------------------------------------------------
virtual void blend_solid_hspan(int x, int y, unsigned len,
const color_type& c, const int8u* covers)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(*covers)
{
if(*covers == 255)
{
assign_subtract(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_subtract(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, *covers);
}
}
covers++;
p += 4;
x++;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_solid_vspan(int x, int y, unsigned len,
const color_type& c, const int8u* covers)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
rgb_color color = fPatternHandler->R5ColorAt(x, y);
if(*covers)
{
if(*covers == 255)
{
assign_subtract(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue);
}
else
{
blend_subtract(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
color.red, color.green, color.blue, *covers);
}
}
covers++;
p += m_rbuf->stride();
y++;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_color_hspan(int x, int y, unsigned len,
const color_type* colors,
const int8u* covers,
int8u cover)
{
int8u* p = m_rbuf->row(y) + (x << 2);
do
{
uint8 alpha = covers ? *covers++ : cover;
if(alpha)
{
if(alpha == 255)
{
assign_subtract(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
colors->r, colors->g, colors->b);
}
else
{
blend_subtract(&p[Order::R], &p[Order::G], &p[Order::B], &p[Order::A],
colors->r, colors->g, colors->b, alpha);
}
}
p += 4;
++colors;
}
while(--len);
}
//--------------------------------------------------------------------
virtual void blend_color_vspan(int x, int y, unsigned len,
const color_type* colors,
const int8u* covers,
int8u cover)
{
printf("DrawingModeSubtract::blend_color_vspan()\n");
}
};
typedef DrawingModeSubtract<order_rgba32> DrawingModeRGBA32Subtract; //----DrawingModeRGBA32Subtract
typedef DrawingModeSubtract<order_argb32> DrawingModeARGB32Subtract; //----DrawingModeARGB32Subtract
typedef DrawingModeSubtract<order_abgr32> DrawingModeABGR32Subtract; //----DrawingModeABGR32Subtract
typedef DrawingModeSubtract<order_bgra32> DrawingModeBGRA32Subtract; //----DrawingModeBGRA32Subtract
}
#endif // DRAWING_MODE_SUBTRACT_H