PreferredStatusBarStyle ไม่ได้ถูกเรียก


257

ฉันติดตามกระทู้นี้เพื่อลบล้าง-preferredStatusBarStyleแต่ไม่ได้เรียก มีตัวเลือกใดบ้างที่ฉันสามารถเปลี่ยนเพื่อเปิดใช้งานได้ (ฉันใช้ XIB ในโครงการของฉัน)


มันไม่ได้ถูกเรียกในบริบทใด: ตัวจำลอง? บนอุปกรณ์หรือไม่
bneely

@ เกือบทั้งคู่
trgoofi

คุณใช้เครื่องมือจำลอง iOS 7 อุปกรณ์ iOS 7 และ SDK พื้นฐานของคุณคือ 7.0 ใช่ไหม
bneely

@benely iOS SDK 7.0 แสดงใต้ชื่อโปรเจคของฉันนั่นหมายความว่า SDK พื้นฐานของฉันคือ 7.0 หรือไม่
trgoofi

ในการตั้งค่าการสร้าง "Base SDK" เป็นที่ตั้งค่า ดูเหมือนว่าโปรเจคของคุณตั้งไว้ที่ 7.0
'56

คำตอบ:


117

สาเหตุที่เป็นไปได้

ฉันมีปัญหาเดียวกันและคิดว่ามันเกิดขึ้นเพราะฉันไม่ได้ตั้งค่าตัวควบคุมรูทวิวในหน้าต่างแอปพลิเคชันของฉัน

สิ่งUIViewControllerที่ฉันนำpreferredStatusBarStyleมาใช้นั้นถูกใช้ใน a UITabBarControllerซึ่งควบคุมลักษณะที่ปรากฏของมุมมองบนหน้าจอ

เมื่อฉันตั้งค่าตัวควบคุมรูทมุมมองให้ชี้ไปที่สิ่งนี้UITabBarControllerแถบสถานะเปลี่ยนเริ่มทำงานได้อย่างถูกต้องตามที่คาดไว้ (และเรียกpreferredStatusBarStyleวิธีการ)

(BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions
{
    ... // other view controller loading/setup code

    self.window.rootViewController = rootTabBarController;
    [self.window makeKeyAndVisible];
    return YES;
}

วิธีอื่น (คัดค้านใน iOS 9)

หรือคุณสามารถเรียกวิธีการใดวิธีการหนึ่งต่อไปนี้ตามความเหมาะสมในแต่ละตัวควบคุมมุมมองของคุณขึ้นอยู่กับสีพื้นหลังของมันแทนที่จะต้องใช้setNeedsStatusBarAppearanceUpdate:

[[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];

หรือ

[[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleDefault];

โปรดทราบว่าคุณยังจะต้องตั้งUIViewControllerBasedStatusBarAppearanceไปNOในไฟล์ plist ถ้าคุณใช้วิธีนี้


2
ฉันมีปัญหาเช่นเดียวกับคุณไม่ได้ตั้งค่าตัวควบคุมมุมมองราก คุณค้นพบสิ่งนั้นได้อย่างไร
trgoofi

1
ฉันสงสัยว่ามีบางอย่างในกรอบที่ไม่ได้รับการแจ้งเตือนsetNeedsStatusBarAppearanceUpdate- ความสงสัยของฉันได้รับการยืนยันเมื่อฉันทำการเปลี่ยนแปลงนี้
AbdullahC

2
ปัญหาที่เกี่ยวข้องที่ฉันพบในแอพเป็นตัวควบคุมมุมมองที่มีตัวควบคุมมุมมองลูกแบบเต็มหน้าจอที่ไม่ได้แทนที่ childViewControllerForStatusBarStyle และ childViewControllerForStatusBarHidden เพื่อส่งคืนตัวควบคุมมุมมองลูกนั้น หากคุณมีลำดับชั้นตัวควบคุมมุมมองของคุณเองคุณจำเป็นต้องจัดเตรียมวิธีการเหล่านี้เพื่อแจ้งให้ระบบทราบว่าควรใช้ตัวควบคุมมุมมองใดเพื่อกำหนดลักษณะของแถบสถานะ
Jon Steinmetz

การตั้งค่า rootviewcontroller ไม่เปลี่ยนแปลงอะไรเลย คุณควรทำงานกับความคิดเห็นของจอน และระวังเมื่อเรียก setneedsstatusbarappearanceUpdate คุณควรเรียกมันจากผู้ปกครองเพื่อให้ทำงานได้
doozMen

1
@ Hippo คุณเป็นอัจฉริยะ !! คุณพบได้อย่างไรว่าเป็นเพราะไม่ได้ตั้งค่า rootviewcontroller
ViruMax

1019

สำหรับทุกคนที่ใช้ UINavigationController:

UINavigationControllerไม่ไปข้างหน้าบนpreferredStatusBarStyleสายไปยังตัวควบคุมมุมมองของเด็ก แต่จะจัดการสถานะของตัวเอง - ตามที่ควรมันจะวาดที่ด้านบนของหน้าจอที่แถบสถานะอยู่และควรรับผิดชอบ ดังนั้นการใช้งานpreferredStatusBarStyleใน VC ของคุณภายในตัวควบคุมการนำทางจะไม่ทำอะไรเลย - จะไม่มีการเรียกใช้

เคล็ดลับคือสิ่งที่UINavigationControllerใช้ในการตัดสินใจว่าจะกลับมาหรือUIStatusBarStyleDefault มันฐานนี้ในตัวของมันUIStatusBarStyleLightContent UINavigationBar.barStyleค่าเริ่มต้น ( UIBarStyleDefault) ส่งผลให้UIStatusBarStyleDefaultแถบสถานะส่วนหน้ามืด และUIBarStyleBlackจะให้UIStatusBarStyleLightContentแถบสถานะ

TL; DR:

หากคุณต้องการUIStatusBarStyleLightContentในUINavigationControllerการใช้งาน:

self.navigationController.navigationBar.barStyle = UIBarStyleBlack;

59
ดี! โปรดทราบว่าpreferredStatusBarStyleในความเป็นจริงจะถูกเรียกบนตัวควบคุมมุมมองลูกถ้าคุณซ่อนแถบนำทาง (ตั้งค่าnavigationBarHiddenเป็นYES) ตามความเหมาะสม
Patrick Pijnappel

25
ขอบคุณสำหรับคำตอบนี้ หากคุณต้องการตั้งค่า barStyle สำหรับแถบการนำทางทั้งหมดของคุณโทร[[UINavigationBar appearance] setBarStyle:UIBarStyleBlack]
Thomas Desert

15
คำตอบที่สมบูรณ์แบบ ไม่มีคำตอบอื่น ๆ ใน SO จึงนำ UINavigationController มาพิจารณา 2 ชั่วโมงของการต่อสู้กับหัวของฉันกับแป้นพิมพ์
Ryan Alford

10
รุ่งโรจน์เพื่อ @ แพทริกสำหรับแสดงให้เห็นว่าnavigationBarHiddenพร้อมจะYESจริงจะได้preferredStatusBarStyleเรียกและเตือนให้กับผู้ที่อาจจะสะดุดกับเรื่องนี้: มันทำงานร่วมกับnavigationBarHiddenแต่ไม่ได้มีnavigationBar.hidden!
jcaron

4
ควรชัดเจน แต่คุณต้องตั้งค่า "ดูแถบสถานะตามตัวควบคุม" เป็น YES ใน Info.plist เพื่อให้สิ่งนี้ทำงานได้
Code Baller

99

ดังนั้นฉันจริงเพิ่มหมวดหมู่เพื่อ UINavigationController แต่ใช้วิธีการ:

-(UIViewController *)childViewControllerForStatusBarStyle;
-(UIViewController *)childViewControllerForStatusBarHidden;

และส่งคืน UIViewController ที่มองเห็นในปัจจุบัน ที่ช่วยให้ตัวควบคุมมุมมองที่มองเห็นในปัจจุบันตั้งค่าสไตล์ / ทัศนวิสัยที่ต้องการได้

นี่เป็นข้อมูลโค้ดที่สมบูรณ์สำหรับมัน:

ในสวิฟต์:

extension UINavigationController {

    public override func childViewControllerForStatusBarHidden() -> UIViewController? {
        return self.topViewController
    }

    public override func childViewControllerForStatusBarStyle() -> UIViewController? {
        return self.topViewController
    }
}

ในวัตถุประสงค์ -C:

@interface UINavigationController (StatusBarStyle)

@end

@implementation UINavigationController (StatusBarStyle)

-(UIViewController *)childViewControllerForStatusBarStyle {
    return self.topViewController;
}

-(UIViewController *)childViewControllerForStatusBarHidden {
    return self.topViewController;
}

@end

และสำหรับการวัดที่ดีนี่คือวิธีการใช้งานใน UIViewController:

ในสวิฟท์

override public func preferredStatusBarStyle() -> UIStatusBarStyle {
    return .LightContent
}

override func prefersStatusBarHidden() -> Bool {
    return false
}

ในวัตถุประสงค์ -C

-(UIStatusBarStyle)preferredStatusBarStyle {
    return UIStatusBarStyleLightContent; // your own style
}

- (BOOL)prefersStatusBarHidden {
    return NO; // your own visibility code
}

สุดท้ายให้แน่ใจว่า plist ของแอปไม่ไม่ได้ "ดูตัวควบคุมตามแถบสถานะลักษณะ" ชุดที่จะไม่มี อาจลบบรรทัดนั้นหรือตั้งค่าเป็นใช่ (ซึ่งฉันเชื่อว่าเป็นค่าเริ่มต้นสำหรับ iOS 7 ตอนนี้)


ดูเหมือนreturn self.topViewController;งานสำหรับฉัน แต่return self.visibleViewController;- ไม่ใช่
k06a

visibleViewController สามารถส่งคืนตัวควบคุม modal ที่นำเสนอในปัจจุบันเมื่อคุณปิดมัน ซึ่งคนเกียจคร้าน ใช้ topViewController
เบ็นซินแคล

1
@ d.lebedev ตกลง แต่ฉันไม่คิดว่าปัญหาเหล่านี้จะมีผลกับที่นี่ คุณไม่จำเป็นต้องโทรsuperในวิธีนี้และคุณต้องการเปลี่ยนพฤติกรรมของคอนโทรลเลอร์ทั้งหมดประเภทนี้
ed '

1
สิ่งนี้ไม่ทำงานสำหรับฉันบน iOS 9.3 ฉันเดาว่านี่เป็นปัญหา: ปัญหานี้มีความสำคัญเป็นพิเศษเนื่องจากมีการใช้คลาส Cocoa หลายประเภทโดยใช้หมวดหมู่ วิธีการกำหนดเฟรมเวิร์กที่คุณพยายามแทนที่อาจถูกนำไปใช้ในหมวดหมู่และดังนั้นการใช้งานที่มีความสำคัญกว่านั้นไม่ได้ถูกกำหนดไว้
vikingosegundo

2
นี่เป็นสิ่งที่ผิดและจะหยุดใน iOS 13.4 เนื่องจากการขยายคลาส C วัตถุประสงค์ใน Swift ถูกนำไปใช้ผ่านหมวดหมู่ Objective C ไม่แนะนำให้ใช้วิธีการเอาชนะผ่านหมวดหมู่ Objective C และทำลายได้ ดูstackoverflow.com/a/38274660/2438634
Marc Etcheverry

79

สำหรับทุกคนที่ยังคงดิ้นรนอยู่กับสิ่งนี้ส่วนขยายที่ง่ายและรวดเร็วนี้ควรแก้ไขปัญหาให้คุณ

extension UINavigationController {
    override open var childForStatusBarStyle: UIViewController? {
        return self.topViewController
    }
}

10
คุณสมควรได้รับเหรียญ
nikans

2
ขอบคุณมาก ๆ ฉันกลับมามองเห็นViewControllerแทนโดยไม่ประสบความสำเร็จ
Fábio Salata

1
นี่คือทองคำ ฉันมีตัวควบคุมการนำทางที่ฝังอยู่ในแถบแท็บและฉันเพิ่งโยนมันลงในไฟล์และตอนนี้ฉันสามารถเปลี่ยนรูปลักษณ์ของแถบสถานะได้ทุกที่ที่ฉันต้องการ
Vahid Amiri

2
นี่เป็นสิ่งที่ผิดและจะหยุดใน iOS 13.4 เนื่องจากการขยายคลาส C วัตถุประสงค์ใน Swift ถูกนำไปใช้ผ่านหมวดหมู่ Objective C ไม่แนะนำให้ใช้วิธีการเอาชนะผ่านหมวดหมู่ Objective C และทำลายได้ ดูstackoverflow.com/a/38274660/2438634
Marc Etcheverry

1
@MarcEtcheverry อินสแตนซ์เฉพาะนี้ไม่ผิด ข้อเท็จจริงของเรื่องนี้ก็คือว่า subclasses ของวัตถุ / โปรโตคอลอื่น ๆ เช่น UINavigationController นั้นไม่เคยมีการใช้สิ่งเหล่านี้มาก่อนในการขัดแย้งในการจัดส่งแบบไดนามิก ไม่มีค่าเริ่มต้นหรือการใช้งานภายในคลาสย่อยจริงซึ่งเป็นเหตุผลว่าทำไมนี่เป็นวิธีที่ดีที่สุดในการติดตั้งแอพนี้โดยไม่ต้องสร้างการพึ่งพาที่ไม่จำเป็น (จุด) น่าเสียดายที่ 13.4 ดูเหมือนจะเปลี่ยนพฤติกรรมนี้ ฉันคาดเดาเบื้องหลังที่พวกเขามีการตรวจสอบหรือการนำไปใช้งานซึ่งไม่ได้มีมานานหลายปี .........
TheCodingArt

20

app ของฉันใช้ทั้งสาม: UINavigationController, UISplitViewController, UITabBarControllerจึงทั้งหมดเหล่านี้ดูเหมือนจะใช้ควบคุมแถบสถานะและจะทำให้preferedStatusBarStyleไม่ได้รับการเรียกร้องให้เด็กของพวกเขา ในการลบล้างพฤติกรรมนี้คุณสามารถสร้างส่วนขยายได้เหมือนกับคำตอบที่เหลือ นี่คือส่วนขยายสำหรับทั้งสามใน Swift 4 หวังว่า Apple จะมีความชัดเจนมากขึ้นเกี่ยวกับเนื้อหาประเภทนี้

extension UINavigationController {
    open override var childViewControllerForStatusBarStyle: UIViewController? {
        return self.topViewController
    }

    open override var childViewControllerForStatusBarHidden: UIViewController? {
        return self.topViewController
    }
}

extension UITabBarController {
    open override var childViewControllerForStatusBarStyle: UIViewController? {
        return self.childViewControllers.first
    }

    open override var childViewControllerForStatusBarHidden: UIViewController? {
        return self.childViewControllers.first
    }
}

extension UISplitViewController {
    open override var childViewControllerForStatusBarStyle: UIViewController? {
        return self.childViewControllers.first
    }

    open override var childViewControllerForStatusBarHidden: UIViewController? {
        return self.childViewControllers.first
    }
}

แก้ไข: อัปเดตสำหรับการเปลี่ยนแปลง Swift 4.2 API

extension UINavigationController {
    open override var childForStatusBarStyle: UIViewController? {
        return self.topViewController
    }

    open override var childForStatusBarHidden: UIViewController? {
        return self.topViewController
    }
}

extension UITabBarController {
    open override var childForStatusBarStyle: UIViewController? {
        return self.children.first
    }

    open override var childForStatusBarHidden: UIViewController? {
        return self.children.first
    }
}

extension UISplitViewController {
    open override var childForStatusBarStyle: UIViewController? {
        return self.children.first
    }

    open override var childForStatusBarHidden: UIViewController? {
        return self.children.first
    }
}

1
นี่เป็นทางออกเดียวที่ใช้งานได้ คำตอบทั้งหมดเกี่ยวกับ SO ชี้ไปที่โซลูชันมาตรฐานซึ่งไม่สามารถใช้ได้กับแอพใด ๆ ที่มี NavigationControllers ขอบคุณ!!!
Houman

การใช้ส่วนขยายสำหรับการเอาชนะนั้นผิด ไม่ปลอดภัย มีวิธีแก้ไขปัญหาที่ง่ายกว่ามากมาย ใช้คลาสย่อยแทน
Sulthan

2
นี่เป็นสิ่งที่ผิดและจะหยุดใน iOS 13.4 เนื่องจากการขยายคลาส C วัตถุประสงค์ใน Swift ถูกนำไปใช้ผ่านหมวดหมู่ Objective C ไม่แนะนำให้ใช้วิธีการเอาชนะผ่านหมวดหมู่ Objective C และทำลายได้ ดูstackoverflow.com/a/38274660/2438634
Marc Etcheverry

1
@MarcEtcheverry อินสแตนซ์เฉพาะนี้ไม่ผิด ข้อเท็จจริงของเรื่องนี้ก็คือว่า subclasses ของวัตถุ / โปรโตคอลอื่น ๆ เช่น UINavigationController นั้นไม่เคยมีการใช้สิ่งเหล่านี้มาก่อนในการขัดแย้งในการจัดส่งแบบไดนามิก ไม่มีค่าเริ่มต้นหรือการใช้งานภายในคลาสย่อยจริงซึ่งเป็นเหตุผลว่าทำไมนี่เป็นวิธีที่ดีที่สุดในการติดตั้งแอพนี้โดยไม่ต้องสร้างการพึ่งพาที่ไม่จำเป็น (จุด) น่าเสียดายที่ 13.4 ดูเหมือนจะเปลี่ยนพฤติกรรมนี้ ฉันคาดเดาเบื้องหลังที่พวกเขามีการตรวจสอบหรือการนำไปใช้งานซึ่งไม่ได้มีมานานหลายปี .........
TheCodingArt

15

ไทสันUINavigationControllerคำตอบคือถูกต้องสำหรับการเปลี่ยนสีแถบสถานะในสีขาว

หากใครต้องการที่จะบรรลุผลเดียวกันโดยการเขียนรหัสAppDelegateจากนั้นใช้รหัสด้านล่างและเขียนมันภายในAppDelegate's didFinishLaunchingWithOptionsวิธี

และไม่ลืมที่จะตั้งค่าUIViewControllerBasedStatusBarAppearanceไปYESในแฟ้ม .plist อื่นเปลี่ยนแปลงจะไม่ได้สะท้อนให้เห็นถึง

รหัส

- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
     // status bar appearance code
     [[UINavigationBar appearance] setBarStyle:UIBarStyleBlack];

     return YES;
}

14

เมื่อวันที่ UINavigationController ที่preferredStatusBarStyleไม่ได้เรียกว่าเพราะเป็นที่ต้องการtopViewController selfดังนั้นเพื่อให้ได้รับการpreferredStatusBarStyleเรียกว่าใน UINavigationController childViewControllerForStatusBarStyleคุณจำเป็นต้องเปลี่ยนมัน

คำแนะนำ

แทนที่ UINavigationController ของคุณในคลาสของคุณ:

class MyRootNavigationController: UINavigationController {
    override var preferredStatusBarStyle: UIStatusBarStyle {
        return .lightContent
    }
    override var childViewControllerForStatusBarStyle: UIViewController? {
        return nil
    }
}

ทางเลือกที่ไม่แนะนำ

หากต้องการทำเพื่อ UINavigationController ทั้งหมดคุณสามารถแทนที่ในส่วนขยาย (คำเตือน: มีผลกับ UIDocumentPickerViewController, UIImagePickerController ฯลฯ ) แต่คุณไม่ควรทำตามเอกสารของ Swift :

extension UINavigationController {
    open override var preferredStatusBarStyle: UIStatusBarStyle {
        return .lightContent
    }
    open override var childViewControllerForStatusBarStyle: UIViewController? {
        return nil
    }
}

11

นอกเหนือจากคำตอบของ Serenn หากคุณแสดงตัวควบคุมมุมมองด้วยmodalPresentationStyle(ตัวอย่าง.overCurrentContext) คุณควรเรียกสิ่งนี้ในตัวควบคุมมุมมองที่นำเสนอใหม่:

presentedViewController.modalPresentationCapturesStatusBarAppearance = true

อย่าลืมที่จะแทนที่preferredStatusBarStyleในตัวควบคุมมุมมองที่นำเสนอ


9

นอกเหนือจากคำตอบของฮิปโป: ถ้าคุณใช้ UINavigationController มันอาจจะเป็นการดีกว่าถ้าคุณเพิ่มหมวดหมู่:

//  UINavigationController+StatusBarStyle.h:

@interface UINavigationController (StatusBarStyle)

@end



//  UINavigationController+StatusBarStyle.m:

@implementation UINavigationController (StatusBarStyle)

- (UIStatusBarStyle)preferredStatusBarStyle
{
    //also you may add any fancy condition-based code here
    return UIStatusBarStyleLightContent;
}

@end

ทางออกนั้นน่าจะดีกว่าการเปลี่ยนไปใช้พฤติกรรมที่เลิกใช้เร็ว ๆ นี้


อย่าทำอย่างนี้มันใช้ได้ผลในตอนนี้ แต่อาจทำลายพฤติกรรมในอนาคต เพียงเปลี่ยนสไตล์ navBar - ดูคำตอบของฉันstackoverflow.com/a/19513714/505457
Tyson

2
คุณควรใช้คลาสย่อยไม่ใช่หมวดหมู่
shuiyouren

2Tyson: ทำไมมันจะทำลายพฤติกรรมในอนาคต PreferredStatusBarStyle: เป็นวิธีการที่ Apple เลือกใช้ในการตั้งค่าสไตล์แถบสถานะ
Artem Abramov

2shuiyouren: ทำไมฉันต้องเพิ่มความซับซ้อนด้วยการทำคลาสย่อยถ้าฉันสามารถใช้หมวดหมู่และรวมไว้ในทุกที่ที่ฉันต้องการ อย่างไรก็ตามนั่นเป็นคำถามของสถาปัตยกรรมไม่ใช่การใช้งาน
Artem Abramov

2
@ArtemAbramov เนื่องจาก UINavigationController ดำเนินการแล้วpreferredStatusBarStyleและใช้ตรรกะเฉพาะของ UINavigationController ตอนนี้ตรรกะนี้ขึ้นอยู่กับnavigationBar.barStyleแต่ฉันสามารถดูการตรวจสอบเพิ่มเติมที่เพิ่มเข้ามา (เช่นการUISearchDisplayControllerย้ายเพื่อซ่อนโหมด navbar) ด้วยการแทนที่ตรรกะเริ่มต้นคุณจะไม่สามารถใช้งานฟังก์ชั่นทั้งหมดนี้และปล่อยให้ตัวเองเปิดสำหรับช่วงเวลาที่น่ารำคาญในอนาคต ดูคำตอบของฉันด้านบนสำหรับวิธีที่ถูกต้องในการทำเช่นนี้ในขณะที่ยังสนับสนุนพฤติกรรมของตัวควบคุม nav ในตัว
Tyson

9

Swift 4.2 ขึ้นไป

ดังที่กล่าวไว้ในคำตอบที่เลือกสาเหตุที่แท้จริงคือการตรวจสอบวัตถุตัวควบคุมมุมมองหน้าต่างของคุณ

กรณีที่เป็นไปได้ของโครงสร้างการไหลของคุณ

  • วัตถุ UIViewController แบบกำหนดเองเป็นตัวควบคุมมุมมองราก

    ของหน้าต่างตัวควบคุมมุมมองรากหน้าต่างของคุณคือวัตถุ UIViewController และเพิ่มหรือเอาตัวควบคุมการนำทางหรือ tabController เพิ่มเติมตามโฟลว์แอปพลิเคชันของคุณ

    โฟลว์ประเภทนี้มักจะใช้หากแอปของคุณมีโฟลว์การล็อกอินก่อนหน้าบนสแต็กการนำทางโดยไม่มีแท็บและโพสต์โฟลว์การเข้าสู่ระบบด้วยแท็บและอาจเป็นไปได้ว่า

  • วัตถุ TabBarController เป็นตัวควบคุมมุมมองรูทของหน้าต่าง

    นี่คือโฟลว์ที่ตัวควบคุมมุมมองรูทของหน้าต่างคือ tabBarController ซึ่งอาจเป็นไปได้ว่าทุกแท็บมีตัวควบคุมการนำทางเพิ่มเติม

  • วัตถุ NavigationController เป็นตัวควบคุมมุมมองรูทของหน้าต่าง

    นี่คือโฟลว์ที่คอนโทรลเลอร์มุมมองรูทของหน้าต่างคือ NavigationController

    ฉันไม่แน่ใจว่ามีความเป็นไปได้ที่จะเพิ่มตัวควบคุมแถบแท็บหรือตัวควบคุมทิศทางใหม่ในตัวควบคุมทิศทางที่มีอยู่ แต่ถ้ามีกรณีเช่นนี้เราต้องผ่านการควบคุมรูปแบบแถบสถานะไปยังภาชนะถัดไป ดังนั้นฉันจึงเพิ่มการตรวจสอบเดียวกันในส่วนขยาย UINavigationController เพื่อค้นหาchildForStatusBarStyle

ใช้ส่วนขยายต่อไปนี้มันจัดการสถานการณ์ข้างต้นทั้งหมด -

extension UITabBarController {
    open override var childForStatusBarStyle: UIViewController? {
        return selectedViewController?.childForStatusBarStyle ?? selectedViewController
    }
}

extension UINavigationController {
    open override var childForStatusBarStyle: UIViewController? {
        return topViewController?.childForStatusBarStyle ?? topViewController
    }
}

extension AppRootViewController {
    open override var preferredStatusBarStyle: UIStatusBarStyle {
        return children.first { $0.childForStatusBarStyle != nil }?.childForStatusBarStyle?.preferredStatusBarStyle ?? .default
    }
}
  • คุณไม่จำเป็นต้องใส่UIViewControllerBasedStatusBarAppearanceรหัสinfo.plistตามจริงโดยค่าเริ่มต้น

คะแนนที่ต้องพิจารณาสำหรับการไหลที่ซับซ้อนมากขึ้น

  • ในกรณีที่คุณแสดงโฟลว์ใหม่แบบค่อยเป็นค่อยไปมันจะแยกออกจากโฟลว์ลักษณะแถบสถานะที่มีอยู่ ดังนั้นสมมติว่าคุณกำลังนำเสนอNewFlowUIViewControllerและจากนั้นเพิ่มการนำทางใหม่หรือตัวควบคุม tabBarNewFlowUIViewControllerจากนั้นเพิ่มส่วนขยายNewFlowUIViewControllerเช่นกันเพื่อจัดการลักษณะแถบสถานะของตัวควบคุมเพิ่มเติม

  • ในกรณีที่คุณตั้งmodalPresentationStyleนอกเหนือจากfullScreenการนำเสนอ modally คุณต้องตั้งค่าmodalPresentationCapturesStatusBarAppearanceเป็นจริงเพื่อให้ตัวควบคุมมุมมองที่นำเสนอต้องได้รับการควบคุมลักษณะที่ปรากฏของแถบสถานะ


คำตอบที่ยอดเยี่ยม!
อามินเบนาริบ

3
นี่เป็นสิ่งที่ผิดและจะหยุดใน iOS 13.4 เนื่องจากการขยายคลาส C วัตถุประสงค์ใน Swift ถูกนำไปใช้ผ่านหมวดหมู่ Objective C ไม่แนะนำให้ใช้วิธีการเอาชนะผ่านหมวดหมู่ Objective C และทำลายได้ ดูstackoverflow.com/a/38274660/2438634
Marc Etcheverry

@MarcEtcheverry อินสแตนซ์เฉพาะนี้ไม่ผิด ข้อเท็จจริงของเรื่องนี้ก็คือว่า subclasses ของวัตถุ / โปรโตคอลอื่น ๆ เช่น UINavigationController นั้นไม่เคยมีการใช้สิ่งเหล่านี้มาก่อนในการขัดแย้งในการจัดส่งแบบไดนามิก ไม่มีค่าเริ่มต้นหรือการใช้งานภายในคลาสย่อยจริงซึ่งเป็นเหตุผลว่าทำไมนี่เป็นวิธีที่ดีที่สุดในการติดตั้งแอพนี้โดยไม่ต้องสร้างการพึ่งพาที่ไม่จำเป็น (จุด) น่าเสียดายที่ 13.4 ดูเหมือนจะเปลี่ยนพฤติกรรมนี้ ฉันคาดเดาเบื้องหลังที่พวกเขามีการตรวจสอบหรือการนำไปใช้งานซึ่งไม่ได้มีมานานหลายปี .........
TheCodingArt

8

โซลูชัน iOS 13

UINavigationController เป็นคลาสย่อยของ UIViewController (ใครจะรู้🙃)!

ดังนั้นเมื่อแสดงตัวควบคุมมุมมองที่ฝังอยู่ในตัวควบคุมทิศทางคุณไม่ได้นำเสนอตัวควบคุมมุมมองที่ฝังอยู่จริงๆ คุณกำลังนำเสนอตัวควบคุมการนำทาง! UINavigationControllerเป็นคลาสย่อยของUIViewControllerสืบทอดpreferredStatusBarStyleและchildForStatusBarStyleคุณสามารถตั้งค่าได้ตามต้องการ

วิธีใดวิธีหนึ่งต่อไปนี้ควรใช้งานได้:

  1. ยกเลิกการใช้โหมดมืดทั้งหมด
    • ในของคุณinfo.plistเพิ่มคุณสมบัติต่อไปนี้:
      • คีย์ - UIUserInterfaceStyle(aka. "รูปแบบส่วนต่อประสานผู้ใช้")
      • ค่า - แสง
  2. แทนที่preferredStatusBarStyleภายในUINavigationController

    • preferredStatusBarStyle( doc ) - สไตล์แถบสถานะที่ต้องการสำหรับคอนโทรลเลอร์มุมมอง
    • ซับคลาสหรือขยาย UINavigationController

      class MyNavigationController: UINavigationController {
          override var preferredStatusBarStyle: UIStatusBarStyle {
              .lightContent
          }
      }

      หรือ

      extension UINavigationController {
          open override var preferredStatusBarStyle: UIStatusBarStyle {
              .lightContent
          }
      }
  3. แทนที่childForStatusBarStyleภายในUINavigationController

    • childForStatusBarStyle( doc ) - เรียกใช้เมื่อระบบต้องการตัวควบคุมมุมมองเพื่อใช้ในการกำหนดรูปแบบแถบสถานะ
    • ตามเอกสารของ Apple

      "ถ้าตัวควบคุมมุมมองคอนเทนเนอร์ของคุณได้รับลักษณะแถบสถานะจากหนึ่งในตัวควบคุมมุมมองลูกของมัน, [แทนที่คุณสมบัตินี้] และส่งกลับตัวควบคุมมุมมองลูกนั้นถ้าคุณกลับศูนย์หรือไม่แทนที่วิธีนี้สไตล์แถบสถานะสำหรับตนเอง หากค่าส่งคืนจากเมธอดนี้เปลี่ยนแปลงให้เรียกเมธอด setNeedsStatusBarAppearanceUpdate ()

    • กล่าวอีกนัยหนึ่งถ้าคุณไม่ใช้โซลูชัน 3 ที่นี่ระบบจะย้อนกลับไปใช้โซลูชัน 2 ด้านบน
    • ซับคลาสหรือขยาย UINavigationController

      class MyNavigationController: UINavigationController {
          override var childForStatusBarStyle: UIViewController? {
              topViewController
          }
      }

      หรือ

      extension UINavigationController {    
          open override var childForStatusBarStyle: UIViewController? {
              topViewController
          }
      }
    • คุณสามารถส่งคืนตัวควบคุมมุมมองใด ๆ ที่คุณต้องการด้านบน ฉันขอแนะนำอย่างใดอย่างหนึ่งต่อไปนี้:

      • topViewController(จากUINavigationController) ( doc ) - ตัวควบคุมมุมมองที่ด้านบนสุดของการนำทางสแต็ก
      • visibleViewController(จากUINavigationController) ( doc ) - ตัวควบคุมมุมมองที่เกี่ยวข้องกับมุมมองที่มองเห็นได้ในปัจจุบันในส่วนต่อประสานการนำทาง (คำแนะนำ: สิ่งนี้อาจรวมถึง "ตัวควบคุมมุมมองที่นำเสนอแบบ Modally ด้านบนของตัวควบคุมทิศทาง")

หมายเหตุ: หากคุณตัดสินใจที่จะคลาสย่อย UINavigationControllerอย่าลืมใช้คลาสนั้นกับตัวควบคุม nav ของคุณผ่านตัวตรวจสอบตัวตนใน IB

PS รหัสของฉันใช้ไวยากรณ์ของ Swift 5.1


แถบสถานะของฉันเป็นสีดำหลังจากหมุนหน้าจอ มีความคิดอะไรไหม สิ่งนี้จะเกิดขึ้นกับเครื่องจำลอง iPad Pro เท่านั้น
Pedro Paulo Amorim

@PedroPauloAmorim คุณสามารถให้ข้อมูลเพิ่มเติมได้หรือไม่ ตัวควบคุมมุมมองด้านบนนำเสนออย่างไร (โมดอลเต็มหน้าจอแสดง) มันซ้อนอยู่ในตัวควบคุมทิศทางหรือไม่? ข้อความเปลี่ยนเป็นสีดำหรือเป็นพื้นหลังด้วยหรือไม่ คุณพยายามทำอะไรให้สำเร็จ
Andrew Kirna

ฉันตั้งแถบสถานะแสงในแอพทั้งหมดของฉัน มันจะได้รับแสงในสองการหมุนในที่สามมันเปลี่ยนเป็นความมืดและไม่เคยกลับสู่แสงแม้กระทั่งบังคับให้วาดใหม่ มันเกิดขึ้นในเครื่องจำลอง iPad Pro มุมมองจะถูกนำเสนอในแบบเต็มหน้าจอและไม่ซ้อนอยู่ภายในตัวควบคุมการนำทาง เฉพาะข้อความที่เปลี่ยนเป็นสีเข้ม
Pedro Paulo Amorim

คุณจะตั้งแถบสถานะแสงได้อย่างไรในตอนแรก?
Andrew Kirna

3
การแทนที่ด้วยส่วนขยายของคุณไม่ใช่การแทนที่จริง มันเป็นการใช้ภาษาที่ผิดอย่างไม่ปลอดภัย ที่สามารถทำลายได้ง่ายมาก
Sulthan

7

คำตอบของ @ serenn ข้างต้นยังคงเป็นคำตอบที่ยอดเยี่ยมสำหรับกรณีของ UINavigationControllers อย่างไรก็ตามสำหรับรวดเร็ว 3 ฟังก์ชั่น childViewController varsจะถูกเปลี่ยนให้ ดังนั้นUINavigationControllerรหัสส่วนขยายควรเป็น:

override open var childViewControllerForStatusBarStyle: UIViewController? {
  return topViewController
}

override open var childViewControllerForStatusBarHidden: UIViewController? {
  return topViewController
}

และจากนั้นในตัวควบคุมมุมมองที่ควรกำหนดรูปแบบแถบสถานะ:

override var preferredStatusBarStyle: UIStatusBarStyle {
   return .lightContent
}

2
นี่เป็นสิ่งที่ผิดและจะหยุดใน iOS 13.4 เนื่องจากการขยายคลาส C วัตถุประสงค์ใน Swift ถูกนำไปใช้ผ่านหมวดหมู่ Objective C ไม่แนะนำให้ใช้วิธีการเอาชนะผ่านหมวดหมู่ Objective C และทำลายได้ ดูstackoverflow.com/a/38274660/2438634
Marc Etcheverry

@MarcEtcheverry อินสแตนซ์เฉพาะนี้ไม่ผิด ข้อเท็จจริงของเรื่องนี้ก็คือว่า subclasses ของวัตถุ / โปรโตคอลอื่น ๆ เช่น UINavigationController นั้นไม่เคยมีการใช้สิ่งเหล่านี้มาก่อนในการขัดแย้งในการจัดส่งแบบไดนามิก ไม่มีค่าเริ่มต้นหรือการใช้งานภายในคลาสย่อยจริงซึ่งเป็นเหตุผลว่าทำไมนี่เป็นวิธีที่ดีที่สุดในการติดตั้งแอพนี้โดยไม่ต้องสร้างการพึ่งพาที่ไม่จำเป็น (จุด) น่าเสียดายที่ 13.4 ดูเหมือนจะเปลี่ยนพฤติกรรมนี้ ฉันคาดเดาเบื้องหลังที่พวกเขามีการตรวจสอบหรือการนำไปใช้งานซึ่งไม่ได้มีมานานหลายปี .........
TheCodingArt

6

หาก viewController ของคุณอยู่ภายใต้ UINavigationController

คลาสย่อย UINavigationController และเพิ่ม

override var preferredStatusBarStyle: UIStatusBarStyle {
    return topViewController?.preferredStatusBarStyle ?? .default
}

preferredStatusBarStyleจะเรียกViewController



4

UIStatusBarStyle ใน iOS 7

แถบสถานะใน iOS 7 นั้นโปร่งใสมองเห็นด้านหลัง

รูปแบบของแถบสถานะอ้างถึงลักษณะที่ปรากฏของเนื้อหา ใน iOS 7 เนื้อหาแถบสถานะจะมืด ( UIStatusBarStyleDefault) หรือเบา ( UIStatusBarStyleLightContent) ทั้งสองUIStatusBarStyleBlackTranslucentและUIStatusBarStyleBlackOpaqueเลิกใช้แล้วใน iOS 7.0 ใช้UIStatusBarStyleLightContentแทน

วิธีการเปลี่ยน UIStatusBarStyle

หากด้านล่างแถบสถานะเป็นแถบนำทางสไตล์ของแถบสถานะจะถูกปรับให้ตรงกับสไตล์ของแถบนำทาง ( UINavigationBar.barStyle):

โดยเฉพาะถ้าสไตล์แถบนำทางเป็น UIBarStyleDefault สไตล์แถบสถานะจะUIStatusBarStyleDefault; หากรูปแบบแถบนำทางคือUIBarStyleBlackรูปแบบแถบสถานะจะเป็นUIStatusBarStyleLightContentสไตล์แถบสถานะจะเป็น

หากไม่มีแถบนำทางใต้แถบสถานะคุณสามารถควบคุมและเปลี่ยนลักษณะของแถบสถานะได้โดยตัวควบคุมมุมมองแต่ละรายการในขณะที่แอปทำงาน

- [UIViewController preferredStatusBarStyle]เป็นวิธีการใหม่ที่เพิ่มเข้ามาใน iOS 7 มันสามารถถูกแทนที่เพื่อส่งคืนสไตล์แถบสถานะที่ต้องการ:

- (UIStatusBarStyle)preferredStatusBarStyle
  {
      return UIStatusBarStyleLightContent;
  }

หากสไตล์แถบสถานะควรถูกควบคุมโดยตัวควบคุมมุมมองลูกแทนที่จะเป็นตัวเองให้แทนที่ -[UIViewController childViewControllerForStatusBarStyle]เพื่อกลับไปที่ตัวควบคุมมุมมองที่เด็ก

หากคุณต้องการเลิกใช้ลักษณะการทำงานนี้และตั้งค่าสไตล์ของแถบสถานะโดยใช้-[UIApplication statusBarStyle]วิธีการให้เพิ่มUIViewControllerBasedStatusBarAppearanceรหัสลงในInfo.plistไฟล์ของแอพและระบุค่า NO


3

หากใครก็ตามกำลังใช้ Navigation Controller และต้องการให้ตัวควบคุมการนำทางทั้งหมดมีสไตล์สีดำคุณสามารถเขียนส่วนขยายไปยัง UINavigationController เช่นนี้ใน Swift 3 และจะใช้กับตัวควบคุมทิศทางทั้งหมด (แทนที่จะกำหนดให้กับคอนโทรลเลอร์หนึ่งตัวที่ เวลา).

extension UINavigationController {

    override open func viewDidLoad() {
        super.viewDidLoad()

        self.navigationBar.barStyle = UIBarStyle.black
    }

}

1
แต่ถ้าฉันใช้แถบนำทางถูกซ่อนอยู่ล่ะ?
Slavcho

1
เพราะฉันต้องการซ่อนการนำทางและแถบสถานะให้มองเห็นได้
Slavcho

1

ใน Swift สำหรับ UIViewController ชนิดใดก็ได้:

ในAppDelegateชุดของคุณ:

func application(application: UIApplication, didFinishLaunchingWithOptions launchOptions: [NSObject: AnyObject]?) -> Bool {
    window!.rootViewController = myRootController
    return true
}

myRootControllerสามารถชนิดใดUIViewControllerเช่นหรือUITabBarControllerUINavigationController

จากนั้นให้แทนที่คอนโทรลเลอร์รูทนี้ดังนี้

class RootController: UIViewController {
    override func preferredStatusBarStyle() -> UIStatusBarStyle {
        return .LightContent
    }
}

สิ่งนี้จะเปลี่ยนลักษณะที่ปรากฏของแถบสถานะในแอปทั้งหมดของคุณเนื่องจากตัวควบคุมรูทเป็นผู้รับผิดชอบ แต่เพียงผู้เดียวสำหรับลักษณะที่ปรากฏของแถบสถานะ

อย่าลืมตั้งค่าคุณสมบัติView controller-based status bar appearanceเป็น YES ของคุณInfo.plistเพื่อทำงานนี้ (ซึ่งเป็นค่าเริ่มต้น)


@ มันเป็น swift3 อย่างไร?
เครื่องบิน


1

คำตอบส่วนใหญ่ไม่รวมถึงการใช้childViewControllerForStatusBarStyleวิธีการที่UINavigationControllerดี จากประสบการณ์ของฉันคุณควรจัดการกับกรณีเช่นเมื่อมีการนำเสนอตัวควบคุมมุมมองแบบโปร่งใสบนตัวควบคุมการนำทาง ในกรณีเหล่านี้คุณควรผ่านการควบคุมไปยังตัวควบคุม modal ( visibleViewController) แต่ไม่ใช่เมื่อมันหายไป

override var childViewControllerForStatusBarStyle: UIViewController? {
  var childViewController = visibleViewController
  if let controller = childViewController, controller.isBeingDismissed {
    childViewController = topViewController
  }
  return childViewController?.childViewControllerForStatusBarStyle ?? childViewController
}

1

ในกรณีของฉันฉันได้นำเสนอ View / Navigation Controller โดยไม่ตั้งใจUIModalPresentationStyle.overFullScreenซึ่งทำให้preferredStatusBarStyleไม่ถูกเรียก หลังจากเปลี่ยนกลับเป็นUIModalPresentationStyle.fullScreenทุกอย่างทำงานได้


1

ในฐานะที่เป็น iOS 13.4 preferredStatusBarStyleวิธีการในUINavigationControllerจะไม่เรียกหมวดหมู่การใช้คำสั่ง swizzling นั้นเป็นตัวเลือกเดียวโดยไม่จำเป็นต้องใช้คลาสย่อย

ตัวอย่าง:

ส่วนหัวของหมวดหมู่:

@interface UINavigationController (StatusBarStyle)
+ (void)setUseLightStatusBarStyle;
@end

การดำเนินงาน:

#import "UINavigationController+StatusBarStyle.h"
#import <objc/runtime.h>

@implementation UINavigationController (StatusBarStyle)

void (^swizzle)(Class, SEL, SEL) = ^(Class c, SEL orig, SEL new){
    Method origMethod = class_getInstanceMethod(c, orig);
    Method newMethod = class_getInstanceMethod(c, new);
    if(class_addMethod(c, orig, method_getImplementation(newMethod), method_getTypeEncoding(newMethod)))
        class_replaceMethod(c, new, method_getImplementation(origMethod), method_getTypeEncoding(origMethod));
    else
        method_exchangeImplementations(origMethod, newMethod);
};

+ (void)setUseLightStatusBarStyle {
    swizzle(self.class, @selector(preferredStatusBarStyle), @selector(_light_preferredStatusBarStyle));
}

- (UIStatusBarStyle)_light_preferredStatusBarStyle {
    return UIStatusBarStyleLightContent;
}    
@end

การใช้งานใน AppDelegate.h:

#import "UINavigationController+StatusBarStyle.h"

[UINavigationController setUseLightStatusBarStyle];

0

นี่คือวิธีของฉันสำหรับการแก้ปัญหานี้

กำหนดโปรโตคอลที่เรียกว่าAGViewControllerAppearance AGViewControllerAppearance

AGViewControllerAppearance.h

#import <Foundation/Foundation.h>

@protocol AGViewControllerAppearance <NSObject>

@optional

- (BOOL)showsStatusBar;
- (BOOL)animatesStatusBarVisibility;
- (UIStatusBarStyle)preferredStatusBarStyle;
- (UIStatusBarAnimation)prefferedStatusBarAnimation;

@end

กำหนดหมวดหมู่บนUIViewControllerชื่อUpgradeอัพเกรด

UIViewController + Upgrade.h

#import <UIKit/UIKit.h>

@interface UIViewController (Upgrade)

//
//  Replacements
//

- (void)upgradedViewWillAppear:(BOOL)animated;

@end

UIViewController + Upgrade.m

#import "UIViewController+Upgrade.h"

#import <objc/runtime.h>

#import "AGViewControllerAppearance.h" // This is the appearance protocol

@implementation UIViewController (Upgrade)

+ (void)load
{
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wselector"
    Method viewWillAppear = class_getInstanceMethod(self, @selector(viewWillAppear:));
#pragma clang diagnostic pop
    Method upgradedViewWillAppear = class_getInstanceMethod(self, @selector(upgradedViewWillAppear:));
    method_exchangeImplementations(viewWillAppear, upgradedViewWillAppear);
}

#pragma mark - Implementation

- (void)upgradedViewWillAppear:(BOOL)animated
{
    //
    //  Call the original message (it may be a little confusing that we're
    //  calling the 'same' method, but we're actually calling the original one :) )
    //

    [self upgradedViewWillAppear:animated];

    //
    //  Implementation
    //

    if ([self conformsToProtocol:@protocol(AGViewControllerAppearance)])
    {
        UIViewController <AGViewControllerAppearance> *viewControllerConformingToAppearance =
        (UIViewController <AGViewControllerAppearance> *)self;

        //
        //  Status bar
        //

        if ([viewControllerConformingToAppearance respondsToSelector:@selector(preferredStatusBarStyle)])
        {
            BOOL shouldAnimate = YES;

            if ([viewControllerConformingToAppearance respondsToSelector:@selector(animatesStatusBarVisibility)])
            {
                shouldAnimate = [viewControllerConformingToAppearance animatesStatusBarVisibility];
            }

            [[UIApplication sharedApplication] setStatusBarStyle:[viewControllerConformingToAppearance preferredStatusBarStyle]
                                                        animated:shouldAnimate];
        }

        if ([viewControllerConformingToAppearance respondsToSelector:@selector(showsStatusBar)])
        {
            UIStatusBarAnimation animation = UIStatusBarAnimationSlide;

            if ([viewControllerConformingToAppearance respondsToSelector:@selector(prefferedStatusBarAnimation)])
            {
                animation = [viewControllerConformingToAppearance prefferedStatusBarAnimation];
            }

            [[UIApplication sharedApplication] setStatusBarHidden:(! [viewControllerConformingToAppearance showsStatusBar])
                                                    withAnimation:animation];
        }
    }
}

@end

ตอนนี้ได้เวลาบอกว่าคุณกำลังดูคอนโทรลเลอร์กำลังใช้งานAGViewControllerAppearanceโปรโตคอล

ตัวอย่าง:

@interface XYSampleViewController () <AGViewControllerAppearance>

... the rest of the interface

@end

แน่นอนคุณสามารถใช้ส่วนที่เหลือของวิธีการ ( showsStatusBar , animatesStatusBarVisibility , prefferedStatusBarAnimation ) จากโปรโตคอลและUIViewController + Upgradeจะทำการปรับแต่งที่เหมาะสมตามค่าที่ให้ไว้


0

หากมีคนพบปัญหานี้กับ UISearchController เพียงสร้างคลาสย่อยใหม่ของ UISearchController แล้วเพิ่มรหัสด้านล่างลงในคลาสนั้น:

override func preferredStatusBarStyle() -> UIStatusBarStyle {
    return .LightContent
}

0

โปรดทราบว่าเมื่อใช้ self.navigationController.navigationBar.barStyle = UIBarStyleBlack;โซลูชัน

อย่าลืมไปที่ plist ของคุณและตั้งค่า "ดูแถบสถานะตามตัวควบคุม" เป็น YES ถ้าไม่ใช่มันจะไม่ทำงาน


การตั้งค่า UIViewControllerBasedStatusBarAppearance ให้เป็น YES ในแผนงานของโครงการทำให้ฉันแตกต่าง ฉันลืมไปแล้ว
filo

0

ตั้งแต่ Xcode 11.4, การเอาชนะ preferredStatusBarStyleคุณสมบัติในส่วนขยาย UINavigationController จะไม่ทำงานอีกต่อไปเนื่องจากจะไม่ถูกเรียกใช้

การตั้งค่าbarStyleของnavigationBarเป็น.blackทำงานได้จริง แต่สิ่งนี้จะเพิ่มผลข้างเคียงที่ไม่พึงประสงค์หากคุณเพิ่ม subviews ไปที่แถบนำทางซึ่งอาจมีลักษณะที่แตกต่างกันสำหรับโหมดแสงและสีเข้ม เนื่องจากการตั้งค่าเป็นbarStyleสีดำuserInterfaceStyleมุมมองที่ฝังอยู่ในแถบนำทางจะมีอยู่เสมอuserInterfaceStyle.darkโดยไม่คำนึงถึงuserInterfaceStyleแอพ

ทางออกที่เหมาะสมที่ฉันเกิดขึ้นคือการเพิ่มคลาสย่อยUINavigationControllerและแทนที่ที่preferredStatusBarStyleนั่น หากคุณใช้ UINavigationController ที่กำหนดเองนี้สำหรับมุมมองทั้งหมดของคุณคุณจะอยู่ในด้านการบันทึก


-1

NavigationController หรือ TabBarController เป็นสิ่งที่ต้องการจัดเตรียมสไตล์ นี่คือวิธีที่ฉันแก้ไข: https://stackoverflow.com/a/39072526/242769


หากคุณคิดว่านี่เป็นคำถามที่ซ้ำกันของคำถามอื่นโปรดปิดโหวตให้มันซ้ำซ้อน
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.