Tower Defenseãžã£ã³ã«ã¯ãiOSã§æã人æ°ã®ããã²ãŒã ã®ãžã£ã³ã«ã®1ã€ã§ãã ãã®çç±ã¯ããã®éåžžã«é²åŸ¡ãçªç Žããããšããã¢ã³ã¹ã¿ãŒã®å€§çŸ€ã«å¯ŸããæåŸã®é²åŸ¡ãã€ã³ããäœæããããã®å¡ã®å»ºèšã§å³ä»ããããæ¥œãã嚯楜ã§ãã
Pablo Ruizã«ãã£ãŠæžããã
raywenderlich.comã§èŠã€ããèšäºã®ç¿»èš³ã
玹ä»ããŸãã
ãã®ãã¥ãŒããªã¢ã«ã§ã¯ãCocos2Dã䜿çšããŠãŒãããã¿ã¯ãŒãã£ãã§ã³ã¹ã²ãŒã ãäœæããæ¹æ³ã瀺ããŸãã
ãã®éçšã§ã次ã®ããšãåŠã³ãŸãã
- æµã®æ³¢ãäœæããæµã®åºçŸæéã調æŽããæ¹æ³ã
- ãããã®æµãç¹å®ã®ãã€ã³ãïŒãŠã§ã€ãã€ã³ãïŒã«æ²¿ã£ãŠç§»åãããæ¹æ³ã
- ãããäžã®æå®ããããšãªã¢ã«ã¿ã¯ãŒãæ§ç¯ããæ¹æ³ã
- ã¿ã¯ãŒãæµã«æã€æ¹æ³ã
- ãŠã§ã€ãã€ã³ããèŠèŠåããã¿ã¯ãŒã®ååŸãæ»æããæ¹æ³ã
ã¬ãã¹ã³ã®æåŸã«ã¯ããã®ã¿ã€ãã®ã²ãŒã ãäœæããããã®ç¬èªã®ãã¬ãŒã ã¯ãŒã¯ããããæ°ããã¿ã€ãã®æµãã¿ã¯ãŒããããã远å ããããšã§æ¡åŒµã§ããŸãã
ãã®ãã¥ãŒããªã¢ã«ãçè§£ããã«ã¯ãCocos2Dã®åºæ¬çãªçè§£ãå¿
èŠã§ãã åå¿è
ã®å Žåã¯ã
Rayã®Webãµã€ãã§ç°¡åãªãã¥ãŒããªã¢ã«ã
ã芧ãã ãã ã
ã¢ã€ããªãŒã¿ã¯ãŒããã®çºã
ãžã£ã³ã«ã«æ
£ããŠããªãå Žåãã¿ã¯ãŒãã£ãã§ã³ã¹ã¯æŠç¥ã²ãŒã ã§ããããã¬ã€ã€ãŒã¯åºå°ã«å°éããŠç Žå£ããããšããæµã®æ³¢ã黿¢ããããã«ãæŠç¥ãã€ã³ãã«æŠè£
ããã¿ã¯ãŒã賌å
¥ããŠé
眮ããŸãã
æµã®æ¬¡ã®æ³¢ã¯éåžžãåã®æ³¢ããã匷ããªããŸããããã¯ãæŠåšã«å¯Ÿããæµæåãé«ããããéãåãèœåã«ãã£ãŠéæãããŸãã æµã®æ³¢ããã¹ãŠçãæ®ã£ããšãïŒåå©ïŒïŒããŸãã¯æµãåºå°ã«å°çããŠç Žå£ããå ŽåïŒè² ãïŒïŒã«ã²ãŒã ã¯çµäºããŸãã
以äžã¯ãã¬ãã¹ã³ã®æåŸã«æžãçµããã²ãŒã ã®ã¹ã¯ãªãŒã³ã·ã§ããã§ãã

