added support for software cursor needed for single buffered mode
git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@12561 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
@@ -84,6 +84,25 @@ DisplayDriverPainter::Shutdown()
|
||||
DisplayDriver::Shutdown();
|
||||
}
|
||||
|
||||
// ConstrainClippingRegion
|
||||
void DisplayDriverPainter::ConstrainClippingRegion(BRegion *region)
|
||||
{
|
||||
if (Lock()) {
|
||||
if (!region) {
|
||||
// BRegion empty;
|
||||
// fPainter->ConstrainClipping(empty);
|
||||
if (RenderingBuffer* buffer = fGraphicsCard->DrawingBuffer()) {
|
||||
BRegion all;
|
||||
all.Include(BRect(0, 0, buffer->Width() - 1, buffer->Height() - 1));
|
||||
fPainter->ConstrainClipping(all);
|
||||
}
|
||||
} else {
|
||||
fPainter->ConstrainClipping(*region);
|
||||
}
|
||||
Unlock();
|
||||
}
|
||||
}
|
||||
|
||||
// CopyRegion() does a topological sort of the rects in the
|
||||
// region. The algorithm was suggested by Ingo Weinhold.
|
||||
// It compares each rect with each rect and builds a tree
|
||||
@@ -199,6 +218,8 @@ DisplayDriverPainter::CopyRegion(/*const*/ BRegion* region,
|
||||
int32 xOffset, int32 yOffset)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor(fPainter->ClipRect(region->Frame()));
|
||||
|
||||
int32 count = region->CountRects();
|
||||
|
||||
// TODO: make this step unnecessary
|
||||
@@ -276,6 +297,7 @@ DisplayDriverPainter::CopyRegion(/*const*/ BRegion* region,
|
||||
inDegreeZeroNodes.push(n->pointers[k]);
|
||||
}
|
||||
}
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -314,9 +336,12 @@ void
|
||||
DisplayDriverPainter::InvertRect(const BRect &r)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor(fPainter->ClipRect(r));
|
||||
|
||||
BRect touched = fPainter->InvertRect(r);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -333,12 +358,14 @@ DisplayDriverPainter::DrawBitmap(BRegion *region, ServerBitmap *bitmap,
|
||||
return;
|
||||
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->ConstrainClipping(*region);
|
||||
fPainter->SetDrawData(d);
|
||||
fPainter->DrawBitmap(bitmap, source, dest);
|
||||
|
||||
fGraphicsCard->Invalidate(dest);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -350,6 +377,7 @@ DisplayDriverPainter::FillArc(const BRect &r, const float &angle,
|
||||
const float &span, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
|
||||
@@ -361,6 +389,7 @@ DisplayDriverPainter::FillArc(const BRect &r, const float &angle,
|
||||
BRect touched = fPainter->FillArc(center, xRadius, yRadius, angle, span);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -371,12 +400,14 @@ void
|
||||
DisplayDriverPainter::FillBezier(BPoint *pts, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
|
||||
BRect touched = fPainter->FillBezier(pts);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -387,6 +418,7 @@ void
|
||||
DisplayDriverPainter::FillEllipse(const BRect &r, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
|
||||
@@ -398,6 +430,7 @@ DisplayDriverPainter::FillEllipse(const BRect &r, const DrawData *d)
|
||||
BRect touched = fPainter->FillEllipse(center, xRadius, yRadius);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -409,11 +442,13 @@ DisplayDriverPainter::FillPolygon(BPoint *ptlist, int32 numpts,
|
||||
const BRect &bounds, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
BRect touched = fPainter->FillPolygon(ptlist, numpts);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -424,14 +459,18 @@ void
|
||||
DisplayDriverPainter::FillRect(const BRect &r, const RGBColor &color)
|
||||
{
|
||||
if (Lock()) {
|
||||
BRect vr(min_c(r.left, r.right),
|
||||
min_c(r.top, r.bottom),
|
||||
max_c(r.left, r.right),
|
||||
max_c(r.top, r.bottom));
|
||||
vr = fPainter->ClipRect(vr);
|
||||
|
||||
fPainter->FillRect(r, color.GetColor32());
|
||||
BRect touched(min_c(r.left, r.right),
|
||||
min_c(r.top, r.bottom),
|
||||
max_c(r.left, r.right),
|
||||
max_c(r.top, r.bottom));
|
||||
fGraphicsCard->HideSoftwareCursor(vr);
|
||||
|
||||
fGraphicsCard->Invalidate(fPainter->ClipRect(touched));
|
||||
fPainter->FillRect(vr, color.GetColor32());
|
||||
|
||||
fGraphicsCard->Invalidate(vr);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -442,11 +481,19 @@ void
|
||||
DisplayDriverPainter::FillRect(const BRect &r, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
BRect vr(min_c(r.left, r.right),
|
||||
min_c(r.top, r.bottom),
|
||||
max_c(r.left, r.right),
|
||||
max_c(r.top, r.bottom));
|
||||
vr = fPainter->ClipRect(vr);
|
||||
|
||||
fGraphicsCard->HideSoftwareCursor(vr);
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
BRect touched = fPainter->FillRect(r);
|
||||
BRect touched = fPainter->FillRect(vr);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -458,6 +505,8 @@ DisplayDriverPainter::FillRegion(BRegion& r, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
|
||||
fGraphicsCard->HideSoftwareCursor(fPainter->ClipRect(r.Frame()));
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
|
||||
BRect touched = fPainter->FillRect(r.RectAt(0));
|
||||
@@ -468,6 +517,7 @@ DisplayDriverPainter::FillRegion(BRegion& r, const DrawData *d)
|
||||
}
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -480,11 +530,13 @@ DisplayDriverPainter::FillRoundRect(const BRect &r,
|
||||
const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
BRect touched = fPainter->FillRoundRect(r, xrad, yrad);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -511,11 +563,13 @@ DisplayDriverPainter::FillTriangle(BPoint *pts, const BRect &bounds,
|
||||
const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
BRect touched = fPainter->FillTriangle(pts[0], pts[1], pts[2]);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -527,6 +581,7 @@ DisplayDriverPainter::StrokeArc(const BRect &r, const float &angle,
|
||||
const float &span, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
|
||||
@@ -538,6 +593,7 @@ DisplayDriverPainter::StrokeArc(const BRect &r, const float &angle,
|
||||
BRect touched = fPainter->StrokeArc(center, xRadius, yRadius, angle, span);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -548,11 +604,13 @@ void
|
||||
DisplayDriverPainter::StrokeBezier(BPoint *pts, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
BRect touched = fPainter->StrokeBezier(pts);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -563,6 +621,7 @@ void
|
||||
DisplayDriverPainter::StrokeEllipse(const BRect &r, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
|
||||
@@ -574,6 +633,7 @@ DisplayDriverPainter::StrokeEllipse(const BRect &r, const DrawData *d)
|
||||
BRect touched = fPainter->StrokeEllipse(center, xRadius, yRadius);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -587,18 +647,22 @@ void
|
||||
DisplayDriverPainter::StrokeLine(const BPoint &start, const BPoint &end, const RGBColor &color)
|
||||
{
|
||||
if (Lock()) {
|
||||
BRect touched(min_c(start.x, end.x),
|
||||
min_c(start.y, end.y),
|
||||
max_c(start.x, end.x),
|
||||
max_c(start.y, end.y));
|
||||
touched = fPainter->ClipRect(touched);
|
||||
fGraphicsCard->HideSoftwareCursor(touched);
|
||||
|
||||
if (!fPainter->StraightLine(start, end, color.GetColor32())) {
|
||||
DrawData context;
|
||||
static DrawData context;
|
||||
context.SetHighColor(color);
|
||||
context.SetDrawingMode(B_OP_COPY);
|
||||
context.SetDrawingMode(B_OP_OVER);
|
||||
StrokeLine(start, end, &context);
|
||||
} else {
|
||||
BRect touched(min_c(start.x, end.x),
|
||||
min_c(start.y, end.y),
|
||||
max_c(start.x, end.x),
|
||||
max_c(start.y, end.y));
|
||||
fGraphicsCard->Invalidate(fPainter->ClipRect(touched));
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
}
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
Unlock();
|
||||
}
|
||||
}
|
||||
@@ -608,8 +672,51 @@ void
|
||||
DisplayDriverPainter::StrokeLine(const BPoint &start, const BPoint &end, DrawData* context)
|
||||
{
|
||||
if (Lock()) {
|
||||
BRect touched = fPainter->StrokeLine(start, end, context);
|
||||
BRect touched(min_c(start.x, end.x),
|
||||
min_c(start.y, end.y),
|
||||
max_c(start.x, end.x),
|
||||
max_c(start.y, end.y));
|
||||
touched = fPainter->ClipRect(touched);
|
||||
fGraphicsCard->HideSoftwareCursor(touched);
|
||||
|
||||
touched = fPainter->StrokeLine(start, end, context);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
}
|
||||
|
||||
// StrokeLineArray
|
||||
void
|
||||
DisplayDriverPainter::StrokeLineArray(const int32 &numlines,
|
||||
const LineArrayData *linedata,
|
||||
const DrawData *d)
|
||||
{
|
||||
if(!d || !linedata || numlines <= 0)
|
||||
return;
|
||||
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
DrawData context;
|
||||
context.SetDrawingMode(B_OP_COPY);
|
||||
const LineArrayData *data;
|
||||
|
||||
data = (const LineArrayData *)&(linedata[0]);
|
||||
context.SetHighColor(data->color);
|
||||
BRect touched = fPainter->StrokeLine(data->pt1, data->pt2, &context);
|
||||
|
||||
for (int32 i = 1; i < numlines; i++) {
|
||||
data = (const LineArrayData *)&(linedata[i]);
|
||||
context.SetHighColor(data->color);
|
||||
touched = touched | fPainter->StrokeLine(data->pt1, data->pt2, &context);
|
||||
}
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
}
|
||||
@@ -637,11 +744,13 @@ DisplayDriverPainter::StrokePolygon(BPoint *ptlist, int32 numpts,
|
||||
bool closed)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
BRect touched = fPainter->StrokePolygon(ptlist, numpts, closed);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -654,6 +763,8 @@ void
|
||||
DisplayDriverPainter::StrokeRect(const BRect &r, const RGBColor &color)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
// support invalid rects
|
||||
BRect vr(min_c(r.left, r.right),
|
||||
min_c(r.top, r.bottom),
|
||||
@@ -662,14 +773,16 @@ DisplayDriverPainter::StrokeRect(const BRect &r, const RGBColor &color)
|
||||
|
||||
fPainter->StrokeRect(vr, color.GetColor32());
|
||||
|
||||
fGraphicsCard->Invalidate(fPainter->ClipRect(BRect(vr.left, vr.top,
|
||||
/* fGraphicsCard->Invalidate(fPainter->ClipRect(BRect(vr.left, vr.top,
|
||||
vr.right, vr.top)));
|
||||
fGraphicsCard->Invalidate(fPainter->ClipRect(BRect(vr.left, vr.top + 1,
|
||||
vr.left, vr.bottom - 1)));
|
||||
fGraphicsCard->Invalidate(fPainter->ClipRect(BRect(vr.right, vr.top + 1,
|
||||
vr.right, vr.bottom - 1)));
|
||||
fGraphicsCard->Invalidate(fPainter->ClipRect(BRect(vr.left, vr.bottom,
|
||||
vr.right, vr.bottom)));
|
||||
vr.right, vr.bottom)));*/
|
||||
fGraphicsCard->Invalidate(fPainter->ClipRect(vr));
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -680,11 +793,13 @@ void
|
||||
DisplayDriverPainter::StrokeRect(const BRect &r, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
BRect touched = fPainter->StrokeRect(r);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -695,6 +810,7 @@ void
|
||||
DisplayDriverPainter::StrokeRegion(BRegion& r, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
|
||||
@@ -706,6 +822,7 @@ DisplayDriverPainter::StrokeRegion(BRegion& r, const DrawData *d)
|
||||
}
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -717,11 +834,13 @@ DisplayDriverPainter::StrokeRoundRect(const BRect &r, const float &xrad,
|
||||
const float &yrad, const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
BRect touched = fPainter->StrokeRoundRect(r, xrad, yrad);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -747,11 +866,13 @@ DisplayDriverPainter::StrokeTriangle(BPoint *pts, const BRect &bounds,
|
||||
const DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
BRect touched = fPainter->StrokeTriangle(pts[0], pts[1], pts[2]);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -763,7 +884,7 @@ DisplayDriverPainter::DrawString(const char *string, const int32 &length,
|
||||
const BPoint &pt, const RGBColor &color,
|
||||
escapement_delta *delta)
|
||||
{
|
||||
DrawData d;
|
||||
static DrawData d;
|
||||
d.SetHighColor(color);
|
||||
|
||||
if (delta)
|
||||
@@ -778,11 +899,14 @@ DisplayDriverPainter::DrawString(const char *string, const int32 &length,
|
||||
const BPoint &pt, DrawData *d)
|
||||
{
|
||||
if (Lock()) {
|
||||
fGraphicsCard->HideSoftwareCursor();
|
||||
|
||||
fPainter->SetDrawData(d);
|
||||
|
||||
BRect touched = fPainter->DrawString(string, length, pt);
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
fGraphicsCard->ShowSoftwareCursor();
|
||||
|
||||
Unlock();
|
||||
}
|
||||
@@ -1010,35 +1134,6 @@ DisplayDriverPainter::DumpToBitmap()
|
||||
return NULL;
|
||||
}
|
||||
|
||||
// StrokeLineArray
|
||||
void
|
||||
DisplayDriverPainter::StrokeLineArray(const int32 &numlines,
|
||||
const LineArrayData *linedata,
|
||||
const DrawData *d)
|
||||
{
|
||||
if(!d || !linedata || numlines <= 0)
|
||||
return;
|
||||
|
||||
if (Lock()) {
|
||||
DrawData context;
|
||||
context.SetDrawingMode(B_OP_COPY);
|
||||
const LineArrayData *data;
|
||||
|
||||
data = (const LineArrayData *)&(linedata[0]);
|
||||
context.SetHighColor(data->color);
|
||||
BRect touched = fPainter->StrokeLine(data->pt1, data->pt2, &context);
|
||||
|
||||
for (int32 i = 1; i < numlines; i++) {
|
||||
data = (const LineArrayData *)&(linedata[i]);
|
||||
context.SetHighColor(data->color);
|
||||
touched = touched | fPainter->StrokeLine(data->pt1, data->pt2, &context);
|
||||
}
|
||||
|
||||
fGraphicsCard->Invalidate(touched);
|
||||
Unlock();
|
||||
}
|
||||
}
|
||||
|
||||
// SetDPMSMode
|
||||
status_t
|
||||
DisplayDriverPainter::SetDPMSMode(const uint32 &state)
|
||||
@@ -1150,46 +1245,6 @@ DisplayDriverPainter::WaitForRetrace(bigtime_t timeout)
|
||||
return ret;
|
||||
}
|
||||
|
||||
// CopyBitmap
|
||||
void
|
||||
DisplayDriverPainter::CopyBitmap(ServerBitmap *bitmap,
|
||||
const BRect &source, const BRect &dest,
|
||||
const DrawData *d)
|
||||
{
|
||||
}
|
||||
|
||||
// CopyToBitmap
|
||||
void DisplayDriverPainter::CopyToBitmap(ServerBitmap *target,
|
||||
const BRect &source)
|
||||
{
|
||||
}
|
||||
|
||||
// Invalidate
|
||||
void DisplayDriverPainter::Invalidate(const BRect &r)
|
||||
{
|
||||
// nothing to be done here
|
||||
}
|
||||
|
||||
// ConstrainClippingRegion
|
||||
void DisplayDriverPainter::ConstrainClippingRegion(BRegion *region)
|
||||
{
|
||||
if (Lock()) {
|
||||
if (!region) {
|
||||
// BRegion empty;
|
||||
// fPainter->ConstrainClipping(empty);
|
||||
if (RenderingBuffer* buffer = fGraphicsCard->DrawingBuffer()) {
|
||||
BRegion all;
|
||||
all.Include(BRect(0, 0, buffer->Width() - 1,
|
||||
buffer->Height() - 1));
|
||||
fPainter->ConstrainClipping(all);
|
||||
}
|
||||
} else {
|
||||
fPainter->ConstrainClipping(*region);
|
||||
}
|
||||
Unlock();
|
||||
}
|
||||
}
|
||||
|
||||
// _CopyRect
|
||||
BRect
|
||||
DisplayDriverPainter::_CopyRect(BRect src, int32 xOffset, int32 yOffset) const
|
||||
|
||||
@@ -16,6 +16,8 @@
|
||||
// constructor
|
||||
HWInterface::HWInterface(bool doubleBuffered)
|
||||
: BLocker("hw interface lock"),
|
||||
fCursorAreaBackup(NULL),
|
||||
fSoftwareCursorHidden(false),
|
||||
fCursor(NULL),
|
||||
fCursorVisible(true),
|
||||
fCursorLocation(0, 0),
|
||||
@@ -28,6 +30,7 @@ HWInterface::HWInterface(bool doubleBuffered)
|
||||
// destructor
|
||||
HWInterface::~HWInterface()
|
||||
{
|
||||
delete fCursorAreaBackup;
|
||||
delete fCursor;
|
||||
delete fUpdateExecutor;
|
||||
}
|
||||
@@ -40,9 +43,17 @@ HWInterface::SetCursor(ServerCursor* cursor)
|
||||
if (fCursor != cursor) {
|
||||
BRect oldFrame = _CursorFrame();
|
||||
delete fCursor;
|
||||
delete fCursorAreaBackup;
|
||||
fCursor = cursor;
|
||||
Invalidate(oldFrame);
|
||||
Invalidate(_CursorFrame());
|
||||
BRect r = _CursorFrame();
|
||||
if (fCursor && !IsDoubleBuffered()) {
|
||||
fCursorAreaBackup = new buffer_clip(r.IntegerWidth() + 1,
|
||||
r.IntegerHeight() + 1);
|
||||
_DrawCursor(r);
|
||||
} else
|
||||
fCursorAreaBackup = NULL;
|
||||
Invalidate(r);
|
||||
}
|
||||
Unlock();
|
||||
}
|
||||
@@ -82,6 +93,10 @@ HWInterface::MoveCursorTo(const float& x, const float& y)
|
||||
if (p != fCursorLocation) {
|
||||
BRect oldFrame = _CursorFrame();
|
||||
fCursorLocation = p;
|
||||
if (fCursorAreaBackup) {
|
||||
_RestoreCursorArea(oldFrame);
|
||||
_DrawCursor(_CursorFrame());
|
||||
}
|
||||
Invalidate(oldFrame);
|
||||
Invalidate(_CursorFrame());
|
||||
}
|
||||
@@ -136,7 +151,7 @@ HWInterface::Invalidate(const BRect& frame)
|
||||
}
|
||||
return B_BAD_VALUE;*/
|
||||
} else {
|
||||
_DrawCursor(frame);
|
||||
// _DrawCursor(frame);
|
||||
}
|
||||
return B_OK;
|
||||
}
|
||||
@@ -181,6 +196,46 @@ HWInterface::CopyBackToFront(const BRect& frame)
|
||||
return B_BAD_VALUE;
|
||||
}
|
||||
|
||||
// HideSoftwareCursor
|
||||
void
|
||||
HWInterface::HideSoftwareCursor(const BRect& area)
|
||||
{
|
||||
if (fCursorAreaBackup && !fSoftwareCursorHidden) {
|
||||
BRect backupArea(fCursorAreaBackup->left,
|
||||
fCursorAreaBackup->top,
|
||||
fCursorAreaBackup->right,
|
||||
fCursorAreaBackup->bottom);
|
||||
if (area.Intersects(backupArea)) {
|
||||
_RestoreCursorArea(backupArea);
|
||||
fSoftwareCursorHidden = true;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// HideSoftwareCursor
|
||||
void
|
||||
HWInterface::HideSoftwareCursor()
|
||||
{
|
||||
if (fCursorAreaBackup && !fSoftwareCursorHidden) {
|
||||
_RestoreCursorArea(BRect(fCursorAreaBackup->left,
|
||||
fCursorAreaBackup->top,
|
||||
fCursorAreaBackup->right,
|
||||
fCursorAreaBackup->bottom));
|
||||
fSoftwareCursorHidden = true;
|
||||
}
|
||||
}
|
||||
|
||||
// ShowSoftwareCursor
|
||||
void
|
||||
HWInterface::ShowSoftwareCursor()
|
||||
{
|
||||
if (fCursorAreaBackup && fSoftwareCursorHidden) {
|
||||
_DrawCursor(_CursorFrame());
|
||||
fSoftwareCursorHidden = false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// _DrawCursor
|
||||
// * default implementation, can be used as fallback or for
|
||||
// software cursor
|
||||
@@ -232,26 +287,65 @@ HWInterface::_DrawCursor(BRect area) const
|
||||
|
||||
uint8* dst = buffer;
|
||||
|
||||
// blending
|
||||
for (int32 y = top; y <= bottom; y++) {
|
||||
uint8* s = src;
|
||||
uint8* c = crs;
|
||||
uint8* d = dst;
|
||||
for (int32 x = left; x <= right; x++) {
|
||||
// assume backbuffer alpha = 255
|
||||
// TODO: it appears alpha in cursor is upside down
|
||||
uint8 a = 255 - c[3];
|
||||
d[0] = (((s[0] - c[0]) * a) + (c[0] << 8)) >> 8;
|
||||
d[1] = (((s[1] - c[1]) * a) + (c[1] << 8)) >> 8;
|
||||
d[2] = (((s[2] - c[2]) * a) + (c[2] << 8)) >> 8;
|
||||
d[3] = 255;
|
||||
s += 4;
|
||||
c += 4;
|
||||
d += 4;
|
||||
if (fCursorAreaBackup) {
|
||||
// remember which area the backup contains
|
||||
fCursorAreaBackup->left = left;
|
||||
fCursorAreaBackup->top = top;
|
||||
fCursorAreaBackup->right = right;
|
||||
fCursorAreaBackup->bottom = bottom;
|
||||
uint8* bup = fCursorAreaBackup->buffer;
|
||||
uint32 bupBPR = fCursorAreaBackup->bpr;
|
||||
// blending and backup of drawing buffer
|
||||
for (int32 y = top; y <= bottom; y++) {
|
||||
uint8* s = src;
|
||||
uint8* c = crs;
|
||||
uint8* d = dst;
|
||||
uint8* b = bup;
|
||||
for (int32 x = left; x <= right; x++) {
|
||||
// assumes backbuffer alpha = 255
|
||||
// TODO: it appears alpha in cursor is upside down
|
||||
uint8 a = 255 - c[3];
|
||||
b[0] = s[0];
|
||||
b[1] = s[1];
|
||||
b[2] = s[2];
|
||||
// TODO: unnecessary?
|
||||
b[3] = 255;
|
||||
d[0] = (((s[0] - c[0]) * a) + (c[0] << 8)) >> 8;
|
||||
d[1] = (((s[1] - c[1]) * a) + (c[1] << 8)) >> 8;
|
||||
d[2] = (((s[2] - c[2]) * a) + (c[2] << 8)) >> 8;
|
||||
d[3] = 255;
|
||||
s += 4;
|
||||
c += 4;
|
||||
d += 4;
|
||||
b += 4;
|
||||
}
|
||||
crs += crsBPR;
|
||||
src += srcBPR;
|
||||
dst += width * 4;
|
||||
bup += bupBPR;
|
||||
}
|
||||
} else {
|
||||
// blending
|
||||
for (int32 y = top; y <= bottom; y++) {
|
||||
uint8* s = src;
|
||||
uint8* c = crs;
|
||||
uint8* d = dst;
|
||||
for (int32 x = left; x <= right; x++) {
|
||||
// assumes backbuffer alpha = 255
|
||||
// TODO: it appears alpha in cursor is upside down
|
||||
uint8 a = 255 - c[3];
|
||||
d[0] = (((s[0] - c[0]) * a) + (c[0] << 8)) >> 8;
|
||||
d[1] = (((s[1] - c[1]) * a) + (c[1] << 8)) >> 8;
|
||||
d[2] = (((s[2] - c[2]) * a) + (c[2] << 8)) >> 8;
|
||||
d[3] = 255;
|
||||
s += 4;
|
||||
c += 4;
|
||||
d += 4;
|
||||
}
|
||||
crs += crsBPR;
|
||||
src += srcBPR;
|
||||
dst += width * 4;
|
||||
}
|
||||
crs += crsBPR;
|
||||
src += srcBPR;
|
||||
dst += width * 4;
|
||||
}
|
||||
|
||||
// copy result to front buffer
|
||||
@@ -515,5 +609,31 @@ HWInterface::_CursorFrame() const
|
||||
return frame;
|
||||
}
|
||||
|
||||
// _RestoreCursorArea
|
||||
void
|
||||
HWInterface::_RestoreCursorArea(const BRect& area) const
|
||||
{
|
||||
if (fCursorAreaBackup) {
|
||||
|
||||
// clip backup area against "area"
|
||||
int32 left = max_c((int32)area.left, fCursorAreaBackup->left);
|
||||
int32 top = max_c((int32)area.top, fCursorAreaBackup->top);
|
||||
int32 right = min_c((int32)area.right, fCursorAreaBackup->right);
|
||||
int32 bottom = min_c((int32)area.bottom, fCursorAreaBackup->bottom);
|
||||
|
||||
if (left <= right && top <= bottom) {
|
||||
|
||||
uint8* src = fCursorAreaBackup->buffer;
|
||||
if (fCursorAreaBackup->left < left)
|
||||
src += left - fCursorAreaBackup->left;
|
||||
if (fCursorAreaBackup->top < top)
|
||||
src += (top - fCursorAreaBackup->top) * fCursorAreaBackup->bpr;
|
||||
|
||||
_CopyToFront(src, fCursorAreaBackup->bpr,
|
||||
left, top, right, bottom);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
|
||||
@@ -21,7 +21,7 @@ class UpdateQueue;
|
||||
|
||||
class HWInterface : public BLocker {
|
||||
public:
|
||||
HWInterface(bool doubleBuffered = true);
|
||||
HWInterface(bool doubleBuffered = false);
|
||||
virtual ~HWInterface();
|
||||
|
||||
virtual status_t Initialize() = 0;
|
||||
@@ -67,6 +67,17 @@ class HWInterface : public BLocker {
|
||||
// while as CopyBackToFront() actually performs the operation
|
||||
status_t CopyBackToFront(const BRect& frame);
|
||||
|
||||
// TODO: Just a quick and primitive way to get single buffered mode working.
|
||||
// Later, the implementation should be smarter, right now, it will
|
||||
// draw the cursor for almost every drawing operation.
|
||||
// It seems to me, BeOS hides the cursor (in laymans words) before
|
||||
// BView::Draw() is called, then, after all drawing commands that triggered
|
||||
// have been caried out, it shows the cursor again. This approach would
|
||||
// have the adventage of the code not cluttering/slowing down DisplayDriverPainter.
|
||||
void HideSoftwareCursor(const BRect& area);
|
||||
void HideSoftwareCursor();
|
||||
void ShowSoftwareCursor();
|
||||
|
||||
protected:
|
||||
// implement this in derived classes
|
||||
virtual void _DrawCursor(BRect area) const;
|
||||
@@ -77,6 +88,39 @@ class HWInterface : public BLocker {
|
||||
int32 right, int32 bottom) const;
|
||||
|
||||
BRect _CursorFrame() const;
|
||||
void _RestoreCursorArea(const BRect& frame) const;
|
||||
|
||||
// If we draw the cursor somewhere in the drawing buffer,
|
||||
// we need to backup its contents before drawing, so that
|
||||
// we can restore that area when the cursor needs to be
|
||||
// drawn somewhere else.
|
||||
struct buffer_clip {
|
||||
buffer_clip(int32 width, int32 height)
|
||||
{
|
||||
bpr = width * 4;
|
||||
if (bpr > 0 && height > 0)
|
||||
buffer = new uint8[bpr * height];
|
||||
else
|
||||
buffer = NULL;
|
||||
left = 0;
|
||||
top = 0;
|
||||
right = -1;
|
||||
bottom = -1;
|
||||
}
|
||||
~buffer_clip()
|
||||
{
|
||||
delete[] buffer;
|
||||
}
|
||||
uint8* buffer;
|
||||
int32 left;
|
||||
int32 top;
|
||||
int32 right;
|
||||
int32 bottom;
|
||||
int32 bpr;
|
||||
};
|
||||
|
||||
buffer_clip* fCursorAreaBackup;
|
||||
bool fSoftwareCursorHidden;
|
||||
|
||||
ServerCursor* fCursor;
|
||||
bool fCursorVisible;
|
||||
|
||||
Reference in New Issue
Block a user