UIImagePickerController merusak tampilan bilah status

137

Di file .plist saya, saya telah menyetel " Tampilan bilah status berbasis pengontrol " ke NO. Tapi setelah itu UIImagePickerController, aplikasi saya berperilaku seolah-olah opsi disetel ke YES.

Di aplikasi saya, saya menyajikan VC yang menampilkan file UIImagePickerController.

Masalahnya terjadi seperti ini:

  • Setelah pemilih foto ditampilkan, saat perpustakaan foto dipilih, warna teks bilah status berubah.
  • Kemudian setelah, UIImagePickerControllerdiberhentikan, perubahan jarak bilah status untuk sisa aplikasi saya dan semua bilah navigasi untuk pengontrol lain ditampilkan di bawah bilah status.

Apakah ada cara untuk mengatasi ini tanpa mengelola bilah status di pengontrol tampilan saya?

Alex L.
sumber
Jawaban dalam kasus saya terkait dengan childviewcontrollers. Saya harus membuatnya kembali daripada menggunakannya kembali.
Alex L
7
Ini benar-benar tampak seperti bug iOS 7, apakah ada yang mengajukan laporan ke Apple?
Dan F
stackoverflow.com/questions/21225978/… pertanyaan serupa dengan solusi sederhana
Ting Wu
Hai @AlexL, apakah Anda tahu mengapa itu terjadi?
Shabarinath Pabba

Jawaban:

192

Tidak ada solusi di atas yang berhasil untuk saya, tetapi dengan menggabungkan jawaban Rich86man dan iOS_DEV_09, saya mendapatkan solusi yang berfungsi secara konsisten:

UIImagePickerController* imagePicker = [[UIImagePickerController alloc] init];
imagePicker.delegate = self;

dan

- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated
{
    [[UIApplication sharedApplication] setStatusBarHidden:YES];
}

Mengenai solusi luar biasa ini. Untuk 2014 / iOS8 saya menemukan dalam beberapa kasus Anda perlu JUGA menyertakan prefersStatusBarHiddendan, mungkin, childViewControllerForStatusBarHiddenJadi ...

-(void)navigationController:(UINavigationController *)navigationController
        willShowViewController:(UIViewController *)viewController
        animated:(BOOL)animated
    {
    [[UIApplication sharedApplication] setStatusBarHidden:YES];
    }

-(BOOL)prefersStatusBarHidden   // iOS8 definitely needs this one. checked.
    {
    return YES;
    }

-(UIViewController *)childViewControllerForStatusBarHidden
    {
    return nil;
    }

-(void)showCamera
    {
    self.cameraController = [[UIImagePickerController alloc] init];
    self.cameraController.delegate = (id)self; // dpjanes solution!
    etc...

Semoga bisa membantu seseorang

dpjanes.dll
sumber
3
Inilah triknya (seperti yang dikatakan Rich86man): "Karena UIImagePickerController adalah jenis pengontrol Navigasi, Anda juga menyetel diri sendiri sebagai delegasi UINavigationController."
Beto
2
bagaimana setelah memberhentikan UIImaegPicker ..? saya mengatur statusbar hide false maka latar belakangnya menjadi hitam.
Nitin Gohel
Apakah Anda sudah menyiapkan plist sesuai pertanyaan di atas?
dpjanes
Apakah Anda memperhatikan masalah saat menggunakan UIImagePickerControllerSourceTypePhotoLibrary, membuka beberapa album, lalu menggeser mundur sedikit, dan membatalkan isyarat?
Kukosk
3
Ini berfungsi, meskipun bilah status muncul masuk dan keluar dengan sangat tersentak-sentak. Saya telah melaporkan bug ke Apple.
jjxtra
84

Saya menghadapi masalah yang sama hari ini. Inilah solusi saya.

Di pengontrol tampilan yang memanggil pemilih gambar, tetapkan diri Anda sebagai delegasi Pemilih gambar. (Anda mungkin sudah melakukan ini)

UIImagePickerController* imagePicker = [[UIImagePickerController alloc] init];
imagePicker.delegate = self;

Karena UIImagePickerController adalah jenis pengontrol Navigasi, Anda juga menyetel diri sendiri sebagai delegasi UINavigationController. Kemudian :

- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated
{
    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];
}

Ganti UIStatusBarStyleLightContent dengan gaya apa pun yang Anda cari.

Rich86man
sumber
10

Jawaban yang diterima akan berfungsi jika Anda menyetel 'Lihat tampilan bilah status berbasis pengontrol' ke NO di file .plist Anda. Jika memang Anda perlu mengontrol bilah status di beberapa pengontrol tampilan lain dan menyetel opsi ini ke YA, cara lain untuk membuat UIImagePickerController berperilaku benar adalah dengan membuat subkelasnya

// .h
@interface MYImagePickerController : UIImagePickerController
@end

