How to move a object by titling the screen in cocos2d - iphone

i have his code for making movemnt of the object through horizontal postion.
#define kAccelerationSpeed 10
#define kAccelerometerFrequency 200
-(void) accelerometer:(UIAccelerometer *)accelerometer didAccelerate:(UIAcceleration *)acceleration
{
CGPoint pt = thePlayer.position ;
CGFloat accel = acceleration.x * kAccelerationSpeed;
pt = [[CCDirector sharedDirector] convertToGL:pt];
pt = ccp (pt.x+accel>0 , yLocationOfPlayer+accel<768 );
}
in init statment
-(id) init
{
// always call "super" init
// Apple recommends to re-assign "self" with the "super" return value
if( (self=[super init])) {
[[UIAccelerometer sharedAccelerometer] setUpdateInterval:(1.0 / kAccelerometerFrequency)];
[[UIAccelerometer sharedAccelerometer] setDelegate:self];
}
whats wrong with the above code,it is not working,when i tilt the screen,it is not making any movemnt for the "theplayer" object.please help me to do this.
thanks in advance.

Are you sure your delegates are setup to report accelerometer information? Are you also assigning thePlayer.position in the accelerometer callback? I can't recall why but I do recall trying assignment within the callback and the results were rather stuttered and problematic. The solution for me was to have a variable the accelerometer delegate call will modify and assign the position of thePlayer inside of a tick script based on the variable update in the delegate callback.

you're not assigning the position of the player sprite. Try this:
NSLog(#"position before = %#", [NSValue valueWithCGPoint:thePlayer.position]);
thePlayer.position = ccp (pt.x+accel>0 , yLocationOfPlayer+accel<768 );
NSLog(#"position after = %#", [NSValue valueWithCGPoint:thePlayer.position]);
The logging will help you to determine if 1) the delegate method is getting fired and 2) the positions are as you are expecting.

Related

Acceleration in a for..... loop

I have a for....loop and the UI then is blocked when in the loop.
Is the accelerometer also blocked?
I have following code in viewDidLoad
- (void)viewDidLoad{
[super viewDidLoad];
UIAccelerometer *accel = [UIAccelerometer sharedAccelerometer];
accel.delegate = self;
accel.updateInterval = 1.0f/60.0f;
}
and further down
- (void)accelerometer:(UIAccelerometer *)acel didAccelerate:(UIAcceleration *)acceleration {
acc=acceleration.x;
}
then an IBAction connected to a button which starts a loop
- (IBAction)doSomething {
for (int n = 1; n<=100;n++) {
// do someting in the loop
NSLog(#"x: %g", acc);
}
}
when logging the accelerometer x value it shows only the first value when the button is pressed and does not update when the loop is running. The same first value is repeating continuously.
Is there a way to log the acceleration when in the loop?
It would seem that UIAccelerometer needs the main thread so is getting blocked by the for...loop. Core Motion also has an accelerometer property in the CMMotionManager object that can report acceleration, and does better backgrounding since it's what Nike+ uses. There are two ways to access it - a pull method where you get the data directly, or a call-back. To be honest, I just tried it and couldn't get the call-back to work (mostly because it requires NSOperationQueue and I don't have much experience with that so I'm probably putting it on the wrong queue), but if you're ok with pulling data, which your approach seems to need, then this works:
CMMotionManager *motionManager = [[CMMotionManager alloc] init];
[motionManager startAccelerometerUpdates];
for (int i = 0; i < 10000; i++)
{
NSLog(#"Acceleration: %f", motionManager.accelerometerData.acceleration.x);
}
I just tried it on a device and the values reported in the for...loop update with the current acceleration.
Source: UIBackgroundModes and UIAccelerometer

How to call accelerator method using IBAction method?

I want to add a start button which will start the accelerometer, how can I set an IBAction to do that, in my code I use:
-(void)accelerometer:(UIAccelerometer *)accelerometer didAccelerate:(UIAcceleration *)acceleration
{
x.text = [NSString stringWithFormat:#"X is: %f", acceleration.x];
y.text = [NSString stringWithFormat:#"Y is: %f", acceleration.y];
z.text = [NSString stringWithFormat:#"Z is: %f", acceleration.z];
NSLog (#"Y = #%f", y.text);
}
-(IBAction)startPedometerPressed {
[startButton accelerometer:(UIAccelerometer *)accelerometer didAccelerate:(UIAcceleration *)acceleration];
}
This returns an error because of the undeclared identifier 'accelerometer'.
I'm sure there is something wrong in how I call the method but not sure what is it!
you have to write your accelerometer initialization code in the IBAction function. remove it from ViewDidLoad. now accelerometer works after the button pressed.
-(IBAction)startPedometerPressed
{
[[UIAccelerometer sharedAccelerometer] setUpdateInterval:(1.0 / kAccelerometerFrequency)];
[[UIAccelerometer sharedAccelerometer] setDelegate:self];
}
Hope this helps.

iPhone, Cocos2D - moving sprite left/right while touching screen

I'm new to Objective C and app development so please go easy on me!
I'm trying to make a basic game and need to move a sprite left or right continuously while the user's finger is on the screen - left side to go left, right to go right...
I'm trying to use update to repeat movements of a few pixels every 1/60th second. So far, this is what I have (and sorry about the formatting):
#import "GameplayLayer.h"
#implementation GameplayLayer
-(id)init {
self = [super init];
if (self != nil) {
CGSize screenSize = [CCDirector sharedDirector].winSize;
// enable touches
self.isTouchEnabled = YES;
blobSprite = [CCSprite spriteWithFile:#"blob.png"];
[blobSprite setPosition: CGPointMake(screenSize.width/2, screenSize.height*0.17f)];
ball = [CCSprite spriteWithFile:#"ball.png"];
[ball setPosition:CGPointMake(10, screenSize.height*0.75f)];
[self addChild:blobSprite];
[self addChild:ball];
[self schedule:#selector(update) interval:1.0f/60.0f];
}
return self;
}
-(void) update:(ccTime)dt{
if (_tapDownLeft == YES){
blobSprite.position.x==blobSprite.position.x-5;
}
if (_tapDownRight == YES){
blobSprite.position.x==blobSprite.position.x+5;
}
}
-(void) ccTouchesBegan:(UITouch*)touch withEvent: (UIEvent *)event{
CGPoint touchLocation = [touch locationInView:[touch view]];
touchLocation = [[CCDirector sharedDirector] convertToGL:touchLocation];
if (touchLocation.x > 400) {
if ((blobSprite.position.x+10)<460){
_tapDownRight = YES;
}
}
if (touchLocation.x < 200) {
if ((blobSprite.position.x-10>20)){
_tapDownLeft = YES;
}
}
else {
_tapDownLeft = NO;
_tapDownRight = NO;
}
}
-(void)ccTouchEnded:(UITouch *)touch withEvent:(UIEvent *)event{
_tapDownLeft = NO;
_tapDownRight = NO;
}
-(void) registerWithTouchDispatcher{
[[CCTouchDispatcher sharedDispatcher]addTargetedDelegate:self priority:0 swallowsTouches:YES];
}
#end
Am I on the right lines with this? At the moment it's giving me 'expression result unused' in update. Could anyone tell me what I'm missing? Any help would be greatly appreciated.
Thanks,
Patrick
i see a few things here:
not certain your selector will call update : #selector(update:)
I would not rely on dt being either exactly 1/60th of a second, nor being constant. I would favor defining a speed constant (in points per second) and compute the deltaX in points based on the desired speed and dt, at each update cycle.
I dont see a 'registerWithTouchDispatcher' call (i try to place them in onEnter and onExit) methods.
Somewhere in there, make certain you remove your children (either in dealloc, or better in a local cleanup method (dont forget to invoke [super cleanup]).
Remove the argument in the update function

How to notice a quick forward motion with didAccelerate deprecated?

What i want to do is read the acceleration.y and do something like:
if (acceleration.y > 0.8) {
// Do something
}
As didAccelerate is deprecated I wonder how to get the y-value:
motionManager = [[[CMMotionManager alloc] init] autorelease];
motionManager.accelerometerUpdateInterval = kUpdateInterval;
if (motionManager.accelerometerAvailable) {
[motionManager startAccelerometerUpdates];
}
else {
//this device doesn't have accelerometer notice somewhere??
}
- (void)startAccelerometerUpdates {
// READ Y-VALUE?????
}
I want to use raw accelerometer data so the app also works on 3GS. Is it possible to read the Y-value?
EDIT: the answer below is deprecated, check these posts for the right way.
Old answer:
Use a UIAccelerometer singleton instance for this, for example in your AppDelegate
//in your launching method
UIAccelerometer * accel = [UIAccelerometer sharedAccelerometer];
accel.delegate = self;
//delegate method:
-(void)accelerometer:(UIAccelerometer *)accelerometer didAccelerate:(UIAcceleration *)acceleration{
// use the y-property of the acceleration
}
Look at the CMMotionManager class reference and search section named "Handing Motion Updates at Specified Intervals". In the "Accelerometer" bullet, it says
Set the accelerometerUpdateInterval property to specify an update interval. Call the startAccelerometerUpdatesToQueue:withHandler: method, passing in a block of type CMAccelerometerHandler. Accelerometer data is passed into the block as CMAccelerometerData objects.
CMAccelerometerData has a reference to CMAcceleration which is a struct that holds per axis acceleration.

ccp & cpv - function difference & full form of cocoa

I have following code in my Application.
I am new to game development in iPhone using COCOS.
Sprite *bg=[Sprite spriteWithFile:#"menu.png"];
[bg setPosition:ccp(240,160)];
[self addChild:bg z:0];
[self addChild:[GameLayer node] z:1];
}
return self;
}
#end
#implementation GameLayer
-(id)init{
if(self=[super init]){
Label *test=[Label labelWithString:#"Hello World" fontName:#"Helvetica" fontSize:24];
test.position=cpv(160, 240);
test.visible=YES;
[self addChild:test];
}
return self;
}
What is the function of ccp & cpv?
( I think it is for setting the layer's position, But I am not sure. So I am Asking)
Sagar
ccp is a simple macro defined by COCOS to easily create a CGPoint. So it's nothing more than just a point (x,y coordinate) It is defined as:
#define ccp(__X__,__Y__) CGPointMake(__X__,__Y__)
position is a property of the Label object, which probably sets the position on the screen to the point created by ccp(). I don't know which corner is being used as a reference point (center/top-left/bottom-left?) as I've never used COCOS so please try that yourself.
Good luck
From the source code:
From CGPointExtension.h
#define ccp(__X__,__Y__) CGPointMake(__X__,__Y__)
From cpVect.h
#define cpVect CGPoint
static inline cpVect cpv(const cpFloat x, const cpFloat y)
{
cpVect v = {x, y};
return v;
}