Avoid hiding and unhiding the mouse cursor when copying bitmaps to the
screen. Instead, copy a merged bitmap 1 line at a time. This fixes flashing of the cursor and is faster in all modes (especially in planar modes).
This commit is contained in:
parent
c7432537b1
commit
a07067ea3f
@ -167,8 +167,17 @@ int
|
||||
__VGLBitmapCopy(VGLBitmap *src, int srcx, int srcy,
|
||||
VGLBitmap *dst, int dstx, int dsty, int width, int hight)
|
||||
{
|
||||
int srcline, dstline, yend, yextra, ystep;
|
||||
|
||||
byte *buffer, *p;
|
||||
int mousemerge, srcline, dstline, yend, yextra, ystep;
|
||||
|
||||
mousemerge = 0;
|
||||
if (hight < 0) {
|
||||
hight = -hight;
|
||||
mousemerge = (dst == VGLDisplay &&
|
||||
VGLMouseOverlap(dstx, dsty, width, hight));
|
||||
if (mousemerge)
|
||||
buffer = alloca(width*src->PixelBytes);
|
||||
}
|
||||
if (srcx>src->VXsize || srcy>src->VYsize
|
||||
|| dstx>dst->VXsize || dsty>dst->VYsize)
|
||||
return -1;
|
||||
@ -204,8 +213,13 @@ __VGLBitmapCopy(VGLBitmap *src, int srcx, int srcy,
|
||||
}
|
||||
for (srcline = srcy + yextra, dstline = dsty + yextra; srcline != yend;
|
||||
srcline += ystep, dstline += ystep) {
|
||||
WriteVerticalLine(dst, dstx, dstline, width,
|
||||
src->Bitmap+(srcline*src->VXsize+srcx)*dst->PixelBytes);
|
||||
p = src->Bitmap+(srcline*src->VXsize+srcx)*dst->PixelBytes;
|
||||
if (mousemerge && VGLMouseOverlap(dstx, dstline, width, 1)) {
|
||||
bcopy(p, buffer, width*src->PixelBytes);
|
||||
p = buffer;
|
||||
VGLMouseMerge(dstx, dstline, width, p);
|
||||
}
|
||||
WriteVerticalLine(dst, dstx, dstline, width, p);
|
||||
}
|
||||
return 0;
|
||||
}
|
||||
@ -214,36 +228,29 @@ int
|
||||
VGLBitmapCopy(VGLBitmap *src, int srcx, int srcy,
|
||||
VGLBitmap *dst, int dstx, int dsty, int width, int hight)
|
||||
{
|
||||
int error, mouseoverlap;
|
||||
int error;
|
||||
|
||||
if (hight < 0)
|
||||
return -1;
|
||||
if (src == VGLDisplay)
|
||||
src = &VGLVDisplay;
|
||||
if (src->Type != MEMBUF)
|
||||
return -1; /* invalid */
|
||||
if (dst == VGLDisplay) {
|
||||
VGLMouseFreeze();
|
||||
mouseoverlap = VGLMouseOverlap(dstx, dsty, width, hight);
|
||||
if (mouseoverlap)
|
||||
VGLMousePointerHide();
|
||||
__VGLBitmapCopy(src, srcx, srcy, &VGLVDisplay, dstx, dsty, width, hight);
|
||||
error = __VGLBitmapCopy(src, srcx, srcy, &VGLVDisplay, dstx, dsty,
|
||||
width, hight);
|
||||
if (error != 0) {
|
||||
if (mouseoverlap)
|
||||
VGLMousePointerShow();
|
||||
VGLMouseUnFreeze();
|
||||
if (error != 0)
|
||||
return error;
|
||||
}
|
||||
src = &VGLVDisplay;
|
||||
srcx = dstx;
|
||||
srcy = dsty;
|
||||
} else if (dst->Type != MEMBUF)
|
||||
return -1; /* invalid */
|
||||
error = __VGLBitmapCopy(src, srcx, srcy, dst, dstx, dsty, width, hight);
|
||||
if (dst == VGLDisplay) {
|
||||
if (mouseoverlap)
|
||||
VGLMousePointerShow();
|
||||
error = __VGLBitmapCopy(src, srcx, srcy, dst, dstx, dsty, width, -hight);
|
||||
if (dst == VGLDisplay)
|
||||
VGLMouseUnFreeze();
|
||||
}
|
||||
return error;
|
||||
}
|
||||
|
||||
|
@ -355,6 +355,25 @@ VGLMouseOverlap(int x, int y, int width, int hight)
|
||||
return overlap > 0;
|
||||
}
|
||||
|
||||
void
|
||||
VGLMouseMerge(int x, int y, int width, byte *line)
|
||||
{
|
||||
int pos, x1, xend, xstart;
|
||||
|
||||
xstart = x;
|
||||
if (xstart < VGLMouseXpos)
|
||||
xstart = VGLMouseXpos;
|
||||
xend = x + width;
|
||||
if (xend > VGLMouseXpos + MOUSE_IMG_SIZE)
|
||||
xend = VGLMouseXpos + MOUSE_IMG_SIZE;
|
||||
for (x1 = xstart; x1 < xend; x1++) {
|
||||
pos = (y - VGLMouseYpos) * MOUSE_IMG_SIZE + x1 - VGLMouseXpos;
|
||||
if (VGLMouseAndMask->Bitmap[pos])
|
||||
bcopy(&VGLMouseOrMask->Bitmap[pos * VGLDisplay->PixelBytes],
|
||||
&line[(x1 - x) * VGLDisplay->PixelBytes], VGLDisplay->PixelBytes);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
VGLMouseUnFreeze()
|
||||
{
|
||||
|
@ -136,6 +136,7 @@ void VGLMouseRestore(void);
|
||||
int VGLMouseStatus(int *x, int *y, char *buttons);
|
||||
void VGLMouseFreeze(void);
|
||||
int VGLMouseFreezeXY(int x, int y);
|
||||
void VGLMouseMerge(int x, int y, int width, byte *line);
|
||||
int VGLMouseOverlap(int x, int y, int width, int hight);
|
||||
void VGLMouseUnFreeze(void);
|
||||
/* simple.c */
|
||||
|
Loading…
Reference in New Issue
Block a user