@@ -0,0 +1,551 @@
internal import CPlaydate
private var spriteAPI : UnsafePointer < playdate_sprite > { Playdate . spriteAPI . unsafelyUnwrapped }
// / A s p r i t e : a d r a w a b l e o b j e c t w i t h p o s i t i o n , z - o r d e r , a n d c o l l i s i o n
// / s u p p o r t . W r a p s ` L C D S p r i t e ` . S t a t i c m e m b e r s w r a p t h e g l o b a l s p r i t e
// / s y s t e m f u n c t i o n s .
public final class Sprite {
let pointer : OpaquePointer
let isOwned : Bool
// / P o s i t i o n i n t h e s t a t i c ` d i s p l a y L i s t ` , o r - 1 w h e n n o t i n i t ; m a k e s
// / ` a d d ( ) ` / ` r e m o v e ( ) ` O ( 1 ) i n s t e a d o f s c a n n i n g t h e l i s t .
private var displayListIndex = - 1
// / P e r - s p r i t e c a l l b a c k s a n d r e t a i n e d r e s o u r c e s .
var updateFunction : ( ( Sprite ) -> Void ) ?
var drawFunction : ( ( Sprite , _ bounds : Rect , _ drawRect : Rect ) -> Void ) ?
var collisionResponseFunction : ( ( Sprite , _ other : Sprite ) -> CollisionResponse ) ?
private var retainedImage : Graphics . Bitmap ?
private var retainedStencil : Graphics . Bitmap ?
private var retainedTilemap : Graphics . TileMap ?
// / F r e e - f o r m s t o r a g e f o r g a m e u s e ( t h e C u s e r d a t a s l o t i s r e s e r v e d
// / b y t h e b i n d i n g ) .
public var userdata : AnyObject ?
init ( pointer : OpaquePointer , isOwned : Bool ) {
self . pointer = pointer
self . isOwned = isOwned
// T r a n s i e n t w r a p p e r s f o r s p r i t e s c r e a t e d o u t s i d e t h e b i n d i n g m u s t n o t
// s t o r e a b a c k - r e f e r e n c e : i t w o u l d d a n g l e o n c e t h e w r a p p e r i s
// d e a l l o c a t e d , a n d o n l y o w n e d w r a p p e r s c l e a r i t i n ` d e i n i t ` .
if isOwned {
spriteAPI . pointee . setUserdata . unsafelyUnwrapped ( pointer , Unmanaged . passUnretained ( self ) . toOpaque ( ) )
}
}
// / A l l o c a t e s a n e w s p r i t e .
public convenience init ( ) {
self . init ( pointer : spriteAPI . pointee . newSprite . unsafelyUnwrapped ( ) . unsafelyUnwrapped , isOwned : true )
}
deinit {
if isOwned {
spriteAPI . pointee . setUserdata . unsafelyUnwrapped ( pointer , nil )
spriteAPI . pointee . freeSprite . unsafelyUnwrapped ( pointer )
}
}
// / R e t u r n s t h e S w i f t w r a p p e r s t o r e d i n t h e s p r i t e ' s u s e r d a t a , o r a
// / t r a n s i e n t u n o w n e d w r a p p e r f o r s p r i t e s c r e a t e d o u t s i d e t h e b i n d i n g .
static func wrapper ( for pointer : OpaquePointer ) -> Sprite {
if let userdata = spriteAPI . pointee . getUserdata . unsafelyUnwrapped ( pointer ) {
return Unmanaged < Sprite > . fromOpaque ( userdata ) . takeUnretainedValue ( )
}
return Sprite ( pointer : pointer , isOwned : false )
}
// / C o p i e s t h e s p r i t e . C a l l b a c k s a n d r e t a i n e d r e s o u r c e s a r e c a r r i e d
// / o v e r t o t h e c o p y .
public func copy ( ) -> Sprite {
let copy = Sprite ( pointer : spriteAPI . pointee . copy . unsafelyUnwrapped ( pointer ) . unsafelyUnwrapped ,
isOwned : true )
copy . updateFunction = updateFunction
copy . drawFunction = drawFunction
copy . collisionResponseFunction = collisionResponseFunction
copy . retainedImage = retainedImage
copy . retainedStencil = retainedStencil
copy . retainedTilemap = retainedTilemap
return copy
}
// MARK: - D i s p l a y l i s t
// / S p r i t e s c u r r e n t l y a d d e d t o t h e d i s p l a y l i s t , k e p t a l i v e h e r e .
nonisolated ( unsafe ) private static var displayList : [ Sprite ] = [ ]
// / W h e n ` t r u e ` , a l l s p r i t e s r e d r a w e v e r y f r a m e i n s t e a d o f o n l y w h e n
// / m a r k e d d i r t y .
public static func setAlwaysRedraw ( _ flag : Bool ) {
spriteAPI . pointee . setAlwaysRedraw . unsafelyUnwrapped ( flag ? 1 : 0 )
}
// / M a r k s t h e g i v e n s c r e e n r e g i o n a s n e e d i n g a r e d r a w .
public static func addDirtyRect ( _ rect : Graphics . Rect ) {
spriteAPI . pointee . addDirtyRect . unsafelyUnwrapped ( rect . cValue )
}
// / D r a w s e v e r y s p r i t e i n t h e d i s p l a y l i s t .
public static func drawAll ( ) {
spriteAPI . pointee . drawSprites . unsafelyUnwrapped ( )
}
// / U p d a t e s a n d t h e n d r a w s e v e r y s p r i t e i n t h e d i s p l a y l i s t .
public static func updateAndDrawAll ( ) {
spriteAPI . pointee . updateAndDrawSprites . unsafelyUnwrapped ( )
}
// / T h e n u m b e r o f s p r i t e s i n t h e d i s p l a y l i s t .
public static var count : Int {
Int ( spriteAPI . pointee . getSpriteCount . unsafelyUnwrapped ( ) )
}
// / A d d s t h e s p r i t e t o t h e d i s p l a y l i s t .
public func add ( ) {
spriteAPI . pointee . addSprite . unsafelyUnwrapped ( pointer )
if displayListIndex < 0 {
displayListIndex = Sprite . displayList . count
Sprite . displayList . append ( self )
}
}
// / R e m o v e s t h e s p r i t e f r o m t h e d i s p l a y l i s t .
public func remove ( ) {
spriteAPI . pointee . removeSprite . unsafelyUnwrapped ( pointer )
guard displayListIndex >= 0 else { return }
// S w a p - r e m o v e : t h e k e e p - a l i v e l i s t i s u n o r d e r e d ( t h e O S k e e p s t h e
// d r a w o r d e r ) , s o t h e l a s t s p r i t e c a n t a k e t h e v a c a t e d s l o t .
let index = displayListIndex
let last = Sprite . displayList . removeLast ( )
if last !== self {
Sprite . displayList [ index ] = last
last . displayListIndex = index
}
displayListIndex = - 1
}
// / R e m o v e s t h e g i v e n s p r i t e s f r o m t h e d i s p l a y l i s t .
public static func remove ( _ sprites : [ Sprite ] ) {
for sprite in sprites { sprite . remove ( ) }
}
// / R e m o v e s e v e r y s p r i t e f r o m t h e d i s p l a y l i s t .
public static func removeAll ( ) {
spriteAPI . pointee . removeAllSprites . unsafelyUnwrapped ( )
for sprite in displayList { sprite . displayListIndex = - 1 }
displayList = [ ]
}
// MARK: - G e o m e t r y
// / T h e s p r i t e ' s b o u n d s . S e t t i n g t h i s p o s i t i o n s a n d s i z e s t h e s p r i t e .
public var bounds : Rect {
get { Rect ( spriteAPI . pointee . getBounds . unsafelyUnwrapped ( pointer ) ) }
set { spriteAPI . pointee . setBounds . unsafelyUnwrapped ( pointer , newValue . cValue ) }
}
// / M o v e s t h e s p r i t e s o i t s a n c h o r p o i n t i s a t ( x , y ) .
public func moveTo ( x : Float , y : Float ) {
spriteAPI . pointee . moveTo . unsafelyUnwrapped ( pointer , x , y )
}
// / M o v e s t h e s p r i t e b y ( d x , d y ) .
public func moveBy ( dx : Float , dy : Float ) {
spriteAPI . pointee . moveBy . unsafelyUnwrapped ( pointer , dx , dy )
}
// / T h e s p r i t e ' s a n c h o r p o s i t i o n .
public var position : ( x : Float , y : Float ) {
var x : Float = 0 , y : Float = 0
spriteAPI . pointee . getPosition . unsafelyUnwrapped ( pointer , & x , & y )
return ( x , y )
}
// / S e t s t h e s p r i t e ' s s i z e w i t h o u t c h a n g i n g i t s i m a g e .
public func setSize ( width : Float , height : Float ) {
spriteAPI . pointee . setSize . unsafelyUnwrapped ( pointer , width , height )
}
// / T h e a n c h o r p o i n t u s e d f o r p o s i t i o n i n g , w h e r e ( 0 , 0 ) i s t h e t o p
// / l e f t a n d ( 1 , 1 ) t h e b o t t o m r i g h t . D e f a u l t s t o ( 0 . 5 , 0 . 5 ) .
public var center : ( x : Float , y : Float ) {
get {
var x : Float = 0 , y : Float = 0
spriteAPI . pointee . getCenter . unsafelyUnwrapped ( pointer , & x , & y )
return ( x , y )
}
set { spriteAPI . pointee . setCenter . unsafelyUnwrapped ( pointer , newValue . x , newValue . y ) }
}
// / D r a w o r d e r : h i g h e r v a l u e s d r a w o n t o p .
public var zIndex : Int16 {
get { spriteAPI . pointee . getZIndex . unsafelyUnwrapped ( pointer ) }
set { spriteAPI . pointee . setZIndex . unsafelyUnwrapped ( pointer , newValue ) }
}
// MARK: - A p p e a r a n c e
// / S e t s t h e s p r i t e ' s i m a g e , r e s i z i n g i t s b o u n d s t o m a t c h .
public func setImage ( _ image : Graphics . Bitmap ? , flip : Graphics . BitmapFlip = . unflipped ) {
retainedImage = image
spriteAPI . pointee . setImage . unsafelyUnwrapped ( pointer , image ? . pointer , flip . cValue )
}
// / T h e s p r i t e ' s i m a g e .
public var image : Graphics . Bitmap ? {
if let retainedImage { return retainedImage }
guard let image = spriteAPI . pointee . getImage . unsafelyUnwrapped ( pointer ) else { return nil }
return Graphics . Bitmap ( pointer : image , isOwned : false )
}
// / S e t s t h e s p r i t e ' s t i l e m a p , r e s i z i n g i t s b o u n d s t o m a t c h .
public var tilemap : Graphics . TileMap ? {
get { retainedTilemap }
set {
retainedTilemap = newValue
spriteAPI . pointee . setTilemap . unsafelyUnwrapped ( pointer , newValue ? . pointer )
}
}
// / T h e m o d e u s e d t o d r a w t h e s p r i t e ' s i m a g e .
public func setDrawMode ( _ mode : Graphics . DrawMode ) {
spriteAPI . pointee . setDrawMode . unsafelyUnwrapped ( pointer , mode . cValue )
}
// / H o w t h e s p r i t e ' s i m a g e i s m i r r o r e d w h e n d r a w n .
public var imageFlip : Graphics . BitmapFlip {
get { Graphics . BitmapFlip ( spriteAPI . pointee . getImageFlip . unsafelyUnwrapped ( pointer ) ) }
set { spriteAPI . pointee . setImageFlip . unsafelyUnwrapped ( pointer , newValue . cValue ) }
}
// / S e t s t h e s t e n c i l a p p l i e d w h e n d r a w i n g t h e s p r i t e . I f ` t i l e ` i s
// / ` t r u e ` t h e i m a g e w i d t h m u s t b e a m u l t i p l e o f 3 2 .
public func setStencil ( _ stencil : Graphics . Bitmap ? , tile : Bool = false ) {
retainedStencil = stencil
spriteAPI . pointee . setStencilImage . unsafelyUnwrapped ( pointer , stencil ? . pointer , tile ? 1 : 0 )
}
// / S e t s a n 8 × 8 s t e n c i l p a t t e r n ( 8 r o w s o f i m a g e d a t a ) .
public func setStencilPattern ( _ rows : ( UInt8 , UInt8 , UInt8 , UInt8 , UInt8 , UInt8 , UInt8 , UInt8 ) ) {
// T h e t u p l e i s a l r e a d y 8 c o n t i g u o u s b y t e s ; t h e C s i d e c o p i e s t h e
// p a t t e r n , s o p a s s i n g t h e s t a c k s t o r a g e d i r e c t l y i s s a f e .
withUnsafeBytes ( of : rows ) { buffer in
let pattern = UnsafeMutablePointer (
mutating : buffer . baseAddress . unsafelyUnwrapped . assumingMemoryBound ( to : UInt8 . self ) )
spriteAPI . pointee . setStencilPattern . unsafelyUnwrapped ( pointer , pattern )
}
}
public func clearStencil ( ) {
retainedStencil = nil
spriteAPI . pointee . clearStencil . unsafelyUnwrapped ( pointer )
}
// / C l i p s t h e s p r i t e ' s d r a w i n g t o ` r e c t ` ( s c r e e n c o o r d i n a t e s ) .
public func setClipRect ( _ rect : Graphics . Rect ) {
spriteAPI . pointee . setClipRect . unsafelyUnwrapped ( pointer , rect . cValue )
}
public func clearClipRect ( ) {
spriteAPI . pointee . clearClipRect . unsafelyUnwrapped ( pointer )
}
// / C l i p s a l l s p r i t e s w i t h z - i n d e x i n ` s t a r t Z . . . e n d Z ` t o ` r e c t ` .
public static func setClipRectsInRange ( _ rect : Graphics . Rect , startZ : Int , endZ : Int ) {
spriteAPI . pointee . setClipRectsInRange . unsafelyUnwrapped ( rect . cValue , Int32 ( startZ ) , Int32 ( endZ ) )
}
public static func clearClipRectsInRange ( startZ : Int , endZ : Int ) {
spriteAPI . pointee . clearClipRectsInRange . unsafelyUnwrapped ( Int32 ( startZ ) , Int32 ( endZ ) )
}
// MARK: - B e h a v i o r f l a g s
// / W h e t h e r t h e s p r i t e ' s u p d a t e f u n c t i o n i s c a l l e d b y ` u p d a t e A n d D r a w A l l ( ) ` .
public var updatesEnabled : Bool {
get { spriteAPI . pointee . updatesEnabled . unsafelyUnwrapped ( pointer ) != 0 }
set { spriteAPI . pointee . setUpdatesEnabled . unsafelyUnwrapped ( pointer , newValue ? 1 : 0 ) }
}
public var collisionsEnabled : Bool {
get { spriteAPI . pointee . collisionsEnabled . unsafelyUnwrapped ( pointer ) != 0 }
set { spriteAPI . pointee . setCollisionsEnabled . unsafelyUnwrapped ( pointer , newValue ? 1 : 0 ) }
}
public var isVisible : Bool {
get { spriteAPI . pointee . isVisible . unsafelyUnwrapped ( pointer ) != 0 }
set { spriteAPI . pointee . setVisible . unsafelyUnwrapped ( pointer , newValue ? 1 : 0 ) }
}
// / M a r k i n g a s p r i t e o p a q u e t e l l s t h e s y s t e m i t d o e s n o t n e e d t o r e d r a w
// / a n y t h i n g b e h i n d i t .
public func setOpaque ( _ flag : Bool ) {
spriteAPI . pointee . setOpaque . unsafelyUnwrapped ( pointer , flag ? 1 : 0 )
}
// / F o r c e s t h e s p r i t e t o r e d r a w t h i s f r a m e .
public func markDirty ( ) {
spriteAPI . pointee . markDirty . unsafelyUnwrapped ( pointer )
}
// / M a r k s p a r t o f t h e s p r i t e ( i n s p r i t e - l o c a l c o o r d i n a t e s ) a s n e e d i n g
// / a r e d r a w .
public func markDirty ( rect : Rect ) {
spriteAPI . pointee . markDirtyRect . unsafelyUnwrapped ( pointer , rect . cValue )
}
// / A n i n t e g e r t a g f o r i d e n t i f y i n g s p r i t e s ( e . g . i n c o l l i s i o n s ) .
public var tag : UInt8 {
get { spriteAPI . pointee . getTag . unsafelyUnwrapped ( pointer ) }
set { spriteAPI . pointee . setTag . unsafelyUnwrapped ( pointer , newValue ) }
}
// / W h e n ` t r u e ` , t h e s p r i t e d r a w s i n s c r e e n c o o r d i n a t e s , i g n o r i n g t h e
// / g l o b a l d r a w o f f s e t .
public func setIgnoresDrawOffset ( _ flag : Bool ) {
spriteAPI . pointee . setIgnoresDrawOffset . unsafelyUnwrapped ( pointer , flag ? 1 : 0 )
}
// MARK: - C a l l b a c k s
// / S e t s t h e f u n c t i o n c a l l e d b y ` u p d a t e A n d D r a w A l l ( ) ` f o r t h i s s p r i t e .
public func setUpdateFunction ( _ update : ( ( Sprite ) -> Void ) ? ) {
updateFunction = update
if update != nil {
spriteAPI . pointee . setUpdateFunction . unsafelyUnwrapped ( pointer , { spritePointer in
guard let spritePointer else { return }
let sprite = Sprite . wrapper ( for : spritePointer )
sprite . updateFunction ? ( sprite )
} )
} else {
spriteAPI . pointee . setUpdateFunction . unsafelyUnwrapped ( pointer , nil )
}
}
// / S e t s a c u s t o m d r a w f u n c t i o n , c a l l e d w h e n t h e s p r i t e n e e d s t o d r a w .
// / ` b o u n d s ` i s t h e s p r i t e ' s b o u n d s ; ` d r a w R e c t ` i s t h e r e g i o n t h a t
// / n e e d s r e d r a w i n g .
public func setDrawFunction ( _ draw : ( ( Sprite , _ bounds : Rect , _ drawRect : Rect ) -> Void ) ? ) {
drawFunction = draw
if draw != nil {
spriteAPI . pointee . setDrawFunction . unsafelyUnwrapped ( pointer , { spritePointer , bounds , drawRect in
guard let spritePointer else { return }
let sprite = Sprite . wrapper ( for : spritePointer )
sprite . drawFunction ? ( sprite , Rect ( bounds ) , Rect ( drawRect ) )
} )
} else {
spriteAPI . pointee . setDrawFunction . unsafelyUnwrapped ( pointer , nil )
}
}
// MARK: - C o l l i s i o n s
// / C l e a r s t h e c o l l i s i o n w o r l d . C a l l w h e n c h a n g i n g s c e n e s .
public static func resetCollisionWorld ( ) {
spriteAPI . pointee . resetCollisionWorld . unsafelyUnwrapped ( )
}
// / T h e r e c t ( i n s p r i t e - l o c a l c o o r d i n a t e s ) u s e d f o r c o l l i s i o n s .
public var collideRect : Rect {
get { Rect ( spriteAPI . pointee . getCollideRect . unsafelyUnwrapped ( pointer ) ) }
set { spriteAPI . pointee . setCollideRect . unsafelyUnwrapped ( pointer , newValue . cValue ) }
}
public func clearCollideRect ( ) {
spriteAPI . pointee . clearCollideRect . unsafelyUnwrapped ( pointer )
}
// / S e t s t h e f u n c t i o n d e c i d i n g h o w t h i s s p r i t e r e s p o n d s w h e n i t
// / c o l l i d e s w i t h ` o t h e r ` .
public func setCollisionResponseFunction ( _ filter : ( ( Sprite , _ other : Sprite ) -> CollisionResponse ) ? ) {
collisionResponseFunction = filter
if filter != nil {
spriteAPI . pointee . setCollisionResponseFunction . unsafelyUnwrapped ( pointer , { spritePointer , otherPointer in
guard let spritePointer , let otherPointer else { return kCollisionTypeFreeze }
let sprite = Sprite . wrapper ( for : spritePointer )
let other = Sprite . wrapper ( for : otherPointer )
return sprite . collisionResponseFunction ? ( sprite , other ) . cValue ? ? kCollisionTypeFreeze
} )
} else {
spriteAPI . pointee . setCollisionResponseFunction . unsafelyUnwrapped ( pointer , nil )
}
}
// / V i s i t s a n d f r e e s a C c o l l i s i o n i n f o a r r a y .
private static func visitCollisions ( _ pointer : UnsafeMutablePointer < SpriteCollisionInfo > ? ,
count : Int32 , _ visit : ( CollisionInfo ) -> Void ) {
guard let pointer else { return }
for index in 0. . < Int ( count ) {
visit ( CollisionInfo ( pointer [ index ] ) )
}
System . systemFree ( pointer )
}
// / C o n v e r t s a n d f r e e s a C c o l l i s i o n i n f o a r r a y .
private static func collisionInfos ( _ pointer : UnsafeMutablePointer < SpriteCollisionInfo > ? ,
count : Int32 ) -> [ CollisionInfo ] {
var infos = [ CollisionInfo ] ( )
infos . reserveCapacity ( Int ( count ) )
visitCollisions ( pointer , count : count ) { infos . append ( $0 ) }
return infos
}
// / R e t u r n s t h e c o l l i s i o n s t h a t w o u l d o c c u r i f t h e s p r i t e m o v e d t o w a r d
// / ( g o a l X , g o a l Y ) , w i t h o u t m o v i n g i t .
public func checkCollisions ( goalX : Float , goalY : Float )
-> ( actual : ( x : Float , y : Float ) , collisions : [ CollisionInfo ] ) {
var actualX : Float = 0 , actualY : Float = 0 , count : Int32 = 0
let result = spriteAPI . pointee . checkCollisions . unsafelyUnwrapped (
pointer , goalX , goalY , & actualX , & actualY , & count )
return ( ( actualX , actualY ) , Sprite . collisionInfos ( result , count : count ) )
}
// / L i k e ` c h e c k C o l l i s i o n s ( g o a l X : g o a l Y : ) ` , b u t v i s i t s e a c h c o l l i s i o n
// / i n s t e a d o f b u i l d i n g a n a r r a y , a v o i d i n g p e r - c a l l a l l o c a t i o n s .
public func checkCollisions ( goalX : Float , goalY : Float ,
_ visit : ( CollisionInfo ) -> Void ) -> ( x : Float , y : Float ) {
var actualX : Float = 0 , actualY : Float = 0 , count : Int32 = 0
let result = spriteAPI . pointee . checkCollisions . unsafelyUnwrapped (
pointer , goalX , goalY , & actualX , & actualY , & count )
Sprite . visitCollisions ( result , count : count , visit )
return ( actualX , actualY )
}
// / M o v e s t h e s p r i t e t o w a r d ( g o a l X , g o a l Y ) , r e s o l v i n g c o l l i s i o n s , a n d
// / r e t u r n s w h e r e i t e n d e d u p a n d w h a t i t h i t .
@ discardableResult
public func moveWithCollisions ( goalX : Float , goalY : Float )
-> ( actual : ( x : Float , y : Float ) , collisions : [ CollisionInfo ] ) {
var actualX : Float = 0 , actualY : Float = 0 , count : Int32 = 0
let result = spriteAPI . pointee . moveWithCollisions . unsafelyUnwrapped (
pointer , goalX , goalY , & actualX , & actualY , & count )
return ( ( actualX , actualY ) , Sprite . collisionInfos ( result , count : count ) )
}
// / L i k e ` m o v e W i t h C o l l i s i o n s ( g o a l X : g o a l Y : ) ` , b u t v i s i t s e a c h c o l l i s i o n
// / i n s t e a d o f b u i l d i n g a n a r r a y , a v o i d i n g p e r - c a l l a l l o c a t i o n s .
@ discardableResult
public func moveWithCollisions ( goalX : Float , goalY : Float ,
_ visit : ( CollisionInfo ) -> Void ) -> ( x : Float , y : Float ) {
var actualX : Float = 0 , actualY : Float = 0 , count : Int32 = 0
let result = spriteAPI . pointee . moveWithCollisions . unsafelyUnwrapped (
pointer , goalX , goalY , & actualX , & actualY , & count )
Sprite . visitCollisions ( result , count : count , visit )
return ( actualX , actualY )
}
// / V i s i t s a n d f r e e s a C s p r i t e p o i n t e r a r r a y .
private static func visitSprites ( _ pointer : UnsafeMutablePointer < OpaquePointer ? >? ,
count : Int32 , _ visit : ( Sprite ) -> Void ) {
guard let pointer else { return }
for index in 0. . < Int ( count ) {
if let spritePointer = pointer [ index ] {
visit ( wrapper ( for : spritePointer ) )
}
}
System . systemFree ( pointer )
}
// / C o n v e r t s a n d f r e e s a C s p r i t e p o i n t e r a r r a y .
private static func sprites ( _ pointer : UnsafeMutablePointer < OpaquePointer ? >? ,
count : Int32 ) -> [ Sprite ] {
var sprites = [ Sprite ] ( )
sprites . reserveCapacity ( Int ( count ) )
visitSprites ( pointer , count : count ) { sprites . append ( $0 ) }
return sprites
}
// / S p r i t e s w i t h c o l l i s i o n r e c t s c o n t a i n i n g t h e p o i n t .
public static func query ( atPoint x : Float , _ y : Float ) -> [ Sprite ] {
var count : Int32 = 0
let result = spriteAPI . pointee . querySpritesAtPoint . unsafelyUnwrapped ( x , y , & count )
return sprites ( result , count : count )
}
// / L i k e ` q u e r y ( a t P o i n t : _ : ) ` , v i s i t i n g e a c h s p r i t e w i t h o u t b u i l d i n g a n
// / a r r a y .
public static func query ( atPoint x : Float , _ y : Float , _ visit : ( Sprite ) -> Void ) {
var count : Int32 = 0
let result = spriteAPI . pointee . querySpritesAtPoint . unsafelyUnwrapped ( x , y , & count )
visitSprites ( result , count : count , visit )
}
// / S p r i t e s w i t h c o l l i s i o n r e c t s i n t e r s e c t i n g t h e r e c t .
public static func query ( inRect x : Float , _ y : Float , width : Float , height : Float ) -> [ Sprite ] {
var count : Int32 = 0
let result = spriteAPI . pointee . querySpritesInRect . unsafelyUnwrapped ( x , y , width , height , & count )
return sprites ( result , count : count )
}
// / L i k e ` q u e r y ( i n R e c t : _ : w i d t h : h e i g h t : ) ` , v i s i t i n g e a c h s p r i t e w i t h o u t
// / b u i l d i n g a n a r r a y .
public static func query ( inRect x : Float , _ y : Float , width : Float , height : Float ,
_ visit : ( Sprite ) -> Void ) {
var count : Int32 = 0
let result = spriteAPI . pointee . querySpritesInRect . unsafelyUnwrapped ( x , y , width , height , & count )
visitSprites ( result , count : count , visit )
}
// / S p r i t e s w i t h c o l l i s i o n r e c t s i n t e r s e c t i n g t h e l i n e s e g m e n t .
public static func query ( alongLine x1 : Float , _ y1 : Float , _ x2 : Float , _ y2 : Float ) -> [ Sprite ] {
var count : Int32 = 0
let result = spriteAPI . pointee . querySpritesAlongLine . unsafelyUnwrapped ( x1 , y1 , x2 , y2 , & count )
return sprites ( result , count : count )
}
// / L i k e ` q u e r y ( a l o n g L i n e : _ : _ : _ : ) ` , v i s i t i n g e a c h s p r i t e w i t h o u t b u i l d i n g
// / a n a r r a y .
public static func query ( alongLine x1 : Float , _ y1 : Float , _ x2 : Float , _ y2 : Float ,
_ visit : ( Sprite ) -> Void ) {
var count : Int32 = 0
let result = spriteAPI . pointee . querySpritesAlongLine . unsafelyUnwrapped ( x1 , y1 , x2 , y2 , & count )
visitSprites ( result , count : count , visit )
}
// / L i k e ` q u e r y ( a l o n g L i n e : ) ` , w i t h e n t r y / e x i t i n f o r m a t i o n f o r e a c h s p r i t e .
public static func queryInfo ( alongLine x1 : Float , _ y1 : Float ,
_ x2 : Float , _ y2 : Float ) -> [ QueryInfo ] {
var count : Int32 = 0
guard let result = spriteAPI . pointee . querySpriteInfoAlongLine . unsafelyUnwrapped (
x1 , y1 , x2 , y2 , & count ) else { return [ ] }
var infos = [ QueryInfo ] ( )
infos . reserveCapacity ( Int ( count ) )
for index in 0. . < Int ( count ) {
infos . append ( QueryInfo ( result [ index ] ) )
}
System . systemFree ( result )
return infos
}
// / S p r i t e s w h o s e c o l l i s i o n r e c t s o v e r l a p t h i s s p r i t e ' s .
public var overlappingSprites : [ Sprite ] {
var count : Int32 = 0
let result = spriteAPI . pointee . overlappingSprites . unsafelyUnwrapped ( pointer , & count )
return Sprite . sprites ( result , count : count )
}
// / L i k e ` o v e r l a p p i n g S p r i t e s ` , v i s i t i n g e a c h s p r i t e w i t h o u t b u i l d i n g a n
// / a r r a y .
public func overlappingSprites ( _ visit : ( Sprite ) -> Void ) {
var count : Int32 = 0
let result = spriteAPI . pointee . overlappingSprites . unsafelyUnwrapped ( pointer , & count )
Sprite . visitSprites ( result , count : count , visit )
}
// / A l l s p r i t e s i n t h e d i s p l a y l i s t t h a t o v e r l a p a n o t h e r s p r i t e .
public static var allOverlappingSprites : [ Sprite ] {
var count : Int32 = 0
let result = spriteAPI . pointee . allOverlappingSprites . unsafelyUnwrapped ( & count )
return sprites ( result , count : count )
}
// / L i k e ` a l l O v e r l a p p i n g S p r i t e s ` , v i s i t i n g e a c h s p r i t e w i t h o u t b u i l d i n g
// / a n a r r a y .
public static func allOverlappingSprites ( _ visit : ( Sprite ) -> Void ) {
var count : Int32 = 0
let result = spriteAPI . pointee . allOverlappingSprites . unsafelyUnwrapped ( & count )
visitSprites ( result , count : count , visit )
}
}