Create a WKWebView subclass (ugh) in order to hide items in its contextual menu. Fix #120.

This commit is contained in:
Brent Simmons
2018-02-10 11:16:09 -08:00
parent d46ae4df33
commit 9ac2d7d033
3 changed files with 72 additions and 2 deletions

View File

@@ -16,7 +16,7 @@ final class DetailViewController: NSViewController, WKNavigationDelegate, WKUIDe
@IBOutlet var containerView: DetailContainerView!
var webview: WKWebView!
var webview: DetailWebView!
var noSelectionView: NoSelectionView!
var article: Article? {
@@ -54,7 +54,7 @@ final class DetailViewController: NSViewController, WKNavigationDelegate, WKUIDe
userContentController.add(self, name: MessageName.mouseDidExit)
configuration.userContentController = userContentController
webview = WKWebView(frame: self.view.bounds, configuration: configuration)
webview = DetailWebView(frame: self.view.bounds, configuration: configuration)
webview.uiDelegate = self
webview.navigationDelegate = self
webview.translatesAutoresizingMaskIntoConstraints = false

View File

@@ -0,0 +1,66 @@
//
// DetailWebView.swift
// Evergreen
//
// Created by Brent Simmons on 2/10/18.
// Copyright © 2018 Ranchero Software. All rights reserved.
//
import AppKit
import WebKit
// Theres no API for affecting a WKWebViews contextual menu.
// (WebView had API for this.)
//
// This a minor hack. It hides unwanted menu items.
// The menu item identifiers are not documented anywhere;
// they could change, and this code would need updating.
final class DetailWebView: WKWebView {
// MARK: NSView
override func willOpenMenu(_ menu: NSMenu, with event: NSEvent) {
for menuItem in menu.items {
if shouldHideMenuItem(menuItem) {
menuItem.isHidden = true
}
}
super.willOpenMenu(menu, with: event)
}
}
private extension NSUserInterfaceItemIdentifier {
static let DetailMenuItemIdentifierReload = NSUserInterfaceItemIdentifier(rawValue: "WKMenuItemIdentifierReload")
static let DetailMenuItemIdentifierOpenLink = NSUserInterfaceItemIdentifier(rawValue: "WKMenuItemIdentifierOpenLink")
}
private extension DetailWebView {
static let menuItemIdentifiersToHide: [NSUserInterfaceItemIdentifier] = [.DetailMenuItemIdentifierReload, .DetailMenuItemIdentifierOpenLink]
static let menuItemIdentifierMatchStrings = ["newwindow", "download"]
func shouldHideMenuItem(_ menuItem: NSMenuItem) -> Bool {
guard let identifier = menuItem.identifier else {
return false
}
if DetailWebView.menuItemIdentifiersToHide.contains(identifier) {
return true
}
let lowerIdentifier = identifier.rawValue.lowercased()
for matchString in DetailWebView.menuItemIdentifierMatchStrings {
if lowerIdentifier.contains(matchString) {
return true
}
}
return false
}
}