// .m
@implementation MYImagePickerController
- (UIStatusBarStyle)preferredStatusBarStyle
{
    return UIStatusBarStyleLightContent; // change this to match your style
}
@end
mgcm
sumber
6

saya menghadapi masalah yang sama.

inilah solusi saya. letakkan ini di viewWillAppear dari pengontrol tampilan tempat Anda membuka tampilan pemilih gambar

-(void) viewWillAppear:(BOOL)animated{
[super viewWillAppear:YES];

[[UIApplication sharedApplication] setStatusBarHidden:YES];

}
iOS_DEV
sumber
4

Bisakah kamu mencobanya. Saya pikir needsStatusBarApperanceUpdate akan berfungsi.

1 -Set UIViewControllerBasedStatusBarAppearance to NO.
2- Call [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];
3- [self setNeedsStatusBarAppearanceUpdate];
Burcu Geneci
sumber
4

Saya menemukan ini untuk menawarkan penanganan yang tepat, ada dua bagian.

- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated
{
    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleBlackOpaque];
}


- (void)viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];

    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleBlackOpaque];
...

UIImagePickerController sendiri menyajikan pengontrol tampilan, jadi delegasi ini berfungsi untuk semua penyaji di tumpukan.

viewWillAppear memastikan pengontrol tampilan ini sendiri selalu disetel ulang setiap kali pengontrol tampilan yang ditampilkan menutup di atasnya.

Jesse Tayler
sumber
3

Saya memiliki masalah yang sama. Tambahkan info plist: "Lihat tampilan bilah status berbasis pengontrol" dengan nilai "NO"

Contoh di sini https://stackoverflow.com/a/19211669

Solusi ini berhasil untuk saya.

serj
sumber
2

Ini mungkin bug. Saya memecahkan masalah dengan menyetel "Lihat tampilan bilah status berbasis pengontrol" disetel ke YA dan di setiap pengontrol tampilan menempelkan kode berikut:

- (BOOL)prefersStatusBarHidden
{
    return YES;
}

Kemudian aplikasi saya berperilaku seperti yang diharapkan.

Jonas
sumber
2

Untuk menyembunyikan bilah status di UIImagePicker:

-

 (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated
{
    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent];
}

dan ketika UIImagePicker ditutup untuk menyembunyikan bilah status di pengontrol Tampilan, gunakan kode berikut:

-(void) viewWillAppear:(BOOL)animated{
    [super viewWillAppear:YES];

    [[UIApplication sharedApplication] setStatusBarHidden:YES];

}
Panky
sumber
2

coba ini ....

ini akan berfungsi di kedua kasus, yaitu apakah Anda menggunakan presentModalViewController dan pushViewController

UIImagePickerController *picker = [[UIImagePickerController alloc] init];
picker.delegate = self;

mendelegasikan metode

-(void)imagePickerController:(UIImagePickerController*)picker didFinishPickingMediaWithInfo:(NSDictionary*)info
{
    [[UIApplication sharedApplication] setStatusBarHidden:YES];
    [picker dismissViewControllerAnimated:YES completion:^{}];
}


- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker
{
    [[UIApplication sharedApplication] setStatusBarHidden:YES];
    [picker dismissViewControllerAnimated:YES completion:nil];
}
Shaik Riyaz
sumber
2

Semua hal di atas tidak berhasil untuk saya. Saya memecahkan masalah dengan mengubah gaya presentasi menjadi:

imagePickerController.modalPresentationStyle = UIModalPresentationFullScreen;
d.ennis
sumber
2

Tidak ada solusi di atas yang berhasil untuk saya.

Saya menyajikan UIImagePickerController sebagai pengontrol tampilan modal. Setelah menutup UIImagePickerController, status bilahnya adalah:

[UIApplication sharedApplication].statusBarOrientation = 0 (UIDeviceOrientationUnknown)
[UIApplication sharedApplication].statusBarFrame = { 0, 0, 0, 0}

Solusi yang memperbaiki masalah saya adalah memulihkan statusBarOrientation setelah menutup UIImagePickerController:

UIImagePickerController *cameraUI = [[UIImagePickerController alloc] init];
[self.viewController presentViewController:cameraUI animated:true completion:^(void){ }];

...

[self.viewController dismissViewControllerAnimated:animated completion:^(void){
    [UIApplication sharedApplication].statusBarOrientation = UIInterfaceOrientationPortrait;
}];
Mihail Varbanov
sumber
2

Kode ini membantu saya menyesuaikan gaya bilah status.

EDIT: solusi ini berfungsi jika "Lihat tampilan bilah status berbasis pengontrol" == YA

@implementation UIImagePickerController (IOS7_StatusBarStyle)

-(UIViewController*)childViewControllerForStatusBarStyle
{
   return nil;
}

