toying with arrays - help pls

BlitzMax Forums/BlitzMax Beginners Area/toying with arrays - help pls

Hello Blitzers,

i need a little help with the following piece of code.

I am trying to load an image, slice it into 32^2 tiles, store these in an array and then draw the array.
This works on one computer but on another i get a

Unhandled Exception:Attempt to access field or method of Null object

SuperStrict
Global iwidth%,iheight%
Global twidth%=32,theight%=32
Global tilesx%,tilesy%
Global imagemap:TImage[tilesx,tilesy]

'GFX SETUP

SetGraphicsDriver GLMax2DDriver()
'SetGraphicsDriver GLGraphicsDriver()
Graphics 1024,768,32,60

Function iLoad(image_path:String)
	Local image:TImage = LoadImage(image_path)
	iwidth = ImageWidth(image)
	iheight = ImageHeight(image)
	tilesx%=iwidth/twidth
	tilesy%=iheight/theight
	imagemap = New TImage[tilesx,tilesy]
	DebugLog "Variables Set."
End Function

Function iTile(image_path:String)
	Local animimage:TImage = LoadAnimImage(image_path , twidth , theight , 0 , tilesx*tilesy)
	Local counti%=0
	For Local i% = 0 Until tilesy
		For Local j% = 0 Until tilesx
			imagemap[j,i] = LoadImage(animimage.pixmaps[counti])
			counti:+1
		Next
	Next
	DebugLog "Added "+ counti +" images."
End Function

Function Drawtiles()
	'DebugStop()
	For Local i% = 0 Until tilesx
		For Local j% = 0 Until tilesy
			DrawImage (imagemap[i,j],i*twidth,j*theight)
		Next
	Next
	DebugLog "Tiles Drawn"
End Function

iLoad ("tilerender_test1.bmp")
iTile ("tilerender_test1.bmp")
Drawtiles()
'For Local i% = 0 Until tilesx
'	DrawImage (imagemap[i,3],i*32,0)
'Next

Flip
WaitKey

EndGraphics


I put a debugstop in the Drawtiles Function as this seems to be the culprit.

I just don't understand why this works on some computers but not on others..

I think the following statement
counti:+1
in iTile() should be countJ: +1.

I'll have a closer look at it later.


counti:+1
in iTile() should be countJ: +1.



na thats not it. its just a counter and its name is currently "counti"

Thanks for looking :)

Does the program work on your computer btw?
Just put some image in the folder and exchange the hardcoded filename.

when using arrays they start at 0 so

32 images would be 0 to 31

try adding -1 to
tilesx
tilesy

ie
Function Drawtiles()
	'DebugStop()
	For Local i% = 0 Until tilesx-1
		For Local j% = 0 Until tilesy-1
			DrawImage (imagemap[i,j],i*twidth,j*theight)
		Next
	Next
	DebugLog "Tiles Drawn"
End Function


to explain a bit more a 320pix image is 10 32pix sprites they are added to the array at points 0-9
SuperStrict
Global iwidth%,iheight%
Global twidth%=32,theight%=32
Global tilesx%,tilesy%
Global imagemap:TImage[tilesx,tilesy]

'GFX SETUP

SetGraphicsDriver GLMax2DDriver()
'SetGraphicsDriver GLGraphicsDriver()
Graphics 1024,768,32,60

Function iLoad(image_path:String)
	Local image:TImage = LoadImage(image_path)
	iwidth = ImageWidth(image)
	iheight = ImageHeight(image)
	tilesx%=iwidth/twidth
	tilesy%=iheight/theight
	imagemap = New TImage[tilesx,tilesy]
	DebugLog "Variables Set."
End Function

Function iTile(image_path:String)
	Local animimage:TImage = LoadAnimImage(image_path , twidth , theight , 0 , tilesx*tilesy)
	Local counti%=0
	For Local i% = 0 Until tilesy-1
		For Local j% = 0 Until tilesx-1
			imagemap[j,i] = LoadImage(animimage.pixmaps[counti])
			counti:+1
		Next
	Next
	DebugLog "Added "+ counti +" images."
End Function

Function Drawtiles()
	'DebugStop()
	For Local i% = 0 Until tilesx-1
		For Local j% = 0 Until tilesy-1
			DrawImage (imagemap[i,j],i*twidth,j*theight)
		Next
	Next
	DebugLog "Tiles Drawn"
End Function

iLoad ("tilerender_test1.bmp")
iTile ("tilerender_test1.bmp")
Drawtiles()
'For Local i% = 0 Until tilesx-1
'	DrawImage (imagemap[i,3],i*32,0)
'Next

Flip
WaitKey

EndGraphics


Thanks Duckstab[o] but this also is not the case here i think.

You are correct with your explanation but that is why i am using 'until' in these loops so the 32th(last) iteration is not carried out.

