I can definitely see thsi coming in handy somewhere down the road! Thanks for the code!
Code archives/Graphics/Large 2D Image Object
This code has been declared by its author to be Public Domain code.
Download source code
| Some Graphics cards have a problem displaying large textures. This object splits the textures into manageble sizes but still lets you rotate and scale the image as a single entity. |
' ------------------------------------------------------------------------------------
' Large Image made up of multiple fixed size textures.
' o - handles rotation and scaling
' o - displays large images irrespective of graphic card limitations.
' tesuji 2005
' -------------------------------------------------------------------------------------
Strict
Const FRAGSIZE = 256 ' maximum image fragment size
' ------------------------------------------------------------------------------------
' example usage
' ------------------------------------------------------------------------------------
Graphics 800,600,0
Local imageUrl:String = "/Users/sean/Pictures/1280x1024_starwars.jpg" ' <----- edit image file path
Local pixmap:TPixmap = LoadPixmap(imageUrl)
Local img:BigImage = BigImage.Create(pixmap)
Local scaleinc:Float = .01
While Not KeyHit(KEY_ESCAPE)
Cls
img.rotation :+ 1
img.scale :+ scaleinc
If img.scale < 0 Or img.scale > 2 scaleinc = -scaleinc
img.render()
Flip
Wend
End
' =============================
' Image Fragment
' =============================
Type ImageFragment
Field img:TImage
Field x,y
Field rotation:Float = 0
Field angle:Double
Field distance:Double
' ----------------------------------
' constructor
' ----------------------------------
Function create:ImageFragment(pmap:TPixmap,x:Float,y:Float,w,h)
Local frag:ImageFragment = New ImageFragment
frag.img = LoadImage(PixmapWindow(pmap,x,y,w,h),0|FILTEREDIMAGE)
x = (pmap.width*.5) - x
y = (pmap.height*.5) - y
frag.x = x
frag.y = y
frag.angle = ATan2(y,x)-180
frag.distance = Sqr(x*x + y*y)
Return frag
End Function
' --------------------
' Draw individual tile
' --------------------
Method render(scale:Float,xoff:Float=0,yoff:Float=0,rot:Float=0)
SetRotation rot
Local d:Float = Self.distance*scale
SetScale(scale,scale)
DrawImage(Self.img,(Cos(rot+Self.angle)*d)+xoff,(Sin(rot+Self.angle)*d)+yoff )
End Method
End Type
' ==================================
' Big Image
' ==================================
Type BigImage
Field pixmap:TPixmap
Field px,py
Field fragments:TList
Field scale:Float = 1
Field width
Field height
Field x:Float = 0
Field y:Float = 0
Field rotation:Float = 0
' ----------------------------------
' constructor
' ----------------------------------
Function create:BigImage(p:TPixmap)
Local bi:BigImage = New BigImage
bi.pixmap = p
bi.width = p.width
bi.height = p.height
bi.fragments = CreateList()
bi.load()
Return bi
End Function
' -------------------------------------
' convert pixmap into image fragments
' -------------------------------------
Method load()
Local px = 0
Local py = 0
Local loading = True
While (loading)
'FlushMem
Local w = FRAGSIZE
If Self.pixmap.width - px < FRAGSIZE w = Self.pixmap.width - px
Local h = FRAGSIZE
If Self.pixmap.height - py < FRAGSIZE h = Self.pixmap.height - py
Local f1:ImageFragment = ImageFragment.create(Self.pixmap,px,py,w,h)
ListAddLast Self.fragments,f1
px:+FRAGSIZE
If px >= Self.pixmap.width
px = 0
py:+FRAGSIZE
If py >= Self.pixmap.height loading = False
End If
Wend
End Method
' -----------------
' Draw entire image
' -----------------
Method render()
SetOrigin(GraphicsWidth()*.5,GraphicsHeight()*.5)
For Local f:ImageFragment = EachIn Self.fragments
f.render(Self.scale,Self.x,Self.y,Self.rotation)
Next
SetOrigin(0,0)
End Method
End Type |
Comments
Really nice, thanks.The Large 2D Image Object example zooms in and out , is there any way to modify it to scroll left to right ?
The Large 2D Image Object example zooms in and out , is there any way to modify it to scroll left to right ?
The fields X and Y in the BigImage type controls the offset as far as I can tell.
Need to remove flushmem from the code of course.
Yes, img.x,img.y can be used for positioning,img.scale for size and img.rotation to rotate the image :).
Have commented out the Flushmem so it'll compile ok now.
Have commented out the Flushmem so it'll compile ok now.
I Love this code! God Bless your generous heart!
I get "Unhandled Exception:Attempt to access field or method of Null object"
Weird.
Weird.
Works for me once I "edit image file path".
Ah yes.
Here's a question... Can you use regular collision detection using this method if you have a transparent background? This seems like it could be a pretty handy "level". Would the size make that difficult?
Here's a question... Can you use regular collision detection using this method if you have a transparent background? This seems like it could be a pretty handy "level". Would the size make that difficult?
This looks really great, but I'm thinking that possibly you could optimize it even more by only render ImageFragments that are actually in the viewport. Perhaps you're already doing this and I'm missing it, but it seems like each time in your render() loop you iterate through each fragment, regardless of if its on the screen or not.
(Though perhaps blitzmax is already optimized to handle this for you, in which case, nm)
(Though perhaps blitzmax is already optimized to handle this for you, in which case, nm)