Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[BottomSheet] Add property so clients can set a custom height for bottom sheet #5139

Merged
merged 9 commits into from
Sep 18, 2018
Merged

[BottomSheet] Add property so clients can set a custom height for bottom sheet #5139

merged 9 commits into from
Sep 18, 2018

Conversation

codeman7
Copy link
Contributor

@codeman7 codeman7 commented Sep 17, 2018

Previously clients could only set a custom height for bottom sheet by setting the preferredContentSize this adds a property so clients can set a specific height and not touch preferredContentSize.

Related to #4945

self.presentationController.preferredSheetHeight = preferredSheetHeight;

// When
[self.presentationController updatePreferredSheetHeight:self.presentationController.presentedViewController.preferredContentSize.height];

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-format suggested the following change:

-  [self.presentationController updatePreferredSheetHeight:self.presentationController.presentedViewController.preferredContentSize.height];
+  [self.presentationController
+      updatePreferredSheetHeight:self.presentationController.presentedViewController
+                                     .preferredContentSize.height];

self.presentationController.preferredSheetHeight = preferredSheetHeight;

// When
[self.presentationController updatePreferredSheetHeight:self.presentationController.presentedViewController.preferredContentSize.height];

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-format suggested the following change:

-  [self.presentationController updatePreferredSheetHeight:self.presentationController.presentedViewController.preferredContentSize.height];
+  [self.presentationController
+      updatePreferredSheetHeight:self.presentationController.presentedViewController
+                                     .preferredContentSize.height];

@material-automation
Copy link

API diff detected the following changes

BottomSheet

MDCBottomSheetTransitionController

new property: preferredSheetHeight in MDCBottomSheetTransitionController

MDCBottomSheetPresentationController

new property: preferredSheetHeight in MDCBottomSheetPresentationController

Copy link
Contributor

@jverkoey jverkoey left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We may need a test that checks what happens when preferredSheetHeight is set to a positive value and then back to zero.


@note This will override setting the preferredContentSize if a positive value is passed.
@note If a non-positive value is passed then the sheet will open up to either half the screen
height or the size of the contentViewController whatever value is smaller.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

tip: I find documentation like this can be a bit easier to parse if written as a logical statement, like so:

If this, then this. Otherwise, this.

So in this case:

If a positive value is passed, overrides preferredContentSize. Otherwise, the sheet will open up to...

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Done