But that was a lil problem when i used 'For ... to ...' statements :) where i used the -1 to circumvent the out of bounds array problem.

Tanks for looking :)

Right now i am starting to think it might have to do with the gfx-initialisation. This computer here (at work) is an old P3 with an onboard intel gfx chip.
So if the initialisation fails could a subsequent problem be that images are nulled?

I'm new and baffled *g*

Oh man, what was I thinking. I guess I read counti as i...your outer loop variable.

Meh, no wonder my code has been riddled with bugs tonight. Coding on no sleep = no fun.

Lol Sculp - i know what you mean ;)

Could you please try my code on your computer and see if it works?

If so i could solidify my bug-hunt on the gfx-driver issue.

What size is the image your are specifying in the file path?

I'm wondering if it has to do with OpenGL resizing the image.
Instead of calling LoadAnimImage, which will toss the image into VRAM and possibly require the image to be resized, why don't you just load it as a pixmap and then create your separate images (well, pixmaps in this case) with the PixmapWindow() function.

Here's some sloppy code from my old tile engine proto. The TTile type was basically just an image along with some flags, and you should be able to replace it with an image (with a few code modifications, of course.)

Method ConstructTileArray( Tile_Width:Short, Tile_Height:Short)	'create as many tiles as needed for the tileset and load each
							'of their images from disk
	Local Height:Short = PixmapHeight( TileSetPixMap )
	Local Width:Short = PixmapWidth( TileSetPixMap )
	Local TempPixMap:TPixmap
	Local TempTile:TTile
	
	
	
	
	Height = Height / Tile_Height	'height now equals num of tiles high
	Width = Width / Tile_width		'width now equals num of tiles wide
	
	'let's resize the tile array
	'the length is equal to Height X Width 
	'basically we're stretching the 2D pixmap into a 1D array
	
	TileArray = TileArray[..(Height*Width)]
	Print "Tile array length" + Len(TileArray)
	
	Local count:Short = 0
	
	For Local iter1 = 0 To (Height - 1)
		
		
		
		For Local iter2 = 0 To (Width - 1)
		'Print "Count " + count
		TempTile = New TTile	'create a new tile to put into the array
		'first we create a tile sized pixmap from the master pixmap	
		TempPixMap = PixmapWindow( TileSetPixMap, iter1 * Tile_Width, iter2 * Tile_Height, Tile_Width, Tile_Height)
		'then we make an image out of the temporary pixmap and put it into the tile
		'Print "Pixmap width, height " + PixmapWidth( TempPixMap ) + "," + PixmapHeight( TempPixMap )
		TempTile.Image = LoadImage( TempPixMap )
		'then we toss the tile into the tile array
		TileArray[count] = TempTile
		
		count:+ 1
		
		Next
	
	 
		
	
	Next
	

							
							
EndMethod


I ran the program successfully on my home computer with an image of 1024x768 dimension.

Any image which ist dividable into 32x32 tiles should work flawless.

You see that is the most irritating part for me: yesterday night the program runs great so i zip it up and send it to my office pc where i get an out of bounds/array error :(

Thanks for the code-example. I am much more inclined to track down the current problem though ;) (i hope you understand)

If all fails until i get home again i will research your code and probably work with pixmaps.

Btw. as i understand Animimage consists of pixmaps already.

Actually, if the image is resized it should still be padded to fill out the new boundaries, right? I mean, something has to be in the VRAM there.

I'll post code results in a min.

I'm getting the error

Error: Unable to calcualte tex size

and it's pointng to your DrawImage() function in DrawTiles().

This happened w/ both divisible & non-divisible by 32 tilesets.

no padding.

if you load an 800x600 picture it will get drawn 1:1 in a 1024x768 screen. it will just have an empty border. Thanks - looking forward to your test :)

Of course the OpenGL drivers here at my work computer suck, seeing as it's running an S3 Savage integrated graphics chip. :/

My own tile-engine runs in GL but not well. Some of the textures don't really load and are just white rectangles.

I'll test again in about 2 hours after I get home.

uh a new error :(

no idea what this means.
Did you put an image in the folder AND exchange both occurences of the filename in code?

Yup. Actually I fully specified the path name. The output says that it added 64 images, but then the error pops up.

I had forgotten to test your code in DirectX. It works fine.


Also, I narrowed my OpenGL tex error down to the following code in image.bmx
	Method Frame:TImageFrame( index )
		If seqs[index]=GraphicsSeq Return frames[index]
		seqs[index]=GraphicsSeq
		frames[index]=_max2dDriver.CreateFrameFromPixmap(  Lock(index,True,False),flags )   '<---this line fails.
		Return frames[index]
	End Method


Thanks a bunch Sculp :)

So the error is tied to the driver. As i suspected...

But alas i have no idea how to fix it.
Drawimage in OGL seems to expect something special.
Looks like i will spend some hours testing. Or does anyone know whats going wrong here?