⚠ Archived content — this site is no longer maintained.   Current WebKit documentation is at docs.webkit.org.

Changeset 258092 in webkit


Ignore:
Timestamp:
Mar 7, 2020, 7:41:24 PM (6 years ago)
Author:
Megan Gardner
Message:

Adopt UIContextMenu for WKFileUploadPanel
https://bugs.webkit.org/show_bug.cgi?id=208687

Reviewed by Tim Horton.

Source/WebCore:

New string, no tests needed.

  • en.lproj/Localizable.strings:

Source/WebKit:

Move from the depricated UIDocumentMenuViewController to UIContextMenu.
UI change, not currently testable.

  • Platform/spi/ios/UIKitSPI.h:
  • UIProcess/ios/forms/WKFileUploadPanel.mm:

(-[WKFileUploadPanel dealloc]):
(-[WKFileUploadPanel presentWithParameters:resultListener:]):
(-[WKFileUploadPanel dismiss]):
(-[WKFileUploadPanel _browseFilesButtonLabel]):
(-[WKFileUploadPanel contextMenuInteraction:previewForHighlightingMenuWithConfiguration:]):
(-[WKFileUploadPanel _contextMenuInteraction:styleForMenuWithConfiguration:]):
(-[WKFileUploadPanel contextMenuInteraction:configurationForMenuAtLocation:]):
(-[WKFileUploadPanel contextMenuInteraction:willEndForConfiguration:animator:]):
(-[WKFileUploadPanel _removeInteraction]):
(-[WKFileUploadPanel _initInteraction]):
(-[WKFileUploadPanel _showFilePickerMenu]):
(-[WKFileUploadPanel _showDocumentPickerMenu]):
(-[WKFileUploadPanel _presentPopoverWithContentViewController:animated:]):
(-[WKFileUploadPanel _presentFullscreenViewController:animated:]):
(photoLibraryIcon): Deleted.
(cameraIcon): Deleted.
(-[WKFileUploadPanel documentMenu:didPickDocumentPicker:]): Deleted.
(-[WKFileUploadPanel documentMenuWasCancelled:]): Deleted.

Location:
trunk/Source
Files:
5 edited

Legend:

