在应用程序终止并在iOS中再次启动时,NSNotificationCenter无法启动

时间:2019-11-28 17:23:43

标签: ios objective-c xcode appdelegate nsnotificationcenter

我有一个银行应用程序,该应用程序要求禁用屏幕记录,并且我不希望人们使用新的iOS-11功能来记录带有敏感数据的屏幕并将其公开。由于无法在iOS中禁用屏幕录制,因此我尝试通过检测iOS11屏幕录制功能“开”或“关”来解决此问题。我使用了isCaptured和UIScreenCapturedDidChange Notification。代码如下:

   - (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
  if (@available(iOS 11.0, *)) {
        [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(screenCaptureChanged) name:UIScreenCapturedDidChangeNotification object:nil];
    }

    return YES;
 }




-(void)screenCaptureChanged{

if (@available(iOS 11.0, *)) {

    BOOL isCaptured = [[UIScreen mainScreen] isCaptured];// will keep on checking for screen recorder if it is runnuning or not.

    if(isCaptured){

        UIView *colourView = [[UIView alloc]initWithFrame:self.window.frame];

        colourView.backgroundColor = [UIColor blackColor];

        colourView.tag = 1234;

        colourView.alpha = 0;

        [self.window makeKeyAndVisible];

        [self.window addSubview:colourView];

        // fade in the view

        [UIView animateWithDuration:0.5 animations:^{

            colourView.alpha = 1;

        }];

    }else{

        // grab a reference to our coloured view

        UIView *colourView = [self.window viewWithTag:1234];

        // fade away colour view from main view

        [UIView animateWithDuration:0.5 animations:^{

            colourView.alpha = 0;

        } completion:^(BOOL finished) {

            // remove when finished fading

            [colourView removeFromSuperview];

        }];

    }

} else {

    // Fallback on earlier versions

    // grab a reference to our coloured view

    UIView *colourView = [self.window viewWithTag:1234];

    if(colourView!=nil){

        // fade away colour view from main view

        [UIView animateWithDuration:0.5 animations:^{

            colourView.alpha = 0;

        } completion:^(BOOL finished) {

            // remove when finished fading

            [colourView removeFromSuperview];

        }];

    }

}
}

因此,逻辑是在屏幕录制开始时触发通知,在录制发生时以及录制停止时在视频上放置黑色的逻辑被删除。当应用程序移至后台,活动,非活动和前景方案时,这可以很好地工作。但是,当应用程序被杀死(终止)而屏幕录制仍在进行时,而当我们再次启动应用程序而屏幕录制仍在进行时,黑色则无法覆盖屏幕。因此,如何在选择器方法正常工作的情况下再次调用通知选择器

1 个答案:

答案 0 :(得分:1)

isCaptured中检查屏幕的application:didFinishLaunchingWithOptions:属性的值,并相应地显示或隐藏覆盖视图。

UIWindow + ScreenCapture.h:

#import <UIKit/UIKit.h>

NS_ASSUME_NONNULL_BEGIN

@interface UIWindow (ScreenCapture)

- (void)showOrHideContentDependingOnCapturedState;
- (void)hideContent;
- (void)showContent;

@end

NS_ASSUME_NONNULL_END

UIWindow + ScreenCapture.m:

#import "UIWindow+ScreenCapture.h"

@implementation UIWindow (ScreenCapture)

- (void)showOrHideContentDependingOnCapturedState {
    if (self.screen.isCaptured) {
        [self hideContent];
    } else {
        [self showContent];
    }
}

- (void)hideContent {
    UIView *blackView = [self viewWithTag:1234];
    if (!blackView) {
        blackView = [[UIView alloc] initWithFrame:self.bounds];
    }

    blackView.tag = 1234;
    blackView.backgroundColor = UIColor.blackColor;
    blackView.autoresizingMask = UIViewAutoresizingFlexibleWidth | UIViewAutoresizingFlexibleHeight;

    // This is important! If this is not set, then any new view added to
    // the window (like the root view controller's view) will be overtop of
    // `blackView`, which we don't want.
    blackView.layer.zPosition = 10000;

    [self addSubview:blackView];
}

- (void)showContent {
    [[self viewWithTag:1234] removeFromSuperview];
}

@end

AppDelegate.h:

#import <UIKit/UIKit.h>

@interface AppDelegate : UIResponder <UIApplicationDelegate>

@property (nullable, strong, nonatomic) UIWindow *window;

@end

AppDelegate.m:

#import "AppDelegate.h"
#import "UIWindow+ScreenCapture.h"

@implementation AppDelegate

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
    [[NSNotificationCenter defaultCenter] addObserver:self
                                             selector:@selector(checkIsBeingRecorded)
                                                 name:UIScreenCapturedDidChangeNotification
                                               object:nil];
    [self.window showOrHideContentDependingOnCapturedState];

    return YES;
}

- (void)checkIsBeingRecorded {
    for (UIWindow *window in UIApplication.sharedApplication.windows) {
        [window showOrHideContentDependingOnCapturedState];
    }
}

@end
相关问题