Skip to content

Commit

Permalink
prevent a gap appearing behind the keyboard when it goes away and ref…
Browse files Browse the repository at this point in the history
…actor the code a little
  • Loading branch information
brindy committed Jan 31, 2024
1 parent f66b382 commit c04ff1c
Show file tree
Hide file tree
Showing 5 changed files with 207 additions and 161 deletions.
4 changes: 4 additions & 0 deletions DuckDuckGo.xcodeproj/project.pbxproj
Original file line number Diff line number Diff line change
Expand Up @@ -497,6 +497,7 @@
85DB12EB2A1FE2A4000A4A72 /* LockScreenWidgets.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85DB12EA2A1FE2A4000A4A72 /* LockScreenWidgets.swift */; };
85DB12ED2A1FED0C000A4A72 /* AppDelegate+AppDeepLinks.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85DB12EC2A1FED0C000A4A72 /* AppDelegate+AppDeepLinks.swift */; };
85DDE0402AC6FF65006ABCA2 /* MainView.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85DDE03F2AC6FF65006ABCA2 /* MainView.swift */; };
85DE681A2B6A8BB000DED4FE /* MainViewCoordinator.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85DE68192B6A8BB000DED4FE /* MainViewCoordinator.swift */; };
85DF714624F7FE6100C89288 /* Core.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = F143C2E41E4A4CD400CFDE3A /* Core.framework */; };
85DFEDED24C7CCA500973FE7 /* AppWidthObserver.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85DFEDEC24C7CCA500973FE7 /* AppWidthObserver.swift */; };
85DFEDEF24C7EA3B00973FE7 /* SmallOmniBarState.swift in Sources */ = {isa = PBXBuildFile; fileRef = 85DFEDEE24C7EA3B00973FE7 /* SmallOmniBarState.swift */; };
Expand Down Expand Up @@ -1590,6 +1591,7 @@
85DB12EA2A1FE2A4000A4A72 /* LockScreenWidgets.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LockScreenWidgets.swift; sourceTree = "<group>"; };
85DB12EC2A1FED0C000A4A72 /* AppDelegate+AppDeepLinks.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = "AppDelegate+AppDeepLinks.swift"; sourceTree = "<group>"; };
85DDE03F2AC6FF65006ABCA2 /* MainView.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MainView.swift; sourceTree = "<group>"; };
85DE68192B6A8BB000DED4FE /* MainViewCoordinator.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = MainViewCoordinator.swift; sourceTree = "<group>"; };
85DFEDEC24C7CCA500973FE7 /* AppWidthObserver.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppWidthObserver.swift; sourceTree = "<group>"; };
85DFEDEE24C7EA3B00973FE7 /* SmallOmniBarState.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = SmallOmniBarState.swift; sourceTree = "<group>"; };
85DFEDF024C7EEA400973FE7 /* LargeOmniBarState.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = LargeOmniBarState.swift; sourceTree = "<group>"; };
Expand Down Expand Up @@ -5432,6 +5434,7 @@
851DFD86212C39D300D95F20 /* TabSwitcherButton.swift */,
CBEFB9102ADFFE7900DEDE7B /* CriticalAlerts.swift */,
85B9814D2B5EB618009AC9A6 /* SwipeTabsCoordinator.swift */,
85DE68192B6A8BB000DED4FE /* MainViewCoordinator.swift */,
);
name = Main;
sourceTree = "<group>";
Expand Down Expand Up @@ -6708,6 +6711,7 @@
3151F0EE2735800800226F58 /* VoiceSearchFeedbackView.swift in Sources */,
857EEB752095FFAC008A005C /* HomeRowInstructionsViewController.swift in Sources */,
311BD1AF2836BB4200AEF6C1 /* AutofillItemsLockedView.swift in Sources */,
85DE681A2B6A8BB000DED4FE /* MainViewCoordinator.swift in Sources */,
0290472A29E867800008FE3C /* AppTPTrackerDetailView.swift in Sources */,
F1617C151E57336D00DEDCAF /* TabManager.swift in Sources */,
85449EF523FDA02800512AAF /* KeyboardSettingsViewController.swift in Sources */,
Expand Down
168 changes: 32 additions & 136 deletions DuckDuckGo/MainView.swift
Original file line number Diff line number Diff line change
Expand Up @@ -19,9 +19,6 @@

import UIKit

// swiftlint:disable file_length
// swiftlint:disable line_length