åçã§ãããããã«ãç»é¢ã®å·ŠäžããæµãçŸãããã¬ãŒã€ãŒã®åºå°ãŸã§ç·ã®ã«ãŒãããã©ããŸãã
éè·¯ã«æ²¿ã£ãŠããã¬ã€ã€ãŒãã¿ã¯ãŒãèšçœ®ã§ããå€ãã®ãã©ãããã©ãŒã ããããŸãã ãã¬ã€ã€ãŒã¯ãéã®åèµéãèš±ãéãã®ã¿ã¯ãŒã賌å
¥ã§ããŸãã ã¿ã¯ãŒã®æ»æååŸã¯çœãåã§ç€ºãããŠããŸããæµããã®åã®å
åŽã«ããå Žåãã¿ã¯ãŒã¯ç Žå£ããããŸã§æµãæã¡ãŸããæµãæ»æã®ååŸãé¢ããªãããã«ããŸãã
ãªãœãŒã¹æºå
空ã®Cocos2Dãã³ãã¬ãŒããšãã¬ãã¹ã³ã§äœ¿çšããã»ãšãã©ã®ãªãœãŒã¹ãå«ã
ã¹ã¿ãŒãã¢ãããããžã§ã¯ããæ¢ã«çšæãããŠããŸãã
ã¹ã¿ãŒãã¢ãããããžã§ã¯ãã«ã¯ãåºæ¬çãªCocos2D 1.1ãã³ãã¬ãŒããå«ãŸããŠããŸãããã®ãã³ãã¬ãŒãã¯ãHelloWorldLayerãšç»é¢äžå€®ã®è¡ãå«ãäœæ¥ã¢ããªã±ãŒã·ã§ã³ãæäŸããŸãã ç¬èªã®ã€ã³ã¿ãŒãã§ã€ã¹ãäœæãããããHelloWorldLayerã¯äœ¿çšããŸãããããã®ã¯ã©ã¹ã¯æäŸãããŠããããããã®æ®µéã§ãã¹ãŠãæ©èœããããšã確èªã§ããŸãã
Xcodeã§ãããžã§ã¯ããéããã³ã³ãã€ã«ããŠå®è¡ããŸãã ãHello Worldããšããããã¹ãã¯ãããžã§ã¯ãããåé€ããããããèµ·åããã»ã¹äžã«é»ãç»é¢ã衚瀺ããããšã©ãŒãçºçããããšã¯ãããŸããã
ãããžã§ã¯ãã®æ§é ãèŠãŠãã ããã TowerDefenseãã©ã«ããŒå
ã«ã¯æ¬¡ã®ãã®ããããŸãã
- ã²ãŒã ã§äœ¿çšããããã¹ãŠã®ã¯ã©ã¹
- Cocos2Dã©ã€ãã©ãªãã©ã«ããŒ
- å¿
èŠãªã°ã©ãã£ãã¯ãšãµãŠã³ããå«ããªãœãŒã¹ãã©ã«ããŒ
ããã§ããããã®ã«ã¹ã¿ãã€ãºãéå§ããã¿ã¯ãŒãäœæã§ããŸãïŒ
ã¿ã¯ãŒã®èšçœ®
æåã«ãèæ¯ç»åãã·ãŒã³ã«è¿œå ããŸãã
HelloWorldLayer.mã¯ã©ã¹ãéããinitã¡ãœããã®ifæ¡ä»¶å
ã«æ¬¡ã®ã³ãŒãè¡ã远å ããŸãã
ã»ã¯ã·ã§ã³ïŒ1ã®æåã®è¡ã§ã¯ãã¬ã€ã€ãŒãã¿ããã€ãã³ããåãå
¥ããããšãã§ããŸãã ã»ã¯ã·ã§ã³2ã®æ®ãã®ã³ãŒãã¯ãã·ãŒã³ã«èæ¯ã¹ãã©ã€ãã远å ããŸãã
èæ¯ç»åã¯ããã¬ã€ã€ãŒãã¿ã¯ãŒãèšçœ®ã§ããå Žæã確èªããã®ã«åœ¹ç«ã¡ãŸãã æ¬¡ã«ããã¬ã€ã€ãŒãã¿ã¯ãŒãæ§ç¯ã§ããããã«ã¿ããããŠãç»é¢äžã«ããã€ãã®ãã€ã³ããèšå®ããå¿
èŠããããŸãã
ã¢ã¯ã·ã§ã³ã®æå³ãä¿æããããã«ããã¹ãŠã®ãã€ã³ãã¯ã.plistããã¡ã€ã«ã«é
眮ãããç°¡åã«å€æŽã§ããŸãã
TowerPosition.plistã¯Resourcesãã©ã«ããŒã«ãããæ¢ã«å
éšã«ã¿ã¯ãŒãæ§ç¯ããããã®ããã€ãã®äœçœ®ãå«ãŸããŠããŸãã
ãã®ãã¡ã€ã«ãåç
§ãããšããxããšãyãã®2ã€ã®ããŒã®ã¿ãå«ãèŸæžã®é
åãèŠã€ãããŸãã åèŸæžã¯ãç»é¢äžã®åº§æšã«åŸã£ãŠã¿ã¯ãŒã®äœçœ®ã衚ããŸãã æ¬¡ã«ããã®ãã¡ã€ã«ãç»é²ãããããäžã®ã¿ã¯ãŒã®ããŒã¹ãã€ã³ã¹ããŒã«ããå¿
èŠããããŸãã
HelloWorldLayer.hãéããæ¬¡ã®å€æ°ã远å ããŸãïŒã©ã€ã³
ã€ã³ã¿ãŒãã§ã€ã¹ã®åŸã«äžãã£ãå
ïŒïŒ
NSMutableArray * towerBases;
HelloWorldLayer.mã«æ¬¡ã®å€æŽãå ããŸãã
ã¢ããªã±ãŒã·ã§ã³ãã³ã³ãã€ã«ããŠå®è¡ãããšãéè·¯ã®äž¡åŽã«æ£æ¹åœ¢ã衚瀺ãããã¿ã¯ãŒãèšçœ®ããããã®ããŒã¹ãšããŠæ©èœããŸãã

