I’m Damir Tursunovic, an iOS and Ruby developer in the Netherlands. More.

Changing the status bar style in an iOS 8 action extension

22 September 2014

We've been waiting for app extensions for a long time as iOS developers. And I couldn't be more happy with iOS 8 even though there are some important improvements to make.

One problem is the status bar style. It's dark by default and it seems that there is no way to change it (for now). Typically you return your preferred status bar style in the preferredStatusBarStyle method but that doesn't help if the method is never called.

The problem

Your app action extension root view controller is a child of _UIViewServiceViewControllerOperator, which is the root view controller of _UIHostedWindow. The _UIViewServiceViewControllerOperator returns nil in the childViewControllerForStatusBarStyle (or is not even implemented), which means that your view controller does not have any control over the status bar style. I'm not sure if the iOS team did this deliberately (even though it would be understandable) but there are scenarios where you want to change the status bar style.

Workaround

A possible workaround is to hijack preferredStatusBarStyle in _UIViewServiceViewControllerOperator. Yes, it's bad but it seems that there is no other way. We can do this with class_addMethod or method_setImplementation method.

Here's an example using class_addMethod:

// import <objc/runtime.h>

...

// Add this method in your action extension's root view controller
NSInteger _UIViewServiceViewControllerOperatorPreferredStatusBarStyle(id self, SEL _cmd) {

    return UIStatusBarStyleLightContent; // your preferred status bar style
}

...

// Your action extension's root view controller viewWillAppear:
-(void)viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];
    class_addMethod(NSClassFromString(@"_UIViewServiceViewControllerOperator"),
                    @selector(preferredStatusBarStyle),
                    (IMP)_UIViewServiceViewControllerOperatorPreferredStatusBarStyle,
                    "v@:");

    // Force the status bar appearance update
    [self setNeedsStatusBarAppearanceUpdate];
}