/**
This is used to set a custom height on the sheet view.

@note This will override setting the preferredContentSize if a positive value is passed.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

What does override mean? Please add the answer as documentation.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think I made this more clear.

@@ -179,9 +179,11 @@ - (void)viewWillTransitionToSize:(CGSize)size

@param preferredSheetHeight If positive, the new value for @sheetView.preferredSheetHeight.
*/
- (void)setPreferredSheetHeight:(CGFloat)preferredSheetHeight {
- (void)updatePreferredSheetHeight:(CGFloat)preferredSheetHeight {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think this method doesn't need an argument because you're able to pull the information from either self.presentedViewController.preferredContentSize.height or self.preferredSheetHeight depending on the value of self.preferredSheetHeight. Removing this argument may simplify both this method and the call sites as a result.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The method name in this case could likely be renamed to updatePreferredSheetHeight or something similar to indicate that the value has already changed and we now want to update the sheetView's preferredSheetHeight property accordingly.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I believe #5125 updated this method to make it more testable, I can revert that change if you'd like.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Ah! I see.

I think we don't need to revert that change - you're increasing the surface area of the APIs here to include both a setter and a "did change" method that commits the results to the sheetView.

Prior to this PR, the tests relied on the method previously named setPreferredSheetHeight. The tests were using this method to propagate changes to the sheetView.

After this PR, setPreferredSheetHeight has a different meaning and you're introducing a new method, updatePreferredSheetHeight that models the old meaning of setPreferredSheetHeight.

You can still test as before, but your existing tests will now call the updatePreferredSheetHeight API to propagate changes to the sheetView instead of setPreferredSheetHeight, except in cases where you're testing the new property's behavior specifically.

Copy link
Contributor

@jverkoey jverkoey Sep 17, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Tying this back to my original suggestion, if you remove updatePreferredSheetHeight's argument then your tests will still be able to call this method, but prior to doing so they must set the relevant properties that they are testing (either preferredSheetHeight or preferredContentSize.height).

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Spoke over gvc:

  1. Partial revert of [BottomSheet] Use setter for sheet view height. #5125 so that we still have an updatePreferredSheetHeight method that doesn't accept arguments.
  2. updatePreferredSheetHeight will be exposed to tests so that we can "flush" the calculated sheet height to sheetView once we've configured either preferredSheetHeight or preferredContentSize.height.

Copy link
Contributor

@jverkoey jverkoey Sep 17, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Also discussed the possibility of making updatePreferredSheetHeight more testable by making it stateless, but that doing so can be a follow-up exploration:

+ (CGFloat)preferredSheetHeightForViewController:(UIViewController *)viewController
                                       withFrame:(CGRect)frame
                            preferredSheetHeight:(CGFloat)preferredSheetHeight {
  CGFloat calculatedPreferredSheetHeight =
      (preferredSheetHeight > 0.f) ? preferredSheetHeight : viewController.preferredContentSize.height;
  if (MDCCGFloatEqual(calculatedPreferredSheetHeight, 0)) {
    calculatedPreferredSheetHeight = MDCRound(CGRectGetHeight(frame) / 2);
  }
  return calculatedPreferredSheetHeight;
}

_preferredSheetHeight = preferredSheetHeight;
if (preferredSheetHeight > 0.f) {
[self updatePreferredSheetHeight:preferredSheetHeight];
}
Copy link
Contributor

@jverkoey jverkoey Sep 17, 2018

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You can remove the if statement here if updatePreferredSheetHeight is changed to a updatePreferredSheetHeight-style method.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pending your feedback on reverting #5125.

Copy link
Contributor

@jverkoey jverkoey left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I'm afraid I'm still not certain I understand when someone would set preferredSheetHeight vs preferredContentSize.height. As best I can tell from the code these two properties have equivalent results.

Can you share some additional context that might help me understand the need for this new property?

@note This will override setting the preferredContentSize if a positive value is passed.
@note If a non-positive value is passed then the sheet will open up to either half the screen
height or the size of the contentViewController whatever value is smaller.
*/
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looking at the implementation of MDCSheetContainerView.m, it looks like truncatedPreferredSheetHeight always considers the contentViewController's height when determining the maximum height. This implies that preferredSheetHeight will also be capped to the content's height, which the documentation doesn't yet indicate. We may want to add a test and documentation indicating this.

E.g. pseudo-code:

preferredSheetHeight = 1000
contentViewController.scrollView.contentSize.height = 500

assertEqual(sheet.height, 500) // Docs presently imply 1000

@codeman7
Copy link
Contributor Author

Setting the preferredContentSize also effects the frame of the UIViewController.view so when you rotate or change view.frame it isn't correct, it will be the value of preferredContentSize. This makes it so that the view.frame will always be correct.

@jverkoey
Copy link
Contributor

Ah! Interesting. Who sets view.frame in reaction to preferredContentSize? Is that us?

@codeman7
Copy link
Contributor Author

In order to close #4945 I would either have to set preferredContentSize or this new property.

@@ -107,10 +107,12 @@ - (void)testSetPreferredSheetHeightZeroWhenSheetViewHasUnstandardizedFrame {
- (void)testSetPreferredSheetHeightPositiveValue {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Super-nit, please fix up the test method names. They are no longer testing setPreferredSheetHeight.

self.presentationController.sheetView = sheetView;
self.presentationController.preferredSheetHeight = 5000;


Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

clang-format suggested the following change:

-

Copy link
Contributor

@jverkoey jverkoey left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Awesome! I love how clear this is now.

@codeman7 codeman7 merged commit 553fb01 into material-components:develop Sep 18, 2018
@codeman7 codeman7 deleted the bottom-sheet-height branch October 17, 2018 21:28
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
5 participants