Unmodified
Added
Removed
  • trunk/Source/WebCore/ChangeLog

    r258087 r258092  
     12020-03-07  Megan Gardner  <megan_gardner@apple.com>
     2
     3        Adopt UIContextMenu for WKFileUploadPanel
     4        https://bugs.webkit.org/show_bug.cgi?id=208687
     5
     6        Reviewed by Tim Horton.
     7
     8        New string, no tests needed.
     9
     10        * en.lproj/Localizable.strings:
     11
    1122020-03-07  Daniel Bates  <dabates@apple.com>
    213
  • trunk/Source/WebCore/en.lproj/Localizable.strings

    r257877 r258092  
    155155"Book with Apple Pay" = "Book with Apple Pay";
    156156
     157/* File Upload alert sheet button string for choosing an existing file from the file brower */
     158"Browse (file upload action sheet)" = "Browse";
     159
    157160/* Option in segmented control for inserting a bulleted list in text editing */
    158161"Bulleted list" = "Bulleted list";
  • trunk/Source/WebKit/ChangeLog

    r258090 r258092  
     12020-03-07  Megan Gardner  <megan_gardner@apple.com>
     2
     3        Adopt UIContextMenu for WKFileUploadPanel
     4        https://bugs.webkit.org/show_bug.cgi?id=208687
     5
     6        Reviewed by Tim Horton.
     7
     8        Move from the depricated UIDocumentMenuViewController to UIContextMenu.
     9        UI change, not currently testable.
     10
     11        * Platform/spi/ios/UIKitSPI.h:
     12        * UIProcess/ios/forms/WKFileUploadPanel.mm:
     13        (-[WKFileUploadPanel dealloc]):
     14        (-[WKFileUploadPanel presentWithParameters:resultListener:]):
     15        (-[WKFileUploadPanel dismiss]):
     16        (-[WKFileUploadPanel _browseFilesButtonLabel]):
     17        (-[WKFileUploadPanel contextMenuInteraction:previewForHighlightingMenuWithConfiguration:]):
     18        (-[WKFileUploadPanel _contextMenuInteraction:styleForMenuWithConfiguration:]):
     19        (-[WKFileUploadPanel contextMenuInteraction:configurationForMenuAtLocation:]):
     20        (-[WKFileUploadPanel contextMenuInteraction:willEndForConfiguration:animator:]):
     21        (-[WKFileUploadPanel _removeInteraction]):
     22        (-[WKFileUploadPanel _initInteraction]):
     23        (-[WKFileUploadPanel _showFilePickerMenu]):
     24        (-[WKFileUploadPanel _showDocumentPickerMenu]):
     25        (-[WKFileUploadPanel _presentPopoverWithContentViewController:animated:]):
     26        (-[WKFileUploadPanel _presentFullscreenViewController:animated:]):
     27        (photoLibraryIcon): Deleted.
     28        (cameraIcon): Deleted.
     29        (-[WKFileUploadPanel documentMenu:didPickDocumentPicker:]): Deleted.
     30        (-[WKFileUploadPanel documentMenuWasCancelled:]): Deleted.
     31
    1322020-03-07  Peng Liu  <peng.liu6@apple.com>
    233
  • trunk/Source/WebKit/Platform/spi/ios/UIKitSPI.h

    r258088 r258092  
    10991099@end
    11001100
     1101typedef NS_ENUM(NSUInteger, _UIContextMenuLayout) {
     1102    _UIContextMenuLayoutActionsOnly = 1,
     1103    _UIContextMenuLayoutCompactMenu = 3,
     1104};
     1105
    11011106@interface _UIContextMenuStyle : NSObject <NSCopying>
     1107@property (nonatomic) _UIContextMenuLayout preferredLayout;
     1108+ (instancetype)defaultStyle;
    11021109@end
    11031110
     
    11061113@property (nonatomic, strong, setter=_setOverridePositionTrackingView:) UIView *overridePositionTrackingView;
    11071114@end
     1115
     1116@interface UIContextMenuInteraction ()
     1117- (void)_presentMenuAtLocation:(CGPoint)location;
     1118@end
     1119
    11081120#endif // USE(UICONTEXTMENU)
    11091121
  • trunk/Source/WebKit/UIProcess/ios/forms/WKFileUploadPanel.mm

    r253663 r258092  
    4848#import <WebCore/UTIUtilities.h>
    4949#import <wtf/RetainPtr.h>
     50#import <wtf/WeakObjCPtr.h>
    5051#import <wtf/text/StringView.h>
    5152
     
    6667    }
    6768    return false;
    68 }
    69 
    70 #pragma mark - Document picker icons
    71 
    72 static inline UIImage *photoLibraryIcon()
    73 {
    74     return _UIImageGetWebKitPhotoLibraryIcon();
    75 }
    76 
    77 static inline UIImage *cameraIcon()
    78 {
    79     return _UIImageGetWebKitTakePhotoOrVideoIcon();
    8069}
    8170
     
    162151#pragma mark - WKFileUploadPanel
    163152
    164 @interface WKFileUploadPanel () <UIPopoverControllerDelegate, UINavigationControllerDelegate, UIImagePickerControllerDelegate, UIDocumentPickerDelegate, UIDocumentMenuDelegate>
     153@interface WKFileUploadPanel () <UIPopoverControllerDelegate, UINavigationControllerDelegate, UIImagePickerControllerDelegate, UIDocumentPickerDelegate, UIContextMenuInteractionDelegate>
    165154@end
    166155
    167156@implementation WKFileUploadPanel {
    168     WKContentView *_view;
     157    WeakObjCPtr<WKContentView> _view;
    169158    RefPtr<WebKit::WebOpenPanelResultListenerProxy> _listener;
    170159    RetainPtr<NSArray> _mimeTypes;
     
    177166    RetainPtr<UIPopoverController> _presentationPopover; // iPad for action sheet and Photo Library.
    178167    ALLOW_DEPRECATED_DECLARATIONS_END
    179     RetainPtr<UIDocumentMenuViewController> _documentMenuController;
     168    RetainPtr<UIContextMenuInteraction> _documentContextMenuInteraction;
    180169    RetainPtr<UIDocumentPickerViewController> _documentPickerController;
    181170    WebCore::MediaCaptureType _mediaCaptureType;
     
    194183    [_imagePicker setDelegate:nil];
    195184    [_presentationPopover setDelegate:nil];
    196     [_documentMenuController setDelegate:nil];
    197185    [_documentPickerController setDelegate:nil];
     186    [self removeContextMenuInteraction];
    198187
    199188    [super dealloc];
     
    279268    }
    280269
    281     [self _showDocumentPickerMenu];
     270    [self showDocumentPickerMenu];
    282271}
    283272
     
    287276    // If there is any kind of view controller presented on this view, it will be removed.
    288277   
    289     [[UIViewController _viewControllerForFullScreenPresentationFromView:_view] dismissViewControllerAnimated:NO completion:nil];
     278    [[UIViewController _viewControllerForFullScreenPresentationFromView:_view.getAutoreleased()] dismissViewControllerAnimated:NO completion:nil];
    290279   
    291280    [_presentationPopover setDelegate:nil];
     
    319308
    320309    NSArray *mediaTypes = UTIsForMIMETypes(_mimeTypes.get()).allObjects;
    321     BOOL containsImageMediaType = !mediaTypes.count || arrayContainsUTIThatConformsTo(mediaTypes, kUTTypeImage);
    322     BOOL containsVideoMediaType = !mediaTypes.count || arrayContainsUTIThatConformsTo(mediaTypes, kUTTypeMovie);
    323     if (containsImageMediaType || containsVideoMediaType) {
     310    BOOL allowsImageMediaType = !mediaTypes.count || arrayContainsUTIThatConformsTo(mediaTypes, kUTTypeImage);
     311    BOOL allowsVideoMediaType = !mediaTypes.count || arrayContainsUTIThatConformsTo(mediaTypes, kUTTypeMovie);
     312    if (allowsImageMediaType || allowsVideoMediaType) {
    324313        [actionTitles addObject:@"Photo Library"];
    325         if (containsImageMediaType && containsVideoMediaType)
     314        if (allowsImageMediaType && allowsVideoMediaType)
    326315            [actionTitles addObject:@"Take Photo or Video"];
    327         else if (containsVideoMediaType)
     316        else if (allowsVideoMediaType)
    328317            [actionTitles addObject:@"Take Video"];
    329318        else
     
    387376#pragma mark - Source selection menu
    388377
     378- (NSString *)_browseFilesButtonLabel
     379{
     380    return WEB_UI_STRING_KEY("Browse", "Browse (file upload action sheet)", "File Upload alert sheet button string for choosing an existing file from the file brower");
     381}
     382
    389383- (NSString *)_photoLibraryButtonLabel
    390384{
     
    404398}
    405399
    406 - (void)_showDocumentPickerMenu
     400- (UITargetedPreview *)contextMenuInteraction:(UIContextMenuInteraction *)interaction previewForHighlightingMenuWithConfiguration:(UIContextMenuConfiguration *)configuration
     401{
     402    RetainPtr<UIPreviewParameters> unusedPreviewParameters = adoptNS([[UIPreviewParameters alloc] init]);
     403    RetainPtr<UIPreviewTarget> previewTarget = adoptNS([[UIPreviewTarget alloc] initWithContainer:_view.getAutoreleased() center:CGPointMake(_interactionPoint.x, _interactionPoint.y)]);
     404    RetainPtr<UITargetedPreview> preview = adoptNS([[UITargetedPreview alloc] initWithView:_view.getAutoreleased() parameters:unusedPreviewParameters.get() target:previewTarget.get()]);
     405
     406    return preview.autorelease();
     407}
     408
     409- (_UIContextMenuStyle *)_contextMenuInteraction:(UIContextMenuInteraction *)interaction styleForMenuWithConfiguration:(UIContextMenuConfiguration *)configuration
     410{
     411    _UIContextMenuStyle *style = [_UIContextMenuStyle defaultStyle];
     412    style.preferredLayout = _UIContextMenuLayoutCompactMenu;
     413    return style;
     414}
     415
     416- (UIContextMenuConfiguration *)contextMenuInteraction:(UIContextMenuInteraction *)interaction configurationForMenuAtLocation:(CGPoint)location {
     417
     418    UIContextMenuActionProvider actionMenuProvider = [self, weakSelf = WeakObjCPtr<WKFileUploadPanel>(self)] (NSArray<UIMenuElement *> *) -> UIMenu * {
     419        NSArray *actions;
     420        NSArray *mediaTypes = UTIsForMIMETypes(_mimeTypes.get()).allObjects;
     421
     422        BOOL allowsImageMediaType = !mediaTypes.count || arrayContainsUTIThatConformsTo(mediaTypes, kUTTypeImage);
     423        BOOL allowsVideoMediaType = !mediaTypes.count || arrayContainsUTIThatConformsTo(mediaTypes, kUTTypeMovie);
     424        auto strongSelf = weakSelf.get();
     425       
     426        if (!strongSelf)
     427            return nil;
     428       
     429        UIAction *browseAction = [UIAction actionWithTitle:[strongSelf _browseFilesButtonLabel] image:[UIImage systemImageNamed:@"ellipsis"] identifier:@"browse" handler:^(__kindof UIAction *action) {
     430            [self showFilePickerMenu];
     431        }];
     432
     433        UIAction *photoAction = [UIAction actionWithTitle:[strongSelf _photoLibraryButtonLabel] image:[UIImage systemImageNamed:@"rectangle.on.rectangle"] identifier:@"photo" handler:^(__kindof UIAction *action) {
     434            [self _showPhotoPickerWithSourceType:UIImagePickerControllerSourceTypePhotoLibrary];
     435        }];
     436
     437        if ([UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera]) {
     438            NSString *cameraString = [strongSelf _cameraButtonLabelAllowingPhoto:allowsImageMediaType allowingVideo:allowsVideoMediaType];
     439            UIAction *cameraAction = [UIAction actionWithTitle:cameraString image:[UIImage systemImageNamed:@"camera.fill"] identifier:@"camera" handler:^(__kindof UIAction *action) {
     440                _usingCamera = YES;
     441                [self _showPhotoPickerWithSourceType:UIImagePickerControllerSourceTypeCamera];
     442            }];
     443            actions = @[photoAction, cameraAction, browseAction];
     444        } else
     445            actions = @[photoAction, browseAction];
     446
     447        return [UIMenu menuWithTitle:@"" children:actions];
     448    };
     449   
     450    return [UIContextMenuConfiguration configurationWithIdentifier:nil previewProvider:nil actionProvider:actionMenuProvider];
     451}
     452
     453- (void)contextMenuInteraction:(UIContextMenuInteraction *)interaction willEndForConfiguration:(UIContextMenuConfiguration *)configuration animator:(id<UIContextMenuInteractionAnimating>)animator
     454{
     455    [animator addCompletion:^{
     456        [self removeContextMenuInteraction];
     457        [self _cancel];
     458    }];
     459}
     460
     461- (void)removeContextMenuInteraction
     462{
     463    if (_documentContextMenuInteraction) {
     464        [_view removeInteraction:_documentContextMenuInteraction.get()];
     465        _documentContextMenuInteraction = nil;
     466    }
     467}
     468
     469- (void)ensureContextMenuInteraction
     470{
     471    if (!_documentContextMenuInteraction) {
     472        _documentContextMenuInteraction = adoptNS([[UIContextMenuInteraction alloc] initWithDelegate:self]);
     473        [_view addInteraction:_documentContextMenuInteraction.get()];
     474    }
     475}
     476
     477- (void)showFilePickerMenu
    407478{
    408479    NSArray *mediaTypes = UTIsForMIMETypes(_mimeTypes.get()).allObjects;
    409 
    410     BOOL containsImageMediaType = !mediaTypes.count || arrayContainsUTIThatConformsTo(mediaTypes, kUTTypeImage);
    411     BOOL containsVideoMediaType = !mediaTypes.count || arrayContainsUTIThatConformsTo(mediaTypes, kUTTypeMovie);
    412 
     480    NSArray *documentTypes = mediaTypes.count ? mediaTypes : @[(__bridge NSString *)kUTTypeItem];
     481   
     482    _documentPickerController = adoptNS([[UIDocumentPickerViewController alloc] initWithDocumentTypes:documentTypes inMode:UIDocumentPickerModeImport]);
     483    [_documentPickerController setAllowsMultipleSelection:_allowMultipleFiles];
     484    [_documentPickerController setDelegate:self];
     485    [self _presentFullscreenViewController:_documentPickerController.get() animated:YES];
     486}
     487
     488- (void)showDocumentPickerMenu
     489{
     490    NSArray *mediaTypes = UTIsForMIMETypes(_mimeTypes.get()).allObjects;
     491   
    413492#if PLATFORM(MACCATALYST)
    414493    // FIXME 49961589: Support picking media with UIImagePickerController
    415494    BOOL shouldPresentDocumentMenuViewController = NO;
    416495#else
    417     BOOL shouldPresentDocumentMenuViewController = containsImageMediaType || containsVideoMediaType;
     496    BOOL allowsImageMediaType = !mediaTypes.count || arrayContainsUTIThatConformsTo(mediaTypes, kUTTypeImage);
     497    BOOL allowsVideoMediaType = !mediaTypes.count || arrayContainsUTIThatConformsTo(mediaTypes, kUTTypeMovie);
     498    BOOL shouldPresentDocumentMenuViewController = allowsImageMediaType || allowsVideoMediaType;
    418499#endif
    419 
    420     NSArray *documentTypes = mediaTypes.count ? mediaTypes : @[(__bridge NSString *)kUTTypeItem];
    421500    if (shouldPresentDocumentMenuViewController) {
    422         // FIXME 49979442: UIDocumentMenuViewController is deprecated. Use UIDocumentPickerViewController instead to support multiple file selection.
    423         _documentMenuController = adoptNS([[UIDocumentMenuViewController alloc] _initIgnoringApplicationEntitlementForImportOfTypes:documentTypes]);
    424         [_documentMenuController setDelegate:self];
    425 
    426         [_documentMenuController addOptionWithTitle:[self _photoLibraryButtonLabel] image:photoLibraryIcon() order:UIDocumentMenuOrderFirst handler:^{
    427             [self _showPhotoPickerWithSourceType:UIImagePickerControllerSourceTypePhotoLibrary];
    428         }];
    429 
    430         if ([UIImagePickerController isSourceTypeAvailable:UIImagePickerControllerSourceTypeCamera]) {
    431             NSString *cameraString = [self _cameraButtonLabelAllowingPhoto:containsImageMediaType allowingVideo:containsVideoMediaType];
    432             [_documentMenuController addOptionWithTitle:cameraString image:cameraIcon() order:UIDocumentMenuOrderFirst handler:^{
    433                 _usingCamera = YES;
    434                 [self _showPhotoPickerWithSourceType:UIImagePickerControllerSourceTypeCamera];
    435             }];
    436         }
    437 
    438         [self _presentMenuOptionForCurrentInterfaceIdiom:_documentMenuController.get()];
    439     } else {
    440         // Image and Video types are not accepted so bypass the menu and open the file picker directly.
    441         _documentPickerController = adoptNS([[UIDocumentPickerViewController alloc] initWithDocumentTypes:documentTypes inMode:UIDocumentPickerModeImport]);
    442         [_documentPickerController setAllowsMultipleSelection:_allowMultipleFiles];
    443         [_documentPickerController setDelegate:self];
    444         [self _presentFullscreenViewController:_documentPickerController.get() animated:YES];
    445     }
    446 
    447     // Clear out the view controller we just presented. Don't save a reference to the UIDocumentMenuViewController / UIDocumentPickerViewController as it is self dismissing.
     501        [self ensureContextMenuInteraction];
     502        [_documentContextMenuInteraction _presentMenuAtLocation:CGPointMake(_interactionPoint.x, _interactionPoint.y)];
     503    } else // Image and Video types are not accepted so bypass the menu and open the file picker directly.
     504        [self showFilePickerMenu];
     505   
     506    // Clear out the view controller we just presented. Don't save a reference to the UIDocumentPickerViewController as it is self dismissing.
    448507    _presentationViewController = nil;
    449508}
     
    521580    ALLOW_DEPRECATED_DECLARATIONS_END
    522581    [_presentationPopover setDelegate:self];
    523     [_presentationPopover presentPopoverFromRect:CGRectIntegral(CGRectMake(_interactionPoint.x, _interactionPoint.y, 1, 1)) inView:_view permittedArrowDirections:UIPopoverArrowDirectionAny animated:animated];
     582    [_presentationPopover presentPopoverFromRect:CGRectIntegral(CGRectMake(_interactionPoint.x, _interactionPoint.y, 1, 1)) inView:_view.getAutoreleased() permittedArrowDirections:UIPopoverArrowDirectionAny animated:animated];
    524583}
    525584
     
    528587    [self _dismissDisplayAnimated:animated];
    529588
    530     _presentationViewController = [UIViewController _viewControllerForFullScreenPresentationFromView:_view];
     589    _presentationViewController = [UIViewController _viewControllerForFullScreenPresentationFromView:_view.getAutoreleased()];
    531590    [_presentationViewController presentViewController:viewController animated:animated completion:nil];
    532591}
     
    538597ALLOW_DEPRECATED_IMPLEMENTATIONS_END
    539598{
    540     [self _cancel];
    541 }
    542 
    543 #pragma mark - UIDocumentMenuDelegate implementation
    544 
    545 - (void)documentMenu:(UIDocumentMenuViewController *)documentMenu didPickDocumentPicker:(UIDocumentPickerViewController *)documentPicker
    546 {
    547     documentPicker.delegate = self;
    548     [self _presentFullscreenViewController:documentPicker animated:YES];
    549 }
    550 
    551 - (void)documentMenuWasCancelled:(UIDocumentMenuViewController *)documentMenu
    552 {
    553     [self _dismissDisplayAnimated:YES];
    554599    [self _cancel];
    555600}
Note: See TracChangeset for help on using the changeset viewer.