[Gdal-dev] Writing bit interleaved data with GDALRasterBand::RasterIO

Chapman, Martin MChapman at sanz.com
Wed Jul 7 12:35:29 EDT 2004


Frank,

I'm not sure if I mean byte or pixel interleave.  I want to save data
the I have in a windows DIB.  When I create the DIB from a gdal dataset
I interleave the bits into the following structure something like
this...

unsigned char* pCombinedBytes = (unsigned char*)
CPLMalloc(sizeof(unsigned char) * nWidth * nHeight * nSize);
//Where nSize is the number of bands and nWidth and nHeight is the aoi w
and h...

//then I retrieve the bytes for each band something like this...

void** pBandBuffer = (void**) new unsigned char*[nSize];
//for each band 
	pBandBytes = (unsigned char*) CPLMalloc(sizeof(unsigned char) *
nWidth * nHeight);
	pBand->RasterIO(GF_Read, nXOffset, nYOffset, nWidth, nHeight,
pBandBytes, nWidth , nHeight, GDT_Byte, 0, 0);
	pBandBuffer[n] = pBandBytes;
//end if

// then I interleave the bytes into one array...

for (long i = 0, long j = 0; i < (nWidth * nHeight * nSize); i += nSize,
j++)
{
	int k = i;

	for (int m = nSize - 1; m >= 0; m--, k++)
	{
		unsigned char* pBytes = (unsigned char*) pBandBuffer[m];
		ptr_dest = pCombinedBytes + k;
		unsigned char b = pBytes[j];

		if (pCT != NULL)
		{
			GDALColorEntry ce;
			unsigned int c = (unsigned int) b;
			c = pCT->GetColorEntryAsRGB(c, &ce);
			if (m == 0) c = ce.c1;
			if (m == 1) c = ce.c2;
			if (m == 2) c = ce.c3;
			b = (unsigned char) c;
		}

		ptr_src = &b;
		memcpy(ptr_dest, ptr_src, 1);
	}
}

// then I realign the bytes for a windows DIB...

m_pDIBSection->Create(nWidth ,nHeight, 24);
unsigned int dibwidth = m_pDIBSection->GetTotalWidth();

GByte* dest = (GByte*) m_pDIBSection->GetBits();
GByte* src = (GByte*) pCombinedBytes;

for (int row = 0; row < nHeight; row++)
{
	ptr_dest = dest + row * dibwidth * nSize;
	ptr_src = src + row * nWidth * nSize;
	memcpy(ptr_dest, ptr_src, nWidth * nSize);
}

So I think I am pixel interleaving then?  Anyway, I think the example
you sent me will work if I undo the windows DIB realignment, (which
would be really cool).  I'll let you know if it works.

Thanks for the quick response.

Martin

-----Original Message-----
From: Frank Warmerdam [mailto:warmerdam at pobox.com] 
Sent: Wednesday, July 07, 2004 10:02 AM
To: Chapman, Martin
Cc: gdal-dev
Subject: Re: [Gdal-dev] Writing bit interleaved data with
GDALRasterBand::RasterIO


Chapman, Martin wrote:
> All,
>  
> If I have raster data stored as bit interleaved 
> (r,g,b,r,g,b,r,g,b...),
> can I use the GDALRasterBand::RasterIO function to write this data to 
> disc?  I read that the nPixelSpace and nLineSpace parameters allow 
> reading into or writing from unusually organized buffers.  If this is 
> possible, could someone please provide me a brief example of how to
use 
> these parameters with this type of data structure?

Martin,

Do you literally mean bit interleaved?  Or pixel interleaved?

I'll assume you mean pixel interleaved.   To write from a pixel
interleaved
1 line buffer of 8bit data you might use:

poBandRed->RasterIO( GF_Write, 0, line, xsize, 1,
                      pabyRGB + 0, xsize, 1, GDT_Byte,
                      3, xsize * 3 );

poBandGreen->RasterIO( GF_Write, 0, line, xsize, 1,
                      pabyRGB + 1, xsize, 1, GDT_Byte,
                      3, xsize * 3 );
poBandBlue->RasterIO( GF_Write, 0, line, xsize, 1,
                      pabyRGB + 2, xsize, 1, GDT_Byte,
                      3, xsize * 3 );

Note that the buffer pointer you pass in needs to point to the beginning
of the data to be written (hence the +1 and +2 offsets on pabyRGB for
green and blue).  The nPixelSpace is the number of bytes from the
beginning of one pixel to the beginning of the next.  3 in this case
since there are 3 bytes of data for for each pixel written.  The
linespacing is the offset from the beginning of one line to the next, so
xsize * 3 in this case.

I hope this helps. If your data is really "bit" interleaved you will
need to repack stuff before writing.

Best regards,

-- 
---------------------------------------+--------------------------------
---------------------------------------+------
I set the clouds in motion - turn up   | Frank Warmerdam,
warmerdam at pobox.com
light and sound - activate the windows | http://pobox.com/~warmerdam
and watch the world go round - Rush    | Geospatial Programmer for Rent




More information about the Gdal-dev mailing list