ããã§åºå°ã®æºåãã§ããŸãããããã€ãã®å¡ã建èšããŸãããïŒ
ãŸãã
HelloWorldLayer.hãéããäžæ¬åŒ§ãéããåŸã«æ¬¡ã®è¡ã远å ããŸãã
@property (nonatomic,retain) NSMutableArray *towers;
HelloWorldLayer.mã®@implementationè¡ã®äžã«ããtower倿°ãåæããŸãã
@synthesize towers;
次ã«ãã¿ã¯ãŒãè¡šãæ°ããã¯ã©ã¹ãäœæããŸãã iOS \ Cocoa Touch \ Objective-Cãã³ãã¬ãŒãããæ°ãããã¡ã€ã«ã远å ããŸãã ã¯ã©ã¹ã«
Towerãšããååãä»ãã
CCNodeã®ãµãã¯ã©ã¹ã«ã
ãŸã ã
Tower.hã®å
å®¹ãæ¬¡ã®ãã®ã«çœ®ãæããŸãã
ã³ãŒã #import "cocos2d.h" #import "HelloWorldLayer.h" #define kTOWER_COST 300 @class HelloWorldLayer, Enemy; @interface Tower: CCNode { int attackRange; int damage; float fireRate; } @property (nonatomic,assign) HelloWorldLayer *theGame; @property (nonatomic,assign) CCSprite *mySprite; +(id)nodeWithTheGame:(HelloWorldLayer*)_game location:(CGPoint)location; -(id)initWithTheGame:(HelloWorldLayer *)_game location:(CGPoint)location; @end
次ã«ã
Tower.mã®å
容ã
次ã®ããã«çœ®ãæããŸãã
ã³ãŒã #import "Tower.h" @implementation Tower @synthesize mySprite,theGame; +(id) nodeWithTheGame:(HelloWorldLayer*)_game location:(CGPoint)location { return [[[self alloc] initWithTheGame:_game location:location] autorelease]; } -(id) initWithTheGame:(HelloWorldLayer *)_game location:(CGPoint)location { if( (self=[super init])) { theGame = _game; attackRange = 70; damage = 10; fireRate = 1; mySprite = [CCSprite spriteWithFile:@"tower.png"]; [self addChild:mySprite]; [mySprite setPosition:location]; [theGame addChild:self]; [self scheduleUpdate]; } return self; } -(void)update:(ccTime)dt { } -(void)draw { glColor4f(255, 255, 255, 255); ccDrawCircle(mySprite.position, attackRange, 360, 30, false); [super draw]; } -(void)dealloc { [super dealloc]; } @end
ã¿ã¯ãŒã¯ã©ã¹ã«ã¯ãããã€ãã®å€æ°ãå«ãŸããŠããŸããã¹ãã©ã€ãã¯ãã¿ã¯ãŒã®èŠèŠç衚çŸãç°¡åã«ã¢ã¯ã»ã¹ã§ãã芪ã¬ã€ã€ãŒãžã®ãªã³ã¯ãããã³3ã€ã®å€æ°ã§ãã
- attackRangeïŒã¿ã¯ãŒãæµãæ»æã§ããè·é¢ã決å®ããŸã
- ãã¡ãŒãžïŒã¿ã¯ãŒãæµã«äžãããã¡ãŒãžã決å®ããŸã
- fireRateïŒã¿ã¯ãŒã®ãªããŒãã«å¿
èŠãªæéãæ±ºå®ããŸã
ãããã®3ã€ã®å€æ°ã䜿çšãããšãããŸããŸãªçš®é¡ã®æ»æã䌎ãéåžžã«å€æ§ãªçš®é¡ã®ã¿ã¯ãŒãäœæã§ããŸãã æåŸã«ãã³ãŒãã«ã¯ããã¹ãã容æã«ããããã«ã¿ã¯ãŒã®æ»æç¯å²ãã¬ã³ããªã³ã°ããã¡ãœãããå«ãŸããŠããŸãã
ãã¬ã€ã€ãŒã«ã¿ã¯ãŒã远å ãããŸãããïŒ
HelloWorldLayer.mãéããæ¬¡ã®å€æŽãè¡ããŸãã
ccTouchesBegan ïŒç»é¢ã®ã¿ããããã£ããã£ããŸãã æ¬¡ã«ãã³ãŒãã¯towerBasesé
åãå埩åŠçããã¿ã¯ãŒã®ããŒã¹ã«ã¿ãããã€ã³ããå«ãŸããŠãããã©ããã確èªããŸãã
ãã ããã¿ã¯ãŒãäœæããåã«ã次ã®2ã€ã®ããšã確èªããå¿
èŠããããŸãã
- ãã¬ã€ã€ãŒã¯ãã®ãããªåã³ãèš±ãããšãã§ããŸããïŒ canBuyTowerã¡ãœããã¯ãã¿ã¯ãŒã賌å
¥ããã®ã«ååãªãŽãŒã«ãããããã©ããã確èªããŸãã ãã ããçŸæç¹ã§ã¯ããã¬ã€ã€ãŒã¯ãã©ãŒãããã¯ã¹ã®ãŽãŒã«ãããã¹ãŠæã£ãŠãããããã¡ãœããã¯åžžã«YESãè¿ããŸãã
- ãã¬ã€ã€ãŒã¯å»ºèšã®èŠåã«éåããŠããŸããïŒ tb.UserDataãæå®ãããŠããå Žåãã¿ã¯ãŒã¯æ¢ã«ãã®å Žæã«ç«ã£ãŠãããæ°ããã¿ã¯ãŒãæ§ç¯ããããšã¯ã§ããŸããã
ãã¹ãŠã®æ¡ä»¶ãæºããããŠããå Žåãæ°ããã¿ã¯ãŒãäœæãããããŒã¹ã«ã€ã³ã¹ããŒã«ãããã¿ã¯ãŒã®ã¢ã¬ã€ã«è¿œå ãããŸãã
ã²ãŒã ãã³ã³ãã€ã«ããŠå®è¡ããŸãã ä»»æã®ããŒã¹ãã¿ãããããšãã¿ã¯ãŒã远å ããããã®åšãã«çœãåã衚瀺ãããæ»æã®ååŸã衚瀺ãããŸãã

