I've been working on an iPad app that has gone through fairly extensive testing on the iPad 2. I recently obtained a "New iPad" (iPad 3), and the app feels significantly slower. Animations / scolling behaviors that were silky smooth in the iPad 2 now feel extremely stuttery on the new iPad.
I do a lot of the standard UI performance tips: using shadowPaths, drawing UITableViewCells using CoreGraphics, rasterizing views that don't change often / don't need to animate.
Are there any pitfalls I should watch be watching out for in transitioning my app to the iPad 3?
Update
I swore that I tried this before but removing rounded corners from my UIViews views ended up speeding the app significantly. clipToBounds also seems to be a significant performance hit (although strangely... setting a view's layer's maskToBounds seems to be okay, which makes no sense to me). Some combination of this and other tweaks seems to have resolved the issue.
Once I do a second visual pass over the app, I'll figure out a way to reimplement rounded corners in a more performant way.
4x the pixels, only 2x the fill rate. The maths says it all.
I think that the biggest thing to watch out for is copies of graphics from system memory to the video card since they are 4X larger than previous iPad graphics with about the same CPU power as the iPad 2.
Maybe it's due to upscaling by iOS? After all it has to calculate a higher res version of everything before showing to screen. Since some things on the screen are hi-res already (font and default ui elements) it has to scale every other element individually.
Have you tried just scaling the images yourself and adding them as retina images to your project?
Good luck.
Related
I have two questions about the iOS Simulator in Xcode for my Unity game:
I am using latest version of all the software involved.
1) Why is it so slow? (I have tried the Cmd+T solution and it does
nothing. Note: The game runs smooth even on a real iPhone 4)
2) Why is the size of the iPad simulator screen bigger than my laptop screen? (I know you can
scale it, but just curious why Apple always tries to make our life
difficult)
When you run game on iOS simulator then your game image runs not completely running on your mobile hardware actually runs in compression mode so seems to be slow.
Having high resolutions Apple deceives have bigger number of pixels on their screen, so its not Screen size but it Screen pixels what we need to concern. And it is for creating more smooth effects on visuals for animation, it is to provide user better quality graphics, not to make your life difficult
I've recently been implementing a new project on Swift, targeting iOS 8+. The UI mixes storyboards and XIBs, using autolayout for everything.
I recently took a look at the application using the "color misaligned images" debug feature in the iOS simulator. All my images are fine but for some reason almost every label and textview I have is showing up as magenta, meaning they are supposedly misaligned. All of these views are aligned using autolayout, which is supposed to be very good at avoiding misalignment. Any thoughts on what is going on here?
EDIT:
Nevermind, turns out it was just another Stupid User Error. I forgot I had a scaling function for forcing downscaling on some fonts based on screensize. This was returning fractions which was causing the misalignment.
maybe this will help?
http://blog.xebia.com/2013/07/19/ios-pixel-misalignment-why-its-bad-how-to-fix-it/
"How To Fix Pixel Misalignment?
Once you have found your culprit. It’s a good idea to start looking through your code to determine how the actual frame of the misaligned screen item is calculated. Some debugging will help you here. I’d look in any layoutSubviews or loadView calls for any divisions being performed on view frames. Also using Font metrics in your calculations is a common cause for misaligned images.
Most likely you will have found your culprit pretty soon. How to fix this? There are two ways to go about this. Either use a floorf or ceilf on the exact value causing the misalignment. Or pass the CGRect for the views frame through a CGRectIntegral call.
When it concerns an image on a retina device, make sure the retina version of that image is actually exactly twice the dimensions of the non retina image. Faulty dimensions on retina image resources is a common cause as well for pixel misalignment. So get check those image resources if they show up magenta."
For the past couple of weeks I have been dabbling with SpriteKit, Xcode, and Swift and despite doing a lot of research I have yet to find out the best way to manage sprite size between devices.
In my game I have found a somewhat round-about way of handling sprite size and position to make my sprites somewhat consistent between devices by manually adjusting characteristics like size, font size, and position with if statements checking for the height of the device. Ideally I would like my entire game views, including the sprites that they house, to be sized proportionally to the device size. I have tried messing with the different SKSceneScaleModes but nothing is really doing the trick.
My question: What is the most efficient way of handling sprite size and positioning between devices in SpriteKit (more specifically in Swift)? I don't care too much about supporting the iPad, mainly just the iPhone 4s - 6 plus. Thanks.
Imo, simply scaling relative to the GameScene's size is good enough. In GameViewController, I initialize the scene to be the view.bounds.size. When you create your sprite, just make a setScale call to make it proportional to view.bounds.size. Since view.bounds.size is based on how big the screen is, you'll get proportionally bigger images for bigger screened devices.
I have an app based on "OpenGL Game" Xcode template, for everyday testing/dev I would like to render full screen but at lower resolution in simulator (e.g. 1/2 or 1/4). Any efficient/savvy way to put this in place?
(in case anybody wonder, I want to do this because my app is running very slow in simulator, so rendering at a smaller resolution would make testing/debugging a lot more programmer-friendly)
The contentScaleFactor of the view is 2.0 by default on a Retina display. If you reduce the scale factor, GLKView automatically uses a smaller framebuffer and scales its contents up to screen size for display.
Scale factor 1.0 is half size (or the same number of pixels as a non-Retina screen). 0.5 would be quarter size — big, chunky pixels on any display. Non-integral scale factors between 1.0 and 2.0 work, too, and can be a great way to compromise between quality and performance on a Retina display.
Update: just had a vote remind me of this answer. I'm surprised I wouldn't have said this originally, but I may as well add it now...
The iOS Simulator runs OpenGL ES using a software renderer (i.e. on the host Mac's CPU, not its GPU). That's why it's slow. Performance characteristics and rendering results can vary from renderer to renderer, so never trust the simulator for anything OpenGL/GPU-related (except perhaps in very broad strokes).
I'm currently working on an OpenGL game, and recently began refactoring it to support iPhone in addition to iPad. In an attempt to give myself as little work as possible, I simply resized the containing EAGLView to 480 x 360 (to preserve the iPad aspect ratio) and shifted the view up so it's y origin lay at -20 (in order to centre the content, and as the edges could be cropped).
I found this resulted in jerky performance on the device (despite the CADisplay link reporting a frame duration that equated to 59-61 fps) and was at least 20% slower when compared side by side with the iPad version.
I then tried resizing the view to the screen size 480 x 320 and the performance returned to normal (though the rendered content no longer has the correct aspect ratio).
Why is it that the 'off screen' rendering causes a performance hit and why does the displaylink still think it is running at 60fps?
Any ideas?
Thanks
This is mostly a wild guess, but what about clipping regions? There was this hardware functionality that made it possible to mix windows and hardware accelerated graphics. Maybe it is not implemented very well on mobile devices.
You could, however, avoid making the UIView offscreen and try to use glViewport() to shift the parts of the view offscreen. While it seems to be the same, it is handled by a different part of the pipeline (the rasterizer), and should be much faster.