I am trying to put together a tile-map for a game background. The tiling works in portrait mode but when I switch to landscape, I get a blank screen.
The code is listed below:
-(SKNode *)createBackgroundNode
{
SKNode *backgroundNode = [SKNode node];
for (int nodeCount = 0; nodeCount < 20; nodeCount++) {
NSString *backgroundImageName = [NSString stringWithFormat: #"Background%02d", nodeCount+1];
SKSpriteNode *node = [SKSpriteNode spriteNodeWithImageNamed: backgroundImageName];
node.anchorPoint = CGPointMake(0.0f, 0.0f);
node.position = CGPointMake(nodeCount * 320.0f, 0.0f);
//node.position = CGPointMake(160.0f, nodeCount * 64.0f);
[backgroundNode addChild: node];
}
return backgroundNode;
}
Basically it is a game that is only played in landscape mode, and I need the tiles to be placed horizontally one after the other to create the map.
Any help with this is appreciated! Thanks in advance!
Edit: Sorry if I wasn't clear, my game only supports landscape orientation. When my iPhone is in landscape orientation, I am unable to see my map. If I play with the settings in XCode and allow the app to be in portrait orientation, I am able to see the tile map going across the screen; however, this is NOT what I want and I only did that to see if it works.
Switching screen orientation while using tile maps is not advisable. Once you have loaded your tile map, you would be better off staying in the selected orientation mode. AT least that has been my own experience using the Tiled app.
Related
I have a Class with a SpriteNode that rotates very wide, when rotated within the main Scene(as if the anchor point is in the middle of the screen and the Sprite is rotating around it). I want it to rotate around the anchor point of itself in the main Scene(anchor point on the Sprite).
So in the Class i have something like the following
- (void)createChainWithPos:(CGPoint)pos {
SKTexture *myTex...
SKTexture *myTex2...
SKSpriteNode *chainFront = [SKSpriteNode spriteWithTexture:myTex];
chainFront.position = pos;
chainFront.physicsBody = [SKPhysicsBody bodyWithRectangleOfSize:mytex.size];
[self addChild:chainFront];
[_chainParts addObject:chainFront];
SKSpriteNode *chainSide = [SKSpriteNode spriteWithTexture:myTex2];
chainSide.position = CGPointMake(chainFront.position.x, chainFront.position.y - chainSide.size.height + 6);
chainSide.physicsBody = [SKPhysicsBody bodyWithRectangleOfSize:myTex2.size;
[self addChild:chainSide];
[_chainParts addObject:chainSide];
}
I have an loop creating the chain parts in the main file but couldn't get it rotate so stripped it down in an new project. There is actually 4 chain parts but i only did two. The other two are just mirrors of the ones above with their positions mirroring the chainSide.(to position them in a chain like fashion)
and in the Scene
self.chain1 = [chain node];
[self.chain1 createChainWithPos:CGPointMake(self.size.width/2, self.size.height/2);
self.chain1.zRotation = 3.14/4;
[self addChild:self.chain1];
I have a NSMutableArray in the chain class header that i use to hold the chains.
the physics joints
for (int i = 1; i < self.chain1.chainParts.count; i++ {
SKSpriteNode *nodeA = [[self.chain1 chainParts]objectAtindex:i-1];
SKSpriteNode *nodeB = [[self.chain1 chainParts]objectAtindex:i];
SKPhysicsJointPin *pin = [SKPhysicsJointPin jointWithBodyA:nodeA.physicsBody
bodyB:nodeB.physicsBody
anchor:CGPointMake(CGRectGetMidX(nodeA.frame), CGRectGetMinY(nodeA.Frame))];
}
I found that if i set the position of the chain in the middle in the Class, it rotates correctly in the Scene. However, the physics joints just start moving randomly across the screen and isn't correct to the anchor points set. (the physics joints are set in the Scene)
I don't know if i have to convert the coordinates or play with random anchor point positions , but if someone could shed some light if would be greatly appreciated.
You do not want to use the nodes frame, you want to use the nodes size, the frame mid is the screen coordinate + the fitted node size / 2, you want the middle of your sprite only, also for pi / 4 use M_PI_4
I have an interesting problem. I create an SKSpriteNode with associated physics body.
SKTexture *shipTexture = [SKTexture textureWithImageNamed:#"Spaceship"];
self.heroSpriteNode = [HeroSpriteNode spriteNodeWithTexture:shipTexture size:CGSizeMake(40, 35.2)];
self.heroSpriteNode.physicsBody = [SKPhysicsBody bodyWithTexture:shipTexture size:CGSizeMake(40, 35.2)];
self.heroSpriteNode.physicsBody.dynamic = YES;
self.heroSpriteNode.physicsBody.mass = 1000.0;
self.heroSpriteNode.physicsBody.affectedByGravity = NO;
self.heroSpriteNode.physicsBody.allowsRotation = YES;
self.heroSpriteNode.physicsBody.angularDamping = 0.5;
self.heroSpriteNode.anchorPoint = CGPointMake(0.5,0.5);
self.heroSpriteNode.physicsBody.categoryBitMask = heroCategory;
self.heroSpriteNode.physicsBody.contactTestBitMask = groundCategory;
self.heroSpriteNode.physicsBody.collisionBitMask = groundCategory | edgeCategory;
The Scene itself has no gravity.
In the update routine I call applyTorque: to the physics body.
-(void) updateWithDeltaTime:(NSTimeInterval)seconds
{
CGFloat rotateTorque = self.rotateRate;
switch (self.rotateForceApplied)
{
case leftForceApplied:
break;
case rightForceApplied:
rotateTorque = -1.0 * rotateTorque;
break;
case zeroForceApplied: // separate from default in case behavior should change
rotateTorque = 0.0;
break;
default:
rotateTorque = 0.0;
break;
}
NSLog(#"before physics position: x %f, y %f", self.heroSpriteNode.position.x, self.heroSpriteNode.position.y);
[self.heroSpriteNode.physicsBody applyTorque:rotateTorque];
NSLog(#"after physics position: x %f, y %f", self.heroSpriteNode.position.x, self.heroSpriteNode.position.y);
}
The sprite rotates and appears to rotate in place. What it is actually doing is rotating around a center point (so no net lateral movement). This is seen by logging the sprite position before and after applying the torque. No other actions are being applied to the physics body. The movement in position is about 9 points in each direction at most.
Because the camera is pinned by constraints to the "hero" sprite, and the world moves with the camera (the centerOnNode: sample code), this causes the whole world to move in a circular pattern as the sprite spins. The world itself does not spin but moves at the same rate in a circular pattern with the spinning.
With the sprite anchorPoint being 0.5, 0.5 I would think it should rotate around a center point which should not change the position of the sprite.
What would I being doing wrong with this?
If it matters this is on iOS9, Xcode7, running on device not in the simulator. (The iOS9 SpriteKit documentation is publicly available on Apple's website, as is a public beta of iOS9 itself so this should not be breaking any NDA, and I don't think anything here is iOS9 specific anyway)
Sprite Kit is a physics engine that attempts to mimic characteristics of objects in the real world, so you should expect an object with a physics body in the simulation to behave as they would in nature. In this case, you are rotating a non-uniform physics body that may rotate non-uniformly and, possibly, move over time (unless the body is rotating about its center of mass). If you change the physics body to a circle, the sprite should rotate uniformly and should remain at a fixed location.
I'm trying to position the background all over the scene background, but for some reason it puts it outside of screen.
This is what I used:
SKTexture *backgroundTexture = [self.atlas textureNamed:#"back"];
SKSpriteNode *background = [SKSpriteNode spriteNodeWithTexture:backgroundTexture size:self.view.frame.size];
background.position = (CGPoint) {CGRectGetMidX(self.view.frame), CGRectGetMidY(self.view.frame)};
[self addChild:background];
This is how it puts it:
You need to add your background image to the SKScene view and as such determine the coordinates from self.
SKSpriteNode *backgroundNode = [SKSpriteNode spriteNodeWithImageNamed:#"BackgroundImage"];
backgroundNode.position = CGPointMake(self.size.width/2, self.size.height/2);
backgroundNode.zPosition = 1;
[self addChild:backgroundNode];
Actually the problem was that in the new Xcode 6.3.1 when you create a new scene it adds a SKScene view of some kind, this view is bigger then the iPhone normal screen, maybe it's iPhone 6+ screen size that's why the background image was out of screen bounds. I just had to remove this view file and not reload it from code and then it worked out.
Thanks anyway, the comment above helped me to understand that.
I an new at Sprite kit and I want to add some node to scene.
My problem is positions :
If I put :
SKSpriteNode *sprite = [SKSpriteNode spriteNodeWithImageNamed:#"Poligon"];
sprite.xScale = 0.5;
sprite.yScale = 0.5;
sprite.position = CGPointMake(40, 400);
it looks right when iPhone is in landscape mode, but when it is in portrait it disappear from the screen.
My guess is that it take coordinate from landscape and put it at right side of the screen. This would explain why node is not visible in portrait mode.
My question is how to set that iPhone would take portrait mode by default?
Apparently sprite kid start in landscape mode and take start viewDidLoad before it take rotation in account. Because of this the coordinate system in portrait mode is shifted, even if you set orientation to portrait.
The solution according to :
http://www.ymc.ch/en/ios-7-sprite-kit-setting-up-correct-scene-dimensions
is to set your scene not on viewDidLoad but on
- (void)viewWillLayoutSubviews
This is run after orientation is set and it works.
I am a beginner to iOS app coding but not to coding in general. I am following a tutorial for a sprite game kit app and I am having some trouble with the sizing of stuff. It came time to put in edges so the balls can bounce off of them. I noticed that the edges seemed to be off the screen, the balls would leave the screen then bounce back.
So I had xcode output the width/height, it said 320x568. I also change the scale mode by setting scene.scaleMode = SKSceneScaleModeAspectFit; and you can see the boundaries look like a square:
If I put the scaling back to normal by scene.scaleMode = SKSceneScaleModeAspectFill; It shows the screen like this:
but the balls still go off the screen.
By the way, I believe I am setting the edge nodes correctly to be on the left and right edge so I don't think that is the issue.
// Add edges
SKNode *leftEdge = [[SKNode alloc] init];
leftEdge.physicsBody = [SKPhysicsBody bodyWithEdgeFromPoint:CGPointMake(0, 0) toPoint:CGPointMake(0, self.size.height)];
leftEdge.position = CGPointMake(0, 0);
[self addChild:leftEdge];
SKNode *rightEdge = [[SKNode alloc] init];
rightEdge.physicsBody = [SKPhysicsBody bodyWithEdgeFromPoint:CGPointMake(0, 0) toPoint:CGPointMake(0, self.size.height)];
rightEdge.position = CGPointMake(self.size.width, 0);
[self addChild:rightEdge];
In your GameScene file (or whatever you may have called the SKScene file), add this method to the start of didMoveToView:
self.size = self.view.frame.size;
What is happening is that your game thinks the screen is running a different size. You need to change self.size to the actual size of the frame you are working with. The above method works with SKSceneScaleModeAspectFill, but I have not yet tested it with the other modes. Good luck!