[Date Prev][Date Next][Thread Prev][Thread Next][Thread Index]

RE: [XaraXtreme-dev] Bitmap Gallery drag/View redraw



- Copy the rendered drag into OffscreenDC (XOR-blit)

Sorry, Alex, but this bit should be OR and not XOR...

Gerry

-----Original Message-----
From: owner-dev@xxxxxxxxxxxxxxxx [mailto:owner-dev@xxxxxxxxxxxxxxxx] On
Behalf Of Gerry Iles
Sent: 28 April 2006 13:34
To: dev@xxxxxxxxxxxxxx
Subject: RE: [XaraXtreme-dev] Bitmap Gallery drag/View redraw

Hi Alex,

I though I ported that function pretty accurately but the colour drags
don't use it so I it hasn't really been tested yet.  The original MFC
based function is as below.  I suppose I might have got some of the blit
modes wrong.  It does the following:
- Create ScratchDC of the current drag rectangle
- Copy the current screen contents into ScratchDC
- Copy the old drag rectangle parts of the stored background from BackDC
into ScratchDC.
- Create TempDC of the current drag rectangle
- Ask the DragInfo to render the drag into TempDC
- Apply the MaskBitmap by doing an AND-blit into TempDC
- Create OffscreenDC of the current drag rectangle
- Copy ScratchDC into OffscreenDC
- Apply MaskBitmap to OffscreenDC (AND-blit)
- Copy the rendered drag into OffscreenDC (XOR-blit)
- Copy part of OffscreenDC into stored background (BackDC)
- Copy OffscreenDC to screen
- Copy stored background (BackDC) to screen (old drag rectangle)
- Store away the new background for next time (copy ScratchDC to BackDC)

The AND and XOR parts are a bit tricky to get your head around but they
do make sense.  The wx version calls them something very different so
the Boolean nature isn't obvious...

The problem is almost certainly something to do with the mask bitmap.
Most probably colours for the masking need to be set up (there are two
lines commented out as I wasn't sure what to change them to and wasn't
concerned with transparent drags at the time). 

Gerry


