iOS7 how to understand UIPushBehavior magnitude in UIPushBehaviorModeInstantaneous mode?

1.5k Views Asked by At

I'm looking at Apple documentation for UIPushBehavior and it confuses me in instantaneous mode. I know that the acceleration formula is Force = Mass * acceleration. I assume that mass of a view is width*height*density(1). The documentation describes push magnitude as follows:

The default magnitude is nil, equivalent to no force. A continuous force vector with a magnitude of 1.0, applied to a 100 point x 100 point view whose density value is 1.0, results in view acceleration of 100 points / second² in the direction indicated by the angle or pushDirection property.

This makes sense in terms of continuous pushing, where it provides constant acceleration. It does not say anything about intantaneous push. How can I understand what velocity an instantaneous push of magnitude 1 will provide to a 100x100 view?

2

There are 2 best solutions below

1
On BEST ANSWER

EDIT: it seem like @martin have a better answer. Please check it. I haven't had time to check it yet.

There is no acceleration in the case of an instantaneous push (UIPushBehaviorModeInstantaneous). Then for you can't play with magnitude (it have no impact). Instead you can play with the pushDirection vector value. ie.:

pushBehavior.pushDirection = CGVectorMake(100, 100);

Also you could add a UIDynamicItemBehavior to act directly on the behavior of the object your moving in order to add some resistance, friction, ... If you want slow it down

UIDynamicItemBehavior *resistanceBehavior = [[UIDynamicItemBehavior alloc] initWithItems:@[view]];
resistanceBehavior.resistance = 1.0;
[self.animator addBehavior:resistanceBehavior];
1
On

I initially upvoted @HuguesBR answer, but now I regret because his first paragraph is wrong (can't cancel upvote after 5 minutes).

According to the documentation,

You express a push behavior’s force vector in terms of magnitude (magnitude) and radian angle (angle). Instead of using radian angle, you can equivalently express direction using x and y components by using the pushDirection property. Whichever approach you use, the alternate, equivalent values update automatically.

So if you set a pushDirection vector to (-1, 0), you'll see in debug magnitude = 1 and angle = PI/2, and vice versa.

I experimented UIPushBehaviorModeInstantaneous and UIPushBehaviorModeContinuous modes in a small xcode project, with no UIDynamicItemBehavior defined. And I found strange behaviors:

UIPushBehaviorModeInstantaneous :

  • applies just once a force to the object, the the force remains forever.
  • has it's active property set to NO by default. Setting the active property to YES applies the force! And

    self.pushBehavior1.active = YES;
    self.pushBehavior1.active = YES;
    

    applies the force twice! (see edits)

  • Once the push behavior activated, calling self.pushBehavior1.active = NO; does nothing.

UIPushBehaviorModeContinuous :

  • applies each frame a force on the object. It's definitely and acceleration, but capped to a speed greater than the Instantaneous one...
  • active property is set to YES by default, changing magnitude (or pushDirection) starts the movement.
  • the view speed is first slower the the instant pushed one, but it quickly surpass it.

SO, to answer @AlexStone, I measured in code the speed of the moving object, and giving an instant push to a 100x100 view with a density of 1 and resistance of 0 will give to the object a speed of 100 points / seconds (I observed around 99.8 in fact)

EDIT:

After more tests in Instantaneous mode, it appears that active property is set to YES by default, but comes back to NO at the end of the frame, just after physics are simulated.
Indeed,

self.pushBehavior.magnitude = 1;
[self.animator addBehavior:self.pushBehavior];

will create a movement.
To push again, just do:

self.pushBehavior.active = YES;