How to create 1536x2048 framebuffer for iPad Retina sample (GLGravity)

前端 未结 4 1423
情歌与酒
情歌与酒 2021-02-01 11:06

So of course the first thing I\'m trying on my new iPad (4g) is the old GLGravity example. The only modification I\'ve made is to set the target device to \"iPad\".

Howe

相关标签:
4条回答
  • 2021-02-01 11:30

    As an expansion on this answer, the GLGravity sample needs another change to ensure the GL viewport is set correctly. This is because theboundsproperty returns Quartz points, not pixels.

    -(void)setupView
    {
      ...
      CGRect rect = self.bounds;
      // new code - modify the viewport dimensions.
      rect.size.width *= self.contentScaleFactor;
      rect.size.height *= self.contentScaleFactor;
      // end of new code
      glFrustumf(-size, size, -size / (rect.size.width / rect.size.height), size / (rect.size.width / rect.size.height), zNear, zFar);
      glViewport(0, 0, rect.size.width, rect.size.height);
      ...
    }
    
    0 讨论(0)
  • 2021-02-01 11:33

    To enable conditional support for Retina graphics, as we did for the iPhone 4, you would need to have a line of code like this somewhere in the setup for your OpenGL ES hosting view (GLGravityView, in this case):

    self.contentScaleFactor = [[UIScreen mainScreen] scale];
    

    This makes sure that the content within that view (such as Quartz drawing) is rendered with the 2-pixels-per-point scaling used in the current Retina displays on the iPhone and iPad.

    Your view's bounds will remain at the 768 x 1024 point size, but the render buffer will return 1536 x 2048 as its pixel dimensions when queried by glGetRenderbufferParameterivOES(). This will allow you to render Retina-level graphics within your OpenGL ES context.

    Note that some of Apple's sample code (like GLGravity) uses the view bounds to size other display elements, so they will appear too small in the scene. You might need to replace calculations based on the view bounds (in points) with the backing width (in pixels) to make sure that the 2.0 scaling of the Retina graphics is taken into account.

    0 讨论(0)
  • 2021-02-01 11:33

    I had the same problem: @2x ipad images present, but everything renders @1x on the new iPad. iPhone/iPod Touch works OK on retina and non-retina devices. Searching the Apple dev forums I found the problem: I am still on Xcode 4.2, building for iOS 5.0. This OS does not foresee the possibility of a retina ipad. So I need to build with 5.1.

    0 讨论(0)
  • 2021-02-01 11:38

    I think I kind of get this.

    XIB files measure in pts, not pixels. A pt is a unit of distance, like a cm, or a light-year. A pixel is not a unit of distance, it stands for "picture element". Different devices can have different pixel densities.

    Your XIB file tells the size of your display area in pts. iPhone apps default to 320x480 pts, iPad 768x1024 pts. You can check this out in your xib file.

    Now, self.contentScaleFactor that Brad refers to is the answer. What this value does is: "convert from the default logical coordinate space (768x1024 pts) into the device coordinate space of this screen (1536x2048 px)."

    In other words, self.contentScaleFactor is a measure of pixels/pt used by the device. This value varies naturally from device to device. XCode has you specify UI elements in pts (unit of real world distance), so things don't appear screwed up on different resolutions.

    You can even set self.contentScaleFactor=4, which actually looks kinda cool (it supersamples) (but can run slow).

    Another gotcha here is touch events will always be in pts, never in pixels. That is, retina devices still only resolve touch events on a 768x1024 scale.

    So, if your view supports touch picking, you need to multiply each incoming touch event by self.contentScaleFactor in order for the incoming location in pts to map to pixels in your framebuffer.

    0 讨论(0)
提交回复
热议问题