program tip

iOS7의 UIActivityViewController에서 표시 될 때 메일 작성기에서 보내기 및 취소 단추의 텍스트 색상을 설정할 수 없습니다.

radiobox 2020. 11. 11. 19:42
반응형

iOS7의 UIActivityViewController에서 표시 될 때 메일 작성기에서 보내기 및 취소 단추의 텍스트 색상을 설정할 수 없습니다.


UIActivityViewController를 사용하여 iOS7에서 항목을 공유하고 있습니다. 메일 옵션을 탭하면 메일 작성기가 팝업되지만 내비게이션 바의 취소 및 보내기 버튼과 내비게이션 바 자체가 파란색으로 읽기가 매우 어렵 기 때문에 색상을 변경하고 싶습니다. iOS6에서는 작동하지만 iOS7에서는 작동하지 않습니다.

나는 시도했다

[[UIBarButtonItem appearance] setTitleTextAttributes:[NSDictionary dictionaryWithObjectsAndKeys:[UIColor redColor], UITextAttributeTextColor, [UIColor clearColor], UITextAttributeTextShadowColor, nil] forState:UIControlStateNormal];

iOS6에서 작동하며 시도했습니다.

[[UIBarButtonItem appearance] setTintColor:[UIColor redColor]];
[[UINavigationBar appearance] setBarTintColor:[UIColor redColor]];

이로 인해 앱이 처음 실행될 때 색상이 빨간색으로 깜박이고 즉시 파란색으로 전환됩니다.


의 텍스트 색상 변경 관리 보내기취소 에있는 버튼, UINavigationBar에서 MFMailComposerViewController(모두 보내기취소 ) 및 MFMessageComposeViewController(만 취소 에서 발표 할 때) UIActivityViewController.

UIActivityViewController를 사용하여 Message또는 탭하십시오 Mail.

UIActivityViewController 사용

보내기취소 버튼 의 기본 텍스트 색상 이 파란색 임을 알 수 있습니다 .

기본 파란색

이를 변경하려면 AppDelegate.m클래스의 didFinishLaunchingWithOptions메소드에 다음 행을 삽입하십시오.

[[UIBarButtonItem appearanceWhenContainedIn:[UINavigationBar class], nil] setTintColor:[UIColor whiteColor]];

결과는 다음과 같습니다.

흰색으로 변경

예를 들어 다른 색상을 사용할 수도 있습니다.

[UIColor purpleColor];

보라색으로 변경

[UIColor greenColor];

녹색으로 변경

어떻게 테스트 했나요? 이 솔루션은 다음과 같은 경우에 작동합니다.

  • Xcode 5.1을 사용하여 iOS 7.1 시뮬레이터에서 기본 iOS SDK 7.1로 빌드 (프로젝트 파일-> 빌드 설정-> 기본 SDK 선택에서 선택할 수 있습니다. 또한 일반-> 배포 대상-> 7.1에서 선택)
  • Xcode 5.1, iPhone 4에서 기본 iOS SDK 7.0으로 빌드 (프로젝트 파일-> 빌드 설정-> 기본 SDK 선택에서 선택할 수 있습니다. 또한 일반-> 배포 대상-> 7.0에서 선택)
  • Xcode 5.1, iPhone 4에서 기본 iOS SDK 7.1로 빌드 (프로젝트 파일-> 빌드 설정-> 기본 SDK 선택에서 선택할 수 있습니다. 또한 일반-> 배포 대상-> 7.1에서 선택)

다음과 같이 테스트 할 때는 작동하지 않았습니다.

  • Xcode 5.1, iOS 7.0 시뮬레이터에서 기본 iOS SDK 7.0으로 빌드 (프로젝트 파일-> 빌드 설정-> 기본 SDK 선택에서 선택할 수 있습니다. 또한 일반-> 배포 대상-> 7.0에서 선택)

따라서 실제 장치의 동작이 iOS 시뮬레이터의 동작보다 중요하다고 생각하므로 사용하는 것이 안전해야합니다. iOS 7.0 시뮬레이터에서 작동하지 않는 이유를 아는 사람이 있다면 알고 싶습니다. :)


UIActivityViewController의 막대 색조 색상 및 상태 표시 줄 색상. Swift 3 솔루션 :

extension MFMailComposeViewController {
    override open func viewDidAppear(_ animated: Bool) {
        super.viewDidAppear(animated)
        UIApplication.shared.statusBarStyle = UIStatusBarStyle.lightContent
    }

