en

hi, it seems you are using microsoft internet explorer. it doesn't match web standard and causes problems browsing this site. please please please use mozilla firefox or google chrome instead. thank you!

zh

哦哦!您正在使用Internet Explorer 瀏覽器,它與我們的網頁標準並不相容,可能會導致畫面顯示不正常。
請改用 Mozilla Firefox 或者 Google Chrome 才能正常瀏覽本網站,謝謝!

10.17.2013

使用 UIKit Dynamics 實作遊戲中的撞擊效果

 

在之前的關於 UIKit Dynamics 的二三事一文中,我們已經介紹過 iOS 7 SDK 中的新成員 UIKit Dynamics,下面示範我們就透過 UIKit Dynamics 來實作遊戲中常見的物理這裡撞擊效果,這只是一個簡單的示範,如果你正打算使用 UIKit Dynamics 來寫遊戲的話這邊並不建議,反而,在遊戲方面你可以透過 iOS 7 SDK 中的另一個新成員 Sprite Kit Framework  或是 cocos2d API 來達成。

示範中將參考憤怒鳥(Angry birds)的遊戲機制,來實作一個簡單的碰撞效果,當手指點擊畫面上任意一處時,紅色方塊便會飛向手指所點擊的位置,沿途如果觸碰到棕色矩型或是綠色方塊,都會產稱物理碰撞的效果,並且會以閃爍來做顯示被碰撞的物件。


相關文章

使用 UIKit Dynamics 中的 UIGravityBehavior、UICollisionBehavior 和 UIPushBehavior 物件,來幫助我們實現自由落體(拋物線)、物理碰撞、飛躍的效果。
捕捉手勢點擊的瞬間,並將位置換算成飛躍時的向量。
透過 <UICollisionBehaviorDelegate> 協定來取得兩個 UIView 碰撞的瞬間,並且使用 Block 技術在當前的函式中就設定好閃爍動畫。

部分關鍵程式碼
@Interface 區塊的設定
@interface MLViewController ()<UICollisionBehaviorDelegate> {
    UIDynamicAnimator* animator;
    UIGravityBehavior* gravity;
    UICollisionBehavior* collision;
    UIPushBehavior *push;

UIView *bird, *pig, *woodH, *woodV;
}

@end

設定場景(所有UIView的初始位置)
- (void)settingScenes {
//鳥
    CGRect tmp = CGRectMake(10, 290, 30, 30);
    bird = [[UIView alloc]initWithFrame:tmp];
    [bird setBackgroundColor:[UIColor redColor]];
    [bird setTag:1];
    [[self view]addSubview:bird];

//垂直木條
    tmp = CGRectMake(420, 200, 20, 120);
    woodV = [[UIView alloc]initWithFrame:tmp];
    [woodV setBackgroundColor:[UIColor brownColor]];
    [woodV setTag:2];
    [[self view]addSubview:woodV];

//水平木條
    tmp = CGRectMake(370, 180, 120, 20);
    woodH = [[UIView alloc]initWithFrame:tmp];
    [woodH setBackgroundColor:[UIColor brownColor]];
    [woodH setTag:2];
    [[self view]addSubview:woodH];

//豬
    tmp = CGRectMake(415, 150, 30, 30);
    pig = [[UIView alloc]initWithFrame:tmp];
    [pig setBackgroundColor:[UIColor greenColor]];
    [pig setTag:3];
    [[self view]addSubview:pig];
}

UIKit Dynamics 設定
- (void)settingDynamic {
//替self.view作UIDynamicBehavior的容器
    animator = [[UIDynamicAnimator alloc] initWithReferenceView:[self view]];

//UIGravityBehavior
    gravity = [[UIGravityBehavior alloc] initWithItems:@[bird, woodH, woodV, pig]];
    [animator addBehavior:gravity];

//UICollisionBehavior(能與ReferenceView邊界產生碰撞)
    collision = [[UICollisionBehavior alloc] initWithItems:@[bird, woodH, woodV, pig]];
    [animator addBehavior:collision];
    [collision setTranslatesReferenceBoundsIntoBoundary:YES];
    [collision setCollisionDelegate:self];

//UIDynamicItemBehavior
    UIDynamicItemBehavior* itemBehaviour = [[UIDynamicItemBehavior alloc]  initWithItems:@[woodH,woodV]];
    [itemBehaviour setElasticity:0.4]; //反彈係數
    [itemBehaviour setAllowsRotation:YES];//旋轉
    [itemBehaviour setFriction:0.2]; //磨擦力
    [itemBehaviour setResistance:0.0]; //阻力
    [animator addBehavior:itemBehaviour];
}

<UICollisionBehaviorDelegate> 協定
//碰撞時所觸發的函式
- (void)collisionBehavior:(UICollisionBehavior*)behavior beganContactForItem:(id <uidynamicitem>)item1 withItem:(id <uidynamicitem>)item2 atPoint:(CGPoint)p {
    UIView* view1 = (UIView*)item1;
    UIView* view2 = (UIView*)item2;

//判斷碰撞是由鳥所引起
    if (view1.tag == 1) {
    [view2 setBackgroundColor:[UIColor whiteColor]];

    //閃爍效果
        [UIView animateWithDuration:0.3 animations:^{
            if (view2.tag == 2)
                [view2 setBackgroundColor:[UIColor brownColor]];

            if (view2.tag == 3)
                [view2 setBackgroundColor:[UIColor greenColor]];
        }];
    }
}

手指觸碰畫面
//朝向座標點發射
- (void)touchesEnded:(NSSet *)touches withEvent:(UIEvent *)event {
    UITouch *touch = [[event allTouches] anyObject];
    CGPoint p = [touch locationInView:[self view]];
    CGPoint bp = [bird frame].origin;

//飛出去
    push = [[UIPushBehavior alloc] initWithItems:@[bird]mode:UIPushBehaviorModeInstantaneous];
    [push setPushDirection:CGVectorMake((p.x - bp.x)*0.003, (p.y - bp.y)*0.003)];
    [animator addBehavior:push];
}

執行結果
  


  










沒有留言:

張貼留言