BOOL CaptureWnd::DrawTransparentDrag(CPoint point, int Transparency)
{
	// offset mouse pos by drag offset
	
point.Offset(DragManagerOp::CurrentManager->CurrentDragInfo->SolidDragOf
fset);

	// size of solid drag draw bounds
	CSize DSize =
DragManagerOp::CurrentManager->CurrentDragInfo->SolidDragSize;


  	// create a few	DCs !!!
	
	// this one will hold the old background
 	CDC * BackDC;
 	TRY
	{
 		BackDC = new CDC();
	}
	END_TRY

	CBitmap * OldBackBit;
	
	if(BackDC == NULL)
		return FALSE;

	BackDC->CreateCompatibleDC(pDisplayDC);
	// select bitmap into the dc
	OldBackBit = BackDC->SelectObject(BackBitmap);

	// this one is just temp
	CDC * ScratchDC;

	TRY
	{
		ScratchDC = new CDC();
	}
	END_TRY

	CBitmap * ScratchBit;

	TRY
	{
		ScratchBit = new CBitmap();
	}
	END_TRY

	TRY
	{
		TempBitmap = new CBitmap();
	}
	END_TRY

	TRY
	{
		pTempDC = new CDC();
	}
	END_TRY

	TRY
	{
		pMaskDC = new CDC();
	}
	END_TRY

	CBitmap * RestoreBitmap;
	
	if(ScratchDC == NULL ||ScratchBit == NULL)
		return FALSE;

	if(pTempDC == NULL ||TempBitmap == NULL)
		return FALSE;

	if(pMaskDC == NULL)
		return FALSE;

	// get a compatible DC
	ScratchDC->CreateCompatibleDC(pDisplayDC);
	
	// make a compatible bitmap
	
ScratchBit->CreateCompatibleBitmap(pDisplayDC,DSize.cx,DSize.cy);

	// select bitmap into the dc
	RestoreBitmap = ScratchDC->SelectObject(ScratchBit);
	
	// make copy of last rect
	CRect OldRect = DragRect;
	
	// set new drag draw bounds
	
DragRect.SetRect(point.x,point.y,point.x+DSize.cx,point.y+DSize.cy);
	
	// Copy screen to new background
	
ScratchDC->BitBlt(0,0,DSize.cx,DSize.cy,pDisplayDC,DragRect.left,DragRec
t.top,SRCCOPY);

	CPoint Change;
	Change.x = OldRect.left - DragRect.left;
	Change.y = OldRect.top - DragRect.top;
	

	// Replace part of new bkg with old background
	if(!OldRect.IsRectEmpty())
	
ScratchDC->BitBlt(Change.x,Change.y,DSize.cx,DSize.cy,BackDC,0,0,SRCCOPY
);

	// Create a CBitmap the same size as our one
	TempBitmap->CreateCompatibleBitmap(pDisplayDC, DSize.cx,
DSize.cy);
	pTempDC->CreateCompatibleDC(pDisplayDC);

	CBitmap* OldTempBmp = pTempDC->SelectObject(TempBitmap);

	// Render into the temporary bitmap
	DragManagerOp::CurrentManager->CurrentDragInfo->
		OnDrawSolidDrag(CPoint(0,0), pTempDC);

	// set the colours for the masking
	pTempDC->SetBkColor(RGB(0,0,0));
	pTempDC->SetTextColor(RGB(255,255,255));

	pMaskDC->CreateCompatibleDC(pDisplayDC);
	CBitmap* OldMaskBmp = pMaskDC->SelectObject(MaskBitmap);

	pTempDC->BitBlt(		0, 0,
							DSize.cx,
							DSize.cy,
							pMaskDC,
							0,0,
							SRCAND
							);

	CBitmap OffScreenBmp;
	// Create a CBitmap the same size as our one
	OffScreenBmp.CreateCompatibleBitmap(pDisplayDC, DSize.cx,
DSize.cy);

	CDC OffScreenDC;
	// Create a memory DC based on this render region
	OffScreenDC.CreateCompatibleDC(pDisplayDC);

	CBitmap* OldOffScreenBmp =
OffScreenDC.SelectObject(&OffScreenBmp);

	OffScreenDC.BitBlt(0,0,DSize.cx,DSize.cy,ScratchDC,0,0,SRCCOPY);

	OffScreenDC.BitBlt(			0, 0,
	
DSize.cx,
	
DSize.cy,
								pMaskDC,
								0,0,
								SRCAND
								);

	OffScreenDC.BitBlt(			0, 0,
	
DSize.cx,
	
DSize.cy,
								pTempDC,
								0,0,
								SRCPAINT
								);

	// Copy part of image to old background
	BackDC->BitBlt(-Change.x,-Change.y, DSize.cx, DSize.cy,
&OffScreenDC, 0,0, SRCCOPY);
	
	// Copy image to screen
	pDisplayDC->BitBlt(DragRect.left,DragRect.top,DSize.cx,DSize.cy,
&OffScreenDC,0,0,SRCCOPY);

	OffScreenDC.SelectObject(OldOffScreenBmp);
	OffScreenBmp.DeleteObject();

	pTempDC->SelectObject(OldTempBmp);
	TempBitmap->DeleteObject();
	
	delete pTempDC;
	delete TempBitmap;

	pMaskDC->SelectObject(OldMaskBmp);
	delete pMaskDC;

	// Copy old background to screen
	if(!OldRect.IsRectEmpty())
	
pDisplayDC->BitBlt(OldRect.left,OldRect.top,DSize.cx,DSize.cy,BackDC,0,0
,SRCCOPY);
	
	// copy new background into old for next time round
	BackDC->BitBlt(0,0,DSize.cx,DSize.cy,ScratchDC,0,0,SRCCOPY);

	// clean up and delete scratch dc and bitmap
	ScratchDC->SelectObject(RestoreBitmap);
	delete ScratchDC;
	delete ScratchBit;

	BackDC->SelectObject(OldBackBit);
	delete BackDC;

	FirstBlit = FALSE;
	
	return TRUE;
}

-----Original Message-----
From: owner-dev@xxxxxxxxxxxxxxxx [mailto:owner-dev@xxxxxxxxxxxxxxxx] On
Behalf Of Alex Bligh
Sent: 28 April 2006 12:54
To: dev@xxxxxxxxxxxxxx
Cc: Alex Bligh
Subject: Re: [XaraXtreme-dev] Bitmap Gallery drag/View redraw

Gerry,

Gerry Iles wrote:
> I've just fixed up dragbmp.cpp/.h to compile though the rendering code
> is currently PORTNOTEd out.
> 
> It should be reasonably simple to port the rest by looking at other
bits
> of rendering code that have already been ported...
> 
> I think that using the wx dragging classes would involve modifying the
> whole DragManagerOp system to suit it...

OK, I fixed this up, but I am having problems with:

BOOL CaptureWnd::DrawTransparentDrag(wxPoint point, INT32 Transparency)

which I think you fixed up earlier. In essence, it doesn't seem to work!
(it always draws black).

I have #ifdef'd out its use (so it isn't called on GTK) but I don't
really understand how it was meant to work in the first place and
don't have the windows code. Any chance you could take a look please?

Dragging a bitmap in the bitmap gallery is a good test.

(the remaining portnote is for when there is no bitmap - I'll
fix that up in a bit).

Alex