    open override func viewDidLoad() {
        super.viewDidLoad()
        navigationBar.isTranslucent = false
        navigationBar.isOpaque = false
        navigationBar.barTintColor = UIColor.white
        navigationBar.tintColor = UIColor.white
    }
}

다음은 현재 iOS 7.1에서 작동하는 기능입니다.

UIActivityViewController를 하위 클래스로 만들고 다음 메서드를 재정의합니다.

- (void)presentViewController:(UIViewController *)viewControllerToPresent animated:(BOOL)flag completion:(void (^)(void))completion
{
    viewControllerToPresent.view.tintColor = [UIColor whiteColor];

    [super presentViewController:viewControllerToPresent animated:flag completion:^{
        [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];

        if (completion) {
            completion();
        }
    }];
}

이렇게하면 버튼이 흰색이고 상태 표시 줄이 흰색이됩니다.


대한 스위프트 :

self.navigationController?.presentViewController(activityViewController, animated: true, completion: { () in
   UIBarButtonItem.appearance().tintColor = UIColor.whiteColor()
   UINavigationBar.appearance().barTintColor = UIColor.whiteColor() // optional to change bar backgroundColor           
}

이렇게하면 전송취소 버튼 색상이 흰색 (iOS 7,8에서 테스트 됨)으로 변경되지만 여전히 상태 표시 줄 텍스트 색상을 흰색으로 만들 수 없습니다 (상태 표시 줄 텍스트 색상 UIActivityViewController을 변경하기 위해 해당 하위 클래스 솔루션을 시도하지는 않았지만 ).


이것은 iOS 7의 버그 인 것 같습니다. 온라인에서이 문제에 대한 다른보고를 보았습니다. 또한 iOS 7.1에서는 수정되지 않은 것으로 보입니다.

구체적으로 말하면, 어떤 작업을하든 UIActivityViewController에서 표시되는 대화 상자의 탐색 모음에 색조 색상을 설정할 수 없습니다.


외관 프록시 덕분에 모든 곳에서 tintColor속성 UINavigationBar이 흰색 인 내 앱에서 동일한 문제가 발생했습니다 . 그 결과 UIBarButtonItem메일 작성기에서보기 컨트롤러 navigationBar가 표시되지 않았습니다 (흰색 탐색 모음의 흰색 단추).

application:didFinishLaunchingWithOptions:방법 에이 호출이 있습니다 .

[[UINavigationBar appearance] setTintColor:[UIColor whiteColor]];

UINavigationBar에서 메일 작성기 뷰 컨트롤러에 액세스하는 것이 불가능하기 때문에 (지금은?) UIActivityViewControllerAlex의 답변에서 영감을 얻은 다음 해결 방법을 수행했습니다.

UIColor *normalColor = [[UINavigationBar appearance] tintColor];
UIActivityViewController *activityViewController = [[UIActivityViewController alloc] initWithActivityItems:dataToShare applicationActivities:nil];
            [activityViewController setCompletionHandler:^(NSString *activityType, BOOL completed) {
                // back to normal color
                [[UINavigationBar appearance] setTintColor:normalColor];
            }];
            [self presentViewController:activityViewController animated:YES completion:^{
                // change color temporary
                [[UINavigationBar appearance] setTintColor:[UIColor colorWithRed:232.0f/255.0f green:51.0f/255.0f blue:72.0f/255.0f alpha:1.0f]];
            }];

추신 :이 코드는 iOS 7 용으로 작성되었지만 [[UIBarButtonItem appearance] setTintColor:]iOS 6에서도 사용할 수 있습니다 (Kevin van Mierlo의 답변 참조).


UIActivityViewController를 이와 같이 서브 클래 싱하여 문제를 해결했습니다. viewWillAppear viewWilldisapper

extension UIActivityViewController {
        override open func viewDidAppear(_ animated: Bool) {
            super.viewDidAppear(animated)
            UINavigationBar.appearance().barTintColor = .white
        }

        open override func viewDidLoad() {
            super.viewDidLoad()
            navigationController?.navigationBar.isTranslucent = false
            navigationController?.navigationBar.isOpaque = false
            navigationController?.navigationBar.barTintColor = UIColor(red: (247/255), green: (247/255), blue: (247/255), alpha: 1)
            //navigationBar.tintColor = UIColor.white
        }
        open override func viewWillDisappear(_ animated: Bool) {
            super.viewWillDisappear(true)
            UINavigationBar.appearance().barTintColor = mycustomColor
        }
    }

애플 코드의 UI가있는 방식을 바꿀 수없는 이유가 있습니다. 대부분 사과이기 때문입니다. MFMailComposerViewController의 UI가 어떤 식 으로든 보이는 방식을 편집 할 수 없습니다. 방법이 있다면 나는 그것에 대한 단서가 없지만 그것을 할 방법을 본 적이 없습니다. MFMailComposeViewController는 iOS 3.0에서 생성 되었기 때문에 외관 속성을 지원하지 않으며, iOS 5.0까지는 외관이되지 않았습니다.

다음은 MFMailComposeViewController 애플 문서에 대한 링크입니다. MFMailComposeViewController

도움이 되었기를 바랍니다!


iOS 7에서 취소 및 보내기 버튼의 색상을 설정하려면 다음을 사용해야합니다.

// Change the colours of the buttons in iOS 7
[[UINavigationBar appearance] setTintColor:[UIColor redColor]];

iOS 6에서는 실제로 다음과 같이 코드에 그대로 두어야합니다.

// Change the colours of the buttons in iOS 6
[[UIBarButtonItem appearance] setTintColor:[UIColor redColor]];

// Change the color of the the navigation bar in iOS 6 and 7
[[UINavigationBar appearance] setBarTintColor:[UIColor redColor]];

이 코드를 시도하면 도움이 될 수 있습니다.

[[mailComposer navigationBar] setTintColor:[UIColor blackColor]];

Alex의 솔루션을 작동시킬 수는 없었지만 제 상황에서 barTintColor와 titleTextAttributes를 모두 설정해야했지만 작업에 대한 Paillou의 답변의 변형을 얻을 수있었습니다.

UIActivityViewController *activityViewController = [[UIActivityViewController alloc] initWithActivityItems:activityItems applicationActivities:applicationActivities];

activityViewController.excludedActivityTypes = @[UIActivityTypePrint, UIActivityTypeCopyToPasteboard, UIActivityTypeAssignToContact, UIActivityTypeSaveToCameraRoll, UIActivityTypeAddToReadingList, UIActivityTypePostToVimeo, UIActivityTypePostToFlickr, UIActivityTypeAirDrop];

[activityViewController setCompletionHandler:^(NSString *activityType, BOOL completed) {
    // back to normal color
    [[UINavigationBar appearance] setBarTintColor:AAColorInputBorder];
    [[UINavigationBar appearance] setTitleTextAttributes:[NSDictionary dictionaryWithObjectsAndKeys:
                                                         [UIFont fontWithName:@"Avenir-Medium" size:18], NSFontAttributeName,
                                                         [UIColor whiteColor], NSForegroundColorAttributeName,
                                                         nil]];
}];

[self presentViewController:activityViewController animated:YES completion:^{
// change color temporary
[[UINavigationBar appearance] setBarTintColor:[UIColor whiteColor]];
[[UINavigationBar appearance] setTitleTextAttributes:[NSDictionary dictionaryWithObjectsAndKeys:
                                                     [UIFont fontWithName:@"Avenir-Medium" size:18], NSFontAttributeName,
                                                     AAColorInputBorder, NSForegroundColorAttributeName,
                                                     nil]];

감사합니다 Paillou!


이것은 나를 위해 일했습니다 : AppDelegate.m의 함수 :

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions

다음 코드를 입력했습니다.

//mail composer
[[UINavigationBar appearanceWhenContainedIn:[MFMailComposeViewController class], nil] setBarTintColor:myBackgroundColor];
[[UINavigationBar appearanceWhenContainedIn:[MFMailComposeViewController class], nil] setTintColor:myBarItemsColor];

iOS7 + iOS8에서 잘 작동하며 최신 버전에서는 시도하지 않았습니다.


appearance발표하기 전에 설정할 수 있습니다 UIActivityViewController. 의에 모양 재설정을 추가 completionWithItemsHandler하십시오 activity VC.

setNavBarAppearance()

activityVC.completionWithItemsHandler = { [weak self] _, _, _, _ in
    self?.resetNavBarAppearance()
}

present(activityVC, animated: true, completion: nil)

유일한 문제는 활동이 메일 전송과 같은 경우 전체 화면이라는 것입니다. 현재 보이는보기에는 외모가 적용되지 않습니다. 그것을 해결하기위한 약간의 해킹 :

setNavBarAppearance()

activityVC.completionWithItemsHandler = { [weak self] _, _, _, _ in
    self?.resetNavBarAppearance()

    // Hacks(choose one of them):
    // 1)
    self?.navigationController?.isNavigationBarHidden = true
    self?.navigationController?.isNavigationBarHidden = false
    // 2)
    let redrawTriggerVC = UIViewController()
    redrawTriggerVC.modalPresentationStyle = .popover
    self.present(redrawTriggerVC, animated: false, completion: nil)
    redrawTriggerVC.dismiss(animated: false, completion: nil)
}

present(activityVC, animated: true, completion: nil)

ios7의 경우이 코드를 거쳐야한다고 생각합니다.

[[UINavigationBar appearance] setTintColor:[UIColor redColor]];

작동하지 않는 경우 인터넷에서 사용할 수있는 Mail Compose View Controller 애플 문서를 사용해보십시오.


메일 작성기를 제시하기 전에 다음과 같이 삽입하십시오.

[mailComposer.navigationBar setTintColor:[UIColor whiteColor]];
[self presentViewController:mailComposer animated:YES completion:nil];

응용 프로그램에서 상태 표시 줄 스타일을 설정했지만 시작이 완료되었지만 다음과 같이 완료 블록에서 다시 설정해야했습니다.

[self presentViewController:mailComposer animated:YES completion:^{[[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];}];

나는 이것에 대해 엄청난 문제가 있었다. 특히 MFMailComposeViewController/ MFMessageViewController자신이 UIActivityViewController.

나는 https://github.com/rentzsch/jrswizzle의 도움을 받아 viewDidAppear/ viewDidDisappear에서 방법 전환을 사용하여 실행 취소 한 다음 앱의 색상 및 글꼴 사용자 정의를 다시 실행했습니다 .

SwizzledComposeViewControllers.h

#import <MessageUI/MessageUI.h>

@interface MFMailComposeViewController (GMSwizzling)
@end

@interface MFMessageComposeViewController (GMSwizzling)
@end

SwizzledComposeViewControllers.m

#import "SwizzledComposeViewControllers.h"
#import "AppDelegate.h"
#import "JRSwizzle.h"

@implementation MFMailComposeViewController (GMSwizzling)

+ (void)load {
  static dispatch_once_t onceToken;
  dispatch_once(&onceToken, ^{
    [self jr_swizzleMethod:@selector(init) withMethod:@selector(gmswizzled_init) error:nil];
    [self jr_swizzleMethod:@selector(viewWillAppear:) withMethod:@selector(gmswizzled_viewWillAppear:) error:nil];
    [self jr_swizzleMethod:@selector(viewWillDisappear:) withMethod:@selector(gmswizzled_viewWillDisappear:) error:nil];
  });
}

- (instancetype)gmswizzled_init {
  [(AppDelegate*)UIApplication.sharedApplication.delegate uncustomiseAppearance];
  return [self gmswizzled_init];
}

- (void)gmswizzled_viewWillAppear:(BOOL)animated {
  [(AppDelegate*)UIApplication.sharedApplication.delegate uncustomiseAppearance];
  [self gmswizzled_viewWillAppear:animated];
}

- (void)gmswizzled_viewWillDisappear:(BOOL)animated {
  [(AppDelegate*)UIApplication.sharedApplication.delegate customiseAppearance];
  [self gmswizzled_viewWillDisappear:animated];
}

@end


@implementation MFMessageComposeViewController (GMSwizzling)

+ (void)load {
  static dispatch_once_t onceToken;
  dispatch_once(&onceToken, ^{
    [self jr_swizzleMethod:@selector(init) withMethod:@selector(gmswizzled_init) error:nil];
    [self jr_swizzleMethod:@selector(viewWillAppear:) withMethod:@selector(gmswizzled_viewWillAppear:) error:nil];
    [self jr_swizzleMethod:@selector(viewWillDisappear:) withMethod:@selector(gmswizzled_viewWillDisappear:) error:nil];
  });
}

- (instancetype)gmswizzled_init {
  [(AppDelegate*)UIApplication.sharedApplication.delegate uncustomiseAppearance];
  return [self gmswizzled_init];
}

- (void)gmswizzled_viewWillAppear:(BOOL)animated {
  [(AppDelegate*)UIApplication.sharedApplication.delegate uncustomiseAppearance];
  [self gmswizzled_viewWillAppear:animated];
}

- (void)gmswizzled_viewWillDisappear:(BOOL)animated {
  [(AppDelegate*)UIApplication.sharedApplication.delegate customiseAppearance];
  [self gmswizzled_viewWillDisappear:animated];
}

@end

(내가 기억 할 수없는 인정해야하는 이유 uncustomised 모습 모두 initviewWillAppear,하지만 난 꽤 확실 ... 이유가 있었다거야).


Swift에서 UIViewController다음을 확장했습니다 .

extension UIViewController {

    func presentActivityViewController(viewControllerToPresent: UIViewController) {
        self.presentViewController(viewControllerToPresent, animated: true) { _ in
            UIBarButtonItem.appearance().tintColor = UIColor.whiteColor()
            UINavigationBar.appearance().barTintColor = Config.primaryColor
        }
    }
}

When I need to present an UIActivityViewController I call:

    let activityViewController = UIActivityViewController(activityItems: items, applicationActivities: [])
    presentActivityViewController(activityViewController)

In Swift, on iOS9, setting

UINavigationBar.appearance().barTintColor = UIColor.greenColor() // eg
UINavigationBar.appearance().translucent = false

before presenting the activity view controller did the trick for me.


I tried many different methods in iOS 9 and 10, but this is the only one that worked. Note that I have a background image behind the navigationBar as well:

[UIApplication.sharedApplication setStatusBarStyle:UIStatusBarStyleLightContent animated:YES];
NSDictionary *attribs = @{NSForegroundColorAttributeName:UIColor.whiteColor};
UINavigationBar.appearance.titleTextAttributes = attribs;
UINavigationBar.appearance.tintColor = UIColor.whiteColor;
[UINavigationBar.appearance setBackgroundImage:[UIImage imageNamed:@"IOSNavigationBar"] forBarMetrics:UIBarMetricsDefault];
UIBarButtonItem.appearance.tintColor = UIColor.whiteColor;

I haven't found a mechanism I liked, so for what it's worth here's mine. Part of the trouble is later versions of iOS add the capability for apps to add system-wide Share and Action Extensions. These third-party items seem to be coded all sorts of ways. Some inherit the app's nav bar style, some use their own, and some seem to assume a white nav bar (but actually inherits from the app).

This is tested on iOS 12.2.

I create an UIActivityItemSource, to which I have:

- (nullable id)activityViewController:(nonnull UIActivityViewController *)activityViewController itemForActivityType:(nullable UIActivityType)activityType {
    if (activityType == UIActivityTypePrint || [activityType.lowercaseString containsString:@"extension"] || [activityType containsString:@"AssignToContact"]) {
        //What a hack, but the best I can do.  Seems some extensions inherit nav style from parent, others don't.
        //ActionExtension is bottom row; all those I tested need this.  The string comparison catches most non-OS extensions (the type is set by developer).
        [[UINavigationBar appearance] setBarTintColor:[UIColor kNavigationBarBackgroundColor]]; //kNavigationBarBackgroundColor is my app's custom nav bar background color
    } else {
        [[UINavigationBar appearance] setBarTintColor:[UIColor whiteColor]];
    }
    return self.pdfData; //In my case I'm sharing a PDF as NSData - modify as needed for your shared item
}

그럼 내에서 UIActivityViewControllercompletionWithItemsHandlerI은 다음과 같습니다 :

[[UINavigationBar appearance] setBarTintColor:[UIColor kNavigationBarBackgroundColor]]; //Again, this is my app's custom nav bar background color

특정 문제와 관련이 없지만 현재 문제가없는 경우 UIActivityItemSource다음과 같이해야합니다.

NSArray *activities=@[self]; //And set self to be a UIActivityItemSource
UIActivityViewController *controller = [[UIActivityViewController alloc] initWithActivityItems:activities applicationActivities:nil];

이것이 100 % 신뢰할 수있는 것은 아니지만 내가 시도한 모든 확장 기능과 함께 작동한다고 확신합니다.

참고 URL : https://stackoverflow.com/questions/19368122/cannot-set-text-color-of-send-and-cancel-buttons-in-the-mail-composer-when-prese

반응형