Board index » delphi » Help in Algorithm i wrote for Getting Partial Bitmap

Help in Algorithm i wrote for Getting Partial Bitmap

Hi ,
    I wrote the following procedure to Extract a portion of the Bitmap.

Function BytesPerLine(Width , BPP : DWord) : Word;
Begin
     Result :=  ((((Width * BPP + 31) shr 5)) shl 2);
End;

//HDIB - Contains  Bitmap Header and Data
//StartPos - Point Inside Bitmap Say 10,11
//BmpSize - How many pixels in X,Y direction to be copied.

Function GetPartialBitmap(var hDIB : HGlobal; Var StartPos,BmpSize : TPoint)
: Boolean;
Var
   hDIBRes : HGlobal;
   hDIbInput,
   hDIBResult  : PBITMAPINFOHEADER;
   lpDIBBitsInput,
   lpDIBBitsResult : Pointer;
   hdrsize,
   i,ORowBytes,
   NRowBytes : Integer;
   EndPos   : TPoint;
   Sptr,EPtr,
   Tptr : Pointer;
   NumSkipBytes : Integer;
Begin
    Result := True;
    hDIBInput := PBitmapInfoHeader(GlobalLock(hDIB));
    EndPos.x := StartPos.x + BmpSize.x;
    EndPos.y := StartPos.y + BmpSize.y;
    If (StartPos.x=0) and (StartPos.y=0) and
       (EndPos.x=hDIBInput^.biWidth) and (EndPos.y=hDIBInput^.biHeight) then
    Begin
       GlobalUnlock(hDIB);
       Exit;
    End;

    hdrsize := hDIBInput^.biSize+hDIBInput^.biClrUsed * sizeof(TRGBQUAD);
    lpDIBBitsInput := Pointer(longint(hDIBInput) + hdrsize);

    ORowBytes := BytesPerLine(hDIBInput^.biWidth,hDIBInput^.biBitCount); //
Original Row Bytes
    NRowBytes := BytesPerLine(BmpSize.x,hDIBInput^.biBitCount); // New Row
Bytes
    hDIBRes := GlobalAlloc(GMEM_MOVEABLE,(nRowBytes*BmpSize.y)+hdrsize);
    If hDIBRes = 0 then
    Begin
       Result := False;
    End Else
    Begin
       hDIBResult := PBitmapInfoHeader(GlobalLock(hDIBRes));
       lpDIBBitsResult := Pointer(longint(hDIBResult) + hdrsize);
       // Initialize the header information from the Previos Bitmap
       CopyMemory(hDIBResult,hDIBInput, hdrsize);
      // Updates its header with new size's
       hDIBResult^.biWidth := BmpSize.x;
       hDIBResult^.biheight := BmpSize.y;
       hDIBResult^.biSizeImage := nRowBytes*BmpSize.y;

     // Skip Start-height Rows of scanlines
       SPtr := Pointer(longint(lpDIBBitsInput)+StartPos.y*ORowBytes);
       EPtr := lpDIBBitsResult;
// These many bytes needed to skipped for X- Location
       NumSkipBytes := BytesPerLine(StartPos.x,hDIBInput^.biBitCount);
// Now copy data , line by line
       For i := 1 to BmpSize.y do
       Begin
            TPtr := Pointer(longint(Sptr) + NumSkipBytes);
            CopyMemory( EPtr, TPtr, nRowBytes);
            Sptr := Pointer(longint(Sptr)+ORowBytes);
            EPtr := Pointer(longint(EPtr)+NRowBytes);
       End;
       GlobalUnlock(hDIBRes);
    End;
    GlobalUnlock(hDIB);
    GlobalFree(hDIB);
    hDIB := hDIBRes;
End;

The problem what i am facing is that sometimes my colors will change to some
other colors . I am not able to understand to what is wrong in this code.
Logically it lookds really correct.
If I pick one pixel to the left or right then the colors comes OK. I am
testing this with a 24bpp Color Bitmap. Is there any relation between Bitmap
Width/Height and how data is stored.

Thanks in advance

TG.

 

Re:Help in Algorithm i wrote for Getting Partial Bitmap


TG,

I've not looked at your code in detail, but I do recall that bytes per
line has to be a multiple of 4, i.e. adjacent lines are aligned on 4-byte
boundaries.....

Oh, and if you want a partial bitmap, why not just use the GDI draw
functions?

David

Quote
"T.G" <toon_garfi...@hotmail.com> wrote in message

news:3b8eabfe_2@dnews...
Quote
> Hi ,
>     I wrote the following procedure to Extract a portion of the Bitmap.

> Function BytesPerLine(Width , BPP : DWord) : Word;
> Begin
>      Result :=  ((((Width * BPP + 31) shr 5)) shl 2);
> End;

Re:Help in Algorithm i wrote for Getting Partial Bitmap


Hi ,
    I need to rotate the partial Bitmap , which i cannot do unless i extract
a portion , rotate it and then draw.
Is there a work around to this or am i stuck.

TG

--

"David J Taylor" <david-tay...@blueyonder.co.uk> wrote in message
news:3b8f4a55$2_1@dnews...

Quote
> TG,

> I've not looked at your code in detail, but I do recall that bytes per
> line has to be a multiple of 4, i.e. adjacent lines are aligned on 4-byte
> boundaries.....

> Oh, and if you want a partial bitmap, why not just use the GDI draw
> functions?

> David

> "T.G" <toon_garfi...@hotmail.com> wrote in message
> news:3b8eabfe_2@dnews...
> > Hi ,
> >     I wrote the following procedure to Extract a portion of the Bitmap.

> > Function BytesPerLine(Width , BPP : DWord) : Word;
> > Begin
> >      Result :=  ((((Width * BPP + 31) shr 5)) shl 2);
> > End;

Re:Help in Algorithm i wrote for Getting Partial Bitmap


"T.G" <toon_garfi...@hotmail.com> wrote in <3b8f8d9d$2_2@dnews>:

Quote
>Hi ,
>    I need to rotate the partial Bitmap , which i cannot do unless i
>    extract
>a portion , rotate it and then draw.
>Is there a work around to this or am i stuck.

Well it depends havelly on the rotate procedure you use
you could add a start end pair of variable as input there
and trim the function to use only the portion you have
specify but it would need to return the results in a second
bitmap.

Regards
Johnnie.

Other Threads