How to get the actual [UIScreen mainScreen] frame size?

被刻印的时光 ゝ 提交于 2019-11-29 20:34:56

Actually that is very usefull.
When you ask a UIScreen for it's Bounds you get the bounds of the screen, which is the whole device screen. (the status bar is part of the screen)
But if you ask a UIScreen to tell you where and how big can be the root view of your application asking for the applicationFrame is usefull. There is no direct relationship between the 2 calls except that the applicationFrame is returned in the UIScreen bounds coordinate system. (But the status bar is not part of your application, that explain the different result)

applicationFrame
The frame rectangle to use for your application’s window. (read-only)
@property(nonatomic, readonly) CGRect applicationFrame
Discussion
This property contains the screen bounds minus the area occupied by the status bar, if it is visible. Using this property is the recommended way to retrieve your application’s initial window size. The rectangle is specified in points.

Actually 0 does not start at the bottom of the status bar. It starts at the top of it. Add a UILabel at (0,0) and you won't see it unless you have the status bar hidden. So bounds gives you the total screen area, and applicationFrame gives you the area your application has to work with. I bet if you hide the status bar the application frame will match the bounds.

I had a similar issue. What I was doing was pretty dumb, but I hope this helps someone.

In the subview I had:

- (id)initWithFrame:(CGRect)frame
{
    self = [super initWithFrame:frame];
    if (self) {
        UIView * otherSubview = [[UIView alloc] initWithFrame:frame];
        [self addSubview:otherSubview];
    }
    return self;
}

Because I was creating my subview with a frame with an origin not at (0,0), but then using that same frame to generate subviews for my subview, those subviews also got shifted down. The result was that annoying black banner you mentioned.

I fixed this by doing the following:

- (id)initWithFrame:(CGRect)frame
{
    self = [super initWithFrame:frame];
    if (self) {
        CGRect rect = frame;
        rect.origin.x = 0;
        rect.origin.y = 0;
        UIView * otherSubview = [[UIView alloc] initWithFrame:rect];
        [self addSubview:otherSubview];
    }
    return self;
}

You might look at UIWindow. It inherits from UIView so it will have bounds and a frame, and iOS apps are all single window. -[UIApplication keyWindow] will return the window set up by the app delegate. Since all other views are anchored in the main window, I imagine this ought to give you correct bounds.

Swift 2.0 update:

func presentAboveAll() {
       //Get the view from the nib. Assuming the view is is in AboveAllView.xib
        let nibContents = NSBundle.mainBundle().loadNibNamed("AboveAllView", owner: nil, options: nil)

        //Get hold of your view
        let views =  nibContents.filter {
          if let _ = $0 as? UIView{
            return true
          }
          return false
        }

        guard views.count > 0  else {
          return
        }

        //Set up frame and add to the app's key window
        let view  = views.first as! UIView
        view.frame = UIScreen.mainScreen().bounds
        UIApplication.sharedApplication().keyWindow?.addSubview(view)
}
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!