-(UIStatusBarStyle)preferredStatusBarStyle
{
   return UIStatusBarStyleLightContent;
}

@end
Igor Palaguta
sumber
2

Semua jawaban di atas ok dan bisa membantu.

Saya memiliki masalah yang sama karena harus mengelola aplikasi yang dijalankan di bawah versi iOS yang berbeda .

UIImagePickerController *imagePickerController = [[UIImagePickerController alloc] init];

if(IS_IOS8_AND_UP) {
    imagePickerController.modalPresentationStyle = UIModalPresentationFullScreen;
} else {
    imagePickerController.modalPresentationStyle = UIModalPresentationCurrentContext;
}

imagePickerController.delegate = self;
[self presentViewController:imagePickerController animated:YES completion:nil];

Kemudian, di delegasikan:

- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated {
    /* Cancel button color  */
    _imagePicker.navigationBar.tintColor = <custom_color>
    /* Status bar color */
    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleDefault];
}
Luca Davanzo
sumber
2

Namun solusi lain yang mungkin berhasil dalam beberapa situasi.

let imagePicker =  UIImagePickerController()
imagePicker.sourceType = .PhotoLibrary
imagePicker.navigationBar.barStyle = .Black
SoftDesigner
sumber
1

Sudahkah Anda mencoba menelepon [self setNeedsStatusBarAppearanceUpdate]saat pengontrol tampilan presentasi Anda muncul kembali?

Ash Furrow
sumber
Mungkin itu bug - Saya akan mengajukan radar dengan proyek contoh dan kembali ke sistem lama dalam mengelola bilah status :(
Ash Furrow
1

Saya mencoba menyembunyikan bilah status di UIImagePickerController di iOS7, tetapi saya masih tidak tahu bagaimana melakukan ini. saya menggunakan

- (void)viewWillAppear:(BOOL)animated
{
    [[UIApplication sharedApplication] setStatusBarHidden:YES
                                        withAnimation:UIStatusBarAnimationNone];
}

di ViewController yang memanggil UIImagePickerController, dan setel "Lihat tampilan bilah status berbasis pengontrol = NO" di file plist. Semoga ini bisa membantu.

jxdwinter.dll
sumber
1

coba ini :

UIImagePickerController *picker = [[UIImagePickerController alloc] init];
picker.delegate = self;

dan dalam implementasi protokol, gunakan ini:

- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated
{
    [[UIApplication sharedApplication] setStatusBarHidden:YES];
}
ouyongyong
sumber
1

Ini menyelesaikannya untuk saya ...:

- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker
{
    [[UIApplication sharedApplication] setStatusBarHidden:YES];
    [picker dismissViewControllerAnimated:YES completion:nil];
}
Seb OH
sumber
1

Tidak ada di sini yang secara khusus memperbaiki masalah yang saya alami (dan mungkin OP juga mengalami), jadi saya pikir saya akan membagikan jawaban saya. Alih-alih menyembunyikan bilah status yang menurut saya merupakan solusi buggy (saya perhatikan bahwa kadang-kadang akan meninggalkan aplikasi saya dalam keadaan di mana bilah status disembunyikan ketika seharusnya tidak). Saya malah memilih untuk mencoba dan bermain bagus denganUIStatusBarStyles .

Ketika UIImagePickerController memiliki tampilan yang disajikan, saya mengatur gaya bilah status ke default karena warna latar belakang default adalah abu-abu terang.

- (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated
{
    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleDefault animated:YES];
}

Kemudian, saat pemilih gambar ditutup, saya menyetelnya kembali ke UIStatusBarStyleLightContent.

- (void)imagePickerController:(UIImagePickerController *)picker didFinishPickingMediaWithInfo:(NSDictionary *)info
{
    //work

    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent animated:YES];

    [self dismissViewControllerAnimated:YES completion:NULL];
}

- (void)imagePickerControllerDidCancel:(UIImagePickerController *)picker
{ 
    //work

    [[UIApplication sharedApplication] setStatusBarStyle:UIStatusBarStyleLightContent animated:YES];

    [self dismissViewControllerAnimated:YES completion:NULL];
}
Ian Hoar
sumber
1

Dalam hal ini, Kami menggunakan 2 langkah

Pada langkah pertama: Tambahkan info.plist: "Lihat tampilan bilah status berbasis pengontrol" dengan nilai "NO"

Pada langkah kedua: Gunakan / panggil kode ini dengan delegasi UIImagePickerController

 - (void)navigationController:(UINavigationController *)navigationController willShowViewController:(UIViewController *)viewController animated:(BOOL)animated
{
     if([navigationController isKindOfClass:[UIImagePickerController class]])
         [[UIApplication sharedApplication] setStatusBarHidden:YES]; 
 }

Dalam kasus IOS-7 tambahkan Satu Fungsi lagi