class MainViewFactory {

private let coordinator: MainViewCoordinator
Expand Down Expand Up @@ -63,6 +60,7 @@ extension MainViewFactory {
createOmniBar()
createToolbar()
createNavigationBarContainer()
createNavigationBarCollectionView()
createProgressView()
}

Expand All @@ -76,24 +74,38 @@ extension MainViewFactory {
coordinator.omniBar.translatesAutoresizingMaskIntoConstraints = false
}

final class NavigationBarContainer: UICollectionView {
final class NavigationBarCollectionView: UICollectionView {

var hitTestInsets = UIEdgeInsets.zero

override func point(inside point: CGPoint, with event: UIEvent?) -> Bool {
var extendedBounds = bounds.inset(by: hitTestInsets)
return extendedBounds.contains(point)
return bounds.inset(by: hitTestInsets).contains(point)
}

// Don't allow the use to drag the scrollbar or the UI will glitch.
override func hitTest(_ point: CGPoint, with event: UIEvent?) -> UIView? {
let view = super.hitTest(point, with: event)
if view == self.subviews.first(where: { $0 is UIImageView }) {
return nil
}
return view
}
}

private func createNavigationBarContainer() {
private func createNavigationBarCollectionView() {
// Layout is replaced elsewhere, but required to construct the view.
coordinator.navigationBarContainer = NavigationBarContainer(frame: .zero, collectionViewLayout: UICollectionViewFlowLayout())
coordinator.navigationBarContainer.decelerationRate = .fast
coordinator.navigationBarCollectionView = NavigationBarCollectionView(frame: .zero, collectionViewLayout: UICollectionViewFlowLayout())

// scrollview subclasses change the default to true, but we need this for the separator on the omnibar
coordinator.navigationBarContainer.clipsToBounds = false
coordinator.navigationBarCollectionView.clipsToBounds = false

coordinator.navigationBarCollectionView.translatesAutoresizingMaskIntoConstraints = false
coordinator.navigationBarContainer.addSubview(coordinator.navigationBarCollectionView)
}

final class NavigationBarContainer: UIView { }
private func createNavigationBarContainer() {
coordinator.navigationBarContainer = NavigationBarContainer()
superview.addSubview(coordinator.navigationBarContainer)
}

Expand Down Expand Up @@ -199,19 +211,26 @@ extension MainViewFactory {
coordinator.constraints.progressBarTop,
])
}

private func constrainNavigationBarContainer() {
let navigationBarContainer = coordinator.navigationBarContainer!
let toolbar = coordinator.toolbar!
let navigationBarCollectionView = coordinator.navigationBarCollectionView!

coordinator.constraints.navigationBarContainerTop = navigationBarContainer.constrainView(superview.safeAreaLayoutGuide, by: .top)
coordinator.constraints.navigationBarContainerBottom = navigationBarContainer.constrainView(toolbar, by: .bottom, to: .top)

coordinator.constraints.navigationBarCollectionViewBottom = navigationBarCollectionView.constrainView(navigationBarContainer, by: .bottom, relatedBy: .greaterThanOrEqual)

Check failure on line 222 in DuckDuckGo/MainView.swift

View workflow job for this annotation

GitHub Actions / SwiftLint

Line should be 150 characters or less; currently it has 178 characters (line_length)

NSLayoutConstraint.activate([
coordinator.constraints.navigationBarContainerTop,
navigationBarContainer.constrainView(superview, by: .leading),
navigationBarContainer.constrainView(superview, by: .trailing),
navigationBarContainer.constrainAttribute(.height, to: 52),
navigationBarContainer.constrainAttribute(.height, to: 52, relatedBy: .greaterThanOrEqual),
navigationBarCollectionView.constrainAttribute(.height, to: 52),
navigationBarCollectionView.constrainView(navigationBarContainer, by: .top),
navigationBarCollectionView.constrainView(navigationBarContainer, by: .leading),
navigationBarCollectionView.constrainView(navigationBarContainer, by: .trailing),
coordinator.constraints.navigationBarCollectionViewBottom
])
}

Expand Down Expand Up @@ -322,126 +341,3 @@ extension MainViewFactory {
}

}

