ja mietin että mihis se cb pystyy. Hiirellä voi vähän muuttaa perspektiiviä.
Code: Select all
Dim ScreenImages(255) As integer
Global ScreenEmptyImage, ScreenImageCount, ScreenImageLimit, ImageScreenInitialized
Global gScaledImage
gScaledImage = MakeImage(1, 1)
CONST BYTE_SIZE = 4
//offset of data in memoryblocks
Const MEMBLOCK_OFFSET_ScreenImageLayers = 0
Const MEMBLOCK_OFFSET_ScreenTextureWidth = 4
Const MEMBLOCK_OFFSET_ScreenTextureHeight = 8
Const MEMBLOCK_OFFSET_ScreenWidth = 12
Const MEMBLOCK_OFFSET_ScreenHeight = 16
Const MEMBLOCK_OFFSET_ScreenLayerAmount = 20
Const MEMBLOCK_OFFSET_ScreenBufferType = 24
Const MEMBLOCK_OFFSET_ScreenBuffer = 25
Const MEMBLOCK_OFFSET_ScreenRenderScaleFactor = 29
Const MEMBLOCK_SIZE_Screen = 33
CONST MEMBLOCK_OFFSET_LayerBaseImage = 0
CONST MEMBLOCK_OFFSET_LayerScaledImage = 4
CONST MEMBLOCK_OFFSET_LayerNewImageCount = 8
CONST MEMBLOCK_OFFSET_LayerNewImageList = 12
CONST MEMBLOCK_OFFSET_LayerNewImageListSize = 16
Const MEMBLOCK_SIZE_Layer = 20
Const MEMBLOCK_OFFSET_ImageIndex = 0
Const MEMBLOCK_OFFSET_ImageX = 4
Const MEMBLOCK_OFFSET_ImageY = 8
Const MEMBLOCK_SIZE_Image = 12
Const LIST_INCREASE_SIZE = 20
CONST BUFFERTYPE_MEMBLOCK = 1
CONST BUFFERTYPE_STREAMFILE = 2
Function InitializeImageScreenLibrary(limit=255)
ScreenEmptyImage = MakeImage(10,10)
ScreenImageLimit = limit
ReDim ScreenImages(limit) As integer
ScreenImageCount = 0
ImageScreenInitialized=1
End Function
Function MakeImageScreen(width=16, height=16, imageW=32, imageH=32, layerAmount=10)
mem = MakeMEMBlock(MEMBLOCK_SIZE_Screen)
width = Max(width, 1)
height = Max(height, 1)
PokeInt mem,MEMBLOCK_OFFSET_ScreenTextureWidth, imageW
PokeInt mem,MEMBLOCK_OFFSET_ScreenTextureHeight, imageH
PokeInt mem,MEMBLOCK_OFFSET_ScreenWidth, width
PokeInt mem,MEMBLOCK_OFFSET_ScreenHeight, height
PokeInt mem,MEMBLOCK_OFFSET_ScreenLayerAmount, layerAmount
PokeFloat mem, MEMBLOCK_OFFSET_ScreenRenderScaleFactor, 1.0
//use buffer only if it's small enough
if (width * height * layerAmount < 100000) Then
PokeByte mem,MEMBLOCK_OFFSET_ScreenBufferType, BUFFERTYPE_MEMBLOCK
else
PokeByte mem,MEMBLOCK_OFFSET_ScreenBufferType, BUFFERTYPE_STREAMFILE
endif
ClearImageScreen(mem)
Return mem
End Function
//Deletes Image Screen
Function DeleteImageScreen(mem)
if (mem and MEMBlockSize(mem) = MEMBLOCK_SIZE_Screen) Then
layerObjects = Peekint(mem,MEMBLOCK_OFFSET_ScreenImageLayers)
layerAmount = PeekInt(mem,MEMBLOCK_OFFSET_ScreenLayerAmount)
// delete previous layer images and memblocks if present
if (layerObjects) then
for iterator=0 to MemBlocksize(layerObjects)-1 step BYTE_SIZE
layer = PeekInt(layerObjects, iterator)
if (layer) Then
layerImage = PeekInt(layer,MEMBLOCK_OFFSET_LayerBaseImage)
if (layerImage) then DeleteImage layerImage
changeList = peekint(layer,MEMBLOCK_OFFSET_LayerNewImageList)
if (changeList) then
DeleteMEMBlock changeList
endif
DeleteMEMBlock layer
Endif
next iterator
DeleteMEMBlock layerObjects
EndIf
bufferType = PeekByte(mem,MEMBLOCK_OFFSET_ScreenBufferType)
if (bufferType = BUFFERTYPE_MEMBLOCK) then
screenBuffer = PeekInt(mem,MEMBLOCK_OFFSET_ScreenBuffer)
// remove screen buffer
if (screenBuffer) then DeleteMEMBlock screenBuffer
endif
DeleteMEMBlock mem
EndIf
End Function
//Clears all ImageScreen layerObjects
Function ClearImageScreen(mem)
If mem Then
If MEMBlockSize(mem) = MEMBLOCK_SIZE_Screen Then
width = PeekInt(mem,MEMBLOCK_OFFSET_ScreenWidth)
height = PeekInt(mem,MEMBLOCK_OFFSET_ScreenHeight)
layerAmount = PeekInt(mem,MEMBLOCK_OFFSET_ScreenLayerAmount)
bufferType = PeekByte(mem,MEMBLOCK_OFFSET_ScreenBufferType)
if (bufferType = BUFFERTYPE_MEMBLOCK) then
screenBuffer = PeekInt(mem,MEMBLOCK_OFFSET_ScreenBuffer)
// remove screen buffer
if (screenBuffer) then DeleteMEMBlock screenBuffer
// init screen buffer
PokeInt mem,MEMBLOCK_OFFSET_ScreenBuffer, MakeMEMBlock(width * height * layerAmount * BYTE_SIZE)
endif
// init new memblocks and images for layerObjects
ImageScreenInitLayers(mem)
endif
endif
end function
//(Re)creates ImageScreen layerObjects
Function ImageScreenInitLayers(mem)
If ImageScreenInitialized=0 Then MakeError "You must call ImageScreenInitialize() before calling other ImageScreen functions!"
if (mem and MEMBlockSize(mem) = MEMBLOCK_SIZE_Screen) Then
previousLayers = Peekint(mem,MEMBLOCK_OFFSET_ScreenImageLayers)
layerAmount = PeekInt(mem,MEMBLOCK_OFFSET_ScreenLayerAmount)
// delete previous layer images and memblocks if present
if (previousLayers) then
for iterator=0 to MemBlocksize(previousLayers)-1 step BYTE_SIZE
layer = PeekInt(previousLayers, iterator)
if (layer) Then
layerImage = PeekInt(layer,MEMBLOCK_OFFSET_LayerBaseImage)
if (layerImage) then DeleteImage layerImage
changeList = peekint(layer,MEMBLOCK_OFFSET_LayerNewImageList)
if (changeList) then
DeleteMEMBlock changeList
endif
DeleteMEMBlock layer
Endif
next iterator
DeleteMEMBlock previousLayers
EndIf
width = PeekInt(mem,MEMBLOCK_OFFSET_ScreenWidth)
height = PeekInt(mem,MEMBLOCK_OFFSET_ScreenHeight)
//create new layerObjects
layerObjects = MakeMemblock(BYTE_SIZE * layerAmount)
textureWidth = PeekInt(mem,MEMBLOCK_OFFSET_ScreenTextureWidth)
textureHeight = PeekInt(mem,MEMBLOCK_OFFSET_ScreenTextureHeight)
for iterator=0 to layerAmount-1
layer = MakeMemBlock(MEMBLOCK_SIZE_Layer)
PokeInt layer, MEMBLOCK_OFFSET_LayerBaseImage, MakeImage(width * textureWidth, height * textureHeight)
PokeInt layer, MEMBLOCK_OFFSET_LayerScaledImage, MakeImage(1,1)
PokeInt layer, MEMBLOCK_OFFSET_LayerNewImageCount, 0
changeListSize = LIST_INCREASE_SIZE * MEMBLOCK_SIZE_Image
PokeInt layer, MEMBLOCK_OFFSET_LayerNewImageListSize, changeListSize
PokeInt layer, MEMBLOCK_OFFSET_LayerNewImageList, MakeMEMBlock(changeListSize)
PokeInt layerObjects, iterator * BYTE_SIZE, layer
next iterator
PokeInt mem, MEMBLOCK_OFFSET_ScreenImageLayers, layerObjects
Endif
End function
//Sets value to ImageScreen
Function ImageScreenPut(mem, x, y, imageIndex=0, layer=0, fillLayer=0, fillAllLayers=0)
If (mem And layer > -1 and imageIndex >= 0 and imageIndex < ScreenImageCount) Then
If MEMBlockSize(mem) = MEMBLOCK_SIZE_Screen Then
width = PeekInt(mem,MEMBLOCK_OFFSET_ScreenWidth)
height = PeekInt(mem,MEMBLOCK_OFFSET_ScreenHeight)
layerAmount = PeekInt(mem,MEMBLOCK_OFFSET_ScreenLayerAmount)
layerObjects = PeekInt(mem,MEMBLOCK_OFFSET_ScreenImageLayers)
bufferType = PeekByte(mem,MEMBLOCK_OFFSET_ScreenBufferType)
if (bufferType = BUFFERTYPE_MEMBLOCK) then screenBuffer = PeekInt(mem,MEMBLOCK_OFFSET_ScreenBuffer)
//put value to only one cell
If (fillLayer=0 and layerObjects <> 0 ) Then
//check that coordinates are inside of screen and layer exists
If ( x => 0)( x < width )( y => 0)( y < height )( layer < layerAmount) Then
//start at last layer if clearing all layerObjects
if (fillAllLayers=1) Then layerIndex = layerAmount-1 Else layerIndex = layer
// loop through all layerObjects
while (layerIndex >= 0)
// if buffer is used check old value
if (bufferType = BUFFERTYPE_MEMBLOCK) then
// get old value
oldValue = PeekInt (screenBuffer,(x + y * width + layerIndex * width * height) * BYTE_SIZE)
writeValue = (oldValue <> imageIndex )
else
writeValue = true
endif
if (writeValue) then
//set buffer value to imageIndex
if (bufferType = BUFFERTYPE_MEMBLOCK) then PokeInt screenBuffer,(x + y * width + layerIndex * width * height) * BYTE_SIZE, imageIndex
layerObject = Peekint(layerObjects, layerIndex * BYTE_SIZE)
if (layerObject <> 0) Then
layerChangeList = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerNewImageList)
if (layerChangeList <> 0) Then
layerChangedAmount = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerNewImageCount)
changeListSize = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerNewImageListSize)
//changelist is too small, increase size
if ( changeListSize < (layerChangedAmount+1) * MEMBLOCK_SIZE_Image) then
newSize = (layerChangedAmount + LIST_INCREASE_SIZE) * MEMBLOCK_SIZE_Image
ResizeMEMBlock layerChangeList, newSize
//resize can alter pointer so save
pokeint layerObject, MEMBLOCK_OFFSET_LayerNewImageList, layerChangeList
//store new size
PokeInt layerObject, MEMBLOCK_OFFSET_LayerNewImageListSize, newSize
endif
// Add value to changelist
PokeInt layerChangeList, layerChangedAmount * MEMBLOCK_SIZE_Image + MEMBLOCK_OFFSET_ImageIndex, imageIndex
PokeInt layerChangeList, layerChangedAmount * MEMBLOCK_SIZE_Image + MEMBLOCK_OFFSET_ImageX, x
PokeInt layerChangeList, layerChangedAmount * MEMBLOCK_SIZE_Image + MEMBLOCK_OFFSET_ImageY, y
//increase changelist counter
PokeInt layerObject, MEMBLOCK_OFFSET_LayerNewImageCount, layerChangedAmount + 1
endif
Endif
EndIf
//break out if not going to clear all layerObjects
if (fillAllLayers=0) Then exit
wend
EndIf
// fill this layer
ElseIf fillLayer=1 And fillAllLayers=0 Then
// layer exists
If (layer < layerAmount) Then
layerObject = Peekint(layerObjects, layer * BYTE_SIZE)
layerChangeList = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerNewImageList)
layerChangedAmount = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerNewImageCount)
changeListSize = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerNewImageListSize)
//loop through layer
For x=0 To width - 1
For y=0 To height - 1
// if buffer is used check old value
if (bufferType = BUFFERTYPE_MEMBLOCK) then
// get old value
oldValue = PeekInt (screenBuffer,(x + y * width + layer * width * height) * BYTE_SIZE)
writeValue = (oldValue <> imageIndex )
else
writeValue = true
endif
if (writeValue) then
//set buffer value to imageIndex
if (bufferType = BUFFERTYPE_MEMBLOCK) then PokeInt screenBuffer,(x + y * width + layer * width * height) * BYTE_SIZE, imageIndex
//changelist is too small, increase size
if ( changeListSize < (layerChangedAmount+1) * MEMBLOCK_SIZE_Image) then
newSize = (layerChangedAmount + LIST_INCREASE_SIZE) * MEMBLOCK_SIZE_Image
ResizeMEMBlock layerChangeList, newSize
//resize can alter pointer so save
pokeint layerObject, MEMBLOCK_OFFSET_LayerNewImageList, layerChangeList
//store new size
PokeInt layerObject, MEMBLOCK_OFFSET_LayerNewImageListSize, newSize
endif
// Add value to changelist
PokeInt layerChangeList, layerChangedAmount * MEMBLOCK_SIZE_Image + MEMBLOCK_OFFSET_ImageIndex, imageIndex
PokeInt layerChangeList, layerChangedAmount * MEMBLOCK_SIZE_Image + MEMBLOCK_OFFSET_ImageX, x
PokeInt layerChangeList, layerChangedAmount * MEMBLOCK_SIZE_Image + MEMBLOCK_OFFSET_ImageY, y
//increase changelist counter
PokeInt layerObject, MEMBLOCK_OFFSET_LayerNewImageCount, layerChangedAmount + 1
EndIf
Next y
Next x
EndIf
// clear all -- this is expensive call, avoid if possible
ElseIf fillLayer=1 And fillAllLayers=1 Then
ClearImageScreen(mem)
EndIf
EndIf
EndIf
End Function
//Applies ImageScreen Changes
Function ImageScreenUpdate(mem)
If mem Then
If MEMBlockSize(mem) = MEMBLOCK_SIZE_Screen Then
width = PeekInt(mem,MEMBLOCK_OFFSET_ScreenWidth)
height = PeekInt(mem,MEMBLOCK_OFFSET_ScreenHeight)
textureWidth = PeekInt(mem,MEMBLOCK_OFFSET_ScreenTextureWidth)
textureHeight = PeekInt(mem,MEMBLOCK_OFFSET_ScreenTextureHeight)
layerAmount = PeekInt(mem,MEMBLOCK_OFFSET_ScreenLayerAmount)
layerObjects = PeekInt(mem, MEMBLOCK_OFFSET_ScreenImageLayers)
scaleFactor# = PeekFloat(mem, MEMBLOCK_OFFSET_ScreenRenderScaleFactor)
if ( layerObjects ) Then
for layerIndex = 0 to layerAmount-1
layerObject = Peekint(layerObjects, layerIndex * BYTE_SIZE)
if (layerObject ) Then
layerImage = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerBaseImage)
if layerImage then
layerChangeList = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerNewImageList)
layerChangedAmount = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerNewImageCount)
changeListSize = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerNewImageListSize)
if (layerChangedAmount > 0 and layerChangeList <> 0) Then
//apply changes to layer
for changeIterator = 0 to layerChangedAmount - 1
value = PeekInt(layerChangeList, changeIterator * MEMBLOCK_SIZE_Image + MEMBLOCK_OFFSET_ImageIndex)
x = PeekInt(layerChangeList, changeIterator * MEMBLOCK_SIZE_Image + MEMBLOCK_OFFSET_ImageX)
y = PeekInt(layerChangeList, changeIterator * MEMBLOCK_SIZE_Image + MEMBLOCK_OFFSET_ImageY)
If value >= 0 and value < ScreenImageCount Then
CopyBox 0,0,textureWidth,textureHeight,x*textureWidth,y*textureHeight,Image(ScreenImages(value)),Image(layerImage)
Else
Drawtoimage layerImage
color 0,0,0
box x*textureWidth,y*textureHeight,textureWidth,textureHeight
drawtoscreen
EndIf
next changeIterator
if (scaleFactor# <> 1.0) then
fLayerIndex# = -scaleFactor#^float( layerIndex)
scaledImage = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerScaledImage)
scaledImage = ScaleImage(layerImage, scaledImage, float(textureWidth*width)*fLayerIndex#, float(height*textureHeight)*fLayerIndex#)
pokeint layerObject, MEMBLOCK_OFFSET_LayerScaledImage, scaledImage
endif
suggestedSize = (layerChangedAmount * 2 ) * MEMBLOCK_SIZE_Image
if (changeListSize > suggestedSize) then
resizememblock layerChangeList, suggestedSize
pokeint layerObject, MEMBLOCK_OFFSET_LayerNewImageList, layerChangeList
pokeint layerObject, MEMBLOCK_OFFSET_LayerNewImageListSize, suggestedSize
endif
//reset changed amount to zero
PokeInt layerObject, MEMBLOCK_OFFSET_LayerNewImageCount, 0
Endif
EndIf
EndIf
next layerIndex
Endif
EndIf
EndIf
End Function
Function ImageScreenDraw(mem,imageScreenX#=0.0,imageScreenY#=0.0,layerOffsetX#=0.0, layerOffsetY#=0.0)
If mem Then
If MEMBlockSize(mem) = MEMBLOCK_SIZE_Screen Then
layerAmount = PeekInt(mem,MEMBLOCK_OFFSET_ScreenLayerAmount)
layerObjects = PeekInt(mem, MEMBLOCK_OFFSET_ScreenImageLayers)
scaleFactor# = PeekFloat(mem,MEMBLOCK_OFFSET_ScreenRenderScaleFactor)
width = PeekInt(mem,MEMBLOCK_OFFSET_ScreenWidth)
height = PeekInt(mem,MEMBLOCK_OFFSET_ScreenHeight)
textureWidth = PeekInt(mem,MEMBLOCK_OFFSET_ScreenTextureWidth)
textureHeight = PeekInt(mem,MEMBLOCK_OFFSET_ScreenTextureHeight)
for layerIndex = 0 to layerAmount-1
layerObject = Peekint(layerObjects, layerIndex * BYTE_SIZE)
layerImage = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerBaseImage)
scaledImage = PeekInt(layerObject, MEMBLOCK_OFFSET_LayerScaledImage)
if (scaleFactor# <> 1.0 ) then
fLayerIndex# = scaleFactor#^float(layerIndex)
w# = float(textureWidth*width)
widthDiff# = w#/2.0 - w#*fLayerIndex#/2.0
h# = float(textureHeight*height)
heightDiff# = h#/2.0 - h#*fLayerIndex#/2.0
DrawImage scaledImage, imageScreenX+layerOffsetX#*float(layerIndex)+widthDiff#, imageScreenY+layerOffsetY#*float(layerIndex)+heightDiff#
else
fLayerIndex# = float(layerIndex)
DrawImage layerImage, imageScreenX+layerOffsetX#*fLayerIndex#, imageScreenY+layerOffsetY#*fLayerIndex#
endif
next layerIndex
EndIf
EndIf
End Function
//Adds image to Screen images and returns index of image
Function AddScreenImage(img)
If (img) Then
If (ScreenImageCount >= ScreenImageLimit) Then
ClearArray OFF
ScreenImageLimit = ScreenImageLimit + LIST_INCREASE_SIZE
ReDim ScreenImages(ScreenImageLimit) As integer
EndIf
ScreenImages(ScreenImageCount) = img
ScreenImageCount = ScreenImageCount + 1
Else
MakeError "Image is not valid to add into ImageScreen"
EndIf
imgIndex = ScreenImageCount - 1
Return imgIndex
End Function
Function DeleteScreenImages()
If ImageScreenInitialized=0 Then MakeError "You must call ImageScreenInitialize() before calling other ImageScreen functions!"
For iterator = 0 To ScreenImageLimit
If ScreenImages(ScreenImageLimit) Then DeleteImage ScreenImages(iterator)
Next iterator
End Function
Function ScaleImage(_image, _scaled, _width, _height)
//By: Marcoder
//Modification: Little optimization handling with ImageWidth() And ImageHeight().
If _width <= 0 Or _height <= 0 Then Return _scaled
DeleteImage _scaled
_scaled = MakeImage(_width, _height)
_image_width = ImageWidth(_image)
_image_height= ImageHeight(_image)
// Tehdään temppikuva johon skaalataan ensin vain leveys
lTempImage = MakeImage(_width, ImageHeight(_image))
DrawToImage lTempImage
For x = 0 To _width - 1
sx# = Float(_image_width) / Float(_width) * Float(x)
DrawImageBox _image, x, 0, sx, 0, 1, _image_height, OFF,OFF
Next x
lTempImage_width = ImageWidth(lTempImage)
DrawToScreen
// Skaalataan myös pystysuunnassa
DrawToImage _scaled
For y = 0 To _height - 1
sy# = Float(_image_height) / Float(_height) * Float(y)
DrawImageBox lTempImage, 0, y, 0, sy, lTempImage_width, 1, OFF,OFF
Next y
DrawToScreen
DeleteImage lTempImage
Return _scaled
End Function
SAFEEXIT OFF
Const LAYERS = 50
SCREEN 1024,768
Const TILE_W = 1
Const TILE_H = 1
Const MARGINX = 200
Const MARGINY = 150
SW = (ScreenWidth() - MARGINX) / TILE_W - 2
SH = (ScreenHeight() - MARGINY) / TILE_H - 2
//alustetaan kuvakirjasto
InitializeImageScreenLibrary()
//luodaan kuvaruutu
map = MakeImageScreen(SW,SH,TILE_W,TILE_H,LAYERS)
img = MakeImage(TILE_W,TILE_H)
DrawToImage img
Color 0,0,0
Box 0,0,TILE_W,TILE_H
DrawToScreen
//viedään kuva kuvataulukkoon
AddScreenImage(img)
//luodaan kuvat etukäteen
For i=1 To 300
f# = Float(i Mod 100)
img = MakeImage(TILE_W,TILE_H)
DrawToImage img
If (i / 100 < 1) Then
Color 0,0 ,f#*(2.25+Rnd(0.2,0.3))
ElseIf (i / 100 < 2) Then
Color 0, f#*(2.25+Rnd(0.2,0.3)), 0
Else
Color f#*(2.25+Rnd(0.2,0.3)), 0, 0
EndIf
Box 0,0,TILE_W,TILE_H
DrawToScreen
//viedään kuva kuvataulukkoon
AddScreenImage(img)
Next i
updateGoingOn = True
Type ball
Field x#
Field y#
Field z#
Field sx#
Field sy#
Field sz#
Field col
End Type
Type point
Field x
Field y
Field z
Field die
End Type
b.ball = New(ball)
b\x = Rnd(SW)
b\y = Rnd(SH)
b\z = Rnd(LAYERS)
b\sx = Rnd(3.0,10.0)
b\sy = Rnd(3.0,10.0)
b\sz = Rnd(1.0,3.0)
b\col = 0
b.ball = New(ball)
b\x = Rnd(SW)
b\y = Rnd(SH)
b\z = Rnd(LAYERS)
b\sx = Rnd(3.0,10.0)
b\sy = Rnd(3.0,10.0)
b\sz = Rnd(1.0,3.0)
b\col = 1
b.ball = New(ball)
b\x = Rnd(SW)
b\y = Rnd(SH)
b\z = Rnd(LAYERS)
b\sx = Rnd(3.0,10.0)
b\sy = Rnd(3.0,10.0)
b\sz = Rnd(1.0,3.0)
b\col = 2
Repeat
If KeyHit(cbkeyreturn) Then updateGoingOn = Not updateGoingOn
If (updateGoingOn) Then
For b.ball = Each ball
For i=0 To 150
size# = 75.0
p.point = New(point)
ang# = Rand(360.0)
d# = Rnd(0.0,size#)
p\x = Int(b\x + Cos(ang#)*d#)
p\y = Int(b\y - Sin(ang#)*d#)
p\z = Min(LAYERS,Max(0, Int(b\z + Rand(-2,2))))
p\die = Timer() + Rand(60.0 * size# / Max(2.0,Float(Abs(b\x-p\x)))) + Rand(60.0 * size# / Max(2.0,Float(Abs(b\y-p\y))))
col = b\col * 100 + Rand(50+p\z)
ImageScreenPut(map, p\x, p\y, col, p\z )
Next i
b\x = b\x + b\sx
b\y = b\y + b\sy
b\z = LAYERS /2 + Cos(Timer()/10.0 + b\col * 120 )* Float(LAYERS /2)
If (b\x > SW) Then
b\x = SW
b\sx = - Abs(b\sx)
EndIf
If (b\x < 0) Then
b\x = 0.0
b\sx = Abs(b\sx)
EndIf
If (b\y > SH) Then
b\y = SH
b\sy = - Abs(b\sy)
EndIf
If (b\y < 0) Then
b\y = 0.0
b\sy = Abs(b\sy)
EndIf
If (b\z > LAYERS) Then
b\z = LAYERS
b\sz = - Abs(b\sz)
EndIf
If (b\z < 0) Then
b\z = 0
b\sz = Abs(b\sz)
EndIf
Next b
t = Timer()
For p.point = Each point
If (t > p\die) Then
ImageScreenPut(map, p\x, p\y, 0, p\z )
Delete p
EndIf
Next p
ImageScreenUpdate(map)
EndIf
mx# = Cos(Timer()/30.0)*(SW/200.0) + MouseWX() * 0.02
my# = -Sin(Timer()/30.0)*(SH/200.0) - MouseWY() * 0.015
ImageScreenDraw(map,MARGINX/2,MARGINY/2,mx#,my#)
SetWindow ""+FPS()
DrawScreen
Until EscapeKey()
//tyhjennetään muisti turhasta tauhkasta
DeleteImageScreen(map)
DeleteScreenImages()
End