Wyłącz interaktywne odrzucanie kontrolera widoku prezentowanego w iOS 13

135

iOS 13 wprowadza nowy projekt modalPresentationStyle .pageSheet(i jego odpowiednika .formSheet) dla kontrolerów widoku prezentowanych modalnie…

Nowa przesuwana prezentacja modalna w iOS 13

… I możemy odrzucić te arkusze, przesuwając kontroler prezentowanego widoku w dół (interaktywne zamknięcie ) . Chociaż nowa funkcja „ściągnij, aby odrzucić” jest całkiem przydatna, nie zawsze może być pożądana.

PYTANIE: Jak możemy wyłączyć interaktywne zwolnienie? - Pamiętaj, że styl prezentacji pozostaje taki sam.

Jakub Truhlář
źródło
4
Możliwy duplikat prezentacji modalu na pełnym ekranie iOS 13
Mehul Thakkar
6
@MehulThakkar To inne pytanie.
Jakub Truhlář

Odpowiedzi:

240

Opcja 1:

viewController.isModalInPresentation = true

Wyłączone interaktywne zwolnienie

(Wyłączone interaktywne .pageSheetzwolnienie działa w ten sposób).

  • Od iOS 13 UIViewControllerzawiera nową właściwość o nazwie, isModalInPresentationktóra musi być ustawiona, trueaby zapobiec interaktywnemu odrzuceniu.
  • Zasadniczo ignoruje zdarzenia poza granicami kontrolera widoku. Pamiętaj o tym, jeśli używasz nie tylko stylu automatycznego, ale także stylów prezentacji, takich jak .popoveritp.
  • Ta właściwość jest falsedomyślna.

Z oficjalnych dokumentów : jeśli trueUIKit ignoruje zdarzenia poza granicami kontrolera widoku i zapobiega interaktywnemu odrzuceniu kontrolera widoku, gdy jest on na ekranie.


Opcja 2:

func presentationControllerShouldDismiss(_ presentationController: UIPresentationController) -> Bool {
    return false
}
  • Od iOS 13 UIAdaptivePresentationControllerDelegatezawiera nową metodę o nazwie presentationControllerShouldDismiss.
  • Ta metoda jest wywoływana tylko wtedy, gdy prezentowany kontroler widoku nie jest odrzucany programowo, a jego isModalInPresentationwłaściwość jest ustawiona na false.

Wskazówka: nie zapomnij przypisać delegata prezentacjiController.

Jakub Truhlář
źródło
2
Jeśli prezentowany kontroler widoku jest kontrolerem nawigacji, możesz ustawić isModalInPresentationgo w kontrolerze nawigacji lub w poszczególnych kontrolerach widoku wyświetlanych w stosie nawigacji. Ta ostatnia pozwala wybrać na ekranie po ekranie, czy możliwe jest interaktywne zwolnienie. Ostrożnie w przypadku kontrolerów wyszukiwania, mają one pierwszeństwo przed indywidualnym kontrolerem widoku (ale nie kontrolerem nawigacji). Więcej informacji w moim poście na blogu: medium.com/@hacknicity/…
Geoff Hackworth
1
Pamiętaj, że jeśli Twój VC jest prezentowany jako popover, zapobiegnie to odrzuceniu popover podczas stukania poza nim
PatrickDotStar
4
Cel-C:viewController.modalInPresentation = YES;
quarac
3
Czy ktoś ma to do pracy podczas ustawiania tej flagi na UIImagePickerController? Dla nas wygląda na UIImagePickerControllerto, że ignoruje go, więc można go odrzucić za pomocą gestu machnięcia. Może to błąd iOS 13.
PatrickDotStar
4
Gdy presentationControllerShouldDismiss(_ presentationController: UIPresentationController)zwraca false, presentationControllerDidAttemptToDismiss(_ presentationController: UIPresentationController)jest wywoływane, więc możesz na przykład dodać okno dialogowe potwierdzenia, jeśli użytkownik wprowadził dane.
Neil
66
  1. Jeśli chcesz zachować to samo zachowanie, co w poprzedniej wersji iOS (<iOS13), takie jak prezentacja modelu na pełnym ekranie, po prostu ustaw styl prezentacji kontrolera widoku docelowego na UIModalPresentationStyle.fullScreen

    let someViewController = \*VIEW CONTROLLER*\
    someViewController.modalPresentationStyle = .fullScreen

    A jeśli używasz storyboardu, po prostu wybierz segua i wybierz z Full Screenlisty Presentationrozwijanej.

    wprowadź opis obrazu tutaj

  2. Jeśli chcesz po prostu wyłączyć interaktywną odwoływania i zachować nowy styl prezentacji określoną UIViewControllerwłaściwość isModalInPresentationdo true.

    if #available(iOS 13.0, *) {
        someViewController.isModalInPresentation = true // available in IOS13
    }
Bilal
źródło
Działa lepiej niż użycie {controller.isModalInPresentation = true}.
Maxim Firsoff
8

Nieruchomość isModalInPresentationmoże pomóc.

Z dokumentacji:

Po ustawieniu na true, UIKit ignoruje zdarzenia poza granicami kontrolera widoku i zapobiega interaktywnemu odrzuceniu kontrolera widoku, gdy jest on na ekranie.

Możesz go używać w ten sposób:

let controller = MyViewController()
controller.isModalInPresentation = true
self.present(controller, animated: true, completion: nil)
Mohit Tomar
źródło
5

Jeśli używasz scenorysów do układania interfejsu użytkownika, znalazłem najlepszy sposób na wyłączenie tego interaktywnego odrzucania podczas korzystania z kontrolera nawigacyjnego, aby zmienić prezentację kontrolera nawigacji w inspektorze atrybutów z automatycznego na pełny ekran. Wszystkie kontrolery widoku w stosie nawigacyjnym będą wtedy pełnoekranowe i nie będą mogły zostać odrzucone przez użytkownika.

Inspektor atrybutów przedstawiający opcję prezentacji dla kontrolera nawigacji

Brandon Whitton
źródło
1

Apple udostępnił przykładowy kod na ten temat pod tym linkiem

Wykorzystuje isModalInPresentationsugestie wielu użytkowników.

Arda Oğul Üçpınar
źródło