class MainViewCoordinator {

let superview: UIView

var contentContainer: UIView!
var lastToolbarButton: UIBarButtonItem!
var logo: UIImageView!
var logoContainer: UIView!
var logoText: UIImageView!
var navigationBarContainer: MainViewFactory.NavigationBarContainer!
var notificationBarContainer: UIView!
var omniBar: OmniBar!
var progress: ProgressView!
var statusBackground: UIView!
var suggestionTrayContainer: UIView!
var tabBarContainer: UIView!
var toolbar: UIToolbar!
var toolbarBackButton: UIBarButtonItem!
var toolbarFireButton: UIBarButtonItem!
var toolbarForwardButton: UIBarButtonItem!
var toolbarTabSwitcherButton: UIBarButtonItem!

let constraints = Constraints()

// The default after creating the hiearchy is top
var addressBarPosition: AddressBarPosition = .top

fileprivate init(superview: UIView) {
self.superview = superview
}

func decorateWithTheme(_ theme: Theme) {
superview.backgroundColor = theme.mainViewBackgroundColor
logoText.tintColor = theme.ddgTextTintColor
omniBar.decorate(with: theme)
}

func showToolbarSeparator() {
toolbar.setShadowImage(nil, forToolbarPosition: .any)
}

func hideToolbarSeparator() {
self.toolbar.setShadowImage(UIImage(), forToolbarPosition: .any)
}

class Constraints {

var navigationBarContainerTop: NSLayoutConstraint!
var navigationBarContainerBottom: NSLayoutConstraint!
var toolbarBottom: NSLayoutConstraint!
var contentContainerTop: NSLayoutConstraint!
var tabBarContainerTop: NSLayoutConstraint!
var notificationContainerTopToNavigationBar: NSLayoutConstraint!
var notificationContainerTopToStatusBackground: NSLayoutConstraint!
var notificationContainerHeight: NSLayoutConstraint!
var progressBarTop: NSLayoutConstraint!
var progressBarBottom: NSLayoutConstraint!
var statusBackgroundToNavigationBarContainerBottom: NSLayoutConstraint!
var statusBackgroundBottomToSafeAreaTop: NSLayoutConstraint!
var contentContainerBottomToToolbarTop: NSLayoutConstraint!
var contentContainerBottomToNavigationBarContainerTop: NSLayoutConstraint!

}

func moveAddressBarToPosition(_ position: AddressBarPosition) {
guard position != addressBarPosition else { return }
switch position {
case .top:
setAddressBarBottomActive(false)
setAddressBarTopActive(true)

case .bottom:
setAddressBarTopActive(false)
setAddressBarBottomActive(true)
}

addressBarPosition = position
}

func hideNavigationBarWithBottomPosition() {
guard addressBarPosition.isBottom else {
return
}

// Hiding the container won't suffice as it still defines the contentContainer.bottomY through constraints
navigationBarContainer.isHidden = true

constraints.contentContainerBottomToNavigationBarContainerTop.isActive = false
constraints.contentContainerBottomToToolbarTop.isActive = true
}

func showNavigationBarWithBottomPosition() {
guard addressBarPosition.isBottom else {
return
}

constraints.contentContainerBottomToToolbarTop.isActive = false
constraints.contentContainerBottomToNavigationBarContainerTop.isActive = true

navigationBarContainer.isHidden = false
}

func setAddressBarTopActive(_ active: Bool) {
constraints.contentContainerBottomToToolbarTop.isActive = active
constraints.navigationBarContainerTop.isActive = active
constraints.progressBarTop.isActive = active
constraints.notificationContainerTopToNavigationBar.isActive = active
constraints.statusBackgroundToNavigationBarContainerBottom.isActive = active
}

func setAddressBarBottomActive(_ active: Bool) {
constraints.contentContainerBottomToNavigationBarContainerTop.isActive = active
constraints.progressBarBottom.isActive = active
constraints.navigationBarContainerBottom.isActive = active
constraints.notificationContainerTopToStatusBackground.isActive = active
constraints.statusBackgroundBottomToSafeAreaTop.isActive = active
}

}

// swiftlint:enable line_length
// swiftlint:enable file_length
6 changes: 2 additions & 4 deletions DuckDuckGo/MainViewController.swift
Original file line number Diff line number Diff line change
Expand Up @@ -483,6 +483,7 @@ class MainViewController: UIViewController {
swipeTabsCoordinator?.addressBarPositionChanged(isTop: true)
viewCoordinator.omniBar.moveSeparatorToBottom()
viewCoordinator.showToolbarSeparator()
viewCoordinator.constraints.navigationBarContainerBottom.isActive = false

case .bottom:
swipeTabsCoordinator?.addressBarPositionChanged(isTop: false)
Expand Down Expand Up @@ -543,7 +544,7 @@ class MainViewController: UIViewController {

if self.appSettings.currentAddressBarPosition.isBottom {
let navBarOffset = min(0, self.toolbarHeight - intersection.height)
self.viewCoordinator.constraints.navigationBarContainerBottom.constant = navBarOffset
self.viewCoordinator.constraints.navigationBarCollectionViewBottom.constant = navBarOffset
UIView.animate(withDuration: duration, delay: 0, options: animationCurve) {
self.viewCoordinator.navigationBarContainer.superview?.layoutIfNeeded()
}
Expand Down Expand Up @@ -1089,7 +1090,6 @@ class MainViewController: UIViewController {
viewCoordinator.omniBar.enterPadState()

swipeTabsCoordinator?.isEnabled = false
// disableSwipeTabs()
}

private func applySmallWidth() {
Expand All @@ -1098,8 +1098,6 @@ class MainViewController: UIViewController {
viewCoordinator.omniBar.enterPhoneState()

swipeTabsCoordinator?.isEnabled = featureFlagger.isFeatureOn(.swipeTabs)

// enableSwipeTabs()
}

@discardableResult
Expand Down
Loading

0 comments on commit c04ff1c

Please sign in to comment.