ãããããªããæªè
ãã®ããªããã®æŠåšãã¹ãŠããããŒãã£ãŒã«åŒã³ãŸããããïŒ
ã²ãŒã ããªã·ãŒïŒæµãæ³¢ããŠã§ã€ãã€ã³ã
æµãäœæããåã«ãæµã®éãåãéããŸãããã æµã¯ãŠã§ã€ãã€ã³ãããã«ãŒãããã©ããŸãããŠã§ã€ãã€ã³ãã¯åºæ¬çã«çžäºæ¥ç¶ããããã€ã³ãã§ãããã¯ãŒã«ãå
ã®æµã®ç§»åçµè·¯ã決å®ããŸãã æµã¯æåã®ãŠã§ã€ãã€ã³ãã«çŸãããªã¹ãå
ã®æ¬¡ã®ãã®ãæ¢ããŠç§»åããæåŸã«å°éãããŸã§ç¹°ãè¿ããŸã-ããªãã®ããŒã¹ïŒ ãããèµ·ãããšããã¡ãŒãžãåããŸãã
iOS \ Cocoa Touch \ Objective-Cã¯ã©ã¹ãã³ãã¬ãŒãããæ°ãããã¡ã€ã«ãäœæããŠããŠã§ã€ãã€ã³ãã®ãªã¹ããäœæããŸãã
Waypointã¯ã©ã¹ã«ååãä»ããŠã
CCNodeã®ãµãã¯ã©ã¹ã«ã
ãŸã ã
Waypoint.hã®å
å®¹ãæ¬¡ã®ãã®ã«çœ®ãæããŸãã
ã³ãŒã #import "cocos2d.h" #import "HelloWorldLayer.h" @interface Waypoint: CCNode { HelloWorldLayer *theGame; } @property (nonatomic,readwrite) CGPoint myPosition; @property (nonatomic,assign) Waypoint *nextWaypoint; +(id)nodeWithTheGame:(HelloWorldLayer*)_game location:(CGPoint)location; -(id)initWithTheGame:(HelloWorldLayer *)_game location:(CGPoint)location; @end
次ã«ãWaypoint.mã®å
容ã眮ãæããŸãã
ã³ãŒã #import "Waypoint.h" @implementation Waypoint @synthesize myPosition, nextWaypoint; +(id)nodeWithTheGame:(HelloWorldLayer*)_game location:(CGPoint)location { return [[[self alloc] initWithTheGame:_game location:location] autorelease]; } -(id)initWithTheGame:(HelloWorldLayer *)_game location:(CGPoint)location { if( (self=[super init])) { theGame = _game; [self setPosition:CGPointZero]; myPosition = location; [theGame addChild:self]; } return self; } -(void)draw { glColor4f(0, 255, 0, 255); ccDrawCircle(myPosition, 6, 360, 30, false); ccDrawCircle(myPosition, 2, 360, 30, false); if(nextWaypoint) ccDrawLine(myPosition, nextWaypoint.myPosition); [super draw]; } -(void)dealloc { [super dealloc]; } @end
æåã«ãã³ãŒãã¯ãŠã§ã€ãã€ã³ããªããžã§ã¯ããäœæããHelloWorldLayerãªããžã§ã¯ããåç
§ãããŠã§ã€ãã€ã³ãã®äœçœ®ã§ããCGPointãå®çŸ©ããŸãã
åãŠã§ã€ãã€ã³ãã«ã¯æ¬¡ãžã®ãªã³ã¯ãå«ãŸããããã«ãããŠã§ã€ãã€ã³ãã®ãªã³ã¯ãªã¹ããäœæãããŸãã åãŠã§ã€ãã€ã³ãã¯ãªã¹ãå
ã®æ¬¡ã®ãã€ã³ãããèªèãããŠããããŠã§ã€ãã€ã³ãã®ãã§ãŒã³ã«æ²¿ã£ãŠç§»åããããšã§æµãæçµç®æšã«å°ãããšãã§ããŸãã
æåŸã«ãã¬ã³ããªã³ã°ã¡ãœããã¯ãŠã§ã€ãã€ã³ããã©ãã«ãããã瀺ãããã¹ãç®çã§ãŠã§ã€ãã€ã³ãéã®æ¥ç¶ç·ãæç»ããŸãã
ãŠã§ã€ãã€ã³ãã®ãªã¹ããäœæããŸãã
HelloWorldLayer.hãéããæ¬¡ã®å€æ°ã远å ããŸãã
ã³ãŒã @property (nonatomic,retain) NSMutableArray *waypoints;
HelloWorldLayer.mã«æ¬¡ã®ã³ãŒãã远å ããŸãã
ã²ãŒã ãã³ã³ãã€ã«ããŠå®è¡ããŸãã

