可可移动重叠NSViews

时间:2011-07-16 07:34:41

标签: objective-c cocoa resize nsview

我在一个主视图中有几个视图。这些观点都是彼此落后的,所以目前只能看到最顶尖的观点。我想要做的是,在一些特定的用户输入时,后面的一个视图在屏幕下方向下移动,因此可以在顶视图下方看到它。我一直试图通过确定两个视图当前是否重叠,降低后面的一个,如果它们仍然重叠,降低它更多,等等直到它们不再重叠并且都完全可见来尝试。然后我想主视图调整大小以便可以看到两个视图,但我认为只是使用setBounds或setFrame,还没有到达那里。

对于第一个问题,我还没有找到一种方法来逐字地看两个视图是否重叠,如果无法完成,我想可能是通过在视图边界上绘制rects并检查它们是否重叠,但我不知道得到我如何能做到这些。我认为需要边界或框架,但我不确定这些是如何不同的。

基本上,我想检查两个NSView是否重叠,如果有,我想降低其中一个。

编辑:问题的这一部分已经解决了,但现在又出现了一个新问题。我有三个视图,一个主视图和两个子视图。主视图没有任何东西,它只包含几个子视图,主视图内部的内容应该是什么。两个子视图堆叠在主视图的顶部,因此最前面的一个是可见的,后面的一个被设置为隐藏。当用户点击开始时,后面的视图变得可见,我设置了一个带有选择器的重复计时器,该选择器将检查视图是否重叠,如@Vince所说,如果他们这样做,它会将后退中的那个偏移一点,再次检查,直到它们不再重叠。使用这个:

- (void)updateViews {
CGRect viewFrame = [view frame]; //view is the frontmost view that will not move
CGRect backroundViewFrame = [backgroundView frame]; //the view in the back

CGRect rectIntersection = CGRectIntersection (viewFrame,
                                              backgroundFrame);

//if the intersect is NOT null, it'll offset down by 2
if (!CGRectIsNull(rectIntersection)) {
    CGRect newFrame = CGRectOffset (
                                    rectIntersection,
                                    0,     //doesn't move in x
                                    -2     //lowers by 2 in y
                                    );
    [backgroundView setFrame:newFrame]; //lowers the view to the new offset rect

} else{
    [viewsUpdater invalidate]; //stops the timer when rects no longer intersect
    viewsUpdater = nil;
}

问题在于,当我降低backgroundView时,它只能在与前视图相交的空间中可见。即使我将主视图向下扩展(这是想法,它们都会以相同的尺寸在另一个上面开始,当backgroundView降低时,主视图将调整并显示两者)。但是现在主视图的大小并不重要,backgroundView只能在与前视图相交的区域中可见。我认为它正在向它所需要的位置移动,但是当它停止时它完全不可见,所以我无法分辨。

感谢您的帮助。

1 个答案:

答案 0 :(得分:4)

基本上,您可以通过获取两个NSView属性(frame)的交集来知道两个CGRectIntersection()对象是否重叠,然后使用null测试结果为null CGRectIsNull()
这是doc

现在,关于将一个视图放在另一个视图上,听起来您需要使用NSView中的此方法:-(void)setSubviews:(NSArray *)newSubviews;,根据documentation,您可以重新排序子视图。

或者只是简单地使用-(void)replaceSubview:(NSView *)oldView with:(NSView *)newView;,因为oldView将被释放,所以要小心保留之前的引用。

如果您只是尝试将视图向下移动,则只需更改接收方框架的origin,例如:

CGRect actualFrame = [aView frame];
CGPoint framesOrigin = actualFrame.origin;
CGRect newFrame = CGRectMake(framesOrigin.x,
                             (framesOrigin.y)+50,
                             actualFrame.width,
                             actualFrame.height);
[aView setFrame:newFrame];

这将通过更改其框架原点的y坐标来降低aView

最后,关于boundsframe属性之间的区别,这篇关于SO Difference between view's frame and view's bound + iPhone的帖子应该回答你的问题;)