如何在平底锅上发生碰撞检测UIDynamicItem?
背景:我从一组颜色/字符串中随机生成20个标签(这部分对于问题不是必不可少的),然后将它们添加到具有随机中心位置的主视图中.从那里,我添加UIDynamicBehaviors,如下:
1)UIDynamicItemBehavior停止旋转2)标签UISnapBehavior的标签捕捉到视图的中心(我想重力状运动,但同样,这不是这个问题)3)UICollisionBehavior所有的标签,其中collisionMode的.Items.
这适用于"初始"设置...所有标签都出现在随机点上,然后在中心快速捕捉,并进行适当的碰撞检测.但问题是,我怎样才能移动标签(通过平移手势),以便继续进行碰撞检测?
我已经UIPanGestureRecognizer在每个标签上设置了一个,当它们开始拖动时,我创建一个UIAttachmentBehavior并使用它来拖动它们.这在标签移动的意义上"起作用",但它只会滑过所有其他标签而不会发生任何碰撞检测.我怎样才能实现这种碰撞检测,这样当我开始将一个标签拖向其他标签时,它们就会移开,只是为了没有重叠(然后根据中心重力点重新回到它们的位置) ?我是否需要将UIAttachmentBehavior所有其他标签附加到我为每个平底锅拖动的标签上?
我已经为我面临的问题创建了一个测试项目,它展示了我刚刚描述的内容:
谢谢!
我正在研究可扩展托盘视图的代码,该视图使用UIDynamicAnimator来实现漂亮的扩展/合约动画.
为了实现逼真的加速度,我使用UIGravityBehavior托盘下降,直到托盘的"标签"碰到屏幕底部.
这很有效,但即使场景中的所有项目都停止移动,UIDynamicAnimatorDelegate dynamicAnimatorDidPause:也从不调用.这意味着动画师继续使用CPU周期为场景设置动画(委托已设置并触发UIDynamicAnimatorDelegate dynamicAnimatorDidPause:).
我尝试UIGravityBehavior从场景中移除,这确实导致动画师最终停止.我没有时间去除重力行为,因为我需要在一切停止移动后将其从场景中移除.
我知道引力是一个恒定的力,但我仍然认为一旦所有的速度都为0且加速度为0,它就会停止动画师.
这最后一个假设是假的吗?
有类似问题的人吗?
我正在使用一个UISnapBehavior,但它的速度太快了,我不喜欢.有没有办法减慢速度?或者换句话说:有没有办法调整物体的弹性以及它应该捕捉的点?
我有一个视图,其边界设置为碰撞(setTranslatesReferenceBoundsIntoBoundaryWithInsets)和一个重力的子视图设置,以便它可以碰撞超视图边界.
我试图使碰撞0%有弹性,但我还没弄明白怎么样.我尝试了一个UIDynamicItemBehavior弹性为0的子视图,同样具有可笑的高摩擦力而且没有任何东西.我的理由是,0弹性已经意味着在力的作用下再次出现力量再生,但即使是负数似乎也没有做任何事情,也没有什么关系.
关于如何进行碰撞的任何想法都会吸收所有能量或任何使得子视图在碰撞边界时不反弹所需的能量?
我知道外部改变了center,bounds并且transform在UIDynamicItem初始化后会被忽略.
但我需要手动更改transform的UIView,在UIDynamicAnimator系统中.
每次我改变transform它,它将立即被覆盖.
那么任何想法?谢谢.
如果我在UIDynamicBehavior视图中添加任何类型,它会在旋转设备时完全破坏.这是肖像画(正确显示):