ãããã«ã¯6ã€ã®ãŠã§ã€ãã€ã³ãããããæµã¯ãã®çµè·¯ããã©ããŸãã åéã«ã²ãŒã ã«è² ããããåã«ãããã€ãã®ãã«ããŒã¡ãœããã远å ããå¿
èŠããããŸãã
éå§ããã«ã¯ãããããŒãã¡ã€ã«ã«ã¡ãœããã®èª¬æã远å ããŠãã³ã³ãã€ã©ããã®èŠåãªãã«ä»ã®ã¯ã©ã¹ããããã®ã¡ãœããã䜿çšã§ããããã«ããŸãã
HelloWorldLayer.hãéããã
end ãè¡ã®åã«æ¬¡ã®ã¡ãœããã®èª¬æã远å ããŸãã
ã³ãŒã -(BOOL)circle:(CGPoint)circlePoint withRadius:(float)radius collisionWithCircle:(CGPoint)circlePointTwo collisionCircleRadius:(float)radiusTwo; void ccFillPoly(CGPoint *poli, int points, BOOL closePolygon);
次ã«ã
HelloWorldLayer.mãéããæ¬¡ã®è¡ããã¡ã€ã«ã®
æåŸ ïŒ
endã®åïŒã«è¿œå ããŸãã
void ccFillPoly( CGPoint *poli, int points, BOOL closePolygon ) {
collisionWithCircleã¡ãœããã¯ã2ã€ã®åãè¡çªãŸãã¯äº€å·®ããã¿ã€ãã³ã°ãèŠã€ããã®ã«åœ¹ç«ã¡ãŸãã ããã¯ãæµããŠã§ã€ãã€ã³ãã«å°éãããã©ãããçè§£ããã¿ã¯ãŒã®æ»æç¯å²å
ã«ããæµãç¹å®ããã®ã«åœ¹ç«ã¡ãŸãã
ccFillPolyã¡ãœããã¯ãOpenGLã䜿çšããŠå¡ãã€ã¶ãããããªãŽã³ãæç»ããŸãã Cocos2dã§ã¯ã空çœã®ããªãŽã³ã®ã¿ãæç»ã§ããŸãã ccFillPolyã¡ãœããã¯ãæµã®ãã«ã¹ããŒãæç»ããããã«äœ¿çšãããŸãã
æµãææŸãæã§ãã
HelloWorldLayer.hãéããæ¬¡ã®ã³ãŒãã远å ããŸãã
ã³ãŒã
HelloWorldLayer.mã«æ¬¡ã®å€æŽãå ããŸãã
æµã«é¢ãããã¹ãŠã®æ
å ±ãå«ãã¯ã©ã¹ãäœæããç»é¢äžã®æµã®åããå¶åŸ¡ããŸãã æ°ããiOS \ Cocoa Touch \ Objective-Cãã¡ã€ã«ãäœæããŸãã ã¯ã©ã¹ã«
Enemyãšããååãä»ãã
CCNodeã®ãµãã¯ã©ã¹ã«ã
ãŸã ã
Enemy.hã®å
容ã眮ãæããŸãã
ã³ãŒã #import "cocos2d.h" #import "HelloWorldLayer.h" #import "GameConfig.h" @class HelloWorldLayer, Waypoint, Tower; @interface Enemy: CCNode { CGPoint myPosition; int maxHp; int currentHp; float walkingSpeed; Waypoint *destinationWaypoint; BOOL active; } @property (nonatomic,assign) HelloWorldLayer *theGame; @property (nonatomic,assign) CCSprite *mySprite; +(id)nodeWithTheGame:(HelloWorldLayer*)_game; -(id)initWithTheGame:(HelloWorldLayer *)_game; -(void)doActivate; -(void)getRemoved; @end
Enemy.mã®ã³ã³ãã³ãïŒ
ã³ãŒã #import "Enemy.h" #import "Tower.h" #import "Waypoint.h" #import "SimpleAudioEngine.h" #define HEALTH_BAR_WIDTH 20 #define HEALTH_BAR_ORIGIN -10 @implementation Enemy @synthesize mySprite, theGame; +(id)nodeWithTheGame:(HelloWorldLayer*)_game { return [[[self alloc] initWithTheGame:_game] autorelease]; } -(id)initWithTheGame:(HelloWorldLayer *)_game { if ((self=[super init])) { theGame = _game; maxHp = 40; currentHp = maxHp; active = NO; walkingSpeed = 0.5; mySprite = [CCSprite spriteWithFile:@"enemy.png"]; [self addChild:mySprite]; Waypoint * waypoint = (Waypoint *)[theGame.waypoints objectAtIndex:([theGame.waypoints count]-1)]; destinationWaypoint = waypoint.nextWaypoint; CGPoint pos = waypoint.myPosition; myPosition = pos; [mySprite setPosition:pos]; [theGame addChild:self]; [self scheduleUpdate]; } return self; } -(void)doActivate { active = YES; } -(void)update:(ccTime)dt { if(!active)return; if([theGame circle:myPosition withRadius:1 collisionWithCircle:destinationWaypoint.myPosition collisionCircleRadius:1]) { if(destinationWaypoint.nextWaypoint) { destinationWaypoint = destinationWaypoint.nextWaypoint; }else { // . [theGame getHpDamage]; [self getRemoved]; } } CGPoint targetPoint = destinationWaypoint.myPosition; float movementSpeed = walkingSpeed; CGPoint normalized = ccpNormalize(ccp(targetPoint.x-myPosition.x,targetPoint.y-myPosition.y)); mySprite.rotation = CC_RADIANS_TO_DEGREES(atan2(normalized.y,-normalized.x)); myPosition = ccp(myPosition.x+normalized.x * movementSpeed,myPosition.y+normalized.y * movementSpeed); [mySprite setPosition:myPosition]; } -(void)getRemoved { [self.parent removeChild:self cleanup:YES]; [theGame.enemies removeObject:self]; // [theGame enemyGotKilled]; } -(void)draw { glColor4f(255, 0, 0, 255); CGPoint healthBarBack[] = {ccp(mySprite.position.x -10,mySprite.position.y+16),ccp(mySprite.position.x+10,mySprite.position.y+16),ccp(mySprite.position.x+10,mySprite.position.y+14),ccp(mySprite.position.x-10,mySprite.position.y+14)}; ccFillPoly(healthBarBack, 4, YES); glColor4f(0, 255, 0, 255); CGPoint healthBar[] = {ccp(mySprite.position.x + HEALTH_BAR_ORIGIN,mySprite.position.y+16),ccp(mySprite.position.x+HEALTH_BAR_ORIGIN+(float)(currentHp * HEALTH_BAR_WIDTH) / maxHp,mySprite.position.y+16),ccp(mySprite.position.x+HEALTH_BAR_ORIGIN+(float)(currentHp * HEALTH_BAR_WIDTH) / maxHp,mySprite.position.y+14),ccp(mySprite.position.x+HEALTH_BAR_ORIGIN,mySprite.position.y+14)}; ccFillPoly(healthBar, 4, YES); } -(void)dealloc { [super dealloc]; } @end
ããã¯å°è±¡çãªã³ãŒãã§ãããç°¡åã«çè§£ã§ããŸãã HelloWorldLayerãåç
§ãããšãæåã«æµãäœæãããŸãã initã¡ãœããã®äžã«ã¯ãããã€ãã®éèŠãªå€æ°ããããŸãã
- maxHPïŒæµãèãããããããæ°ãæ±ºå®ããŸã
- walkingSpeedïŒæµã®ç§»åéåºŠãæ±ºå®ããŸã
- mySpriteïŒæµïŒã¹ãã©ã€ãïŒã®èŠèŠç衚çŸãä¿åããŸã
- destinationWaypointïŒæ¬¡ã®åºå£ç¹ãžã®ãªã³ã¯ãä¿åããŸã
æŽæ°ã¡ãœããã¯ãã¬ãŒã ããšã«åŒã³åºãããŸãããŸããåè¿°ã®collisionWithCircleã¡ãœããã䜿çšããŠãæµã次ã®ãŠã§ã€ãã€ã³ãã«å°éãããã©ããã確èªããŸãã ãããçºçããå ŽåãæåŸã®ãŠã§ã€ãã€ã³ãã«å°éãããŸã§æ¬¡ã®æ¹åã«é²ã¿ããã¬ãŒã€ãŒã«ãã¡ãŒãžãäžããŸãã
ãããŠã§ã€ãã€ã³ãããå¥ã®ãŠã§ã€ãã€ã³ããžã®çŽç·ã«æ²¿ã£ãã¹ãã©ã€ãã®ç§»åãããããã®ç§»åé床ã¯ã次ã®ã¢ã«ãŽãªãºã ã«ãã£ãŠå®çŸãããŸãã
- çŸåšã®äœçœ®ããã¿ãŒã²ãããŸã§ã®ãã¯ãã«ãèšç®ãããäœæ¥ã®äŸ¿å®äžãå€1ãå²ãåœãŠãããŸãïŒæ£èŠåããã倿°ïŒã
- æ£èŠåããããã¯ãã«ã«ç§»åé床ãæããŠããã®ãã¬ãŒã ã§å
æãããã¹ã®éãèšç®ããŸãã 圌ã¯ã次ãååŸããããã«çŸåšã®äœçœ®ãå²ãåœãŠãããŸãã
æåŸã«ãã¬ã³ããªã³ã°ã¡ãœããã¯ã¹ãã©ã€ãäžã«ãã«ã¹ããŒãäœæããŸãã æåã«ãæµã®çŸåšã®HPã®éã«å¿ããŠã圌ã¯èµ€ã®èæ¯ãæããæ¬¡ã«ç·ã§èŠããŸãã
æµã®ã¯ã©ã¹ã®æºåãã§ããŸãããç»é¢ã«è¡šç€ºã§ããŸãïŒ
HelloWorldLayer.hãéããæ¬¡ã®ã¡ãœããã®èª¬æã远å ããŸãã
-(void)enemyGotKilled;
HelloWorldLayer.mã«åãæ¿ããŠãã¡ãœããã説æããŸãã
äžèšã¯ãã¹ãŠèª¬æã«å€ããŸãã æãéèŠãªéšåã¯LoadWaveã¡ãœããã§ãã
Waves.plistããããŒã¿ãèªã¿åããŸãã
Waves.plistãèŠããšã3ã€ã®é
åãå«ãŸããŠããããšã
ããããŸãã ãããã¯ããããæ³¢ã§ãããããã¯äžç·ã«çŸããæµã®ã°ã«ãŒãã§ãã æåã®é
åã«ã¯6ã€ã®èŸæžãå«ãŸããŠããŸãã åèŸæžã¯æµã衚ããŸãã ãã®ã¬ãã¹ã³ã§ã¯ãèŸæžã«ã¯æµãåºçŸããæéã®ã¿ãä¿åãããŸãããæµã®ã¿ã€ãã圌ã®èœåãå¥åº·ãªã©ãå«ããããšãã§ããŸãã
loadWaveã¡ãœããã¯ã次ã®ãŠã§ãŒãã衚瀺ããããã©ããã確èªãããŠã§ãŒãã«é¢ããæ
å ±ã«åºã¥ããŠé©åãªæµãäœæããããã«å¿ããŠçºçæå»ãã¹ã±ãžã¥ãŒã«ããŸãã
enemyGotKilledã¡ãœããã¯ãç»é¢äžã®æµã®æ°ããã§ãã¯ããŸã;æµãããªãå Žåãæ¬¡ã®æ³¢ãåŒãèµ·ãããŸãã åŸã§ãåãæ¹æ³ã䜿çšããŠãã¬ã€ã€ãŒã®åå©ã確èªããŸãã
ä»ããã²ãŒã ãã³ã³ãã€ã«ããŠå®è¡ããŸãã æµãããªãã®åºå°ã«ç§»åããŠããŸãïŒ

ã¿ã¯ãŒæ»æ
ã¿ã¯ãŒã¯èšçœ®ãããŠããŸããïŒ ã芧ãã ããã æµã¯åããŸããïŒ å確èªããŠãã ããïŒ ãããã®äžäœæ³ãæšãŠãæã§ãã
åã¿ã¯ãŒã¯ããã®æåã®ç¯å²å
ã«æµããããã©ããããã§ãã¯ããŸãã ãã®å Žåãã¿ã¯ãŒã¯ãæµãæã®å±ããªããšããã«è¡ãããæµãç Žå£ããããšãã2ã€ã®ããšã®ãããããèµ·ãããŸã§ãçºç ²ãéå§ããŸãã ãã®åŸãã¿ã¯ãŒã¯æ°ããç ç²è
ãæ¢ãå§ããŸãã
åºå°ã®é²è¡ãå§ããŸãããïŒ
Tower.hãéããæ¬¡ã®å€æŽãè¡ããŸãã
æåŸã«ãç©ºã®æŽæ°ã¡ãœãããæ¬¡ã®ããã«çœ®ãæããŸãã
ã³ãŒã -(void)update:(ccTime)dt { if (chosenEnemy){
ããããã®ã³ãŒãããããŸãã ããã«ãã³ãŒãã远å ãããšãã³ã³ãã€ã©ããã®èŠåã®æ°ãå¢ããŠããããšã«æ°ã¥ãããšæããŸãã æåã«ãäžè¶³ããŠããããããããã€ã远å ããŠãèŠåã«å¯ŸåŠããŸãããã
Enemy.hãéããæ¬¡ã®å€æŽãè¡ããŸãã
Enemy.mã§ ïŒ
ã³ãŒã // initWithTheGame: ( "if") attackedBy = [[NSMutableArray alloc] initWithCapacity:5]; // getRemoved: -(void)getRemoved { for(Tower * attacker in attackedBy) { [attacker targetKilled]; } [self.parent removeChild:self cleanup:YES]; [theGame.enemies removeObject:self]; // , , [theGame enemyGotKilled]; } // -(void)getAttacked:(Tower *)attacker { [attackedBy addObject:attacker]; } -(void)gotLostSight:(Tower *)attacker { [attackedBy removeObject:attacker]; } -(void)getDamaged:(int)damage { currentHp -=damage; if(currentHp <=0) { [self getRemoved]; } }
ã³ãŒãã§æãéèŠãªéšåã¯ãTowerã¯ã©ã¹ã®updateã¡ãœããã§ãã ã¿ã¯ãŒã¯ãæ»æç¯å²å
ã§æµã®ååšãåžžã«ãã§ãã¯ããŸãã ããå Žåãã¿ã¯ãŒã¯åœŒã«åããå€ããæã¡å§ããŸãã
æµãã¿ãŒã²ãããšããŠããŒã¯ããããšããã«ããã®æ¹æ³ã¯ãçºå°é床ã«å¿ããŠã¿ã¯ãŒã®å°æã¹ã±ãžã¥ãŒã«ãèšå®ããŸãã åæµã«ã¯åœŒãæã£ãŠããå¡ã®ãªã¹ããå«ãŸããŠãããæµãæ»ãã å Žåããã¹ãŠã®æµã«ãã®äºå®ãéç¥ãããæã¡ãŸãã
ã¢ããªã±ãŒã·ã§ã³ãã³ã³ãã€ã«ããŠå®è¡ããŸãã ãããäžã«ããã€ãã®å¡ãé
眮ããŸãã ã¿ã¯ãŒãååŸå
ãééããæµãã©ã®ããã«æã¡å§ãã圌ãã®ãã«ã¹ã®ã¹ããªãããæ»ã¬ãŸã§ã©ã®ããã«å€åããããããããŸãã

ã¿ã¯ãŒãã£ãã§ã³ã¹ã®å®æçãååŸããããã«ãããã€ãã®è©³çްã远å ããã ãã§ãã é³é¿å¹æã远å ããæµã«ãã¡ãŒãžãäžãããã¬ã€ã€ãŒã®ãŽãŒã«ãã®éãå¶éããããã«ããŒã¹ã«æãããšããã§ãããã
æåŸã®ä»äžã
ãã¬ã€ã€ãŒãæ®ããã©ã€ãã®æ°ãšãçµäºæã«äœãèµ·ãããã衚瀺ããããšããå§ããŸãããïŒ
HelloWorldLayer.h :
ã³ãŒã int playerHp; CCLabelBMFont *ui_hp_lbl; BOOL gameEnded;
playerHp , CCLabelBMFont , . gameEnded , ! :
-(void)getHpDamage; -(void)doGameOver;
HelloWorldLayer.m :
, , , . , !
getHpDamage , .
update Enemy.m .
. . , , .

!
âzero-sumâ, . , .
HelloWorldLayer.h :
int playerGold; CCLabelBMFont *ui_gold_lbl;
, (playerGold) (ui_gold_lbl). :
-(void)awardGold:(int)gold;
HelloWorldLayer.m :
, , . , , . .
getDamaged: ( âifâ)
Enemy.m :
[theGame awardGold:200];
, , . . , ?

!
HelloWorldLayer.m :
Enemy.m :
ããã ãã§ãïŒ ! , ?!
:
TowerDefenseFinished.zip