Question

I am adding a subview programmatically and adding it to the main windows context view to cover up the entire context view like so:

loadingView = [[LoadingView alloc] initWithFrame:[mainWindow.contentView frame]];

NSLog(@"%@", [mainWindow.contentView subviews]);
[mainWindow.contentView addSubview:loadingView];
NSLog(@"%@", [mainWindow.contentView subviews]);

[mainWindow makeFirstResponder:loadingView];

The NSLog's confirm that loadingView is being added last in the contentView subviews. I have also tried:

loadingView = [[LoadingView alloc] initWithFrame:[mainWindow.contentView frame]];
[mainWindow.contentView addSubview:loadingView positioned:NSWindowAbove relativeTo:nil];
[mainWindow makeFirstResponder:loadingView];

That didn't work either. For some reason the two tableviews (created in IB) at the bottom of the window are on top of the new view I've added. Here's a snapshot of the window, note that the red part is what should be on top with the progress bar and a few labels:

loadingView

It's also worth noting that the view has it's alpha set to 0.9 which is why you can somewhat see behind it.

GW

Was it helpful?

Solution

If you place one view above another, the objects in the previous view will be visible in above view. What you need do is remove previous views from window and then add a new subview.

Try using:

//Create IBOutlet of your tableview in your .h file
IBOutlet NSTableView* yourTableView;

// Add this line where you are adding your subview to remove the tableview from superview.
[yourTableView removeFromSuperview];

// Then add your loading view as the subview
loadingView = [[LoadingView alloc] initWithFrame:[mainWindow.contentView frame]];
[mainWindow.contentView addSubview:loadingView];

Then whenever your want your tableView back use:

[window contentView]addSubview: yourTableView];

OTHER TIPS

As long as you use nil here, you will not get predictable results.

[mainWindow.contentView addSubview:loadingView positioned:NSWindowAbove relativeTo:nil];

If you have not already done so, put all the other views inside a containing view. Make the containing view the only view that is a direct child of the window content view. Now add your subview with the above method and replace nil with a reference to the containing view.

In OS X, overlapping siblings have certain nuances when it comes to drawing. In your case, the loadingView and the two table views are siblings because they are all added as subviews of the window's content view and they overlap hence the nuances are coming into play.

From Apple's Documentation

For performance reasons, Cocoa does not enforce clipping among sibling views or guarantee correct invalidation and drawing behavior when sibling views overlap. If you want a view to be drawn in front of another view, you should make the front view a subview (or descendant) of the rear view.

I don't have the definitive solution for this but reading these should help improve your understanding for the long term.

http://www.cocoabuilder.com/archive/cocoa/327817-overlapping-sibling-views.html

Is there a proper way to handle overlapping NSView siblings?

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top