Copy image command?

BlitzMax Forums/BlitzMax Beginners Area/Copy image command?

Kippykip(Posted 2013) [#1]
I want to use CopyImage like in old blitz products but no command exist!


Kippykip(Posted 2013) [#2]
Nevermind, just did this:
tempimage:TImage = image


GfK(Posted 2013) [#3]
That won't work.

All you've done is create an extra handle to the same image data.


Derron(Posted 2013) [#4]

'copies an TImage to not manipulate the source image
Function CopyImage:TImage(src:TImage)
   If src = Null Then Return Null

   Local dst:TImage = New TImage
   MemCopy(dst, src, SizeOf(dst))

   dst.pixmaps = New TPixmap[src.pixmaps.length]
   dst.frames = New TImageFrame[src.frames.length]
   dst.seqs = New Int[src.seqs.length]

   For Local i:Int = 0 To dst.pixmaps.length-1
      dst.pixmaps[i] = CopyPixmap(src.pixmaps[i])
   Next

   For Local i:Int = 0 To dst.frames.length-1
      dst.Frame(i)
   Next

   MemCopy(dst.seqs, src.seqs, SizeOf(dst.seqs))

   Return dst
End Function



bye
Ron


GfK(Posted 2013) [#5]
or...
newImage:TImage = LoadImage(LockImage(oldImage))



Derron(Posted 2013) [#6]
Yours should only rereference the previously used pixmap.

Means:

newImage is changed if you change oldImage's pixmap.


bye
Ron


GfK(Posted 2013) [#7]
Yours should only rereference the previously used pixmap.

Means:

newImage is changed if you change oldImage's pixmap.
Well, you're dead wrong:
Strict

Graphics 1024, 768

Global img1:TImage = CreateImage(256, 256)
Global img2:TImage

'make a random image
SeedRnd(MilliSecs())
For Local n:Int = 1 To 100
	SetColor Rand(0, 255), Rand(0, 255), Rand(0, 255)
	DrawOval(Rand(0, 255), Rand(0, 255), Rand(50, 75), Rand(50, 75))
Next
GrabImage(img1, 0, 0)

'make a copy
img2 = LoadImage(LockImage(img1))  '<<<<<Witchcraft

SetColor 255, 255, 255
While (Not AppTerminate()) And (Not KeyDown(KEY_ESCAPE))
	Cls
		DrawImage img2, 0, 0
		DrawText "copied image", 5, 5
		DrawImage img1, 300, 0
		DrawText "original image", 305, 5
		messWithImage()		
	Flip
Wend

Function messWithImage()
	Local px:TPixmap = LockImage(img1)
	For Local n:Int = 1 To 10
		WritePixel(px, Rand(0, 255), Rand(0, 255), $FFFFFFFF)
	Next
	UnlockImage(img1)
End Function


(and yes, it's messy, horrible code. But it demonstrates that what I said before is truth, and that's the only purpose of it).


Yan(Posted 2013) [#8]
Sorry GFK, they *are* referencing the same pixmap. If you force a texture re-creation/upload...
Strict

Graphics 1024, 768

Global img1:TImage = CreateImage(256, 256)
Global img2:TImage

'make a random image
SeedRnd(MilliSecs())
For Local n:Int = 1 To 100
	SetColor Rand(0, 255), Rand(0, 255), Rand(0, 255)
	DrawOval(Rand(0, 255), Rand(0, 255), Rand(50, 75), Rand(50, 75))
Next
GrabImage(img1, 0, 0)

'make a copy
img2 = LoadImage(LockImage(img1))  '<<<<<Witchcraft
'img2 = LoadImage(LockImage(img1).Copy())  'Copy Pixmap

SetColor 255, 255, 255
While (Not AppTerminate()) And (Not KeyDown(KEY_ESCAPE))
	If KeyHit(KEY_SPACE) Then Graphics 1024, 768
	
	Cls
		DrawImage img2, 0, 0
		DrawText "copied image", 5, 5
		DrawImage img1, 300, 0
		DrawText "original image", 305, 5
		messWithImage()		
	Flip
Wend

Function messWithImage()
	Local px:TPixmap = LockImage(img1)
	For Local n:Int = 1 To 10
		WritePixel(px, Rand(0, 255), Rand(0, 255), $FFFFFFFF)
	Next
	UnlockImage(img1)
End Function



TomToad(Posted 2013) [#9]
Yan is right. The reason you don't see changes in your example is because the pixmap is not actually drawn, but rather copied to a texture in the the video buffer, and then the texture is drawn. Since the second image is never locked, the new, modified pixmap is not copied to the second texture. Here is a modification of your example in which both images are locked. One is modified with white pixels and the other with green. You will notice that both images are drawn with both colors.
Strict

Graphics 1024, 768

Global img1:TImage = CreateImage(256, 256)
Global img2:TImage

'make a random image
SeedRnd(MilliSecs())
For Local n:Int = 1 To 100
	SetColor Rand(0, 255), Rand(0, 255), Rand(0, 255)
	DrawOval(Rand(0, 255), Rand(0, 255), Rand(50, 75), Rand(50, 75))
Next
GrabImage(img1, 0, 0)

'make a copy
img2 = LoadImage(LockImage(img1))  '<<<<<Witchcraft

SetColor 255, 255, 255
While (Not AppTerminate()) And (Not KeyDown(KEY_ESCAPE))
	Cls
		DrawImage img2, 0, 0
		DrawText "copied image", 5, 5
		DrawImage img1, 300, 0
		DrawText "original image", 305, 5
		messWithImage()		
	Flip
Wend

Function messWithImage()
	Local px:TPixmap = LockImage(img1)
	Local px2:TPixmap = LockImage(img2)
	For Local n:Int = 1 To 10
		WritePixel(px, Rand(0, 255), Rand(0, 255), $FFFFFFFF) 'write white pixels to original image
		WritePixel(px2, Rand(0, 255), Rand(0, 255), $FF00FF00) 'write green pixels to second image
	Next
	UnlockImage(img1)
	UnlockImage(img2)
End Function



Bremer(Posted 2013) [#10]
If you add this line:

img2.pixmaps[0] = CopyPixmap(img1.pixmaps[0])


after the line where you make the copy using the LoadImage command, then it seems to be getting its own pixmap to draw from, and the copy will only get the green dots, and the original will only get the white dots.


Yan(Posted 2013) [#11]
@Bremer: Which is essentialy what the commented out...
img2 = LoadImage(LockImage(img1).Copy())
...is doing in my previous post.


GfK(Posted 2013) [#12]
OK, you got me there. But I think we can all agree that this:
img2 = LoadImage(LockImage(img1).Copy())
is a hell of a lot more straightforward than this:
'copies an TImage to not manipulate the source image
Function CopyImage:TImage(src:TImage)
   If src = Null Then Return Null

   Local dst:TImage = New TImage
   MemCopy(dst, src, SizeOf(dst))

   dst.pixmaps = New TPixmap[src.pixmaps.length]
   dst.frames = New TImageFrame[src.frames.length]
   dst.seqs = New Int[src.seqs.length]

   For Local i:Int = 0 To dst.pixmaps.length-1
      dst.pixmaps[i] = CopyPixmap(src.pixmaps[i])
   Next

   For Local i:Int = 0 To dst.frames.length-1
      dst.Frame(i)
   Next

   MemCopy(dst.seqs, src.seqs, SizeOf(dst.seqs))

   Return dst
End Function



Derron(Posted 2013) [#13]
Sure your code is "more straightforward".

Have you tried yours with an animated Image?

"LoadImage(pixmap)" is what _your_ code does.

Mine takes care of animated images.


bye
Ron


Kippykip(Posted 2013) [#14]
Oh wow this thread has certainly grown
I would probably use Gfk copy image

Thanks everyone!