【问题标题】:Rotating sprite with finger in Cocos2d在 Cocos2d 中用手指旋转精灵
【发布时间】:2011-03-29 06:16:13
【问题描述】:

我需要帮助弄清楚我的手指如何旋转精灵。精灵旋转得很好,但在我的手指最初触摸时,它会以某种方式自行旋转几度。

只有当手指围绕精灵的中心旋转时,旋转才有效。

我正在尝试模拟自行车车轮,并有一个齿轮精灵和一个踏板精灵作为齿轮精灵的孩子。我希望自行车车轮在我触摸踏板并旋转时旋转。我还没有到那一步。现在我正试图弄清楚如何摆脱齿轮的初始换档。

这是完整的代码

#import "BicycleScene.h"

@implementation BicycleScene

+(id) scene
{
    // 'scene' is an autorelease object.
    CCScene *scene = [CCScene node];

    // 'layer' is an autorelease object.
    BicycleScene *layer = [BicycleScene node];

    // add layer as a child to scene
    [scene addChild: layer];

    // return the scene
    return scene;
}

-(id) init
{
    if ((self=[super init])) {

        CGSize winSize = [[CCDirector sharedDirector] winSize];

        //place the bicycle sprite
        bicycleSprite = [CCSprite spriteWithFile:@"bike_gear.png"];
        bicycleSprite.position = ccp(bicycleSprite.contentSize.width/2 + 100, winSize.height/2);
        [self addChild:bicycleSprite z:1];

        //place the pedal sprite
        pedalSprite = [CCSprite spriteWithFile:@"bike_pedal.png"];
        [bicycleSprite addChild:pedalSprite z:1];

        pedalSprite.position = ccp(150, 15);

        //enable touch
        self.isTouchEnabled = YES;

        [self schedule:@selector(gameLoop:) interval:.1/100];

    }

    return self;
}

-(void) ccTouchesBegan:(NSSet *)touches withEvent:(UIEvent *)event{

    NSLog(@"Touch begun");

}

-(void)gameLoop:(ccTime) dt{

    bicycleSprite.rotation = cocosAngle;
}

-(void) ccTouchesMoved:(NSSet *)touches withEvent:(UIEvent *)event{

    NSLog(@"Touch moved");

    UITouch *touch = [touches anyObject];
    CGPoint location = [touch locationInView:[touch view]];
    CGPoint previousLocation = [touch previousLocationInView:[touch view]];

    CGPoint touchingPoint = [[CCDirector sharedDirector] convertToGL:location];
    CGPoint previousTouchingPoint = [[CCDirector sharedDirector] convertToGL:previousLocation];

    CGPoint vector = ccpSub(touchingPoint, bicycleSprite.position);
    CGFloat rotateAngle = -ccpToAngle(vector);

    previousAngle = cocosAngle;
    cocosAngle = CC_RADIANS_TO_DEGREES( rotateAngle);

    //bicycleSprite.rotation = cocosAngle;
}

@end

如果这条线我有点困惑:

CGPoint vector = ccpSub(touchingPoint, bicycleSprite.position);

实际上应该是:

CGPoint vector = ccpSub(touchingPoint, previousTouchingPoint );

我也试过了,但是没用。

我还将我的完整 xcodeproj 上传到 4shared 供任何想在这里查看的人:http://www.4shared.com/file/5BaeW4oe/Healthy.html

【问题讨论】:

  • 当你使用 previousTouchingPoint 而不是 bikeSprite.position 会发生什么?同样的行为?什么都没有?
  • 当我使用previousTouchingPoint而不是bikeSprite.position时,齿轮也会跳动很多,并且当齿轮缓慢旋转时也会有很多闪烁。
  • 我刚刚测试了您上面的代码,它完成了我期望它做的事情。是不是在 touchBegan 上没有移动到正确的角度?或者它是跳跃而不是在初始移动时逐渐移动到某个角度?
  • @ lins314159 - 是的,这正是问题所在。在初始移动时,它会跳跃而不是逐渐移动到某个角度。

标签: cocos2d-iphone rotation sprite


【解决方案1】:
@interface MainScene : CCLayer {
    CCSprite *dial;

    CGFloat dialRotation;

}

+ (id)scene;

@end
---------------------------------
@implementation MainScene

+ (id)scene
{
    CCScene *scene = [CCScene node];
    CCLayer *layer = [MainScene node];
    [scene addChild:layer];

    return scene;
}

- (id)init
{
    if((self = [super init])) {
        CCLOG(@"MainScene init");

        CGSize size = [[CCDirector sharedDirector]winSize];

        dial = [CCSprite spriteWithFile:@"dial.png"];
        dial.position = ccp(size.width/2,dial.contentSize.height/2);
             [self addChild:dial];

        self.isTouchEnabled = YES;
        [self scheduleUpdate];

    }
    return self;
}

- (void)dealloc
{
    [super dealloc];
}

- (void)update:(ccTime)delta
{
    dial.rotation = dialRotation;
}

- (void)ccTouchesBegan:(NSSet *)touches withEvent:(UIEvent *)event
{

}

- (void)ccTouchesMoved:(NSSet *)touches withEvent:(UIEvent *)event
{
    UITouch *touch = [touches anyObject];

    //acquire the previous touch location
    CGPoint firstLocation = [touch previousLocationInView:[touch view]];
    CGPoint location = [touch locationInView:[touch view]];

    //preform all the same basic rig on both the current touch and previous touch
    CGPoint touchingPoint = [[CCDirector sharedDirector] convertToGL:location];
    CGPoint firstTouchingPoint = [[CCDirector sharedDirector] convertToGL:firstLocation];

    CGPoint firstVector = ccpSub(firstTouchingPoint, dial.position);
    CGFloat firstRotateAngle = -ccpToAngle(firstVector);
    CGFloat previousTouch = CC_RADIANS_TO_DEGREES(firstRotateAngle);

    CGPoint vector = ccpSub(touchingPoint, dial.position);
        CGFloat rotateAngle = -ccpToAngle(vector);
    CGFloat currentTouch = CC_RADIANS_TO_DEGREES(rotateAngle);

    //keep adding the difference of the two angles to the dial rotation
    dialRotation += currentTouch - previousTouch;
}

- (void)ccTouchesEnded:(NSSet *)touches withEvent:(UIEvent *)event
{

}

编辑:很抱歉,我无法让它保持在代码模式下。但这是解决方案,它应该很容易在您的代码中实现。干杯!

【讨论】:

  • 要将文本格式化为代码,请选择所需的文本并单击带有花括号的按钮。
【解决方案2】:

ccTouchesBegan 中,使用与ccTouchesMoved 中相同的代码来确定角度,然后使用CCRotateTo 移动到该角度。当CCRotateTo 处于活动状态时,您需要对用户移动手指进行一些处理,可能会停止当前操作并开始另一个操作以移动到新角度。

【讨论】:

    猜你喜欢
    • 2011-12-27
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多