diff options
Diffstat (limited to 'libs/cocos2d/CCParallaxNode.m')
-rwxr-xr-x | libs/cocos2d/CCParallaxNode.m | 161 |
1 files changed, 161 insertions, 0 deletions
diff --git a/libs/cocos2d/CCParallaxNode.m b/libs/cocos2d/CCParallaxNode.m new file mode 100755 index 0000000..9d39cc8 --- /dev/null +++ b/libs/cocos2d/CCParallaxNode.m | |||
@@ -0,0 +1,161 @@ | |||
1 | /* | ||
2 | * cocos2d for iPhone: http://www.cocos2d-iphone.org | ||
3 | * | ||
4 | * Copyright (c) 2009-2010 Ricardo Quesada | ||
5 | * Copyright (c) 2011 Zynga Inc. | ||
6 | * | ||
7 | * Permission is hereby granted, free of charge, to any person obtaining a copy | ||
8 | * of this software and associated documentation files (the "Software"), to deal | ||
9 | * in the Software without restriction, including without limitation the rights | ||
10 | * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell | ||
11 | * copies of the Software, and to permit persons to whom the Software is | ||
12 | * furnished to do so, subject to the following conditions: | ||
13 | * | ||
14 | * The above copyright notice and this permission notice shall be included in | ||
15 | * all copies or substantial portions of the Software. | ||
16 | * | ||
17 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR | ||
18 | * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, | ||
19 | * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE | ||
20 | * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER | ||
21 | * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, | ||
22 | * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN | ||
23 | * THE SOFTWARE. | ||
24 | * | ||
25 | */ | ||
26 | |||
27 | #import "CCParallaxNode.h" | ||
28 | #import "Support/CGPointExtension.h" | ||
29 | #import "Support/ccCArray.h" | ||
30 | |||
31 | @interface CGPointObject : NSObject | ||
32 | { | ||
33 | CGPoint ratio_; | ||
34 | CGPoint offset_; | ||
35 | CCNode *child_; // weak ref | ||
36 | } | ||
37 | @property (readwrite) CGPoint ratio; | ||
38 | @property (readwrite) CGPoint offset; | ||
39 | @property (readwrite,assign) CCNode *child; | ||
40 | +(id) pointWithCGPoint:(CGPoint)point offset:(CGPoint)offset; | ||
41 | -(id) initWithCGPoint:(CGPoint)point offset:(CGPoint)offset; | ||
42 | @end | ||
43 | @implementation CGPointObject | ||
44 | @synthesize ratio = ratio_; | ||
45 | @synthesize offset = offset_; | ||
46 | @synthesize child=child_; | ||
47 | |||
48 | +(id) pointWithCGPoint:(CGPoint)ratio offset:(CGPoint)offset | ||
49 | { | ||
50 | return [[[self alloc] initWithCGPoint:ratio offset:offset] autorelease]; | ||
51 | } | ||
52 | -(id) initWithCGPoint:(CGPoint)ratio offset:(CGPoint)offset | ||
53 | { | ||
54 | if( (self=[super init])) { | ||
55 | ratio_ = ratio; | ||
56 | offset_ = offset; | ||
57 | } | ||
58 | return self; | ||
59 | } | ||
60 | @end | ||
61 | |||
62 | @implementation CCParallaxNode | ||
63 | |||
64 | @synthesize parallaxArray = parallaxArray_; | ||
65 | |||
66 | -(id) init | ||
67 | { | ||
68 | if( (self=[super init]) ) { | ||
69 | parallaxArray_ = ccArrayNew(5); | ||
70 | lastPosition = CGPointMake(-100,-100); | ||
71 | } | ||
72 | return self; | ||
73 | } | ||
74 | |||
75 | - (void) dealloc | ||
76 | { | ||
77 | if( parallaxArray_ ) { | ||
78 | ccArrayFree(parallaxArray_); | ||
79 | parallaxArray_ = nil; | ||
80 | } | ||
81 | [super dealloc]; | ||
82 | } | ||
83 | |||
84 | -(void) addChild:(CCNode*)child z:(NSInteger)z tag:(NSInteger)tag | ||
85 | { | ||
86 | NSAssert(NO,@"ParallaxNode: use addChild:z:parallaxRatio:positionOffset instead"); | ||
87 | } | ||
88 | |||
89 | -(void) addChild: (CCNode*) child z:(NSInteger)z parallaxRatio:(CGPoint)ratio positionOffset:(CGPoint)offset | ||
90 | { | ||
91 | NSAssert( child != nil, @"Argument must be non-nil"); | ||
92 | CGPointObject *obj = [CGPointObject pointWithCGPoint:ratio offset:offset]; | ||
93 | obj.child = child; | ||
94 | ccArrayAppendObjectWithResize(parallaxArray_, obj); | ||
95 | |||
96 | CGPoint pos = self.position; | ||
97 | pos.x = pos.x * ratio.x + offset.x; | ||
98 | pos.y = pos.y * ratio.y + offset.y; | ||
99 | child.position = pos; | ||
100 | |||
101 | [super addChild: child z:z tag:child.tag]; | ||
102 | } | ||
103 | |||
104 | -(void) removeChild:(CCNode*)node cleanup:(BOOL)cleanup | ||
105 | { | ||
106 | for( unsigned int i=0;i < parallaxArray_->num;i++) { | ||
107 | CGPointObject *point = parallaxArray_->arr[i]; | ||
108 | if( [point.child isEqual:node] ) { | ||
109 | ccArrayRemoveObjectAtIndex(parallaxArray_, i); | ||
110 | break; | ||
111 | } | ||
112 | } | ||
113 | [super removeChild:node cleanup:cleanup]; | ||
114 | } | ||
115 | |||
116 | -(void) removeAllChildrenWithCleanup:(BOOL)cleanup | ||
117 | { | ||
118 | ccArrayRemoveAllObjects(parallaxArray_); | ||
119 | [super removeAllChildrenWithCleanup:cleanup]; | ||
120 | } | ||
121 | |||
122 | -(CGPoint) absolutePosition_ | ||
123 | { | ||
124 | CGPoint ret = position_; | ||
125 | |||
126 | CCNode *cn = self; | ||
127 | |||
128 | while (cn.parent != nil) { | ||
129 | cn = cn.parent; | ||
130 | ret = ccpAdd( ret, cn.position ); | ||
131 | } | ||
132 | |||
133 | return ret; | ||
134 | } | ||
135 | |||
136 | /* | ||
137 | The positions are updated at visit because: | ||
138 | - using a timer is not guaranteed that it will called after all the positions were updated | ||
139 | - overriding "draw" will only precise if the children have a z > 0 | ||
140 | */ | ||
141 | -(void) visit | ||
142 | { | ||
143 | // CGPoint pos = position_; | ||
144 | // CGPoint pos = [self convertToWorldSpace:CGPointZero]; | ||
145 | CGPoint pos = [self absolutePosition_]; | ||
146 | if( ! CGPointEqualToPoint(pos, lastPosition) ) { | ||
147 | |||
148 | for(unsigned int i=0; i < parallaxArray_->num; i++ ) { | ||
149 | |||
150 | CGPointObject *point = parallaxArray_->arr[i]; | ||
151 | float x = -pos.x + pos.x * point.ratio.x + point.offset.x; | ||
152 | float y = -pos.y + pos.y * point.ratio.y + point.offset.y; | ||
153 | point.child.position = ccp(x,y); | ||
154 | } | ||
155 | |||
156 | lastPosition = pos; | ||
157 | } | ||
158 | |||
159 | [super visit]; | ||
160 | } | ||
161 | @end | ||