Skip to content

Commit 374a64b

Browse files
committed
Fixes defaults and influence areas
1 parent 35c3225 commit 374a64b

7 files changed

Lines changed: 141 additions & 65 deletions

File tree

playground/package-lock.json

Lines changed: 18 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

playground/package.json

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,7 @@
4141
"postcss-safe-parser": "4.0.1",
4242
"react": "^16.6.3",
4343
"react-app-polyfill": "^0.1.3",
44+
"react-art": "^16.6.3",
4445
"react-dev-utils": "^6.1.1",
4546
"react-dom": "^16.6.3",
4647
"react-native-web": "^0.9.7",

playground/src/examples/MoreChatHeads.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -126,8 +126,8 @@ export default class MoreChatHeads extends Component {
126126
}
127127

128128
onStopInteraction(event) {
129-
const x = event.nativeEvent.x;
130-
const y = event.nativeEvent.y;
129+
const x = event.x;
130+
const y = event.y;
131131
console.log(`stopped at x=${x}, y=${y}`);
132132
}
133133

playground/src/interactable/Animator.js

Lines changed: 10 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -37,9 +37,17 @@ export default class PhysicsAnimator {
3737

3838
let { physicsObject, behaviors, View } = this
3939
let hadMovement = false
40+
let {x,y} = View.getAnimated()
41+
42+
let coords = {
43+
x: x._value + x._offset,
44+
y: y._value + y._offset,
45+
dx: x._value,
46+
dy: y._value
47+
}
4048

4149
behaviors.forEach( behavior => {
42-
Behaviors[ behavior.type ].doFrame( behavior, deltaTime, physicsObject, View )
50+
Behaviors[ behavior.type ].doFrame( behavior, deltaTime, physicsObject, coords, View )
4351
})
4452

4553
let dx = 0;
@@ -76,7 +84,7 @@ export default class PhysicsAnimator {
7684
let behaviors = this.behaviors
7785
let idx = 0
7886

79-
while (behaviors.length > idx && behaviors[idx].priority < behavior.priority) {
87+
while (behaviors.length > idx && behaviors[idx].priority <= behavior.priority) {
8088
++idx;
8189
}
8290
behaviors.splice( idx, 0, behavior )

playground/src/interactable/Behaviors.js

Lines changed: 35 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -1,38 +1,39 @@
11
import Utils from './Utils'
22

3+
function def( value, defaultValue ){
4+
return value === undefined ? defaultValue : value
5+
}
6+
37
export default {
48
anchor: {
59
create: (options, isTemp = false) => (
6-
{ x: options.x, y: options.y, priority: 1, isTemp, type: 'anchor' }
10+
{ x0: options.x, y0: options.y, priority: 1, isTemp, type: 'anchor' }
711
),
8-
doFrame: (options, deltaTime, state, target ) => {
9-
let {x,y} = target.getTranslation()
10-
12+
doFrame: (options, deltaTime, state, coords ) => {
1113
// Velocity = dx / deltaTime
12-
state.vx = (options.x - x) / deltaTime
13-
state.vy = (options.y - y) / deltaTime
14+
state.vx = (options.x0 - coords.dx) / deltaTime
15+
state.vy = (options.y0 - coords.dy) / deltaTime
1416
}
1517
},
1618

1719
bounce: {
1820
create: (options, isTemp = false) => ({
1921
type: 'bounce',
20-
bounce: options.bounce || .5,
22+
bounce: def(options.bounce, .5),
2123
minPoint: options.influence.minPoint,
2224
maxPoint: options.influence.maxPoint,
2325
priority: 3,
2426
isTemp
2527
}),
26-
doFrame: ({minPoint, maxPoint, bounce}, deltaTime, state, target ) => {
27-
let {x,y} = target.getTranslation()
28-
28+
doFrame: ({minPoint, maxPoint, bounce}, deltaTime, state, {x,y,dx,dy}, target ) => {
2929
// Apply limits
3030
if (minPoint.x > x) target.setTranslationX(minPoint.x);
3131
if (minPoint.y > y) target.setTranslationY(minPoint.y);
3232
if (maxPoint.x < x) target.setTranslationX(maxPoint.x);
3333
if (maxPoint.y < y) target.setTranslationY(maxPoint.y);
3434

3535
let { vx, vy } = state
36+
console.log( vx, vy, bounce )
3637

3738
if (minPoint.x >= x && vx < 0) {
3839
state.vx = -vx * bounce
@@ -52,14 +53,13 @@ export default {
5253
friction: {
5354
create: ( options, isTemp = false ) => ({
5455
type: 'friction',
55-
damping: options.damping || .7,
56+
damping: def(options.damping, .7),
5657
influence: Utils.createArea( options.influenceArea || {} ),
5758
priority: 2,
5859
isTemp
5960
}),
60-
doFrame: (options, deltaTime, state, target) => {
61-
let pos = target.getTranslation()
62-
if( !Utils.isPointInArea( pos, options.influence) ) return;
61+
doFrame: (options, deltaTime, state, coords) => {
62+
if( !Utils.isPointInArea( coords, options.influence) ) return;
6363

6464
let pow = Math.pow(options.damping, 60.0 * deltaTime)
6565
state.vx = pow * state.vx
@@ -70,26 +70,25 @@ export default {
7070
gravity: {
7171
create: ( options, isTemp = false ) => ({
7272
type: 'gravity',
73-
x: options.x || Infinity,
74-
y: options.y || Infinity,
75-
strength: options.strength || 400,
76-
falloff: options.falloff || 40,
77-
damping: options.damping || 0,
78-
influence: options.damping ? Utils.createAreaFromRadius( 1.4 * options.falloff || 40, options ) : Utils.createArea( options.influenceArea || {} ),
73+
x0: def(options.x, Infinity),
74+
y0: def(options.y, Infinity),
75+
strength: def(options.strength, 400),
76+
falloff: def(options.falloff, 40),
77+
damping: def(options.damping, 0),
78+
influence: options.damping ? Utils.createAreaFromRadius( (1.4 * options.falloff) || 40, options ) : Utils.createArea( options.influenceArea || {} ),
7979
isTemp,
8080
priority: 1
8181
}),
82-
doFrame: (options, deltaTime, state, target) => {
83-
let pos = target.getTranslation()
82+
doFrame: (options, deltaTime, state, coords) => {
83+
if( !Utils.isPointInArea( coords, options.influence) ) return;
8484

85-
if( !Utils.isPointInArea( pos, options.influence) ) return;
86-
let {x, y, falloff, strength} = options
87-
let dx = pos.x - x;
88-
let dy = pos.y - y;
89-
85+
let dx = coords.dx - options.x0;
86+
let dy = coords.dy - options.y0;
9087
let dr = Math.sqrt(dx * dx + dy * dy);
9188
if (!dr) return;
9289

90+
91+
let { falloff, strength } = options
9392
let a = (-strength * dr * Math.exp(-0.5 * (dr * dr) / (falloff * falloff))) / state.mass;
9493
let ax = dx / dr * a;
9594
let ay = dy / dr * a;
@@ -102,23 +101,23 @@ export default {
102101
spring: {
103102
create: ( options, isTemp = false ) => ({
104103
type: 'spring',
105-
x: options.x || 0,
106-
y: options.y || 0,
107-
tension: options.tension || 300,
104+
x0: def(options.x, 0),
105+
y0: def(options.y, 0),
106+
tension: def(options.tension, 300),
108107
influence: Utils.createArea( options.influenceArea || {} ),
109108
isTemp,
110109
priority: 1
111110
}),
112-
doFrame: ( options, deltaTime, state, target) => {
113-
let pos = target.getTranslation()
114-
if( !Utils.isPointInArea( pos, options.influence) ) return;
111+
doFrame: ( options, deltaTime, state, coords) => {
112+
console.log( coords )
113+
if( !Utils.isPointInArea( coords, options.influence) ) return;
115114

116-
let {x,y,tension} = options
115+
let {tension} = options
117116

118-
let dx = pos.x - x;
117+
let dx = coords.dx - options.x0;
119118
let ax = (-tension * dx) / state.mass;
120119

121-
let dy = pos.y - y;
120+
let dy = coords.dy - options.y0;
122121
let ay = (-tension * dy) / state.mass;
123122

124123
state.vx = state.vx + deltaTime * ax

playground/src/interactable/InteractableView.js

Lines changed: 70 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -19,10 +19,10 @@ export default function injectDependencies( Animated, PanResponder ){
1919
gravityPoints: PropTypes.array,
2020
horizontalOnly: PropTypes.bool,
2121
verticalOnly: PropTypes.bool,
22-
dragWithSprings: PropTypes.bool,
22+
dragWithSpring: PropTypes.bool,
2323
dragEnabled: PropTypes.bool,
2424
animatedValueX: PropTypes.instanceOf(Animated.Value),
25-
// animatedValueY: PropTypes.instanceOf(Animated.Value),
25+
animatedValueY: PropTypes.instanceOf(Animated.Value),
2626
onSnap: PropTypes.func,
2727
onSnapStart: PropTypes.func,
2828
onEnd: PropTypes.func,
@@ -40,7 +40,7 @@ export default function injectDependencies( Animated, PanResponder ){
4040
boundaries: {},
4141
initialPosition: {x: 0, y: 0},
4242
dragToss: .1,
43-
dragWithSprings: false,
43+
dragWithSpring: false,
4444
dragEnabled: true,
4545
onSnap: function () { },
4646
onSnapStart: function () { },
@@ -86,7 +86,6 @@ export default function injectDependencies( Animated, PanResponder ){
8686

8787
render() {
8888
let { x, y } = this.getAnimated()
89-
console.log( x === this.lastX, y === this.lastY)
9089
this.lastX = x
9190
this.lastY= y
9291

@@ -113,6 +112,13 @@ export default function injectDependencies( Animated, PanResponder ){
113112
y: animated.y._value
114113
}
115114
}
115+
getAbsoluteTranslation(){
116+
let {x,y} = this.getAnimated()
117+
return {
118+
x: x._value + x._offset,
119+
y: y._value + y._offset
120+
}
121+
}
116122

117123
setTranslationX( tx ){
118124
( this.props.animatedValueX || this.animated.x ).setValue( tx )
@@ -161,21 +167,12 @@ export default function injectDependencies( Animated, PanResponder ){
161167
onMoveShouldSetResponderCapture: () => true,
162168
onMoveShouldSetPanResponderCapture: () => true,
163169

164-
onPanResponderGrant: (e, {x0, y0}) => {
165-
let {x,y} = this.getAnimated()
166-
let offset = {x: x._value, y: y._value}
167-
this.lastEnd = offset
168-
x.setOffset( offset.x )
169-
y.setOffset( offset.y )
170-
x.setValue( 0 )
171-
y.setValue( 0 )
172-
170+
onPanResponderGrant: (e, {x0, y0}) => {
173171
this.startDrag( {x: x0, y: y0} )
174172
},
175173

176-
onPanResponderMove: (evt, { dx, dy }) => {
177-
!this.props.verticalOnly && (this.dragBehavior.x = dx);
178-
!this.props.horizontalOnly && (this.dragBehavior.y = dy);
174+
onPanResponderMove: (evt, gesture ) => {
175+
this.onDragging( gesture )
179176
},
180177

181178
onPanResponderRelease: () => {
@@ -207,14 +204,64 @@ export default function injectDependencies( Animated, PanResponder ){
207204
}
208205

209206
startDrag( ev ){
207+
// Prepare the animated
208+
let {x,y} = this.getAnimated()
209+
let offset = {x: x._value, y: y._value}
210+
x.setOffset( offset.x )
211+
y.setOffset( offset.y )
212+
x.setValue( 0 )
213+
y.setValue( 0 )
214+
215+
// Save the offset for triggering events with the right coordinates
216+
this.lastEnd = offset
217+
218+
// Set relative boundaries to not to drag after them
219+
if( this.propAreas.boundaries ){
220+
let {minPoint, maxPoint} = this.propAreas.boundaries.influence
221+
this.dragBoundaries = {
222+
minPoint: { x: minPoint.x - offset.x, y: minPoint.y - offset.y },
223+
maxPoint: { x: maxPoint.x - offset.x, y: maxPoint.y - offset.y }
224+
}
225+
}
226+
else {
227+
this.dragBoundaries = {}
228+
}
229+
230+
// Prepare the animation
210231
let pos = this.getTranslation()
211232
this.props.onDrag({state: 'start', x: pos.x + this.lastEnd.x, y: pos.y + this.lastEnd.y})
212233
this.dragStartLocation = { x: ev.x, y: ev.y }
213234
this.animator.removeTempBehaviors();
214235
this.animator.isDragging = true
215236
this.animator.vx = 0
216237
this.animator.vy = 0
217-
this.addTempDragBehavior( this.props.dragWithSprings );
238+
this.addTempDragBehavior( this.props.dragWithSpring );
239+
240+
// Stop text selection
241+
if (document) {
242+
let styles = document.body.style
243+
this.userSelectCache = styles.userSelect
244+
styles.userSelect = "none"
245+
}
246+
}
247+
248+
onDragging({dx, dy}){
249+
let {minPoint, maxPoint} = this.dragBoundaries
250+
if( !this.props.verticalOnly ){
251+
if (minPoint) {
252+
if (minPoint.x > dx) dx = minPoint.x
253+
if (maxPoint.x < dx) dx = maxPoint.x
254+
}
255+
this.dragBehavior.x0 = dx
256+
}
257+
258+
if (!this.props.horizontalOnly) {
259+
if (minPoint) {
260+
if (minPoint.y > dy) dy = minPoint.y
261+
if (maxPoint.y < dy) dy = maxPoint.y
262+
}
263+
this.dragBehavior.y0 = dy
264+
}
218265
}
219266

220267
endDrag(){
@@ -244,6 +291,11 @@ export default function injectDependencies( Animated, PanResponder ){
244291

245292
this.addTempSnapToPointBehavior(snapPoint);
246293
this.addTempBoundaries();
294+
295+
// Restore text selection
296+
if (document) {
297+
document.body.userSelect = this.userSelectCache || ''
298+
}
247299
}
248300

249301
addTempDragBehavior( drag ) {
@@ -277,7 +329,6 @@ export default function injectDependencies( Animated, PanResponder ){
277329
}
278330

279331
this.addBehavior( 'spring', springOptions, true )
280-
281332
}
282333

283334
setDragEnabled( dragEnabled ) {
@@ -327,7 +378,6 @@ export default function injectDependencies( Animated, PanResponder ){
327378
}
328379

329380
componentDidUpdate( prevProps ){
330-
console.log('updated')
331381
this.setPropBehaviours( prevProps, this.props )
332382
}
333383

@@ -355,7 +405,7 @@ export default function injectDependencies( Animated, PanResponder ){
355405
this.animator.removeBehavior( this.oldBoundariesBehavior )
356406
if( props.boundaries ){
357407
let bounce = {
358-
bounce: props.boundaries.bounce,
408+
bounce: props.boundaries.bounce || 0,
359409
influence: Utils.createArea( props.boundaries )
360410
}
361411
this.propAreas.boundaries = bounce

0 commit comments

Comments
 (0)