Post not yet marked as solved
The project I'm currently working on will be my last SpriteKit project. With about 14k lines of code I can't afford to switch to another library so I'm stuck for now. I'll never make the same mistake again and rely on this framework though.I had also started sketching out other projects with SpriteKit but will abandon all of them and rebuild with other tools.With all the problems SpriteKit has in iOS 9 and Apple's lack of communication about the issue, have you decided to abandon the framework as well?
Hey everyone,In one of my apps I've been working on where SKShapeNodes fall from the top to the bottom via gravity, if the player recieves a notification in iOS 9 (such as a text message), the game temporarily freezes for around 1 second and then resumes but the nodes have jumped ahead, as if the nodes are still falling but failing to display for that second. Has anyone else come across this? Is there a solution or is it just best to hold out hope for iOS 10? Unfortunately this issue makes the game near unplayable 😟Cheers
Post not yet marked as solved
Anyone know how to fix what seem to be an issue with SKLabelNode where it is very blurry? this started happening after i update xcode.
Post not yet marked as solved
I wanna add a score when the character contacts with the 'coins' and game over when it contacts with the 'enemies'. But it doesn't work. I compiled the ...Category and <SKPhysicsContactDelegate> code in GameScene.h and these:- (instancetype)initWithSize:(CGSize)size {
if (self = [super initWithSize:size]) {
self.character = [SKSpriteNode spriteNodeWithImageNamed:@"character"];
self.character.position = CGPointMake(100, 100);
[self addChild:self.character];
self.physicsWorld.gravity = CGVectorMake(0,0);
self.physicsWorld.contactDelegate = self;
}
return self;
}in .m above didMoveToView method. Can I use initWithSize in Xcode 8? And I do use these code in .m:character.physicsBody = [SKPhysicsBody bodyWithRectangleOfSize:character.size]; //1
character.physicsBody.dynamic = YES; //2
character.physicsBody.categoryBitMask = characterCategory; //3
character.physicsBody.contactTestBitMask = coinCategory | enemiesCategory;//4
character.physicsBody.collisionBitMask = 0; // 5I use them in "setPhysicsBody:(SKPhysicsBody *)physicsBody" method. And of couse I compiled the didBeginContact method. Did I miss anything? Please help me. Thank you very much.
Post not yet marked as solved
Hello! I'm using SpriteKit for my application, and when I add an SKSpriteNode into the scene it lags and the FPS drops from 60 to 45. To make sure this isn't a code issue, I tested this in an app instead of a playground and it worked fine. Will I get penalized for poor performance or is there a way to solve this issue?Thank you 🙂
Post not yet marked as solved
Hi.I am trying to add background with gradient color to my SKScene:class GameScene: SKScene
{
override func didMove(to view: SKView)
{
let gradientView = UIView(frame: CGRect(x: 0, y: 0, width: frame.size.width, height: frame.size.height))
let image = UIImage.gradientBackgroundImage(bounds: CGRect(x: 0, y: 0, width: frame.width, height: frame.height),
colors: [UIColor.yellow.cgColor, UIColor.blue.cgColor])
let background = SKSpriteNode(color: UIColor(patternImage: image), size: frame.size)
addChild(background)
}
}
extension UIImage
{
/**
http://www.riptutorial.com/ios/example/14328/gradient-image-with-colors
*/
static func gradientBackgroundImage(bounds: CGRect, colors: [CGColor]) -> UIImage
{
let gradientLayer = CAGradientLayer()
gradientLayer.frame = bounds
gradientLayer.colors = colors
UIGraphicsBeginImageContext(gradientLayer.bounds.size)
gradientLayer.render(in: UIGraphicsGetCurrentContext()!)
let image = UIGraphicsGetImageFromCurrentImageContext()
UIGraphicsEndImageContext()
return image!
}
}This is not working. Is there a better way to add gradient background to the SKScene?Thanks a lot!EDIT:If I do this in didMove(to view:):self.view?.backgroundColor = UIColor.blue
let backgroundDep = IGABackgroundLayer().gradientMetar() // My method to create CAGradientLayer
backgroundDep.frame = self.view!.bounds
self.view!.layer.insertSublayer(backgroundDep, at: 0)...background is created nicely but added SKNodes are not seen on top of it.
I have a label in a SpriteKit appvar speedLabel: SKLabelNode = SKLabelNode()And when I try to assign it a Font like so:speedLabel.fontName = UIFont.preferredFont(forTextStyle: .body).fontNameIn iOS 11.0-12.x, that returns ".SFUIText" and gives the label the proper san-serif system font.In iOS 13.0, it returns ".SFUI-Regular" and shows up as some serifed, maybe Times New Roman font.I remember having issues with SpriteKit Label Nodes and fonts in the past. If you assigned it an invalid font, it would default to this serifed font.Anyone have any ideas how to fix this?
Post not yet marked as solved
Hi all,I'm having trouble in trying to access the content of a sprite kit particle file in a way that conforms with the recent deprecation of several functions in NSKeyedArchiver.Briefly, my project contains a file named "ParticleSmoke.sks", which I used to access easily with the following lines of code: NSString *smokePath = [[NSBundle mainBundle] pathForResource:@"ParticleSmoke" ofType:@"sks"]; SKEmitterNode* smoke = [NSKeyedUnarchiver unarchiveObjectWithFile:smokePath];now that the unarchiving function has been deprecated, I fail to use the (poorly documented) unarchivedObjectOfClass function. Especially, the code below returns nil. NSString *smokePath = [[NSBundle mainBundle] pathForResource:@"ParticleSmoke" ofType:@"sks"]; NSData* smokeData = [NSData dataWithContentsOfFile:smokePath]; NSError* error=nil; Class cls = [SKEmitterNode class]; SKEmitterNode* smoke = (SKEmitterNode*)[NSKeyedUnarchiver unarchivedObjectOfClass:cls fromData:smokeData error:&error];Unexpectedly, the content of "error" (code 4864) was@"NSDebugDescription" : @"value for key 'NS.objects' was of unexpected class 'NSColor'. Allowed classes are '{(\n SKKeyframeSequence,\n NSArray,\n NSNumber,\n NSMutableArray\n)}'."Has anyone an idea to fix this issue?Thanks for your help....
I am developing an app that contains a SpriteKit scene embedded inside a SwiftUI context.I am trying to render a simple SKShapeNode like this:import Foundation
import SpriteKit
class UIConnection: SKShapeNode {
override init() {
super.init()
self.fillColor = UIColor.clear
self.strokeColor = UIColor.blue
self.lineWidth = 0.01
}
func updatePositions(node1 : CGPoint, node2 : CGPoint) {
let path = CGMutablePath()
path.move(to: node1)
path.addLine(to: CGPoint(x: node1.x, y: node2.y))
path.addLine(to: CGPoint(x: node2.x, y: node2.y))
path.addLine(to: CGPoint(x: node2.x, y: node1.y))
path.addLine(to: node1)
self.path = path
}
required init?(coder aDecoder: NSCoder) {
super.init(coder: aDecoder)
}
}When I am adding that Node inside the standard SpriteKit game project template in XCode (without any SwiftUI things), everything is working fine, I get a non-filled rectangle with a blue outline. The frame.width and frame.height variables are valid pixel dimensions like 750 x 1334.let node = UIConnection()
self.addChild(node)
node.updatePositions(node1: CGPoint(x: frame.midX-frame.width/4, y: frame.midY-frame.height/4), node2: CGPoint(x: frame.midX+frame.width/4, y: frame.midY+frame.height/4))Now I want to embed the SKScene inside a SwiftUI context using this approach:https://dev.to/sgchipman/using-spritekit-with-swiftui-ibcFirst thing I encounter is the fact that frame.width and frame.height both result in a value of 1.Adding the above node to the embedded SKScene results in an extremely blurred rectangle, so no solid line but some weird cloudy object.
Post not yet marked as solved
Ciao,
I would like to use SpriteKit within SwiftUI on WatchOS 7.
Which works fabulously on iOS 14 via SpriteView(scene: scene)
But when I use the same code from iOS 14:
import SwiftUI
import SpriteKit class GameScene: SKScene {
override func didMove(to view: SKView) {
physicsBody = SKPhysicsBody(edgeLoopFrom: frame)
}
} SKView throws an error. And now I'm not sure how to use SpiteKit within SwiftUI on watchOS 7.
Before with WatchKit. I used WKInterfaceSKScene... via Storyboard.
I would love to get some some suggestions what I've been missing.
Grazie
Vasco
Post not yet marked as solved
Building and running a SpriteKit game on iPhone simulator starts up and after did move to view, I get this error and app abends with illegal instruction.
Xcode beta 5, Big Sur beta 5
Apple Silicon
Anyone else seen this?
Post not yet marked as solved
hi,
when i create a game with xcode 12 i have black bars on top and bottom on the phone or in the simulator, scene.scaleMode = .aspectFill doesn't seem to work.
if you do the same in Xcode 11 then it works in full screen without problems.
is that a mistake or are there new settings for it.
if I start the project created with xcode 11 in xcode 12 then it is also in fullscrenn
Hi everyone,
Running Xcode 12, I'm developing a standalone WatchOS App using Spritekit.
I'm using a simple Palette-swap shader using a SKShader with several SKAttributes.
The shader seems to work fine, however I get the following message in the console: [Metal Compiler Warning] Warning: Compilation succeeded with:
program_source:3:19: warning: unused variable 's'
constexpr sampler s(coord::normalized,
I have no idea what this means, there is no variable 's' in my code so I guess this is an issue because GLGS shader code gets compiled to Metal in the background and it goes wrong there? How do I verify this? It seems there is a memory leak associated with this error so I'm prone to solve it. Any help would be appreciated, even if it's just pointing me in a direction. (Like, should I write a new palette shader in Metal?) Thanks in advance!
The function that adds the SKShader (an extension to SKSpriteNode):
func addMultiColorShader(strokeColor: UIColor, colors:[UIColor]) {
let useColors:[UIColor] = shaderColors(colors)
var attributes:[SKAttribute] = [SKAttribute(name: "a_size", type: .vectorFloat2),
SKAttribute(name: "a_scale", type: .vectorFloat2),
SKAttribute(name: "a_alpha", type: .float)]
let colorNames:[String] = ["a_color0","a_color1","a_color2","a_color3"]
for i in 0..<colorNames.count {
attributes += [SKAttribute(name: colorNames[i], type: .vectorFloat4)]
}
let shader = SKShader(fromFile: "SKHMultiColorize", attributes: attributes)
setShaderAttributes(size: self.size, scale: CGSize(width: self.xScale, height: self.yScale), alpha: self.alpha)
setShaderColors(strokeColor: strokeColor, color1: useColors[0], color2: useColors[1], color3: useColors[2])
self.shader = shader
}
The actual shader code (OpenGL GS):
vec2 nearestNeighbor(vec2 loc, vec2 size) {
vec2 onePixel = vec2(1.0, 1.0) / size;
vec2 coordinate = floor(loc * size) / size; // round
return coordinate + (onePixel * 0.5);
}
void main()
{
vec4 colors[4];
colors[0] = a_color0;
colors[1] = a_color1;
colors[2] = a_color2;
colors[3] = a_color3;
vec4 currentColor = texture2D(u_texture, nearestNeighbor(v_tex_coord, a_size));
int colorIndex = int((currentColor.r * 5.1));
vec4 refColor = colors[colorIndex];
gl_FragColor = refColor * currentColor.a;
}
When compiling and testing an old game (Paul Pixel - The Awakening) on the latest Xcode 12.3 for the latest iOS 14.3, the Spritekit particles appeared on top. The SKEmitterNode.zPosition value was ignored.
I regularly compile the app with Xcode. So this regression happened with either iOS 14.2 or Xcode 12.2. It doesn't happen when compiling for macOS. The bug is on iOS only.
Does anybody have the same problem?
I have already reported the bug to Apple, but they're not responding.
Xcode 13 beta 2, iOS 15 beta 2, the following code produces a gray screen (the SKScene GameScene.didMove(to:) never gets called):
import SwiftUI
import SpriteKit
// A simple game scene with falling boxes
class GameScene: SKScene {
override func didMove(to view: SKView) {
physicsBody = SKPhysicsBody(edgeLoopFrom: frame)
}
override func touchesBegan(_ touches: Set<UITouch>, with event: UIEvent?) {
guard let touch = touches.first else { return }
let location = touch.location(in: self)
let box = SKSpriteNode(color: SKColor.red, size: CGSize(width: 50, height: 50))
box.position = location
box.physicsBody = SKPhysicsBody(rectangleOf: CGSize(width: 50, height: 50))
addChild(box)
}
}
// A sample SwiftUI creating a GameScene and sizing it at 300x400 points
struct ContentView: View {
var scene: SKScene {
let scene = GameScene()
scene.size = CGSize(width: 300, height: 400)
scene.scaleMode = .fill
return scene
}
var body: some View {
SpriteView(scene: scene)
.frame(width: 300, height: 400)
.ignoresSafeArea()
}
}
I have no idea how to fix / workaround this issue.
Any thoughts?
Post not yet marked as solved
How do I get the visible screen area dimensions of SKScene while using Spriteview?
I used to do :
let bottomLeft = convertPoint(fromView: .zero)
But when I do that now I get nan, nan
I read about GeometryReader, because its SwiftUI casting a SKScene (lack for better wording). So I should be able to get the needed information out of GeometryReader. But have no idea how.
What I basically need is information on what pixel the SKScene actually starts on bottom left, and where it ends top right. Due to aspect ratios this can vary on different screens, iPad, iPhone etc.
Post not yet marked as solved
Im programmin a plong game
import SpriteKit
import GameplayKit
class GameScene: SKScene {
var ball = SKSpriteNode()
var enemy = SKSpriteNode()
var main = SKSpriteNode()
override func didMove(to view: SKView) {
ball = self.childNode(withName: "ball") as! SKSpriteNode
enemy = self.childNode(withName: "enemy") as! SKSpriteNode
main = self.childNode(withName: "main") as! SKSpriteNode
ball.physicsBody?.applyImpulse(CGVector(dx: -20, dy: -20))
let border = SKPhysicsBody (edgeLoopFrom: self.frame)
border.friction = 0
border.restitution = 1
self.physicsBody = border
}
override func touchesBegan(_ touches: Set, with event: UIEvent?) {
for touch in touches {
let location = touch.location(in: self)
main.run (SKAction.moveTo(x: location.x, duration: 0.2))
}
}
override func touchesMoved(_ touches: Set, with event: UIEvent?) {
for touch in touches {
let location = touch.location(in: self)
main.run (SKAction.moveTo(x: location.x, duration: 0.2))
}
}
override func update(_ currentTime: TimeInterval) {
enemy.run(SKAction.moveTo(x: ball.position.x, duration: 1.0))
}
}
and it comms a problem "Editor placeholder in source file"
what i can do now??
Post not yet marked as solved
For some reason, when I select an .sks file in the navigator, the editor for the scene doesn't show up. I do see the scene hierarchy, which usually appears on the left in the editor, but the actual scene, showing the sprites, labels, etc., is entirely missing.
Is there some setting that causes .sks files to not be shown that I need to change? I've updated to the newest release, and cleared out the Xcode preferences in ~/Library/Application Support/Xcode, but the problem persists.
I was looking to find a way to find out if my SKSpriteNode with an SKPhysicsBody is in motion.
I create a box, raise it above the bar, then set the bar and box masks to collide. The bar is pinned, but would love to know when the box stops bouncing.
I would like to utilize the gestures on the watch to drive interaction with my SpriteKit scene. It seems that the SKScene is recreated inside the tap (see uuid output) but the initial scene shows and while a new one is created it does not get rendered.
Is it possible to handle taps, swipes, and crown actions to change state within my SpriteKit scene?
I want to animate the nodes in the scene not destroy and recreate it on every user interaction. If that is the case then SpriteView itself really doesn't sound all that useful.