- (BOOL)prefersStatusBarHidden
{
    return YES;
}
Vaibhav Sharma
sumber
1

Pada iOS 8.1, sepertinya mereka akhirnya memperbaiki bug ini! Saya dapat menghapus semua solusi yang saya gunakan dari kode saya.

Jeff V
sumber
1

Menggunakan perilaku iOS 8 default, saya mengalami masalah dengan bilah status yang muncul saat saya ingin menyembunyikannya.

Solusi yang saya temukan adalah, langsung setelah memanggil presentPopoverdari pengontrol tampilan saya, saya lakukan:

    [self performSelector:@selector(setNeedsStatusBarAppearanceUpdate) withObject:nil afterDelay:0.01];

Saya juga harus menambahkan ini ke pengontrol tampilan utama saya:

- (UIViewController *)childViewControllerForStatusBarHidden
{
    return nil;
}
JosephH
sumber
1

Jadi saya mengalami masalah ini dan saya dapat menyelesaikannya hanya dengan menerapkan satu fungsi delegasi. Latar belakang bilah status saya berwarna hitam, sehingga UIStatusBarStyle untuk aplikasi saya adalah .LightContent. Ketika saya mempresentasikan UIImagePickerController untuk memilih foto dari penyimpanan perangkat, bilah status baik-baik saja. Namun, saat mengklik ke direktori seperti "Rol Kamera" atau "Favorit," secara efektif mendorong ke tumpukan navigasi, bilah status menghilang. Saat memilih foto, tidak ada bilah status sama sekali; setelah menutup pengontrol tampilan modal lainnya, hanya baterai yang ada, yang menunjukkan bahwa bilah status lainnya mungkin juga hitam.

Saya mencoba beberapa solusi lain seperti memperluas UIImagePickerController, tetapi di Swift, Anda tidak dapat mengganti menggunakan ekstensi. Saya kemudian mencoba membuat subkelas UIImagePickerController dan mencoba menyembunyikan bilah statusnya di viewWillAppear () dan memperlihatkan bilah status di viewWillDisappear. Saya dapat melihat bilah status disembunyikan dengan animasi .Slide, tetapi karena bilah status tidak terlihat saat memilih direktori, saya tidak dapat melihat bilah status ditampilkan. Sekali lagi, baterai hijau kembali dengan sisa bilah status tidak terlihat setelah menutup pengontrol tampilan modal. Saya juga mencoba mengganti prefersStatusBarHidden (), tetapi fungsi itu tidak pernah dipanggil, jadi saya mencoba memanggil setNeedsStatusBarAppearanceUpdate () untuk memastikan bahwa prefersStatusBarHidden () dipanggil oleh sistem, tetapi masih tidak dipanggil. Juga, ada saran untuk menyetel bilah status agar disembunyikan pada metode delegasi navigationController willShowViewController. Sekali lagi, yang dilakukan hanyalah menyembunyikan bilah status, yang tidak menyelesaikan masalah. Ternyata, tampaknya gaya bilah status diubah setelah didorong ke tumpukan navigasi UIImagePickerController. Untuk mengatasi masalah sepenuhnya, saya tidak perlu menulis ekstensi atau subclass UIImagePickerController. Yang perlu Anda lakukan hanyalah menyetel delegasi dan menyetel gaya bilah status agar tetap sama. Penambahan ini seolah-olah masalah tidak pernah ada. tampaknya gaya bilah status diubah saat mendorong ke tumpukan navigasi UIImagePickerController. Untuk mengatasi masalah sepenuhnya, saya tidak perlu menulis ekstensi atau subclass UIImagePickerController. Yang perlu Anda lakukan hanyalah menyetel delegasi dan menyetel gaya bilah status agar tetap sama. Penambahan ini seolah-olah masalah tidak pernah ada. tampaknya gaya bilah status diubah saat mendorong ke tumpukan navigasi UIImagePickerController. Untuk mengatasi masalah sepenuhnya, saya tidak perlu menulis ekstensi atau subclass UIImagePickerController. Yang perlu Anda lakukan hanyalah menyetel delegasi dan menyetel gaya bilah status agar tetap sama. Penambahan ini seolah-olah masalah tidak pernah ada.

let pickerController = UIImagePickerController()
pickerController.delegate = self

func navigationController(navigationController: UINavigationController, willShowViewController viewController: UIViewController, animated: Bool) {
        UIApplication.sharedApplication().setStatusBarStyle(.LightContent, animated: false)
    }
SwiftMatt
sumber
-1

Saya benar-benar menemukan cara yang lebih baik untuk mengatur warna latar belakang bilah status di Image Picker. Pada dasarnya Anda perlu mengatur backgroundImage dari navigationBar menjadi nil, karena secara default di Image Picker memiliki backgroundImage sebagai Image putih.

André Luiz Alves
sumber