在这里它是在风景中,所有破坏:
我不相信这是一个自动布局问题,因为如果我删除添加UIDynamicBehavior它的调用它没有自动布局问题.也不会抛出自动布局错误.这是代码:
@interface SWViewController () {
UICollisionBehavior *coll;
UIDynamicAnimator *dynamicAnimator;
}
@implementation SWViewController
- (void)viewDidLoad {
[super viewDidLoad];
dynamicAnimator = [[UIDynamicAnimator alloc] initWithReferenceView:self.view];
}
- (void)viewDidAppear:(BOOL)animated {
[super viewDidAppear:animated];
[self setupCollisions]; // commenting this out fixes the layout
}
- (void)setupCollisions {
NSArray *dynamicViews = @[greenView];
coll = [[UICollisionBehavior alloc] initWithItems:dynamicViews];
CGFloat topBound = CGRectGetMinY(greenView.frame);
[coll addBoundaryWithIdentifier:@"top"
fromPoint:CGPointMake(0, h1)
toPoint:CGPointMake(CGRectGetWidth(greenView.frame), h1)];
[dynamicAnimator addBehavior:coll];
}
Run Code Online (Sandbox Code Playgroud)
如果我覆盖didRotateFromInterfaceOrientation我可以看到顶部边界greenView不遵循autolayout所说的应该(再次,删除调用以setupCollisions修复此问题).
自动布局边界greenView是:
height …Run Code Online (Sandbox Code Playgroud) autolayout ios7 uicollisionbehavior uidynamicbehavior uikit-dynamics
我正在努力学习UIKit Dynamics.
我创建了一个盒子视图并在其上添加了UIGravityBehavior,但是当我运行Project时没有任何反应!
Viewcontroller.m
#import "ViewController.h"
@interface ViewController ()
@end
@implementation ViewController
- (void)viewDidLoad
{
[super viewDidLoad];
UIView* box = [[UIView alloc]initWithFrame:CGRectMake(100, 50, 100, 100)];
box.backgroundColor = [UIColor blackColor];
[self.view addSubview:box];
UIGravityBehavior* gravityBehaviour = [[UIGravityBehavior alloc]init];
[gravityBehaviour addItem:box];
UIDynamicAnimator* myAnimator = [[UIDynamicAnimator alloc]initWithReferenceView:self.view];
[myAnimator addBehavior:gravityBehaviour];
}
- (void)didReceiveMemoryWarning
{
[super didReceiveMemoryWarning];
// Dispose of any resources that can be recreated.
}
@end
Run Code Online (Sandbox Code Playgroud)
这是我的视图controller.m文件.
程序有什么问题?
我想拖动一个UIView,让它移动附加到其上的其他视图的位置,就像它们都是通过字符串连接一样.起始状态将是一堆UIViews聚集在一起.如果你拉出一个,它附加的项目将在它与被拖动的视图之间达到最小距离后开始移动.我认为实现这一目标的最佳方法是使用UIDynamicItemBehavior,考虑到我需要将其重新捕捉到适当位置并对其施加权重.如果不做荒谬的代码,我不太清楚如何实现这一点.我所拥有的代码可以在下面看到.不幸的是,我遇到的问题是被拖动的方形项目回到了square2.如果有人有任何建议,我会很乐意澄清是否需要.
- (void)viewDidLoad
{
[super viewDidLoad];
_containmentView = [[UIView alloc] initWithFrame:CGRectMake(0.0, self.view.frame.size.height/2, self.view.frame.size.width, 200)];
[self.view addSubview:_containmentView];
[_containmentView setBackgroundColor:[UIColor greenColor]];
_square = [[UIView alloc]initWithFrame:CGRectMake(200, 0, 100, 100)];
_square.backgroundColor = [UIColor yellowColor];
[_containmentView addSubview:_square];
_square2 = [[UIView alloc]initWithFrame:CGRectMake(100, 0, 100, 100)];
_square2.backgroundColor = [UIColor redColor];
[_containmentView addSubview:_square2];
_animator = [[UIDynamicAnimator alloc]initWithReferenceView:_containmentView];
_gravity = [[UIGravityBehavior alloc]initWithItems:@[_square, _square2]];
_gravity.gravityDirection = CGVectorMake(-1.0, 0.0);
[_animator addBehavior:_gravity];
_collision = [[UICollisionBehavior alloc]initWithItems:@[_square]];
_collision.collisionDelegate = self;
_collision.translatesReferenceBoundsIntoBoundary = YES; //causes the boundary to use the bounds of the reference …Run Code Online (Sandbox Code Playgroud) 我一直在寻找一个示例,展示如何在UIKit动态中实现自定义UIDynamicBehavior.所有教程和示例仅显示如何使用基元(碰撞,重力,附件,推动,捕捉等)组装UIDynamicBehavior.
在我的应用程序中,一些视图浮动在屏幕上(使用动态),我想让它们在与其他静止视图重叠时消失.为此,我想测试UIDynamicAnimator和UICollisionBehavior委托方法中的重叠,但不幸的是,这些方法没有提供足够的粒度来执行我需要的测试.
编辑:显然我必须等待一天才回答我自己的问题(新用户),所以我的解决方案现在作为答案发布在下面.
我有一个小UIView在一个盒子里反弹.我正在添加一个瞬时模式.推.事实上,我正在添加很多推 - 5或更多Hz.
神秘:
(1)我必须删除行为???? 如果是的话...... 什么时候?!?"后"是"瞬间"?
(2)UIPushBehaviorModeInstantaneous是一个特例,你不必(或不能)删除那些??
(3)当你添加行为时:那个......保留吗?!UIPushBehavior?要么??WTF?
(4)我似乎无法在任何地方找到这些方面!
-(void)pushMeRight:(CGFloat)mag
{
if ( self.bounceAnimator == nil ) return;
NSLog(@"...........push me right %.2f", mag);
UIPushBehavior *pushRight = [[UIPushBehavior alloc]
initWithItems:@[self]
mode:UIPushBehaviorModeInstantaneous];
pushRight.magnitude = mag;
pushRight.angle = radians(0); // (NB, 0 is right, 90 is down)
[self.bounceAnimator addBehavior:pushRight];
}
Run Code Online (Sandbox Code Playgroud)
{注意:我每次需要时都会分配UIPushBehavior .请注意,如果您尝试使用"只有一个"作为属性,则它不起作用.事实上,Rob在下面解释了原因.}
解
经过极其广泛的测试,我们发现Rob的"第二"解决方案,使用.action,基本上是完美的.
经过大量测试后,我们强烈建议以下代码,实际上是"解决方案",是重复推送代码的唯一方法.感谢Rob的好处:/
-(void)pushAllUp:(CGFloat)mag
{
if ( self.bounceAnimator == nil ) return;
for ( UIView *pushme in self.subviews )
{ …Run Code Online (Sandbox Code Playgroud) 我正在查看UIPushBehavior的Apple文档,它让我在瞬时模式下感到困惑.我知道加速公式是Force = Mass*acceleration.我假设视图的质量是宽度*高度*密度(1).文档描述了推送幅度如下:
默认幅度为零,相当于无力.应用于密度值为1.0的100点×100点视图的大小为1.0的连续力矢量导致在角度或pushDirection属性指示的方向上的视点加速度为100点/秒2.
这在连续推动方面是有意义的,它提供恒定的加速度.它没有说任何关于皮肤推进的内容.如何理解1级瞬时推动对100x100视图的速度?
physics ios7 uidynamicbehavior uidynamicanimator uipushbehavior