How to display a progress indicator overlay/HUD on

2019-01-10 08:54发布

问题:

I want to display a progress indicator in a semi-transparent box that floats over a table view. In other words, when the table contents are being downloaded, I want an "Updating" label to appear over it.

I have seen this in several apps in the store, notably Facebook (when you shake to reload) and Darkslide.

My first impulse is to create a semi-transparent UIView, place a UILabel and a UIProgressIndicatorView inside it, and add it to the view hierarchy... but where? A UIView may not overlap its siblings, so I can't make it a subview of the window. I also can't make it a subview of the table, because then it will scroll up and down with the table content.

I thought about creating a new UIWindow, but the documentation basically says don't.

I know CALayers can overlap each other, so that would be an option, but I can't put a progress indicator inside a CALayer, can I? Should I roll my own progress indicator that animates a CALayer instead of a UIView?

I'm not interested in hearing about private APIs.

Edit: The question was based on a faulty assumption. NSViews (on Mac OS X) may not overlap, but UIViews on the iPhone may.

回答1:

You can definitely overlap views. Just add the transparent overlay as a subview in the tableView.

From UIView's documentation:

UIView objects are arranged within an UIWindow object, in a nested hierarchy of subviews. Parent objects in the view hierarchy are called superviews, and children are called subviews. A view object claims a rectangular region of its enclosing superview, is responsible for all drawing within that region, and is eligible to receive events occurring in it as well. Sibling views are able to overlap without any issues, allowing complex view placement.



回答2:

I've just posted a HUD version of mine : https://github.com/y0n3l/LGViewHUD

you can get this result very easily :

#import "LGViewHUD.h"
.... 
LGViewHUD* hud = [LGViewHUD defaultHUD];
hud.activityIndicatorOn=YES;
hud.topText=@"The longer....";
hud.bottomText=@"The better !";
[hud showInView:self.view];

Once the task is ended, just invoke

[[LGViewHUD defaultHUD] hideWithAnimation:HUDAnimationHideFadeOut];

and that's it !



回答3:

Also there are the quite famous MBProgressHUD & SVProgressHUD
They are the same kind as @yonel 's HUD

Example

[SVProgressHUD show];
[SVProgressHUD dismiss];

MBProgressHUD seems now more popular (if we base on github stars)



回答4:

Any object that lives in your MainWindow.xib can get access to the application window via an outlet. The application delegate in the standard projects already has it, but you'll probably want to add the outlet to your view controller that needs to show the progress overlay.

Since in UIKit the UIWindow is a UIView (unlike NSWindow vs. NSView in Cocoa), you can simply add your progress view as a subview of the window:

[window addSubview:progressView];

progressView will cover the entire application UI.

This example uses the technique to fade out the Default.png splash image:

http://michael.burford.net/2008/11/fading-defaultpng-when-iphone-app.html


With relation to the recent edit, as of MacOS X 10.5 Leopard NSView overlapping is deterministic (they always could overlap, you just got undetermined results), though it has a different front-to-back ordering depending on whether the containing view is layer backed or not. This is most likely a side effect of integrating CALayers into the OS X view system.



回答5:

Answer: Apples docs are pretty awesome. http://developer.apple.com/iphone/library/featuredarticles/ViewControllerPGforiPhoneOS/Introduction/Introduction.html

Currently I'm into over laying transparent views (at least on the back of a napkin at this point). You can use them to hold menu buttons, move them in 3D space, just get nuts.

I mean is this a religious tract of or what? Amazing stuff from the guys at NEXT:

UIView objects are arranged within an UIWindow object, in a nested hierarchy of subviews. Parent objects in the view hierarchy are called superviews, and children are called subviews. A view object claims a rectangular region of its enclosing superview, is responsible for all drawing within that region, and is eligible to receive events occurring in it as well. Sibling views are able to overlap without any issues, allowing complex view placement.