summaryrefslogtreecommitdiffstats
path: root/WebKit/mac
diff options
context:
space:
mode:
authorUpstream <upstream-import@none>1970-01-12 13:46:40 +0000
committerUpstream <upstream-import@none>1970-01-12 13:46:40 +0000
commitd8543bb6618c17b12da906afa77d216f58cf4058 (patch)
treec58dc05ed86825bd0ef8d305d58c8205106b540f /WebKit/mac
downloadexternal_webkit-d8543bb6618c17b12da906afa77d216f58cf4058.zip
external_webkit-d8543bb6618c17b12da906afa77d216f58cf4058.tar.gz
external_webkit-d8543bb6618c17b12da906afa77d216f58cf4058.tar.bz2
external/webkit r30707
Diffstat (limited to 'WebKit/mac')
-rw-r--r--WebKit/mac/Carbon/CarbonUtils.h60
-rw-r--r--WebKit/mac/Carbon/CarbonUtils.m132
-rw-r--r--WebKit/mac/Carbon/CarbonWindowAdapter.h66
-rw-r--r--WebKit/mac/Carbon/CarbonWindowAdapter.m1046
-rw-r--r--WebKit/mac/Carbon/CarbonWindowContentView.h33
-rw-r--r--WebKit/mac/Carbon/CarbonWindowContentView.m37
-rw-r--r--WebKit/mac/Carbon/CarbonWindowFrame.h43
-rw-r--r--WebKit/mac/Carbon/CarbonWindowFrame.m288
-rw-r--r--WebKit/mac/Carbon/HIViewAdapter.h38
-rw-r--r--WebKit/mac/Carbon/HIViewAdapter.m248
-rw-r--r--WebKit/mac/Carbon/HIWebView.h129
-rw-r--r--WebKit/mac/Carbon/HIWebView.m1639
-rw-r--r--WebKit/mac/Configurations/Base.xcconfig37
-rw-r--r--WebKit/mac/Configurations/DebugRelease.xcconfig11
-rw-r--r--WebKit/mac/Configurations/Version.xcconfig27
-rw-r--r--WebKit/mac/Configurations/WebKit.xcconfig19
-rw-r--r--WebKit/mac/DOM/WebDOMOperations.h111
-rw-r--r--WebKit/mac/DOM/WebDOMOperations.mm341
-rw-r--r--WebKit/mac/DOM/WebDOMOperationsPrivate.h46
-rw-r--r--WebKit/mac/DefaultDelegates/WebDefaultContextMenuDelegate.h34
-rw-r--r--WebKit/mac/DefaultDelegates/WebDefaultContextMenuDelegate.mm184
-rw-r--r--WebKit/mac/DefaultDelegates/WebDefaultEditingDelegate.h33
-rw-r--r--WebKit/mac/DefaultDelegates/WebDefaultEditingDelegate.m138
-rw-r--r--WebKit/mac/DefaultDelegates/WebDefaultPolicyDelegate.h39
-rw-r--r--WebKit/mac/DefaultDelegates/WebDefaultPolicyDelegate.m117
-rw-r--r--WebKit/mac/DefaultDelegates/WebDefaultScriptDebugDelegate.h34
-rw-r--r--WebKit/mac/DefaultDelegates/WebDefaultScriptDebugDelegate.m96
-rw-r--r--WebKit/mac/DefaultDelegates/WebDefaultUIDelegate.h36
-rw-r--r--WebKit/mac/DefaultDelegates/WebDefaultUIDelegate.m229
-rw-r--r--WebKit/mac/DefaultDelegates/WebScriptDebugServer.h94
-rw-r--r--WebKit/mac/DefaultDelegates/WebScriptDebugServer.m381
-rw-r--r--WebKit/mac/DefaultDelegates/WebScriptDebugServerPrivate.h82
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/JSLock.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/SavedBuiltins.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/SymbolTable.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/collector.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/dtoa.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/function.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/identifier.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/internal.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/interpreter.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/lookup.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/object.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/operations.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/protect.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/string_object.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/kjs/value.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/pcre/pcre.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/ASCIICType.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/AlwaysInline.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/Assertions.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/DisallowCType.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/FastMalloc.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/Forward.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/GetPtr.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/HashCountedSet.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/HashMap.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/HashSet.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/HashTraits.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/ListHashSet.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/ListRefPtr.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/Locker.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/MathExtras.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/Noncopyable.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/OwnArrayPtr.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/OwnPtr.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/PassRefPtr.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/Platform.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/RefCounted.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/RefPtr.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/RetainPtr.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/Threading.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/Vector.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/VectorTraits.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/unicode/Unicode.h1
-rw-r--r--WebKit/mac/ForwardingHeaders/wtf/unicode/icu/UnicodeIcu.h1
-rw-r--r--WebKit/mac/History/WebBackForwardList.h190
-rw-r--r--WebKit/mac/History/WebBackForwardList.mm279
-rw-r--r--WebKit/mac/History/WebBackForwardListInternal.h41
-rw-r--r--WebKit/mac/History/WebBackForwardListPrivate.h42
-rw-r--r--WebKit/mac/History/WebHistory.h165
-rw-r--r--WebKit/mac/History/WebHistory.mm869
-rw-r--r--WebKit/mac/History/WebHistoryItem.h126
-rw-r--r--WebKit/mac/History/WebHistoryItem.mm520
-rw-r--r--WebKit/mac/History/WebHistoryItemInternal.h63
-rw-r--r--WebKit/mac/History/WebHistoryItemPrivate.h60
-rw-r--r--WebKit/mac/History/WebHistoryPrivate.h113
-rw-r--r--WebKit/mac/History/WebURLsWithTitles.h55
-rw-r--r--WebKit/mac/History/WebURLsWithTitles.m107
-rw-r--r--WebKit/mac/Info.plist24
-rw-r--r--WebKit/mac/MigrateHeaders.make503
-rw-r--r--WebKit/mac/Misc/OldWebAssertions.c38
-rw-r--r--WebKit/mac/Misc/WebAssertions.h35
-rw-r--r--WebKit/mac/Misc/WebCache.h35
-rw-r--r--WebKit/mac/Misc/WebCache.mm85
-rw-r--r--WebKit/mac/Misc/WebCoreStatistics.h72
-rw-r--r--WebKit/mac/Misc/WebCoreStatistics.mm187
-rw-r--r--WebKit/mac/Misc/WebDownload.h67
-rw-r--r--WebKit/mac/Misc/WebDownload.m240
-rw-r--r--WebKit/mac/Misc/WebDownloadInternal.h41
-rw-r--r--WebKit/mac/Misc/WebElementDictionary.h42
-rw-r--r--WebKit/mac/Misc/WebElementDictionary.mm250
-rw-r--r--WebKit/mac/Misc/WebGraphicsExtras.c57
-rw-r--r--WebKit/mac/Misc/WebGraphicsExtras.h37
-rw-r--r--WebKit/mac/Misc/WebIconDatabase.h146
-rw-r--r--WebKit/mac/Misc/WebIconDatabase.mm669
-rw-r--r--WebKit/mac/Misc/WebIconDatabaseDelegate.h35
-rw-r--r--WebKit/mac/Misc/WebIconDatabaseInternal.h49
-rw-r--r--WebKit/mac/Misc/WebIconDatabasePrivate.h59
-rw-r--r--WebKit/mac/Misc/WebKit.h52
-rw-r--r--WebKit/mac/Misc/WebKitErrors.h59
-rw-r--r--WebKit/mac/Misc/WebKitErrors.m163
-rw-r--r--WebKit/mac/Misc/WebKitErrorsPrivate.h53
-rw-r--r--WebKit/mac/Misc/WebKitLogging.h85
-rw-r--r--WebKit/mac/Misc/WebKitLogging.m115
-rw-r--r--WebKit/mac/Misc/WebKitNSStringExtras.h57
-rw-r--r--WebKit/mac/Misc/WebKitNSStringExtras.m343
-rw-r--r--WebKit/mac/Misc/WebKitStatistics.h41
-rw-r--r--WebKit/mac/Misc/WebKitStatistics.m72
-rw-r--r--WebKit/mac/Misc/WebKitStatisticsPrivate.h34
-rw-r--r--WebKit/mac/Misc/WebKitSystemBits.h41
-rw-r--r--WebKit/mac/Misc/WebKitSystemBits.m85
-rw-r--r--WebKit/mac/Misc/WebKitVersionChecks.h60
-rw-r--r--WebKit/mac/Misc/WebKitVersionChecks.m45
-rw-r--r--WebKit/mac/Misc/WebLocalizableStrings.h68
-rw-r--r--WebKit/mac/Misc/WebLocalizableStrings.m60
-rw-r--r--WebKit/mac/Misc/WebNSArrayExtras.h36
-rw-r--r--WebKit/mac/Misc/WebNSArrayExtras.m58
-rw-r--r--WebKit/mac/Misc/WebNSAttributedStringExtras.h38
-rw-r--r--WebKit/mac/Misc/WebNSAttributedStringExtras.mm556
-rw-r--r--WebKit/mac/Misc/WebNSControlExtras.h33
-rw-r--r--WebKit/mac/Misc/WebNSControlExtras.m50
-rw-r--r--WebKit/mac/Misc/WebNSDataExtras.h38
-rw-r--r--WebKit/mac/Misc/WebNSDataExtras.m395
-rw-r--r--WebKit/mac/Misc/WebNSDataExtrasPrivate.h35
-rw-r--r--WebKit/mac/Misc/WebNSDictionaryExtras.h46
-rw-r--r--WebKit/mac/Misc/WebNSDictionaryExtras.m107
-rw-r--r--WebKit/mac/Misc/WebNSEventExtras.h41
-rw-r--r--WebKit/mac/Misc/WebNSEventExtras.m82
-rw-r--r--WebKit/mac/Misc/WebNSFileManagerExtras.h47
-rw-r--r--WebKit/mac/Misc/WebNSFileManagerExtras.m346
-rw-r--r--WebKit/mac/Misc/WebNSImageExtras.h40
-rw-r--r--WebKit/mac/Misc/WebNSImageExtras.m91
-rw-r--r--WebKit/mac/Misc/WebNSNotificationCenterExtras.h39
-rw-r--r--WebKit/mac/Misc/WebNSNotificationCenterExtras.m69
-rw-r--r--WebKit/mac/Misc/WebNSObjectExtras.h54
-rw-r--r--WebKit/mac/Misc/WebNSPasteboardExtras.h89
-rw-r--r--WebKit/mac/Misc/WebNSPasteboardExtras.mm282
-rw-r--r--WebKit/mac/Misc/WebNSPrintOperationExtras.h35
-rw-r--r--WebKit/mac/Misc/WebNSPrintOperationExtras.m38
-rw-r--r--WebKit/mac/Misc/WebNSURLExtras.h95
-rw-r--r--WebKit/mac/Misc/WebNSURLExtras.mm1098
-rw-r--r--WebKit/mac/Misc/WebNSURLRequestExtras.h44
-rw-r--r--WebKit/mac/Misc/WebNSURLRequestExtras.m88
-rw-r--r--WebKit/mac/Misc/WebNSUserDefaultsExtras.h33
-rw-r--r--WebKit/mac/Misc/WebNSUserDefaultsExtras.m130
-rw-r--r--WebKit/mac/Misc/WebNSViewExtras.h73
-rw-r--r--WebKit/mac/Misc/WebNSViewExtras.m243
-rw-r--r--WebKit/mac/Misc/WebNSWindowExtras.h34
-rw-r--r--WebKit/mac/Misc/WebNSWindowExtras.m52
-rw-r--r--WebKit/mac/Misc/WebSearchableTextView.h32
-rw-r--r--WebKit/mac/Misc/WebSearchableTextView.m254
-rw-r--r--WebKit/mac/Misc/WebStringTruncator.h44
-rw-r--r--WebKit/mac/Misc/WebStringTruncator.m92
-rw-r--r--WebKit/mac/Misc/WebTypesInternal.h41
-rw-r--r--WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/classes.nib38
-rw-r--r--WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/info.nib16
-rw-r--r--WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/objects.nibbin0 -> 2931 bytes
-rw-r--r--WebKit/mac/Panels/WebAuthenticationPanel.h68
-rw-r--r--WebKit/mac/Panels/WebAuthenticationPanel.m244
-rw-r--r--WebKit/mac/Panels/WebPanelAuthenticationHandler.h45
-rw-r--r--WebKit/mac/Panels/WebPanelAuthenticationHandler.m164
-rw-r--r--WebKit/mac/Plugins/WebBaseNetscapePluginStream.h93
-rw-r--r--WebKit/mac/Plugins/WebBaseNetscapePluginStream.mm613
-rw-r--r--WebKit/mac/Plugins/WebBaseNetscapePluginView.h182
-rw-r--r--WebKit/mac/Plugins/WebBaseNetscapePluginView.mm3209
-rw-r--r--WebKit/mac/Plugins/WebBaseNetscapePluginViewInternal.h37
-rw-r--r--WebKit/mac/Plugins/WebBaseNetscapePluginViewPrivate.h53
-rw-r--r--WebKit/mac/Plugins/WebBasePluginPackage.h106
-rw-r--r--WebKit/mac/Plugins/WebBasePluginPackage.m453
-rw-r--r--WebKit/mac/Plugins/WebJavaPlugIn.h85
-rw-r--r--WebKit/mac/Plugins/WebKitPluginContainerView.h43
-rw-r--r--WebKit/mac/Plugins/WebKitPluginContainerView.mm74
-rw-r--r--WebKit/mac/Plugins/WebNetscapeDeprecatedFunctions.c50
-rw-r--r--WebKit/mac/Plugins/WebNetscapeDeprecatedFunctions.h35
-rw-r--r--WebKit/mac/Plugins/WebNetscapePluginEmbeddedView.h45
-rw-r--r--WebKit/mac/Plugins/WebNetscapePluginEmbeddedView.mm50
-rw-r--r--WebKit/mac/Plugins/WebNetscapePluginPackage.h104
-rw-r--r--WebKit/mac/Plugins/WebNetscapePluginPackage.m773
-rw-r--r--WebKit/mac/Plugins/WebNetscapePluginStream.h57
-rw-r--r--WebKit/mac/Plugins/WebNetscapePluginStream.mm154
-rw-r--r--WebKit/mac/Plugins/WebNullPluginView.h41
-rw-r--r--WebKit/mac/Plugins/WebNullPluginView.mm97
-rw-r--r--WebKit/mac/Plugins/WebPlugInStreamLoaderDelegate.h46
-rw-r--r--WebKit/mac/Plugins/WebPlugin.h95
-rw-r--r--WebKit/mac/Plugins/WebPluginContainer.h72
-rw-r--r--WebKit/mac/Plugins/WebPluginContainerCheck.h55
-rw-r--r--WebKit/mac/Plugins/WebPluginContainerCheck.mm183
-rw-r--r--WebKit/mac/Plugins/WebPluginContainerPrivate.h37
-rw-r--r--WebKit/mac/Plugins/WebPluginController.h66
-rw-r--r--WebKit/mac/Plugins/WebPluginController.mm435
-rw-r--r--WebKit/mac/Plugins/WebPluginDatabase.h63
-rw-r--r--WebKit/mac/Plugins/WebPluginDatabase.m398
-rw-r--r--WebKit/mac/Plugins/WebPluginJava.h48
-rw-r--r--WebKit/mac/Plugins/WebPluginPackage.h39
-rw-r--r--WebKit/mac/Plugins/WebPluginPackage.m116
-rw-r--r--WebKit/mac/Plugins/WebPluginPrivate.h75
-rw-r--r--WebKit/mac/Plugins/WebPluginViewFactory.h76
-rw-r--r--WebKit/mac/Plugins/WebPluginViewFactoryPrivate.h48
-rw-r--r--WebKit/mac/Plugins/WebPluginsPrivate.h33
-rw-r--r--WebKit/mac/Plugins/WebPluginsPrivate.m31
-rw-r--r--WebKit/mac/Plugins/npapi.m171
-rw-r--r--WebKit/mac/Plugins/npfunctions.h161
-rw-r--r--WebKit/mac/PublicHeaderChangesFromTiger.txt32
-rw-r--r--WebKit/mac/Resources/IDNScriptWhiteList.txt23
-rw-r--r--WebKit/mac/Resources/nullplugin.tiffbin0 -> 1562 bytes
-rw-r--r--WebKit/mac/Resources/url_icon.tiffbin0 -> 1016 bytes
-rw-r--r--WebKit/mac/Storage/WebDatabaseManager.mm140
-rw-r--r--WebKit/mac/Storage/WebDatabaseManagerInternal.h29
-rw-r--r--WebKit/mac/Storage/WebDatabaseManagerPrivate.h64
-rw-r--r--WebKit/mac/Storage/WebDatabaseTrackerClient.h40
-rw-r--r--WebKit/mac/Storage/WebDatabaseTrackerClient.mm70
-rw-r--r--WebKit/mac/Storage/WebSecurityOrigin.mm135
-rw-r--r--WebKit/mac/Storage/WebSecurityOriginInternal.h40
-rw-r--r--WebKit/mac/Storage/WebSecurityOriginPrivate.h53
-rw-r--r--WebKit/mac/WebCoreSupport/WebCachedPagePlatformData.h43
-rw-r--r--WebKit/mac/WebCoreSupport/WebChromeClient.h107
-rw-r--r--WebKit/mac/WebCoreSupport/WebChromeClient.mm428
-rw-r--r--WebKit/mac/WebCoreSupport/WebContextMenuClient.h53
-rw-r--r--WebKit/mac/WebCoreSupport/WebContextMenuClient.mm327
-rw-r--r--WebKit/mac/WebCoreSupport/WebDragClient.h43
-rw-r--r--WebKit/mac/WebCoreSupport/WebDragClient.mm146
-rw-r--r--WebKit/mac/WebCoreSupport/WebEditorClient.h118
-rw-r--r--WebKit/mac/WebCoreSupport/WebEditorClient.mm627
-rw-r--r--WebKit/mac/WebCoreSupport/WebFrameBridge.h83
-rw-r--r--WebKit/mac/WebCoreSupport/WebFrameBridge.mm741
-rw-r--r--WebKit/mac/WebCoreSupport/WebFrameLoaderClient.h219
-rw-r--r--WebKit/mac/WebCoreSupport/WebFrameLoaderClient.mm1276
-rw-r--r--WebKit/mac/WebCoreSupport/WebIconDatabaseClient.h40
-rw-r--r--WebKit/mac/WebCoreSupport/WebIconDatabaseClient.mm58
-rw-r--r--WebKit/mac/WebCoreSupport/WebImageRendererFactory.m47
-rw-r--r--WebKit/mac/WebCoreSupport/WebInspectorClient.h62
-rw-r--r--WebKit/mac/WebCoreSupport/WebInspectorClient.mm535
-rw-r--r--WebKit/mac/WebCoreSupport/WebJavaScriptTextInputPanel.h43
-rw-r--r--WebKit/mac/WebCoreSupport/WebJavaScriptTextInputPanel.m71
-rw-r--r--WebKit/mac/WebCoreSupport/WebKeyGenerator.h47
-rw-r--r--WebKit/mac/WebCoreSupport/WebKeyGenerator.m89
-rw-r--r--WebKit/mac/WebCoreSupport/WebNetscapePlugInStreamLoaderClient.h50
-rw-r--r--WebKit/mac/WebCoreSupport/WebNetscapePlugInStreamLoaderClient.mm57
-rw-r--r--WebKit/mac/WebCoreSupport/WebPasteboardHelper.h45
-rw-r--r--WebKit/mac/WebCoreSupport/WebPasteboardHelper.mm99
-rw-r--r--WebKit/mac/WebCoreSupport/WebSystemInterface.h37
-rw-r--r--WebKit/mac/WebCoreSupport/WebSystemInterface.m99
-rw-r--r--WebKit/mac/WebCoreSupport/WebViewFactory.h35
-rw-r--r--WebKit/mac/WebCoreSupport/WebViewFactory.mm487
-rw-r--r--WebKit/mac/WebInspector/WebInspector.h45
-rw-r--r--WebKit/mac/WebInspector/WebInspector.mm139
-rw-r--r--WebKit/mac/WebInspector/WebNodeHighlight.h67
-rw-r--r--WebKit/mac/WebInspector/WebNodeHighlight.m266
-rw-r--r--WebKit/mac/WebInspector/WebNodeHighlightView.h46
-rw-r--r--WebKit/mac/WebInspector/WebNodeHighlightView.m175
-rw-r--r--WebKit/mac/WebKit.exp113
-rw-r--r--WebKit/mac/WebKit.order1899
-rw-r--r--WebKit/mac/WebKitPrefix.h83
-rw-r--r--WebKit/mac/WebView/WebArchive.h97
-rw-r--r--WebKit/mac/WebView/WebArchive.m255
-rw-r--r--WebKit/mac/WebView/WebArchiver.h46
-rw-r--r--WebKit/mac/WebView/WebArchiver.mm189
-rw-r--r--WebKit/mac/WebView/WebClipView.h42
-rw-r--r--WebKit/mac/WebView/WebClipView.m116
-rw-r--r--WebKit/mac/WebView/WebDataSource.h180
-rw-r--r--WebKit/mac/WebView/WebDataSource.mm528
-rw-r--r--WebKit/mac/WebView/WebDataSourceInternal.h74
-rw-r--r--WebKit/mac/WebView/WebDataSourcePrivate.h40
-rw-r--r--WebKit/mac/WebView/WebDocument.h209
-rw-r--r--WebKit/mac/WebView/WebDocumentInternal.h90
-rw-r--r--WebKit/mac/WebView/WebDocumentLoaderMac.h63
-rw-r--r--WebKit/mac/WebView/WebDocumentLoaderMac.mm156
-rw-r--r--WebKit/mac/WebView/WebDocumentPrivate.h82
-rw-r--r--WebKit/mac/WebView/WebDynamicScrollBarsView.h71
-rw-r--r--WebKit/mac/WebView/WebDynamicScrollBarsView.m350
-rw-r--r--WebKit/mac/WebView/WebEditingDelegate.h57
-rw-r--r--WebKit/mac/WebView/WebEditingDelegatePrivate.h38
-rw-r--r--WebKit/mac/WebView/WebFormDelegate.h74
-rw-r--r--WebKit/mac/WebView/WebFormDelegate.m79
-rw-r--r--WebKit/mac/WebView/WebFormDelegatePrivate.h33
-rw-r--r--WebKit/mac/WebView/WebFrame.h210
-rw-r--r--WebKit/mac/WebView/WebFrame.mm883
-rw-r--r--WebKit/mac/WebView/WebFrameInternal.h171
-rw-r--r--WebKit/mac/WebView/WebFrameLoadDelegate.h196
-rw-r--r--WebKit/mac/WebView/WebFramePrivate.h73
-rw-r--r--WebKit/mac/WebView/WebFrameView.h103
-rw-r--r--WebKit/mac/WebView/WebFrameView.mm960
-rw-r--r--WebKit/mac/WebView/WebFrameViewInternal.h50
-rw-r--r--WebKit/mac/WebView/WebFrameViewPrivate.h65
-rw-r--r--WebKit/mac/WebView/WebHTMLRepresentation.h66
-rw-r--r--WebKit/mac/WebView/WebHTMLRepresentation.mm322
-rw-r--r--WebKit/mac/WebView/WebHTMLRepresentationPrivate.h38
-rw-r--r--WebKit/mac/WebView/WebHTMLView.h63
-rw-r--r--WebKit/mac/WebView/WebHTMLView.mm5711
-rw-r--r--WebKit/mac/WebView/WebHTMLViewInternal.h129
-rw-r--r--WebKit/mac/WebView/WebHTMLViewPrivate.h126
-rw-r--r--WebKit/mac/WebView/WebPDFRepresentation.h35
-rw-r--r--WebKit/mac/WebView/WebPDFRepresentation.m145
-rw-r--r--WebKit/mac/WebView/WebPDFView.h55
-rw-r--r--WebKit/mac/WebView/WebPDFView.mm1486
-rw-r--r--WebKit/mac/WebView/WebPolicyDelegate.h198
-rw-r--r--WebKit/mac/WebView/WebPolicyDelegate.mm120
-rw-r--r--WebKit/mac/WebView/WebPolicyDelegatePrivate.h50
-rw-r--r--WebKit/mac/WebView/WebPreferenceKeysPrivate.h85
-rw-r--r--WebKit/mac/WebView/WebPreferences.h442
-rw-r--r--WebKit/mac/WebView/WebPreferences.m996
-rw-r--r--WebKit/mac/WebView/WebPreferencesPrivate.h108
-rw-r--r--WebKit/mac/WebView/WebRenderNode.h51
-rw-r--r--WebKit/mac/WebView/WebRenderNode.mm137
-rw-r--r--WebKit/mac/WebView/WebResource.h88
-rw-r--r--WebKit/mac/WebView/WebResource.mm349
-rw-r--r--WebKit/mac/WebView/WebResourceLoadDelegate.h166
-rw-r--r--WebKit/mac/WebView/WebResourceLoadDelegatePrivate.h47
-rw-r--r--WebKit/mac/WebView/WebResourcePrivate.h56
-rw-r--r--WebKit/mac/WebView/WebScriptDebugDelegate.h136
-rw-r--r--WebKit/mac/WebView/WebScriptDebugDelegate.mm195
-rw-r--r--WebKit/mac/WebView/WebScriptDebugDelegatePrivate.h41
-rw-r--r--WebKit/mac/WebView/WebUIDelegate.h556
-rw-r--r--WebKit/mac/WebView/WebUIDelegatePrivate.h100
-rw-r--r--WebKit/mac/WebView/WebUnarchivingState.h45
-rw-r--r--WebKit/mac/WebView/WebUnarchivingState.m98
-rw-r--r--WebKit/mac/WebView/WebView.h819
-rw-r--r--WebKit/mac/WebView/WebView.mm4626
-rw-r--r--WebKit/mac/WebView/WebViewInternal.h190
-rw-r--r--WebKit/mac/WebView/WebViewPrivate.h400
-rw-r--r--WebKit/mac/icu/README4
-rw-r--r--WebKit/mac/icu/unicode/parseerr.h88
-rw-r--r--WebKit/mac/icu/unicode/platform.h267
-rw-r--r--WebKit/mac/icu/unicode/putil.h180
-rw-r--r--WebKit/mac/icu/unicode/uchar.h2798
-rw-r--r--WebKit/mac/icu/unicode/uconfig.h186
-rw-r--r--WebKit/mac/icu/unicode/uidna.h310
-rw-r--r--WebKit/mac/icu/unicode/uiter.h707
-rw-r--r--WebKit/mac/icu/unicode/umachine.h371
-rw-r--r--WebKit/mac/icu/unicode/unorm.h575
-rw-r--r--WebKit/mac/icu/unicode/urename.h1468
-rw-r--r--WebKit/mac/icu/unicode/uscript.h148
-rw-r--r--WebKit/mac/icu/unicode/ustring.h1320
-rw-r--r--WebKit/mac/icu/unicode/utf.h221
-rw-r--r--WebKit/mac/icu/unicode/utf16.h605
-rw-r--r--WebKit/mac/icu/unicode/utf8.h627
-rw-r--r--WebKit/mac/icu/unicode/utf_old.h0
-rw-r--r--WebKit/mac/icu/unicode/utypes.h745
-rw-r--r--WebKit/mac/icu/unicode/uversion.h216
350 files changed, 71063 insertions, 0 deletions
diff --git a/WebKit/mac/Carbon/CarbonUtils.h b/WebKit/mac/Carbon/CarbonUtils.h
new file mode 100644
index 0000000..ee4f42e
--- /dev/null
+++ b/WebKit/mac/Carbon/CarbonUtils.h
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2004, 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __HIWEBCARBONUTILS__
+#define __HIWEBCARBONUTILS__
+
+#ifndef __LP64__
+
+// These functions are only available for 32-bit.
+
+#ifdef __OBJC__
+#import <ApplicationServices/ApplicationServices.h>
+@class NSImage;
+#endif
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+extern void
+WebInitForCarbon(void);
+
+#ifdef __OBJC__
+
+extern CGImageRef
+WebConvertNSImageToCGImageRef(NSImage * inImage);
+
+#endif
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
+#endif // __HIWEBCARBONUTILS__
diff --git a/WebKit/mac/Carbon/CarbonUtils.m b/WebKit/mac/Carbon/CarbonUtils.m
new file mode 100644
index 0000000..be749c9
--- /dev/null
+++ b/WebKit/mac/Carbon/CarbonUtils.m
@@ -0,0 +1,132 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+
+#include "CarbonUtils.h"
+#import <WebKitSystemInterface.h>
+
+extern CGImageRef _NSCreateImageRef( unsigned char *const bitmapData[5], int pixelsWide, int pixelsHigh, int bitsPerSample, int samplesPerPixel, int bitsPerPixel, int bytesPerRow, BOOL isPlanar, BOOL hasAlpha, NSString *colorSpaceName, CGColorSpaceRef customColorSpace, id sourceObj);
+
+static void PoolCleaner( EventLoopTimerRef inTimer, EventLoopIdleTimerMessage inState, void *inUserData );
+
+static NSAutoreleasePool* sPool;
+static unsigned numPools;
+static EventLoopRef poolLoop;
+
+void HIWebViewRegisterClass( void );
+
+void
+WebInitForCarbon()
+{
+ static bool sAppKitLoaded;
+
+ if ( !sAppKitLoaded )
+ {
+ ProcessSerialNumber process;
+
+ // Force us to register with process server, this ensure that the process
+ // "flavour" is correctly established.
+ GetCurrentProcess( &process );
+ NSApplicationLoad();
+
+ sPool = [[NSAutoreleasePool allocWithZone:NULL] init];
+ numPools = WKGetNSAutoreleasePoolCount();
+
+ poolLoop = GetCurrentEventLoop ();
+
+ InstallEventLoopIdleTimer( GetMainEventLoop(), 1.0, 0, PoolCleaner, 0, NULL );
+
+ sAppKitLoaded = true;
+
+ HIWebViewRegisterClass();
+ }
+}
+
+/*
+ The pool cleaner is required because Carbon applications do not have
+ an autorelease pool provided by their event loops. Importantly,
+ carbon applications that nest event loops, using any of the various
+ techniques available to Carbon apps, MUST create their our pools around
+ their nested event loops.
+*/
+static void
+PoolCleaner( EventLoopTimerRef inTimer, EventLoopIdleTimerMessage inState, void *inUserData )
+{
+ if ( inState == kEventLoopIdleTimerStarted ) {
+ CFStringRef mode = CFRunLoopCopyCurrentMode( (CFRunLoopRef)GetCFRunLoopFromEventLoop( GetCurrentEventLoop() ));
+ EventLoopRef thisLoop = GetCurrentEventLoop ();
+ if ( CFEqual( mode, kCFRunLoopDefaultMode ) && thisLoop == poolLoop) {
+ unsigned currentNumPools = WKGetNSAutoreleasePoolCount()-1;
+ if (currentNumPools == numPools){
+ [sPool drain];
+
+ sPool = [[NSAutoreleasePool allocWithZone:NULL] init];
+ numPools = WKGetNSAutoreleasePoolCount();
+ }
+ }
+ CFRelease( mode );
+ }
+}
+
+CGImageRef
+WebConvertNSImageToCGImageRef(
+ NSImage* inImage )
+{
+ NSArray* reps = [inImage representations];
+ NSBitmapImageRep* rep = NULL;
+ CGImageRef image = NULL;
+ unsigned i;
+
+ for ( i=0; i < [reps count]; i++ )
+ {
+ if ( [[reps objectAtIndex:i] isKindOfClass:[NSBitmapImageRep class]] )
+ {
+ rep = [reps objectAtIndex:i];
+ break;
+ }
+ }
+
+ if ( rep )
+ {
+ //CGColorSpaceRef csync = (CGColorSpaceRef)[rep valueForProperty:NSImageColorSyncProfileData];
+
+ unsigned char* planes[5];
+
+ [rep getBitmapDataPlanes:planes];
+
+ image = _NSCreateImageRef( planes, [rep pixelsWide], [rep pixelsHigh],
+ [rep bitsPerSample], [rep samplesPerPixel], [rep bitsPerPixel],
+ [rep bytesPerRow], [rep isPlanar], [rep hasAlpha], [rep colorSpaceName],
+ NULL, rep);
+ }
+
+ return image;
+}
+
+#endif
diff --git a/WebKit/mac/Carbon/CarbonWindowAdapter.h b/WebKit/mac/Carbon/CarbonWindowAdapter.h
new file mode 100644
index 0000000..87c50ea
--- /dev/null
+++ b/WebKit/mac/Carbon/CarbonWindowAdapter.h
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+#import <AppKit/AppKit.h>
+#import <HIToolbox/CarbonEvents.h>
+#import <HIToolbox/MacWindows.h>
+
+@interface CarbonWindowAdapter : NSWindow
+{
+@private
+
+ // The Carbon window that's being encapsulated, and whether or not this object owns (has responsibility for disposing) it.
+ WindowRef _windowRef;
+ BOOL _windowRefIsOwned;
+ BOOL _carbon;
+
+ // The UPP for the event handler that we use to deal with various Carbon events, and the event handler itself.
+ EventHandlerUPP _handleEventUPP;
+ EventHandlerRef _eventHandler;
+
+ // Yes if this object should let Carbon handle kEventWindowActivated and kEventWindowDeactivated events. No otherwise.
+ BOOL _passingCarbonWindowActivationEvents;
+}
+
+// Initializers.
+- (id)initWithCarbonWindowRef:(WindowRef)inWindowRef takingOwnership:(BOOL)inWindowRefIsOwned;
+- (id)initWithCarbonWindowRef:(WindowRef)inWindowRef takingOwnership:(BOOL)inWindowRefIsOwned disableOrdering:(BOOL)inDisableOrdering carbon:(BOOL)inCarbon;
+
+// Accessors.
+- (WindowRef)windowRef;
+
+// Update this window's frame and content rectangles to match the Carbon window's structure and content bounds rectangles. Return yes if the update was really necessary, no otherwise.
+- (BOOL)reconcileToCarbonWindowBounds;
+
+// Handle an event just like an NSWindow would.
+- (void)sendSuperEvent:(NSEvent *)inEvent;
+
+- (void)relinquishFocus;
+
+@end
diff --git a/WebKit/mac/Carbon/CarbonWindowAdapter.m b/WebKit/mac/Carbon/CarbonWindowAdapter.m
new file mode 100644
index 0000000..e34cf7a
--- /dev/null
+++ b/WebKit/mac/Carbon/CarbonWindowAdapter.m
@@ -0,0 +1,1046 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// I don't think this class belongs in WebKit. Lets move it out.
+
+// Things that I've never bothered working out:
+// For non-sheet windows, handle Carbon WindowMove events so as to do the same things as -[NSWindow _windowMoved].
+// Check to see how this stuff deals with various screen size change scenarious.
+// M.P. Warning - 9/17/01
+
+// There are some invariants I'm maintaining for objects of this class which have been successfully initialized but not deallocated. These all make it easier to not override every single method of NSWindow.
+// _auxiliaryStorage->auxWFlags.hasShadow will always be false if the Carbon window has a kWindowNoShadowAttribute, and vice versa.
+// _auxiliaryStorage->_auxWFlags.minimized will always reflect the window's Carbon collapsed state.
+// _borderView will always point to an NSCarbonWindowFrame.
+// _contentView will always point to an NSCarbonWindowContentView;
+// _frame will always reflect the window's Carbon kWindowStructureRgn bounds.
+// _styleMask will always have _NSCarbonWindowMask set, and will have NSClosableWindowMask, NSMiniaturizableWindowMask, NSResizableWindowMask, and/or NSTitledWindowMask set as appropriate.
+// _wflags.oneShot and _wflags.delayedOneShot will always be false.
+// _wFlags.visible will always reflect the window's Carbon visibility.
+// _windowNum will always be greater than zero, and valid.
+// The instance variables involved are ones that came to my attention during the initial writing of this class; I haven't methodically gone through NSWindow's ivar list or anything like that. M.P. Notice - 10/10/00
+
+// Things that have to be worked on if NSCarbonWindows are ever used for something other than dialogs and sheets:
+// Clicking on an NSCarbonWindow while a Cocoa app-modal dialog is shown does not beep, as it should [old bug, maybe fixed now].
+// Handling of mouse clicks or key presses for any window control (close, miniaturize, zoom) might not be all there.
+// Handling of miniaturization of Carbon windows via title bar double-click might not be all there.
+// The background on NSCarbonWindowTester's sample window (not sample dialog or sample sheet) might be wrong.
+// The controls on NSCarbonWindowTester's sample window look inactive when the window is inactive, but have first-click behavior.
+// M.P. Warning - 12/14/00
+
+// Some things would have to be made public if someone wanted to subclass this so as to support more menu item commands. M.P. Warning - 9/19/00
+
+#ifndef __LP64__
+
+#import "CarbonWindowAdapter.h"
+
+#import "CarbonWindowFrame.h"
+#import "CarbonWindowContentView.h"
+#import "HIViewAdapter.h"
+
+#import <WebKitSystemInterface.h>
+
+#import <AppKit/AppKit.h>
+//#import <CoreGraphics/CGSWindow.h>
+#import <HIToolbox/CarbonEvents.h>
+#import <HIToolbox/Controls.h>
+#import <HIToolbox/HIView.h>
+#import <assert.h>
+
+#import <WebCore/WebCoreObjCExtras.h>
+
+#import "WebKitLogging.h"
+#import "WebNSObjectExtras.h"
+#import "WebTypesInternal.h"
+
+@interface NSWindow(HIWebFrameView)
+- _initContent:(const NSRect *)contentRect styleMask:(unsigned int)aStyle backing:(NSBackingStoreType)bufferingType defer:(BOOL)flag contentView:aView;
+- (void)_oldPlaceWindow:(NSRect)frameRect;
+- (void)_windowMovedToRect:(NSRect)actualFrame;
+- (void)_setWindowNumber:(NSInteger)nativeWindow;
+- (NSGraphicsContext *)_threadContext;
+- (void)_setFrame:(NSRect)newWindowFrameRect;
+- (void)_setVisible:(BOOL)flag;
+@end
+
+@interface NSApplication(HIWebFrameView)
+- (void)setIsActive:(BOOL)aFlag;
+- (id)_setMouseActivationInProgress:(BOOL)flag;
+- (BOOL)_handleKeyEquivalent:(NSEvent*)theEvent;
+@end
+
+@interface NSInputContext
+- (BOOL)processInputKeyBindings:(NSEvent *)event;
+@end
+
+// Forward declarations.
+static OSStatus NSCarbonWindowHandleEvent(EventHandlerCallRef inEventHandlerCallRef, EventRef inEventRef, void *inUserData);
+
+@implementation CarbonWindowAdapter
+
+
+// Return an appropriate window frame class.
++ (Class)frameViewClassForStyleMask:(unsigned int)style {
+
+ // There's only one appropriate window style, and only one appropriate window frame class.
+ assert(style & WKCarbonWindowMask());
+ return [CarbonWindowFrame class];
+
+}
+
+
+// Overriding of the parent class' designated initializer, just for safety's sake.
+- (id)initWithContentRect:(NSRect)contentRect styleMask:(unsigned int)style backing:(NSBackingStoreType)bufferingType defer:(BOOL)flag {
+
+ // Do the standard Cocoa thing.
+ self = [super initWithContentRect:contentRect styleMask:style backing:bufferingType defer:flag];
+ if (self==nil) return nil;
+
+ // Simple.
+ _windowRef = NULL;
+ _windowRefIsOwned = NO;
+ _eventHandler = NULL;
+
+ // Done.
+ return self;
+
+}
+
+// Given a reference to a Carbon window that is to be encapsulated, an indicator of whether or not this object should take responsibility for disposing of the Carbon window, and an indicator of whether to disable Carbon window ordering, initialize. This is the class' designated initializer.
+- (id)initWithCarbonWindowRef:(WindowRef)inWindowRef takingOwnership:(BOOL)inWindowRefIsOwned disableOrdering:(BOOL)inDisableOrdering carbon:(BOOL)inCarbon {
+
+ NSBackingStoreType backingStoreType;
+ CarbonWindowContentView *carbonWindowContentView;
+ NSWindow *windowAsProperty;
+ OSStatus osStatus;
+ UInt32 windowFeatures;
+ WindowAttributes windowAttributes;
+ unsigned int styleMask;
+ void *nativeWindow;
+ WindowModality windowModality;
+ ControlRef contentView;
+
+ // Simple.
+ // It's very weak to have to put this before the invocation of [super initWithContentRect:...], but -setContentView: is invoked from within that initializer. It turns out that the common admonition about not calling virtual functions from within C++ constructors makes sense in Objective-C too. M.P. Notice - 10/10/00
+ _windowRef = inWindowRef;
+ //_auxiliaryStorage->_windowRef = inWindowRef;
+ _windowRefIsOwned = inWindowRefIsOwned;
+ _carbon = inCarbon;
+
+ // Find out the window's CoreGraphics window reference.
+ nativeWindow = WKGetNativeWindowFromWindowRef(inWindowRef);
+
+ // Find out the window's Carbon window attributes.
+ GetWindowAttributes(inWindowRef, &windowAttributes);
+
+ // Find out the window's Carbon window features.
+ GetWindowFeatures(inWindowRef, &windowFeatures);
+
+ // Figure out the window's backing store type.
+ // At one time, this had code stolen from CreatePlatformWindow in HIToolbox/Windows/Platform/CGSPlatform.c
+ // But now the non-retained window class is a Carbon secret that's not even in
+ // WindowsPriv.h; maybe we'll have to revisit this if someone needs to use WebKit
+ // in a non-retained window.
+ backingStoreType = NSBackingStoreRetained;
+
+ // Figure out the window's style mask.
+ styleMask = WKCarbonWindowMask();
+ if (windowAttributes & kWindowCloseBoxAttribute) styleMask |= NSClosableWindowMask;
+ if (windowAttributes & kWindowResizableAttribute) styleMask |= NSResizableWindowMask;
+ if (windowFeatures & kWindowCanCollapse) styleMask |= NSMiniaturizableWindowMask;
+ if (windowFeatures & kWindowHasTitleBar) styleMask |= NSTitledWindowMask;
+
+ osStatus = GetWindowModality(_windowRef, &windowModality, NULL);
+ if (osStatus != noErr) {
+ NSLog(@"Couldn't get window modality: error=%d", osStatus);
+ return nil;
+ }
+
+ // Create one of our special content views.
+ carbonWindowContentView = [[[CarbonWindowContentView alloc] init] autorelease];
+
+ // Do some standard Cocoa initialization. The defer argument's value is YES because we don't want -[NSWindow _commonAwake] to get called. It doesn't appear that any relevant NSWindow code checks _wFlags.deferred, so we should be able to get away with the lie.
+ self = (CarbonWindowAdapter*)[super _initContent:NULL styleMask:styleMask backing:backingStoreType defer:YES contentView:carbonWindowContentView];
+ if (!self) return nil;
+ assert(_contentView);
+
+ // Record accurately whether or not this window has a shadow, in case someone asks.
+ // _auxiliaryStorage->_auxWFlags.hasShadow = (windowAttributes & kWindowNoShadowAttribute) ? NO : YES;
+
+ // Record the window number.
+ [self _setWindowNumber:(NSInteger)nativeWindow];
+
+ // Set up from the frame rectangle.
+ // We didn't even really try to get it right at _initContent:... time, because it's more trouble that it's worth to write a real +[NSCarbonWindow frameRectForContentRect:styleMask:]. M.P. Notice - 10/10/00
+ [self reconcileToCarbonWindowBounds];
+
+ // Install an event handler for the Carbon window events in which we're interested.
+ const EventTypeSpec kEvents[] = {
+ { kEventClassWindow, kEventWindowActivated },
+ { kEventClassWindow, kEventWindowDeactivated },
+ { kEventClassWindow, kEventWindowBoundsChanged },
+ { kEventClassWindow, kEventWindowShown },
+ { kEventClassWindow, kEventWindowHidden }
+ };
+
+ const EventTypeSpec kControlBoundsChangedEvent = { kEventClassControl, kEventControlBoundsChanged };
+
+ osStatus = InstallEventHandler( GetWindowEventTarget(_windowRef), NSCarbonWindowHandleEvent, GetEventTypeCount( kEvents ), kEvents, (void*)self, &_eventHandler);
+ if (osStatus!=noErr) {
+ [self release];
+ return nil;
+ }
+
+ osStatus = InstallEventHandler( GetControlEventTarget( HIViewGetRoot( _windowRef ) ), NSCarbonWindowHandleEvent, 1, &kControlBoundsChangedEvent, (void*)self, &_eventHandler);
+ if (osStatus!=noErr) {
+ [self release];
+ return nil;
+ }
+
+ HIViewFindByID( HIViewGetRoot( _windowRef ), kHIViewWindowContentID, &contentView );
+ osStatus = InstallEventHandler( GetControlEventTarget( contentView ), NSCarbonWindowHandleEvent, 1, &kControlBoundsChangedEvent, (void*)self, &_eventHandler);
+ if (osStatus!=noErr) {
+ [self release];
+ return nil;
+ }
+
+ // Put a pointer to this Cocoa NSWindow in a Carbon window property tag.
+ // Right now, this is just used by NSViewCarbonControl. M.P. Notice - 10/9/00
+ windowAsProperty = self;
+ osStatus = SetWindowProperty(_windowRef, WKCarbonWindowPropertyCreator(), WKCarbonWindowPropertyTag(), sizeof(NSWindow *), &windowAsProperty);
+ if (osStatus!=noErr) {
+ [self release];
+ return nil;
+ }
+
+ // Ignore the Carbon window activation/deactivation events that Carbon sends to its windows at app activation/deactivation. We'll send such events when we think it's appropriate.
+ _passingCarbonWindowActivationEvents = NO;
+
+ // Be sure to sync up visibility
+ [self _setVisible:(BOOL)IsWindowVisible( _windowRef )];
+
+ // Done.
+ return self;
+
+}
+
+- (void)setViewsNeedDisplay:(BOOL)wellDoThey {
+ // Make sure we can flush anything that needs it.
+
+ // We need to sync the context here. I was hoping I didn't need to do this,
+ // but apparently when scrolling, the AppKit view system draws directly.
+ // When this occurs, I cannot intercept it to make it draw in my HIView
+ // context. What ends up happening is that it draws, but nothing ever
+ // flushes it.
+
+ if ( [self windowNumber] != -1 )
+ {
+ CGContextRef cgContext = (CGContextRef)[[self _threadContext] graphicsPort];
+ CGContextSynchronize( cgContext );
+ }
+}
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
+// Given a reference to a Carbon window that is to be encapsulated, and an indicator of whether or not this object should take responsibility for disposing of the Carbon window, initialize.
+- (id)initWithCarbonWindowRef:(WindowRef)inWindowRef takingOwnership:(BOOL)inWindowRefIsOwned {
+ // for now, set disableOrdering to YES because that is what we've been doing and is therefore lower risk. However, I think it would be correct to set it to NO.
+ return [self initWithCarbonWindowRef:inWindowRef takingOwnership:inWindowRefIsOwned disableOrdering:YES carbon:NO];
+}
+
+
+// Clean up.
+- (void)dealloc {
+
+ // Clean up, if necessary.
+ // if we didn't remove the event handler at dealloc time, we would risk getting sent events after the window has been deallocated. See 2702179. M.P. Notice - 6/1/01
+ if (_eventHandler) RemoveEventHandler(_eventHandler);
+
+ // Do the standard Cocoa thing.
+ [super dealloc];
+
+}
+
+- (void)finalize {
+ ASSERT_MAIN_THREAD();
+ if (_eventHandler) RemoveEventHandler(_eventHandler);
+ [super finalize];
+}
+
+- (WindowRef)windowRef {
+
+ // Simple.
+ return _windowRef;
+
+}
+
+// should always be YES, but check in order to avoid initialization or deallocation surprises
+- (BOOL)_hasWindowRef {
+ return (_windowRef != NULL);
+}
+
+// an NSCarbonWindow does not manage the windowRef. The windowRef manages the NSCarbonWindow
+- (BOOL)_managesWindowRef {
+ return NO;
+}
+
+- (void)_removeWindowRef {
+ _windowRef = NULL;
+
+ if (_eventHandler) RemoveEventHandler(_eventHandler);
+
+ _eventHandler = NULL;
+}
+
+- (WindowClass)_carbonWindowClass {
+ WindowClass windowClass = kDocumentWindowClass;
+ OSStatus osStatus;
+
+ if ([self _hasWindowRef]) {
+ osStatus = GetWindowClass([self windowRef], &windowClass);
+ if (osStatus != noErr) {
+ NSLog(@"Couldn't get window class: error=%d", osStatus);
+ }
+ }
+ return windowClass;
+}
+
+// Update this window's frame and content frame rectangles to match the Carbon window's structure bounds and content bounds rectangles. Return yes if the update was really necessary, no otherwise.
+- (BOOL)reconcileToCarbonWindowBounds {
+
+ OSStatus osStatus;
+ NSRect newContentFrameRect;
+ NSRect newWindowFrameRect;
+ NSRect oldContentFrameRect;
+ Rect windowContentBoundsRect;
+ Rect windowStructureBoundsRect;
+
+ // Initialize for safe returning.
+ BOOL reconciliationWasNecessary = NO;
+
+ // Precondition check.
+ assert(_contentView);
+
+ // Get the Carbon window's bounds, which are expressed in global screen coordinates, with (0,0) at the top-left of the main screen.
+ osStatus = GetWindowBounds(_windowRef, kWindowStructureRgn, &windowStructureBoundsRect);
+ if (osStatus!=noErr) NSLog(@"A Carbon window's structure bounds couldn't be gotten.");
+ osStatus = GetWindowBounds(_windowRef, kWindowContentRgn, &windowContentBoundsRect);
+ if (osStatus!=noErr) NSLog(@"A Carbon window's content bounds couldn't be gotten.");
+
+ // Set the frame rectangle of the border view and this window from the Carbon window's structure region bounds.
+ newWindowFrameRect.origin.x = windowStructureBoundsRect.left;
+ newWindowFrameRect.origin.y = NSMaxY([[[NSScreen screens] objectAtIndex:0] frame]) - windowStructureBoundsRect.bottom;
+ newWindowFrameRect.size.width = windowStructureBoundsRect.right - windowStructureBoundsRect.left;
+ newWindowFrameRect.size.height = windowStructureBoundsRect.bottom - windowStructureBoundsRect.top;
+ if (!NSEqualRects(newWindowFrameRect, _frame)) {
+ [self _setFrame:newWindowFrameRect];
+ [_borderView setFrameSize:newWindowFrameRect.size];
+ reconciliationWasNecessary = YES;
+ }
+
+ // Set the content view's frame rect from the Carbon window's content region bounds.
+ newContentFrameRect.origin.x = windowContentBoundsRect.left - windowStructureBoundsRect.left;
+ newContentFrameRect.origin.y = windowStructureBoundsRect.bottom - windowContentBoundsRect.bottom;
+ newContentFrameRect.size.width = windowContentBoundsRect.right - windowContentBoundsRect.left;
+ newContentFrameRect.size.height = windowContentBoundsRect.bottom - windowContentBoundsRect.top;
+ oldContentFrameRect = [_contentView frame];
+ if (!NSEqualRects(newContentFrameRect, oldContentFrameRect)) {
+ [_contentView setFrame:newContentFrameRect];
+ reconciliationWasNecessary = YES;
+ }
+
+ // Done.
+ return reconciliationWasNecessary;
+
+}
+
+
+// Handle an event just like an NSWindow would.
+- (void)sendSuperEvent:(NSEvent *)inEvent {
+
+ // Filter out a few events that just result in complaints in the log.
+ // Ignore some unknown event that gets sent when NSTextViews in printing accessory views are focused. M.P. Notice - 12/7/00
+ BOOL ignoreEvent = NO;
+ NSEventType eventType = [inEvent type];
+ if (eventType==NSSystemDefined) {
+ short eventSubtype = [inEvent subtype];
+ if (eventSubtype==7) {
+ ignoreEvent = YES;
+ }
+ } else if (eventType == NSKeyDown) {
+ // Handle command-space as [NSApp sendEvent:] does.
+ if ([NSInputContext processInputKeyBindings:inEvent]) {
+ return;
+ }
+ }
+
+ // Simple.
+ if (!ignoreEvent) [super sendEvent:inEvent];
+}
+
+- (void)relinquishFocus
+{
+ NSResponder* firstResponder;
+
+ // Carbon thinks that a control has the keyboard focus,
+ // or we wouldn't be being asked to relinquish focus.
+
+ firstResponder = [self firstResponder];
+ if ([firstResponder isKindOfClass:[NSView class]] ){
+ // Make the window the first responder, so that no view is the key view.
+ [self makeFirstResponder:self];
+ }
+}
+
+- (BOOL)makeFirstResponder:(NSResponder *)aResponder
+{
+ // Let NSWindow focus the appropriate NSView.
+ if (![super makeFirstResponder:aResponder])
+ return NO;
+
+ // Now, if the view we're focusing is in a HIWebView, find the
+ // corresponding HIWebView for the NSView, and tell carbon to
+ // clear any focused control.
+ HIViewRef viewRef = 0;
+ NSResponder *firstResponder = [self firstResponder];
+ if ([firstResponder isKindOfClass:[NSView class]]) {
+ NSView *view = (NSView *)firstResponder;
+ while (view) {
+ viewRef = [HIViewAdapter getHIViewForNSView:view];
+ if (viewRef)
+ break;
+ view = [view superview];
+ }
+ }
+
+ HIViewRef focus;
+ GetKeyboardFocus (_windowRef, &focus);
+ if (focus != viewRef) {
+ SetKeyboardFocus (_windowRef, viewRef, kControlIndicatorPart );
+ }
+
+ return YES;
+}
+
+// There's no override of _addCursorRect:cursor:forView:, despite the fact that NSWindow's invokes [self windowNumber], because Carbon windows won't have subviews, and therefore won't have cursor rects.
+
+
+// There's no override of _autoResizeState, despite the fact that NSWindow's operates on _windowNum, because it looks like it might work on Carbon windows as is.
+
+
+// Disappointingly, -_blockHeartBeat: is not immediately invoked to turn off heartbeating. Heartbeating is turned off by setting the gDefaultButtonPaused global variable, and then this method is invoked later, if that global is set (at heartbeating time I guess). Something has to change if we want to hook this up in Carbon windows. M.P. Warning - 9/17/01
+/*
+// Do the right thing for a Carbon window.
+- (void)_blockHeartBeat:(BOOL)flag {
+
+ ControlRef defaultButton;
+ OSStatus osStatus;
+
+ // Do the standard Cocoa thing.
+ [super _blockHeartBeat:flag];
+
+ // If there's a default Carbon button in this Carbon window, make it stop pulsing, the Carbon way.
+ // This is inspired by HIToolbox/Controls/Definitions/ButtonCDEF.c's ButtonEventHandler(). M.P. Notice - 12/5/00
+ osStatus = GetWindowDefaultButton(_windowRef, &defaultButton);
+ if (osStatus==noErr && defaultButton) {
+ Boolean anotherButtonIsTracking = flag ? TRUE : FALSE;
+ osStatus = SetControlData(defaultButton, kControlNoPart, kControlPushButtonAnotherButtonTrackingTag, sizeof(Boolean), &anotherButtonIsTracking);
+ if (osStatus==noErr) DrawOneControl(defaultButton);
+ else NSLog(@"Some data couldn't be set in a Carbon control.");
+ }
+
+}
+*/
+
+
+// Do the right thing for a Carbon window.
+- (void)_cancelKey:(id)sender {
+
+ // Most of the time the handling of the cancel key will be done by Carbon, but this method will be invoked if an NSCarbonWindow is wrapping a Carbon window that contains an NSViewCarbonControl, and the escape key or whatever is pressed with an NSTextView focused. Just do what Carbon would do.
+ ControlRef cancelButton;
+ GetWindowCancelButton(_windowRef, &cancelButton);
+ if (cancelButton) {
+ if (IsControlActive(cancelButton)) {
+ HIViewSimulateClick(cancelButton, kControlButtonPart, 0, NULL);
+ }
+ }
+
+}
+
+
+
+// Do the right thing for a Carbon window.
+- (void)_commonAwake {
+
+ // Complain, because this should never be called. We insist that -[NSCarbonWindow initWithCarbonWindowRef] is the only valid initializer for instances of this class, and that there's no such thing as a one-shot NSCarbonWindow.
+ NSLog(@"-[NSCarbonWindow _commonAwake] is not implemented.");
+
+}
+
+
+// There's no override of _commonInitFrame:styleMask:backing:defer:, despite the fact that NSWindow's modifies quite a few instance variables, because it gets called in a harmless way if the class instance is properly initialized with -[NSCarbonWindow initWithCarbonWindowRef:takingOwnership:].
+
+
+// Do the right thing for a Carbon window.
+- _destroyRealWindow:(BOOL)orderingOut {
+
+ // Complain, because this should never be called. We don't support one-shot NSCarbonWindows.
+ NSLog(@"-[NSCarbonWindow _destroyRealWindow:] is not implemented.");
+ return self;
+
+}
+
+
+// There's no override of _discardCursorRectsForView, despite the fact that NSWindow's invokes [self windowNumber], because Carbon windows won't have subviews, and therefore won't have cursor rects.
+
+
+// There's no override of _forceFlushWindowToScreen, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+
+
+// There's no override of _getPositionFromServer, despite the fact that NSWindow's operates on _windowNum, because it's only called from -[NSApplication _activateWindows], which is hopefully about to become obsolete any second now.
+
+
+// There's no override of _globalWindowNum, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+
+
+// There's no override of _initContent:styleMask:backing:defer:contentView:, despite the fact that NSWindow's modifies _auxiliaryStorage->_auxWFlags.hasShadow, because it will never get called if the class instance is properly initialized with -[NSCarbonWindow initWithCarbonWindowRef:takingOwnership:].
+
+
+// There's no override of _initContent:styleMask:backing:defer:counterpart:, despite the fact that NSWindow's modifies _auxiliaryStorage->_auxWFlags.hasShadow, because it will never get called if the class instance is properly initialized with -[NSCarbonWindow initWithCarbonWindowRef:takingOwnership:].
+
+
+// Do what NSWindow would do, but then sychronize the Carbon window structures.
+- (void)_oldPlaceWindow:(NSRect)frameRect {
+
+ OSStatus osStatus;
+
+ // Do the standard Cocoa thing.
+ [super _oldPlaceWindow:frameRect];
+
+ // Tell Carbon to update its various regions.
+ // Despite its name, this function should be called early and often, even if the window isn't visible yet. 2702648. M.P. Notice - 7/24/01
+ osStatus = WKSyncWindowWithCGAfterMove(_windowRef);
+ if (osStatus!=noErr) NSLog(@"A Carbon window's bounds couldn't be synchronized (%i).", (int)osStatus);
+
+}
+
+
+// There's no override of _orderOutAndCalcKeyWithCounter:, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+
+
+// There's no override of _realHeartBeatThreadContext, despite the fact that NSWindows's invokes [self windowNumber], because it looks like it might not do anything that will effect a Carbon window.
+
+
+// There's no override of _registerWithDockIfNeeded, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+
+
+// There's no override of _removeCursorRect:cursor:forView:, despite the fact that NSWindow's invokes [self windowNumber], because Carbon windows won't have subviews, and therefore won't have cursor rects.
+
+
+// There's no override of _setAvoidsActivation:, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+
+
+// There's no override of _setFrame:, despite the fact that NSWindow's modifies _frame, because it looks like it might work on Carbon windows as is. The synchronization of the Carbon window bounds rect to the Cocoa frame rect is done in the overrides of _oldPlaceWindow: and _windowMovedToRect:.
+
+
+// There's no override of _setFrameCommon:display:stashSize:, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+
+
+// There's no override of _setWindowNumber:, despite the fact that NSWindow's modifies _windowNum and invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+
+
+// Do what NSWindow would do, but for a Carbon window.
+// This function is mostly cut-and-pasted from -[NSWindow _termWindowIfOwner]. M.P. Notice - 8/7/00
+- (void)_termWindowIfOwner {
+ [self _setWindowNumber:-1];
+ _wFlags.isTerminating = YES;
+ if (_windowRef && _windowRefIsOwned) DisposeWindow(_windowRef);
+ // KW - need to clear window shadow state so it gets reset correctly when new window created
+// if ([_borderView respondsToSelector:@selector(setShadowState:)]) {
+// [_borderView setShadowState:kFrameShadowNone];
+// }
+ _wFlags.isTerminating = NO;
+}
+
+
+// There's no override of _threadContext, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might not do anything that will effect a Carbon window.
+
+
+// There's no override of _windowMoved:, despite the fact that NSWindow's operates on _windowNum, because it looks like it might work on Carbon windows as is.
+
+
+// Do what NSWindow would do, but then sychronize the Carbon window structures.
+- (void)_windowMovedToRect:(NSRect)actualFrame {
+
+ OSStatus osStatus;
+
+ // Do the standard Cocoa thing.
+ [super _windowMovedToRect:actualFrame];
+
+ // Let Carbon know that the window has been moved, unless this method is being called "early."
+ if (_wFlags.visible) {
+ osStatus = WKSyncWindowWithCGAfterMove(_windowRef);
+ if (osStatus!=noErr) NSLog(@"A Carbon window's bounds couldn't be synchronized (%i).", (int)osStatus);
+ }
+
+}
+
+- (NSRect)constrainFrameRect:(NSRect)actualFrame toScreen:(NSScreen *)screen {
+ // let Carbon decide window size and position
+ return actualFrame;
+}
+
+- (void)selectKeyViewFollowingView:(NSView *)aView {
+ HIViewRef view = NULL;
+
+ view = [HIViewAdapter getHIViewForNSView:aView];
+
+ if ( view )
+ {
+ HIViewRef contentView;
+
+ GetRootControl( GetControlOwner( view ), &contentView );
+ HIViewAdvanceFocus( contentView, 0 );
+ }
+ else
+ {
+ [super selectKeyViewFollowingView:aView];
+ }
+}
+
+- (void)selectKeyViewPrecedingView:(NSView *)aView {
+ HIViewRef view = NULL;
+
+ view = [HIViewAdapter getHIViewForNSView:aView];
+
+ if ( view )
+ {
+ HIViewRef contentView;
+
+ GetRootControl( GetControlOwner( view ), &contentView );
+ HIViewAdvanceFocus( contentView, shiftKey );
+ }
+ else
+ {
+ [super selectKeyViewPrecedingView:aView];
+ }
+}
+
+- (void)makeKeyWindow {
+ [NSApp _setMouseActivationInProgress:NO];
+ [NSApp setIsActive:YES];
+ [super makeKeyWindow];
+ WKShowKeyAndMain();
+}
+
+
+// Do the right thing for a Carbon window.
+- (BOOL)canBecomeKeyWindow {
+
+ return YES;
+}
+
+// Do the right thing for a Carbon window.
+- (BOOL)canBecomeMainWindow {
+ OSStatus osStatus;
+ WindowClass windowClass;
+ // By default, Carbon windows cannot become the main window.
+ // What about when the default isn't right? Requiring subclassing seems harsh. M.P. Warning - 9/17/01
+ // KW - modify this to allow document windows to become main
+ // This is primarily to get the right look, so that you don't have two windows that both look active - one Cocoa document and one Carbon document
+ osStatus = GetWindowClass(_windowRef, &windowClass);
+ return (osStatus == noErr && windowClass == kDocumentWindowClass);
+
+}
+
+
+// There's no override of deminiaturize:, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+
+
+// There's no override of disableCursorRects, despite the fact that NSWindow's invokes [self windowNumber], because Carbon windows won't have subviews, and therefore won't have cursor rects.
+
+
+
+// There's no override of enableCursorRects, despite the fact that NSWindow's invokes [self windowNumber], because Carbon windows won't have subviews, and therefore won't have cursor rects.
+
+
+// Do the right thing for a Carbon window.
+- (void)encodeWithCoder:(NSCoder *)coder {
+
+ // Actually, this will probably never be implemented. M.P. Notice - 8/2/00
+ NSLog(@"-[NSCarbonWindow encodeWithCoder:] is not implemented.");
+
+}
+
+
+// There's no override of frame, despite the fact that NSWindow's returns _frame, because _frame is one of the instance variables whose value we're keeping synchronized with the Carbon window.
+
+
+// Do the right thing for a Carbon window.
+- (id)initWithCoder:(NSCoder *)coder {
+
+ // Actually, this will probably never be implemented. M.P. Notice - 8/2/00
+ NSLog(@"-[NSCarbonWindow initWithCoder:] is not implemented.");
+ [self release];
+ return nil;
+
+}
+
+
+// There's no override of level, despite the fact that NSWindow's returns _level, because _level is one of the instance variables whose value we're keeping synchronized with the Carbon window.
+
+
+// There's no override of miniaturize:, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+
+
+// There's no override of resizeToScreenWithEvent:, despite the fact that NSWindow's operates on _windowNum.
+// It looks like it's only called when an _NSForceResizeEventType event is passed into -[NSWindow sendEvent:], and I can't find any instances of that happening.
+
+/*
+// Do the right thing for a Carbon Window.
+- (void)sendEvent:(NSEvent *)theEvent {
+
+ // Not all events are handled in the same manner.
+ NSEventType eventType = [theEvent type];
+ if (eventType==NSAppKitDefined) {
+
+ // Handle the event the Cocoa way. Carbon won't understand it anyway.
+ [super sendEvent:theEvent];
+
+ }
+}
+*/
+
+// There's no override of setAcceptsMouseMovedEvents:, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+
+
+// There's no override of setBackingType:, despite the fact that NSWindow's invokes [self windowNumber], because it's apparently not expected to do anything anyway, judging from the current implementation of PSsetwindowtype().
+
+
+// Do what NSWindow would do, but for a Carbon window.
+- (void)setContentView:(NSView *)aView {
+
+ NSRect contentFrameRect;
+ OSStatus osStatus;
+ Rect windowContentBoundsRect;
+
+ // Precondition check.
+ assert(_borderView);
+ assert([_borderView isKindOfClass:[CarbonWindowFrame class]]);
+ assert(_windowRef);
+
+ // Parameter check.
+ assert(aView);
+ assert([aView isKindOfClass:[CarbonWindowContentView class]]);
+
+ // Find out the window's Carbon window structure region (content) bounds.
+ osStatus = GetWindowBounds(_windowRef, kWindowContentRgn, &windowContentBoundsRect);
+ if (osStatus!=noErr) NSLog(@"A Carbon window's content bounds couldn't be gotten.");
+ contentFrameRect.origin = NSZeroPoint;
+ contentFrameRect.size.width = windowContentBoundsRect.right - windowContentBoundsRect.left;
+ contentFrameRect.size.height = windowContentBoundsRect.bottom - windowContentBoundsRect.top;
+
+ // If the content view is still in some other view hierarchy, pry it free.
+ [_contentView removeFromSuperview];
+ assert(![_contentView superview]);
+
+ // Record the content view, and size it to this window's content frame.
+ _contentView = aView;
+ [_contentView setFrame:contentFrameRect];
+
+ // Make the content view a subview of the border view.
+ [_borderView addSubview:_contentView];
+
+ // Tell the content view it's new place in the responder chain.
+ [_contentView setNextResponder:self];
+
+}
+
+
+// There's no override of setDepthLimit:, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+
+
+- (BOOL)worksWhenModal {
+ WindowClass windowClass = [self _carbonWindowClass];
+ return (windowClass == kFloatingWindowClass || windowClass == kUtilityWindowClass);
+}
+
+- (void)_setModalWindowLevel {
+ return;
+}
+
+- _clearModalWindowLevel {
+ return nil;
+}
+
+// There's no override of setLevel:, despite the fact that NSWindow's invokes [self windowNumber], because it looks like it might work on Carbon windows as is.
+// I thought at first that there should be a mapping between Cocoa level and Carbon window class, but experiments convince me that such is not the case. M.P. Notice - 9/18/00
+
+
+// There's no override of windowNumber, despite the fact that NSWindow's returns _windowNum, because _windowNum is one of the instance variables whose value we're keeping synchronized with the Carbon window.
+
+
+- (UInt32)carbonHICommandIDFromActionSelector:(SEL)inActionSelector {
+
+ // Initialize with the default return value.
+ UInt32 hiCommandID = 0;
+
+ // Pretty simple, if tedious.
+ if (inActionSelector==@selector(clear:)) hiCommandID = kHICommandClear;
+ else if (inActionSelector==@selector(copy:)) hiCommandID = kHICommandCopy;
+ else if (inActionSelector==@selector(cut:)) hiCommandID = kHICommandCut;
+ else if (inActionSelector==@selector(paste:)) hiCommandID = kHICommandPaste;
+ else if (inActionSelector==@selector(redo:)) hiCommandID = kHICommandRedo;
+ else if (inActionSelector==@selector(selectAll:)) hiCommandID = kHICommandSelectAll;
+ else if (inActionSelector==@selector(undo:)) hiCommandID = kHICommandUndo;
+
+ // Done.
+ return hiCommandID;
+
+}
+
+
+- (void)sendCarbonProcessHICommandEvent:(UInt32)inHICommandID {
+
+ EventTargetRef eventTargetRef;
+ HICommand hiCommand;
+ OSStatus osStatus;
+
+ // Initialize for safe error handling.
+ EventRef eventRef = NULL;
+
+ // Create a Process Command event. Don't mention anything about the menu item, because we don't want the Carbon Event handler fiddling with it.
+ hiCommand.attributes = 0;
+ hiCommand.commandID = inHICommandID;
+ hiCommand.menu.menuRef = 0;
+ hiCommand.menu.menuItemIndex = 0;
+ osStatus = CreateEvent(NULL, kEventClassCommand, kEventCommandProcess, GetCurrentEventTime(), kEventAttributeNone, &eventRef);
+ if (osStatus!=noErr) {
+ NSLog(@"CreateEvent() returned %i.", (int)osStatus);
+ goto CleanUp;
+ }
+ osStatus = SetEventParameter(eventRef, kEventParamDirectObject, typeHICommand, sizeof(HICommand), &hiCommand);
+ if (osStatus!=noErr) {
+ NSLog(@"SetEventParameter() returned %i.", (int)osStatus);
+ goto CleanUp;
+ }
+
+ // Send a Carbon event to whatever has the Carbon user focus.
+ eventTargetRef = GetUserFocusEventTarget();
+ osStatus = SendEventToEventTarget(eventRef, eventTargetRef);
+ if (osStatus!=noErr) {
+ NSLog(@"SendEventToEventTarget() returned %i.", (int)osStatus);
+ goto CleanUp;
+ }
+
+CleanUp:
+
+ // Clean up.
+ if (eventRef) ReleaseEvent(eventRef);
+
+}
+
+
+- (Boolean)sendCarbonUpdateHICommandStatusEvent:(UInt32)inHICommandID withMenuRef:(MenuRef)inMenuRef andMenuItemIndex:(UInt16)inMenuItemIndex {
+
+ EventTargetRef eventTargetRef;
+ HICommand hiCommand;
+ OSStatus osStatus;
+
+ // Initialize for safe error handling and flag returning.
+ Boolean eventWasHandled = FALSE;
+ EventRef eventRef = NULL;
+
+ // Create a Process Command event. Don't mention anything about the menu item, because we don't want the Carbon Event handler fiddling with it.
+ hiCommand.attributes = kHICommandFromMenu;
+ hiCommand.commandID = inHICommandID;
+ hiCommand.menu.menuRef = inMenuRef;
+ hiCommand.menu.menuItemIndex = inMenuItemIndex;
+ osStatus = CreateEvent(NULL, kEventClassCommand, kEventCommandUpdateStatus, GetCurrentEventTime(), kEventAttributeNone, &eventRef);
+ if (osStatus!=noErr) {
+ NSLog(@"CreateEvent() returned %i.", (int)osStatus);
+ goto CleanUp;
+ }
+ osStatus = SetEventParameter(eventRef, kEventParamDirectObject, typeHICommand, sizeof(HICommand), &hiCommand);
+ if (osStatus!=noErr) {
+ NSLog(@"SetEventParameter() returned %i.", (int)osStatus);
+ goto CleanUp;
+ }
+
+ // Send a Carbon event to whatever has the Carbon user focus.
+ eventTargetRef = GetUserFocusEventTarget();
+ osStatus = SendEventToEventTarget(eventRef, eventTargetRef);
+ if (osStatus==noErr) {
+ eventWasHandled = TRUE;
+ } else if (osStatus!=eventNotHandledErr) {
+ NSLog(@"SendEventToEventTarget() returned %i.", (int)osStatus);
+ goto CleanUp;
+ }
+
+CleanUp:
+
+ // Clean up.
+ if (eventRef) ReleaseEvent(eventRef);
+
+ // Done.
+ return eventWasHandled;
+
+}
+
+- (void)_handleRootBoundsChanged
+{
+ HIViewRef root = HIViewGetRoot( _windowRef );
+ HIRect frame;
+
+ HIViewGetFrame( root, &frame );
+ [_borderView setFrameSize:*(NSSize*)&frame.size];
+}
+
+- (void)_handleContentBoundsChanged
+{
+ HIViewRef root, contentView;
+ HIRect rootBounds, contentFrame;
+ NSRect oldContentFrameRect;
+
+ root = HIViewGetRoot( _windowRef );
+ HIViewFindByID( root, kHIViewWindowContentID, &contentView );
+ HIViewGetFrame( contentView, &contentFrame );
+ HIViewGetBounds( root, &rootBounds );
+
+ // Set the content view's frame rect from the Carbon window's content region bounds.
+ contentFrame.origin.y = rootBounds.size.height - CGRectGetMaxY( contentFrame );
+
+ oldContentFrameRect = [_contentView frame];
+ if ( !NSEqualRects( *(NSRect*)&contentFrame, oldContentFrameRect ) ) {
+ [_contentView setFrame:*(NSRect*)&contentFrame];
+ }
+}
+
+- (OSStatus)_handleCarbonEvent:(EventRef)inEvent callRef:(EventHandlerCallRef)inCallRef {
+ OSStatus result = eventNotHandledErr;
+
+ switch ( GetEventClass( inEvent ) )
+ {
+ case kEventClassControl:
+ {
+ ControlRef control;
+
+ check( GetEventKind( inEvent ) == kEventControlBoundsChanged );
+
+ GetEventParameter( inEvent, kEventParamDirectObject, typeControlRef, NULL,
+ sizeof( ControlRef ), NULL, &control );
+
+ if ( control == HIViewGetRoot( _windowRef ) )
+ [self _handleRootBoundsChanged];
+ else
+ [self _handleContentBoundsChanged];
+ }
+ break;
+
+ case kEventClassWindow:
+ switch ( GetEventKind( inEvent ) )
+ {
+ case kEventWindowShown:
+ [self _setVisible:YES];
+ break;
+
+ case kEventWindowHidden:
+ [self _setVisible:NO];
+ break;
+
+ case kEventWindowActivated:
+ [self makeKeyWindow];
+ break;
+
+ case kEventWindowDeactivated:
+ [self resignKeyWindow];
+ break;
+
+ case kEventWindowBoundsChanged:
+ [self reconcileToCarbonWindowBounds];
+ break;
+ }
+ break;
+ }
+
+ return result;
+}
+
+// Handle various events that Carbon is sending to our window.
+static OSStatus NSCarbonWindowHandleEvent(EventHandlerCallRef inEventHandlerCallRef, EventRef inEventRef, void *inUserData) {
+
+ // default action is to send event to next handler. We modify osStatus as necessary where we don't want this behavior
+ OSStatus osStatus = eventNotHandledErr;
+
+ // We do different things for different event types.
+ CarbonWindowAdapter *carbonWindow = (CarbonWindowAdapter *)inUserData;
+
+ osStatus = [carbonWindow _handleCarbonEvent: inEventRef callRef: inEventHandlerCallRef];
+
+ // Done. If we want to propagate the event, we return eventNotHandledErr to send it to the next handler
+ return osStatus;
+
+}
+
+// [3364117] We need to make sure this does not fall through to the AppKit implementation! bad things happen.
+- (void)_reallyDoOrderWindow:(NSWindowOrderingMode)place relativeTo:(int)otherWin findKey:(BOOL)doKeyCalc forCounter:(BOOL)isACounter force:(BOOL)doForce isModal:(BOOL)isModal {
+}
+
+- (NSRect) _growBoxRect
+{
+ WindowAttributes attrs;
+ NSRect retRect = NSZeroRect;
+
+ GetWindowAttributes( _windowRef, &attrs );
+
+ if ( attrs & kWindowResizableAttribute )
+ {
+ HIRect bounds, rect;
+ HIViewRef view;
+
+ HIViewGetBounds( HIViewGetRoot( _windowRef ), &bounds );
+ HIViewFindByID( HIViewGetRoot( _windowRef ), kHIViewWindowGrowBoxID, &view );
+ HIViewGetFrame( view, &rect );
+
+ rect.origin.y = bounds.size.height - CGRectGetMaxY( rect ) - 1;
+ rect.origin.x++;
+
+ retRect = *(NSRect*)&rect;
+ }
+
+ return retRect;
+}
+
+@end // implementation CarbonWindowAdapter
+
+#endif
diff --git a/WebKit/mac/Carbon/CarbonWindowContentView.h b/WebKit/mac/Carbon/CarbonWindowContentView.h
new file mode 100644
index 0000000..5ba0478
--- /dev/null
+++ b/WebKit/mac/Carbon/CarbonWindowContentView.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <AppKit/NSView.h>
+
+@interface CarbonWindowContentView : NSView { }
+
+@end // interface CarbonWindowContentView
diff --git a/WebKit/mac/Carbon/CarbonWindowContentView.m b/WebKit/mac/Carbon/CarbonWindowContentView.m
new file mode 100644
index 0000000..d49a6ac
--- /dev/null
+++ b/WebKit/mac/Carbon/CarbonWindowContentView.m
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+
+#import "CarbonWindowContentView.h"
+
+@implementation CarbonWindowContentView
+
+@end
+
+#endif
diff --git a/WebKit/mac/Carbon/CarbonWindowFrame.h b/WebKit/mac/Carbon/CarbonWindowFrame.h
new file mode 100644
index 0000000..4bca98a
--- /dev/null
+++ b/WebKit/mac/Carbon/CarbonWindowFrame.h
@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <AppKit/AppKit.h>
+
+@interface CarbonWindowFrame : NSView
+
+// Instance variables.
+{
+
+ @private
+
+ // Something we keep around just to return when it's asked for.
+ unsigned int _styleMask;
+
+}
+
+@end // interface NSCarbonWindowFrame
diff --git a/WebKit/mac/Carbon/CarbonWindowFrame.m b/WebKit/mac/Carbon/CarbonWindowFrame.m
new file mode 100644
index 0000000..83f093a
--- /dev/null
+++ b/WebKit/mac/Carbon/CarbonWindowFrame.m
@@ -0,0 +1,288 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+
+#import "CarbonWindowFrame.h"
+#import "CarbonWindowAdapter.h"
+#import "CarbonWindowContentView.h"
+#import <Foundation/NSGeometry.h>
+#import <Foundation/NSString.h>
+#import <HIToolbox/MacWindows.h>
+
+#import "WebTypesInternal.h"
+
+@interface NSView(Secret)
+- (void)_setWindow:(NSWindow *)window;
+@end
+
+@class NSButton;
+/*
+
+@interface NSThemeFrame(NSHijackedClassMethods)
+
++ (float)_titlebarHeight:(unsigned int)style;
+
+@end
+*/
+
+@implementation CarbonWindowFrame
+
+
+- (NSRect)titlebarRect
+{
+ NSRect titlebarRect;
+ NSRect boundsRect;
+
+ boundsRect = [self bounds];
+
+ CarbonWindowAdapter *carbonWindow;
+ carbonWindow = (CarbonWindowAdapter *)[self window];
+ WindowRef windowRef = [carbonWindow windowRef];
+ Rect globalBounds;
+ GetWindowBounds (windowRef, kWindowTitleBarRgn, &globalBounds);
+
+ titlebarRect.origin.x = boundsRect.origin.x;
+ titlebarRect.size.width = boundsRect.size.width;
+ titlebarRect.size.height = globalBounds.bottom - globalBounds.top;
+ titlebarRect.origin.y = NSMaxY(boundsRect) - titlebarRect.size.height;
+
+ return titlebarRect;
+}
+
+// Given a content rectangle and style mask, return a corresponding frame rectangle.
++ (NSRect)frameRectForContentRect:(NSRect)contentRect styleMask:(NSUInteger)style {
+
+ // We don't bother figuring out a good value, because content rects weren't so meaningful for NSCarbonWindows in the past, but this might not be a good assumption anymore. M.P. Warning - 12/5/00
+ return contentRect;
+
+}
+
++ (NSRect)contentRectForFrameRect:(NSRect)frameRect styleMask:(NSUInteger)style {
+
+ // We don't bother figuring out a good value, because content rects weren't so meaningful for NSCarbonWindows in the past, but this might not be a good assumption anymore. KW - copied from +frameRectForContentRect:styleMask
+ return frameRect;
+
+}
+
++ (NSSize)minFrameSizeForMinContentSize:(NSSize)cSize styleMask:(NSUInteger)style {
+ // See comments above. We don't make any assumptions about the relationship between content rects and frame rects
+ return cSize;
+}
+
+- (NSRect)frameRectForContentRect:(NSRect)cRect styleMask:(NSUInteger)style {
+ return [[self class] frameRectForContentRect: cRect styleMask:style];
+}
+- (NSRect)contentRectForFrameRect:(NSRect)fRect styleMask:(NSUInteger)style {
+ return [[self class] contentRectForFrameRect: fRect styleMask:style];
+}
+- (NSSize)minFrameSizeForMinContentSize:(NSSize)cSize styleMask:(NSUInteger)style {
+ return [[self class] minFrameSizeForMinContentSize:cSize styleMask: style];
+}
+
+// Initialize.
+- (id)initWithFrame:(NSRect)inFrameRect styleMask:(unsigned int)inStyleMask owner:(NSWindow *)inOwningWindow {
+
+ // Parameter check.
+ if (![inOwningWindow isKindOfClass:[CarbonWindowAdapter class]]) NSLog(@"CarbonWindowFrames can only be owned by CarbonWindowAdapters.");
+
+ // Do the standard Cocoa thing.
+ self = [super initWithFrame:inFrameRect];
+ if (!self) return nil;
+
+ // Record what we'll need later.
+ _styleMask = inStyleMask;
+
+ // Do what NSFrameView's method of the same name does.
+ [self _setWindow:inOwningWindow];
+ [self setNextResponder:inOwningWindow];
+
+ // Done.
+ return self;
+
+}
+
+
+// Deallocate.
+- (void)dealloc {
+
+ // Simple.
+ [super dealloc];
+
+}
+
+
+// Sink a method invocation.
+- (void)_setFrameNeedsDisplay:(BOOL)needsDisplay {
+
+}
+
+
+// Sink a method invocation.
+- (void)_setSheet:(BOOL)sheetFlag {
+
+}
+
+
+// Sink a method invocation.
+- (void)_updateButtonState {
+
+}
+
+#if 0
+// Sink a method invocation.
+- (void)_windowChangedKeyState {
+}
+#endif
+
+// Toolbar methods that NSWindow expects to be there.
+- (BOOL)_canHaveToolbar { return NO; }
+- (BOOL)_toolbarIsInTransition { return NO; }
+- (BOOL)_toolbarIsShown { return NO; }
+- (BOOL)_toolbarIsHidden { return NO; }
+- (void)_showToolbarWithAnimation:(BOOL)animate {}
+- (void)_hideToolbarWithAnimation:(BOOL)animate {}
+- (float)_distanceFromToolbarBaseToTitlebar { return 0; }
+
+
+// Refuse to admit there's a close button on the window.
+- (NSButton *)closeButton {
+
+ // Simple.
+ return nil;
+}
+
+
+// Return what's asked for.
+- (unsigned int)styleMask {
+
+ // Simple.
+ return _styleMask;
+
+}
+
+
+// Return what's asked for.
+- (NSRect)dragRectForFrameRect:(NSRect)frameRect {
+
+ // Do what NSThemeFrame would do.
+ // If we just return NSZeroRect here, _NXMakeWindowVisible() gets all befuddled in the sheet-showing case, a window-moving loop is entered, and the sheet gets moved right off of the screen. M.P. Warning - 3/23/01
+ NSRect dragRect;
+ dragRect.size.height = 27;//[NSThemeFrame _titlebarHeight:[self styleMask]];
+ dragRect.origin.y = NSMaxY(frameRect) - dragRect.size.height;
+ dragRect.size.width = frameRect.size.width;
+ dragRect.origin.x = frameRect.origin.x;
+ return dragRect;
+
+}
+
+
+// Return what's asked for.
+- (BOOL)isOpaque {
+
+ // Return a value that will make -[NSWindow displayIfNeeded] on our Carbon window actually work.
+ return YES;
+
+}
+
+
+// Refuse to admit there's a minimize button on the window.
+- (NSButton *)minimizeButton {
+
+ // Simple.
+ return nil;
+
+}
+
+
+// Do the right thing for a Carbon window.
+- (void)setTitle:(NSString *)title {
+
+ CarbonWindowAdapter *carbonWindow;
+ OSStatus osStatus;
+ WindowRef windowRef;
+
+ // Set the Carbon window's title.
+ carbonWindow = (CarbonWindowAdapter *)[self window];
+ windowRef = [carbonWindow windowRef];
+ osStatus = SetWindowTitleWithCFString(windowRef, (CFStringRef)title);
+ if (osStatus!=noErr) NSLog(@"A Carbon window's title couldn't be set.");
+
+}
+
+
+// Return what's asked for.
+- (NSString *)title {
+
+ CFStringRef windowTitle;
+ CarbonWindowAdapter *carbonWindow;
+ NSString *windowTitleAsNSString;
+ OSStatus osStatus;
+ WindowRef windowRef;
+
+ // Return the Carbon window's title.
+ carbonWindow = (CarbonWindowAdapter *)[self window];
+ windowRef = [carbonWindow windowRef];
+ osStatus = CopyWindowTitleAsCFString(windowRef, &windowTitle);
+ if (osStatus==noErr) {
+ windowTitleAsNSString = (NSString *)windowTitle;
+ } else {
+ NSLog(@"A Carbon window's title couldn't be gotten.");
+ windowTitleAsNSString = @"";
+ }
+ return [windowTitleAsNSString autorelease];
+
+}
+
+
+// Return what's asked for.
+- (float)_sheetHeightAdjustment {
+
+ // Do what NSThemeFrame would do.
+ return 22;//[NSThemeFrame _titlebarHeight:([self styleMask] & ~NSDocModalWindowMask)];
+
+}
+
+// Return what's asked for.
+- (float)_maxTitlebarTitleRect {
+
+ // Do what NSThemeFrame would do.
+ return 22;//[NSThemeFrame _titlebarHeight:([self styleMask] & ~NSDocModalWindowMask)];
+
+}
+
+- (void)_clearDragMargins {
+}
+
+- (void)_resetDragMargins {
+}
+
+
+@end // implementation NSCarbonWindowFrame
+
+#endif
diff --git a/WebKit/mac/Carbon/HIViewAdapter.h b/WebKit/mac/Carbon/HIViewAdapter.h
new file mode 100644
index 0000000..875566d
--- /dev/null
+++ b/WebKit/mac/Carbon/HIViewAdapter.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebKit.h>
+#include <HIToolbox/HIView.h>
+
+@interface HIViewAdapter : NSObject
+
++ (void)bindHIViewToNSView:(HIViewRef)hiView nsView:(NSView*)nsView;
++ (void)unbindNSView:(NSView*)nsView;
++ (HIViewRef)getHIViewForNSView:(NSView*)inView;
+
+@end
diff --git a/WebKit/mac/Carbon/HIViewAdapter.m b/WebKit/mac/Carbon/HIViewAdapter.m
new file mode 100644
index 0000000..c0c46af
--- /dev/null
+++ b/WebKit/mac/Carbon/HIViewAdapter.m
@@ -0,0 +1,248 @@
+/*
+ * Copyright (C) 2005, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+
+#import "HIViewAdapter.h"
+
+#import "WebNSObjectExtras.h"
+#import <JavaScriptCore/Assertions.h>
+
+static void SetViewNeedsDisplay(HIViewRef inView, RgnHandle inRegion, Boolean inNeedsDisplay);
+
+#define WATCH_INVALIDATION 0
+
+@interface NSView(ShhhhDontTell)
+- (NSRect)_dirtyRect;
+@end
+
+@implementation HIViewAdapter
+
+static CFMutableDictionaryRef sViewMap;
+
+static IMP oldNSViewSetNeedsDisplayIMP;
+static IMP oldNSViewSetNeedsDisplayInRectIMP;
+static IMP oldNSViewNextValidKeyViewIMP;
+
+static void _webkit_NSView_setNeedsDisplay(id self, SEL _cmd, BOOL flag);
+static void _webkit_NSView_setNeedsDisplayInRect(id self, SEL _cmd, NSRect invalidRect);
+static NSView *_webkit_NSView_nextValidKeyView(id self, SEL _cmd);
+
++ (void)bindHIViewToNSView:(HIViewRef)hiView nsView:(NSView*)nsView
+{
+ if (sViewMap == NULL) {
+ sViewMap = CFDictionaryCreateMutable(NULL, 0, NULL, NULL);
+
+ // Override -[NSView setNeedsDisplay:]
+ Method setNeedsDisplayMethod = class_getInstanceMethod(objc_getClass("NSView"), @selector(setNeedsDisplay:));
+ ASSERT(setNeedsDisplayMethod);
+ ASSERT(!oldNSViewSetNeedsDisplayIMP);
+ oldNSViewSetNeedsDisplayIMP = method_setImplementation(setNeedsDisplayMethod, (IMP)_webkit_NSView_setNeedsDisplay);
+
+ // Override -[NSView setNeedsDisplayInRect:]
+ Method setNeedsDisplayInRectMethod = class_getInstanceMethod(objc_getClass("NSView"), @selector(setNeedsDisplayInRect:));
+ ASSERT(setNeedsDisplayInRectMethod);
+ ASSERT(!oldNSViewSetNeedsDisplayInRectIMP);
+ oldNSViewSetNeedsDisplayInRectIMP = method_setImplementation(setNeedsDisplayInRectMethod, (IMP)_webkit_NSView_setNeedsDisplayInRect);
+
+ // Override -[NSView nextValidKeyView]
+ Method nextValidKeyViewMethod = class_getInstanceMethod(objc_getClass("NSView"), @selector(nextValidKeyView));
+ ASSERT(nextValidKeyViewMethod);
+ ASSERT(!oldNSViewNextValidKeyViewIMP);
+ oldNSViewNextValidKeyViewIMP = method_setImplementation(nextValidKeyViewMethod, (IMP)_webkit_NSView_nextValidKeyView);
+ }
+
+ CFDictionaryAddValue(sViewMap, nsView, hiView);
+}
+
++ (HIViewRef)getHIViewForNSView:(NSView*)inView
+{
+ return sViewMap ? (HIViewRef)CFDictionaryGetValue(sViewMap, inView) : NULL;
+}
+
++ (void)unbindNSView:(NSView*)inView
+{
+ CFDictionaryRemoveValue(sViewMap, inView);
+}
+
+static void _webkit_NSView_setNeedsDisplay(id self, SEL _cmd, BOOL flag)
+{
+ oldNSViewSetNeedsDisplayIMP(self, _cmd, flag);
+
+ if (!flag) {
+ HIViewRef hiView = NULL;
+ NSRect targetBounds = [self visibleRect];
+ NSRect validRect = targetBounds;
+ NSView *view = self;
+
+ while (view) {
+ targetBounds = [view visibleRect];
+ if ((hiView = [HIViewAdapter getHIViewForNSView:view]) != NULL)
+ break;
+ validRect = [view convertRect:validRect toView:[view superview]];
+ view = [view superview];
+ }
+
+ if (hiView) {
+ // Flip rect here and convert to region
+ HIRect rect;
+ rect.origin.x = validRect.origin.x;
+ rect.origin.y = targetBounds.size.height - NSMaxY(validRect);
+ rect.size.height = validRect.size.height;
+ rect.size.width = validRect.size.width;
+
+ // For now, call the region-based API.
+ RgnHandle rgn = NewRgn();
+ if (rgn) {
+ Rect qdRect;
+ qdRect.top = (SInt16)rect.origin.y;
+ qdRect.left = (SInt16)rect.origin.x;
+ qdRect.bottom = CGRectGetMaxY(rect);
+ qdRect.right = CGRectGetMaxX(rect);
+
+ RectRgn(rgn, &qdRect);
+ SetViewNeedsDisplay(hiView, rgn, false);
+ DisposeRgn(rgn);
+ }
+ }
+ }
+}
+
+static void _webkit_NSView_setNeedsDisplayInRect(id self, SEL _cmd, NSRect invalidRect)
+{
+ invalidRect = NSUnionRect(invalidRect, [self _dirtyRect]);
+ oldNSViewSetNeedsDisplayInRectIMP(self, _cmd, invalidRect);
+
+ if (!NSIsEmptyRect(invalidRect)) {
+ HIViewRef hiView = NULL;
+ NSRect targetBounds = [self bounds];
+ NSView *view = self;
+
+ while (view) {
+ targetBounds = [view bounds];
+ if ((hiView = [HIViewAdapter getHIViewForNSView:view]) != NULL)
+ break;
+ invalidRect = [view convertRect:invalidRect toView:[view superview]];
+ view = [view superview];
+ }
+
+ if (hiView) {
+ if (NSWidth(invalidRect) > 0 && NSHeight(invalidRect)) {
+ // Flip rect here and convert to region
+ HIRect rect;
+ rect.origin.x = invalidRect.origin.x;
+ rect.origin.y = targetBounds.size.height - NSMaxY(invalidRect);
+ rect.size.height = invalidRect.size.height;
+ rect.size.width = invalidRect.size.width;
+
+ // For now, call the region-based API.
+ RgnHandle rgn = NewRgn();
+ if (rgn) {
+ Rect qdRect;
+ qdRect.top = (SInt16)rect.origin.y;
+ qdRect.left = (SInt16)rect.origin.x;
+ qdRect.bottom = CGRectGetMaxY(rect);
+ qdRect.right = CGRectGetMaxX(rect);
+
+ RectRgn(rgn, &qdRect);
+ SetViewNeedsDisplay(hiView, rgn, true);
+ DisposeRgn(rgn);
+ }
+ }
+ } else
+ [[self window] setViewsNeedDisplay:YES];
+ }
+}
+
+static NSView *_webkit_NSView_nextValidKeyView(id self, SEL _cmd)
+{
+ if ([HIViewAdapter getHIViewForNSView:self])
+ return [[self window] contentView];
+ else
+ return oldNSViewNextValidKeyViewIMP(self, _cmd);
+}
+
+@end
+
+static void SetViewNeedsDisplay(HIViewRef inHIView, RgnHandle inRegion, Boolean inNeedsDisplay)
+{
+ WindowAttributes attrs;
+
+ GetWindowAttributes(GetControlOwner(inHIView), &attrs);
+
+ if (attrs & kWindowCompositingAttribute) {
+#if WATCH_INVALIDATION
+ Rect bounds;
+ GetRegionBounds(inRegion, &bounds);
+ printf("%s: rect on input %d %d %d %d\n", inNeedsDisplay ? "INVALIDATE" : "VALIDATE",
+ bounds.top, bounds.left, bounds.bottom, bounds.right);
+#endif
+ HIViewSetNeedsDisplayInRegion(inHIView, inRegion, inNeedsDisplay);
+ } else {
+ Rect bounds, cntlBounds;
+ GrafPtr port, savePort;
+ Rect portBounds;
+
+#if WATCH_INVALIDATION
+ printf("%s: rect on input %d %d %d %d\n", inNeedsDisplay ? "INVALIDATE" : "VALIDATE",
+ bounds.top, bounds.left, bounds.bottom, bounds.right);
+#endif
+ GetControlBounds(inHIView, &cntlBounds);
+
+#if WATCH_INVALIDATION
+ printf("%s: control bounds are %d %d %d %d\n", inNeedsDisplay ? "INVALIDATE" : "VALIDATE",
+ cntlBounds.top, cntlBounds.left, cntlBounds.bottom, cntlBounds.right);
+#endif
+
+ port = GetWindowPort(GetControlOwner(inHIView));
+
+ GetPort(&savePort);
+ SetPort(port);
+ GetPortBounds(port, &portBounds);
+ SetOrigin(0, 0);
+
+ OffsetRgn(inRegion, cntlBounds.left, cntlBounds.top);
+
+ GetRegionBounds(inRegion, &bounds);
+
+#if WATCH_INVALIDATION
+ printf("%s: rect in port coords %d %d %d %d\n", inNeedsDisplay ? "INVALIDATE" : "VALIDATE",
+ bounds.top, bounds.left, bounds.bottom, bounds.right);
+#endif
+
+ if (inNeedsDisplay)
+ InvalWindowRgn(GetControlOwner(inHIView), inRegion);
+ else
+ ValidWindowRgn(GetControlOwner(inHIView), inRegion);
+
+ SetOrigin(portBounds.left, portBounds.top);
+ SetPort(savePort);
+ }
+}
+
+#endif
diff --git a/WebKit/mac/Carbon/HIWebView.h b/WebKit/mac/Carbon/HIWebView.h
new file mode 100644
index 0000000..44d6d86
--- /dev/null
+++ b/WebKit/mac/Carbon/HIWebView.h
@@ -0,0 +1,129 @@
+/*
+ * Copyright (C) 2004, 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __HIWebView__
+#define __HIWebView__
+
+#ifndef __LP64__
+
+#include <Carbon/Carbon.h>
+
+#include <AvailabilityMacros.h>
+
+#if PRAGMA_ONCE
+#pragma once
+#endif
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#ifdef __OBJC__
+@class WebView;
+#endif
+
+/*
+ * HIWebViewCreate()
+ *
+ * Summary:
+ * Creates a new web view.
+ *
+ * Parameters:
+ *
+ * outControl:
+ * The new web view.
+ *
+ * Result:
+ * An operating system status code.
+ *
+ * Availability:
+ * Mac OS X: in version 10.2.7 and later [32-bit only]
+ * CarbonLib: not available
+ * Non-Carbon CFM: not available
+ */
+extern OSStatus
+HIWebViewCreate(HIViewRef * outControl);
+
+#ifdef __OBJC__
+
+/*
+ * HIWebViewCreateWithClass(HIViewRef * outControl, Class aClass)
+ *
+ * Summary:
+ * Creates a new web view using the specified subclass of WebView.
+ *
+ * Parameters:
+ *
+ * aClass:
+ * Either WebView, or a subclass, to be created and wrapped in an HIWebView.
+ * outControl:
+ * The new web view.
+ *
+ * Result:
+ * An operating system status code.
+ *
+ * Availability:
+ * Mac OS X: in version 10.4 and later [32-bit only]
+ * CarbonLib: not available
+ * Non-Carbon CFM: not available
+ */
+extern OSStatus
+HIWebViewCreateWithClass(
+ Class aClass,
+ HIViewRef * outControl);
+
+/*
+ * HIWebViewGetWebView()
+ *
+ * Summary:
+ * Returns the WebKit WebView for a given HIWebView.
+ *
+ * Parameters:
+ *
+ * inView:
+ * The view to inspect.
+ *
+ * Result:
+ * A pointer to a web view object, or NULL.
+ *
+ * Availability:
+ * Mac OS X: in version 10.2.7 and later [32-bit only]
+ * CarbonLib: not available
+ * Non-Carbon CFM: not available
+ */
+extern WebView *
+HIWebViewGetWebView(HIViewRef inView);
+
+#endif
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
+#endif /* __HIWebView__ */
diff --git a/WebKit/mac/Carbon/HIWebView.m b/WebKit/mac/Carbon/HIWebView.m
new file mode 100644
index 0000000..2b9bda4
--- /dev/null
+++ b/WebKit/mac/Carbon/HIWebView.m
@@ -0,0 +1,1639 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+
+#import "HIWebView.h"
+
+#import "CarbonWindowAdapter.h"
+#import "HIViewAdapter.h"
+#import "WebHTMLViewInternal.h"
+#import "WebKit.h"
+
+#import <objc/objc-runtime.h>
+#import <WebKitSystemInterface.h>
+
+@interface NSWindow (AppKitSecretsHIWebViewKnows)
+- (void)_removeWindowRef;
+@end
+
+@interface NSView (AppKitSecretsHIWebViewKnows)
+- (void)_clearDirtyRectsForTree;
+@end
+
+extern "C" void HIWebViewRegisterClass();
+
+@interface MenuItemProxy : NSObject <NSValidatedUserInterfaceItem>
+{
+ int _tag;
+ SEL _action;
+}
+
+- (id)initWithAction:(SEL)action;
+- (SEL)action;
+- (int)tag;
+
+@end
+
+@implementation MenuItemProxy
+
+- (id)initWithAction:(SEL)action
+{
+ [super init];
+ if (self == nil) return nil;
+
+ _action = action;
+
+ return self;
+}
+
+- (SEL)action
+{
+ return _action;
+}
+
+- (int)tag
+{
+ return 0;
+}
+
+@end
+
+struct HIWebView
+{
+ HIViewRef fViewRef;
+
+ WebView* fWebView;
+ NSView* fFirstResponder;
+ CarbonWindowAdapter * fKitWindow;
+ bool fIsComposited;
+ CFRunLoopObserverRef fUpdateObserver;
+};
+typedef struct HIWebView HIWebView;
+
+static const OSType NSAppKitPropertyCreator = 'akit';
+/*
+These constants are not used. Commented out to make the compiler happy.
+static const OSType NSViewCarbonControlViewPropertyTag = 'view';
+static const OSType NSViewCarbonControlAutodisplayPropertyTag = 'autd';
+static const OSType NSViewCarbonControlFirstResponderViewPropertyTag = 'frvw';
+*/
+static const OSType NSCarbonWindowPropertyTag = 'win ';
+
+#ifdef BUILDING_ON_TIGER
+const int typeByteCount = typeSInt32;
+#endif
+
+static SEL _NSSelectorForHICommand( const HICommand* hiCommand );
+
+static const EventTypeSpec kEvents[] = {
+ { kEventClassHIObject, kEventHIObjectConstruct },
+ { kEventClassHIObject, kEventHIObjectDestruct },
+
+ { kEventClassMouse, kEventMouseUp },
+ { kEventClassMouse, kEventMouseMoved },
+ { kEventClassMouse, kEventMouseDragged },
+ { kEventClassMouse, kEventMouseWheelMoved },
+
+ { kEventClassKeyboard, kEventRawKeyDown },
+ { kEventClassKeyboard, kEventRawKeyRepeat },
+
+ { kEventClassCommand, kEventCommandProcess },
+ { kEventClassCommand, kEventCommandUpdateStatus },
+
+ { kEventClassControl, kEventControlInitialize },
+ { kEventClassControl, kEventControlDraw },
+ { kEventClassControl, kEventControlHitTest },
+ { kEventClassControl, kEventControlGetPartRegion },
+ { kEventClassControl, kEventControlGetData },
+ { kEventClassControl, kEventControlBoundsChanged },
+ { kEventClassControl, kEventControlActivate },
+ { kEventClassControl, kEventControlDeactivate },
+ { kEventClassControl, kEventControlOwningWindowChanged },
+ { kEventClassControl, kEventControlClick },
+ { kEventClassControl, kEventControlContextualMenuClick },
+ { kEventClassControl, kEventControlSetFocusPart }
+};
+
+#define kHIViewBaseClassID CFSTR( "com.apple.hiview" )
+#define kHIWebViewClassID CFSTR( "com.apple.HIWebView" )
+
+static HIWebView* HIWebViewConstructor( HIViewRef inView );
+static void HIWebViewDestructor( HIWebView* view );
+
+static OSStatus HIWebViewEventHandler(
+ EventHandlerCallRef inCallRef,
+ EventRef inEvent,
+ void * inUserData );
+
+static UInt32 GetBehaviors();
+static ControlKind GetKind();
+static void Draw( HIWebView* inView, RgnHandle limitRgn, CGContextRef inContext );
+static ControlPartCode HitTest( HIWebView* view, const HIPoint* where );
+static OSStatus GetRegion( HIWebView* view, ControlPartCode inPart, RgnHandle outRgn );
+static void BoundsChanged(
+ HIWebView* inView,
+ UInt32 inOptions,
+ const HIRect* inOriginalBounds,
+ const HIRect* inCurrentBounds );
+static void OwningWindowChanged(
+ HIWebView* view,
+ WindowRef oldWindow,
+ WindowRef newWindow );
+static void ActiveStateChanged( HIWebView* view );
+
+static OSStatus Click( HIWebView* inView, EventRef inEvent );
+static OSStatus ContextMenuClick( HIWebView* inView, EventRef inEvent );
+static OSStatus MouseUp( HIWebView* inView, EventRef inEvent );
+static OSStatus MouseMoved( HIWebView* inView, EventRef inEvent );
+static OSStatus MouseDragged( HIWebView* inView, EventRef inEvent );
+static OSStatus MouseWheelMoved( HIWebView* inView, EventRef inEvent );
+
+static OSStatus ProcessCommand( HIWebView* inView, const HICommand* inCommand );
+static OSStatus UpdateCommandStatus( HIWebView* inView, const HICommand* inCommand );
+
+static OSStatus SetFocusPart(
+ HIWebView* view,
+ ControlPartCode desiredFocus,
+ RgnHandle invalidRgn,
+ Boolean focusEverything,
+ ControlPartCode* actualFocus );
+static NSView* AdvanceFocus( HIWebView* view, bool forward );
+static void RelinquishFocus( HIWebView* view, bool inAutodisplay );
+
+static WindowRef GetWindowRef( HIWebView* inView );
+static void SyncFrame( HIWebView* inView );
+
+static OSStatus WindowHandler( EventHandlerCallRef inCallRef, EventRef inEvent, void* inUserData );
+
+static void StartUpdateObserver( HIWebView* view );
+static void StopUpdateObserver( HIWebView* view );
+
+static inline void HIRectToQDRect( const HIRect* inRect, Rect* outRect )
+{
+ outRect->top = (SInt16)CGRectGetMinY( *inRect );
+ outRect->left = (SInt16)CGRectGetMinX( *inRect );
+ outRect->bottom = (SInt16)CGRectGetMaxY( *inRect );
+ outRect->right = (SInt16)CGRectGetMaxX( *inRect );
+}
+
+static Class webViewClass;
+
+//----------------------------------------------------------------------------------
+// HIWebViewCreate
+//----------------------------------------------------------------------------------
+//
+OSStatus
+HIWebViewCreate( HIViewRef* outControl )
+{
+ OSStatus err;
+
+ HIWebViewRegisterClass();
+
+ webViewClass = [WebView class];
+ err = HIObjectCreate( kHIWebViewClassID, NULL, (HIObjectRef*)outControl );
+
+ return err;
+}
+
+//----------------------------------------------------------------------------------
+// HIWebViewCreateWithClass
+//----------------------------------------------------------------------------------
+//
+OSStatus HIWebViewCreateWithClass(Class aClass, HIViewRef * outControl)
+{
+ OSStatus err;
+
+ HIWebViewRegisterClass();
+
+ webViewClass = aClass;
+ err = HIObjectCreate( kHIWebViewClassID, NULL, (HIObjectRef*)outControl );
+
+ return err;
+}
+
+//----------------------------------------------------------------------------------
+// HIWebViewGetWebView
+//----------------------------------------------------------------------------------
+//
+WebView*
+HIWebViewGetWebView( HIViewRef inView )
+{
+ HIWebView* view = (HIWebView*)HIObjectDynamicCast( (HIObjectRef)inView, kHIWebViewClassID );
+ WebView* result = NULL;
+
+ if ( view )
+ result = view->fWebView;
+
+ return result;
+}
+
+//----------------------------------------------------------------------------------
+// HIWebViewConstructor
+//----------------------------------------------------------------------------------
+//
+
+static HIWebView*
+HIWebViewConstructor( HIViewRef inView )
+{
+ HIWebView* view = (HIWebView*)malloc( sizeof( HIWebView ) );
+
+ if ( view )
+ {
+ NSRect frame = { { 0, 0 }, { 400, 400 } };
+
+ view->fViewRef = inView;
+
+ WebView *webView = [[webViewClass alloc] initWithFrame: frame];
+ CFRetain(webView);
+ [webView release];
+ view->fWebView = webView;
+ [HIViewAdapter bindHIViewToNSView:inView nsView:view->fWebView];
+
+ view->fFirstResponder = NULL;
+ view->fKitWindow = NULL;
+ view->fIsComposited = false;
+ view->fUpdateObserver = NULL;
+ }
+
+ return view;
+}
+
+//----------------------------------------------------------------------------------
+// HIWebViewDestructor
+//----------------------------------------------------------------------------------
+//
+static void
+HIWebViewDestructor( HIWebView* inView )
+{
+ [HIViewAdapter unbindNSView:inView->fWebView];
+ CFRelease(inView->fWebView);
+
+ free(inView);
+}
+
+//----------------------------------------------------------------------------------
+// HIWebViewRegisterClass
+//----------------------------------------------------------------------------------
+//
+void
+HIWebViewRegisterClass()
+{
+ static bool sRegistered;
+
+ if ( !sRegistered )
+ {
+ HIObjectRegisterSubclass( kHIWebViewClassID, kHIViewBaseClassID, 0, HIWebViewEventHandler,
+ GetEventTypeCount( kEvents ), kEvents, 0, NULL );
+ sRegistered = true;
+ }
+}
+
+//----------------------------------------------------------------------------------
+// GetBehaviors
+//----------------------------------------------------------------------------------
+//
+static UInt32
+GetBehaviors()
+{
+ return kControlSupportsDataAccess | kControlSupportsGetRegion | kControlGetsFocusOnClick;
+}
+
+//----------------------------------------------------------------------------------
+// Draw
+//----------------------------------------------------------------------------------
+//
+static void
+Draw( HIWebView* inView, RgnHandle limitRgn, CGContextRef inContext )
+{
+ HIRect bounds;
+ Rect drawRect;
+ HIRect hiRect;
+ bool createdContext = false;
+
+ if (!inView->fIsComposited)
+ {
+ GrafPtr port;
+ Rect portRect;
+
+ GetPort( &port );
+ GetPortBounds( port, &portRect );
+ CreateCGContextForPort( port, &inContext );
+ SyncCGContextOriginWithPort( inContext, port );
+ CGContextTranslateCTM( inContext, 0, (portRect.bottom - portRect.top) );
+ CGContextScaleCTM( inContext, 1, -1 );
+ createdContext = true;
+ }
+
+ HIViewGetBounds( inView->fViewRef, &bounds );
+
+ CGContextRef savedContext = WKNSWindowOverrideCGContext(inView->fKitWindow, inContext);
+ [NSGraphicsContext setCurrentContext:[inView->fKitWindow graphicsContext]];
+
+ GetRegionBounds( limitRgn, &drawRect );
+
+ if ( !inView->fIsComposited )
+ OffsetRect( &drawRect, (SInt16)-bounds.origin.x, (SInt16)-bounds.origin.y );
+
+ hiRect.origin.x = drawRect.left;
+ hiRect.origin.y = bounds.size.height - drawRect.bottom; // flip y
+ hiRect.size.width = drawRect.right - drawRect.left;
+ hiRect.size.height = drawRect.bottom - drawRect.top;
+
+// printf( "Drawing: drawRect is (%g %g) (%g %g)\n", hiRect.origin.x, hiRect.origin.y,
+// hiRect.size.width, hiRect.size.height );
+
+ // FIXME: We need to do layout before Carbon has decided what region needs drawn.
+ // In Cocoa we make sure to do layout and invalidate any new regions before draw, so everything
+ // can be drawn in one pass. Doing a layout here will cause new regions to be invalidated, but they
+ // will not all be drawn in this pass since we already have a fixed rect we are going to display.
+
+ NSView <WebDocumentView> *documentView = [[[inView->fWebView mainFrame] frameView] documentView];
+ if ([documentView isKindOfClass:[WebHTMLView class]])
+ [(WebHTMLView *)documentView _web_layoutIfNeededRecursive];
+
+ if ( inView->fIsComposited )
+ [inView->fWebView displayIfNeededInRect: *(NSRect*)&hiRect];
+ else
+ [inView->fWebView displayRect:*(NSRect*)&hiRect];
+
+ WKNSWindowRestoreCGContext(inView->fKitWindow, savedContext);
+
+ if ( !inView->fIsComposited )
+ {
+ HIViewRef view;
+ HIViewFindByID( HIViewGetRoot( GetControlOwner( inView->fViewRef ) ), kHIViewWindowGrowBoxID, &view );
+ if ( view )
+ {
+ HIRect frame;
+
+ HIViewGetBounds( view, &frame );
+ HIViewConvertRect( &frame, view, NULL );
+
+ hiRect.origin.x = drawRect.left;
+ hiRect.origin.y = drawRect.top;
+ hiRect.size.width = drawRect.right - drawRect.left;
+ hiRect.size.height = drawRect.bottom - drawRect.top;
+
+ HIViewConvertRect( &hiRect, inView->fViewRef, NULL );
+
+ if ( CGRectIntersectsRect( frame, hiRect ) )
+ HIViewSetNeedsDisplay( view, true );
+ }
+ }
+
+ if ( createdContext )
+ {
+ CGContextSynchronize( inContext );
+ CGContextRelease( inContext );
+ }
+}
+
+//----------------------------------------------------------------------------------
+// HitTest
+//----------------------------------------------------------------------------------
+//
+static ControlPartCode
+HitTest( HIWebView* view, const HIPoint* where )
+{
+ HIRect bounds;
+
+ HIViewGetBounds( view->fViewRef, &bounds );
+
+ if ( CGRectContainsPoint( bounds, *where ) )
+ return 1;
+ else
+ return kControlNoPart;
+}
+
+//----------------------------------------------------------------------------------
+// GetRegion
+//----------------------------------------------------------------------------------
+//
+static OSStatus
+GetRegion(
+ HIWebView* inView,
+ ControlPartCode inPart,
+ RgnHandle outRgn )
+{
+ OSStatus err = eventNotHandledErr;
+
+ if ( inPart == -3 ) // kControlOpaqueMetaPart:
+ {
+ if ( [inView->fWebView isOpaque] )
+ {
+ HIRect bounds;
+ Rect temp;
+
+ HIViewGetBounds( inView->fViewRef, &bounds );
+
+ temp.top = (SInt16)bounds.origin.y;
+ temp.left = (SInt16)bounds.origin.x;
+ temp.bottom = (SInt16)CGRectGetMaxY( bounds );
+ temp.right = (SInt16)CGRectGetMaxX( bounds );
+
+ RectRgn( outRgn, &temp );
+ err = noErr;
+ }
+ }
+
+ return err;
+}
+
+static WindowRef
+GetWindowRef( HIWebView* inView )
+{
+ return GetControlOwner( inView->fViewRef );
+}
+
+//----------------------------------------------------------------------------------
+// Click
+//----------------------------------------------------------------------------------
+//
+static OSStatus
+Click(HIWebView* inView, EventRef inEvent)
+{
+ NSEvent *kitEvent = WKCreateNSEventWithCarbonClickEvent(inEvent, GetWindowRef(inView));
+
+ if (!inView->fIsComposited)
+ StartUpdateObserver(inView);
+
+ [inView->fKitWindow sendEvent:kitEvent];
+
+ if (!inView->fIsComposited)
+ StopUpdateObserver(inView);
+
+ [kitEvent release];
+
+ return noErr;
+}
+
+//----------------------------------------------------------------------------------
+// MouseUp
+//----------------------------------------------------------------------------------
+//
+static OSStatus
+MouseUp( HIWebView* inView, EventRef inEvent )
+{
+ NSEvent* kitEvent = WKCreateNSEventWithCarbonEvent(inEvent);
+
+ [inView->fKitWindow sendEvent:kitEvent];
+
+ [kitEvent release];
+
+ return noErr;
+}
+
+//----------------------------------------------------------------------------------
+// MouseMoved
+//----------------------------------------------------------------------------------
+//
+static OSStatus
+MouseMoved( HIWebView* inView, EventRef inEvent )
+{
+ NSEvent *kitEvent = WKCreateNSEventWithCarbonMouseMoveEvent(inEvent, inView->fKitWindow);
+ [inView->fKitWindow sendEvent:kitEvent];
+ [kitEvent release];
+
+ return noErr;
+}
+
+//----------------------------------------------------------------------------------
+// MouseDragged
+//----------------------------------------------------------------------------------
+//
+static OSStatus
+MouseDragged( HIWebView* inView, EventRef inEvent )
+{
+ NSEvent* kitEvent = WKCreateNSEventWithCarbonEvent(inEvent);
+
+ [inView->fKitWindow sendEvent:kitEvent];
+
+ [kitEvent release];
+
+ return noErr;
+}
+
+//----------------------------------------------------------------------------------
+// MouseDragged
+//----------------------------------------------------------------------------------
+//
+static OSStatus
+MouseWheelMoved( HIWebView* inView, EventRef inEvent )
+{
+ NSEvent* kitEvent = WKCreateNSEventWithCarbonEvent(inEvent);
+
+ [inView->fKitWindow sendEvent:kitEvent];
+
+ [kitEvent release];
+
+ return noErr;
+}
+
+//----------------------------------------------------------------------------------
+// ContextMenuClick
+//----------------------------------------------------------------------------------
+//
+static OSStatus
+ContextMenuClick( HIWebView* inView, EventRef inEvent )
+{
+ NSView *webView = inView->fWebView;
+ NSWindow *window = [webView window];
+
+ // Get the point out of the event.
+ HIPoint point;
+ GetEventParameter(inEvent, kEventParamMouseLocation, typeHIPoint, NULL, sizeof(point), NULL, &point);
+ HIViewConvertPoint(&point, inView->fViewRef, NULL);
+
+ // Flip the Y coordinate, since Carbon is flipped relative to the AppKit.
+ NSPoint location = NSMakePoint(point.x, [window frame].size.height - point.y);
+
+ // Make up an event with the point and send it to the window.
+ NSEvent *kitEvent = [NSEvent mouseEventWithType:NSRightMouseDown
+ location:location
+ modifierFlags:0
+ timestamp:GetEventTime(inEvent)
+ windowNumber:[window windowNumber]
+ context:0
+ eventNumber:0
+ clickCount:1
+ pressure:0];
+ [inView->fKitWindow sendEvent:kitEvent];
+ return noErr;
+}
+
+//----------------------------------------------------------------------------------
+// GetKind
+//----------------------------------------------------------------------------------
+//
+static ControlKind
+GetKind()
+{
+ const ControlKind kMyKind = { 'appl', 'wbvw' };
+
+ return kMyKind;
+}
+
+//----------------------------------------------------------------------------------
+// BoundsChanged
+//----------------------------------------------------------------------------------
+//
+static void
+BoundsChanged(
+ HIWebView* inView,
+ UInt32 inOptions,
+ const HIRect* inOriginalBounds,
+ const HIRect* inCurrentBounds )
+{
+ if ( inView->fWebView )
+ {
+ SyncFrame( inView );
+ }
+}
+
+//----------------------------------------------------------------------------------
+// OwningWindowChanged
+//----------------------------------------------------------------------------------
+//
+static void
+OwningWindowChanged(
+ HIWebView* view,
+ WindowRef oldWindow,
+ WindowRef newWindow )
+{
+ if ( newWindow ){
+ WindowAttributes attrs;
+
+ OSStatus err = GetWindowProperty(newWindow, NSAppKitPropertyCreator, NSCarbonWindowPropertyTag, sizeof(NSWindow *), NULL, &view->fKitWindow);
+ if ( err != noErr )
+ {
+ const EventTypeSpec kWindowEvents[] = {
+ { kEventClassWindow, kEventWindowClosed },
+ { kEventClassMouse, kEventMouseMoved },
+ { kEventClassMouse, kEventMouseUp },
+ { kEventClassMouse, kEventMouseDragged },
+ { kEventClassMouse, kEventMouseWheelMoved },
+ { kEventClassKeyboard, kEventRawKeyDown },
+ { kEventClassKeyboard, kEventRawKeyRepeat },
+ { kEventClassKeyboard, kEventRawKeyUp },
+ { kEventClassControl, kEventControlClick },
+ };
+
+ view->fKitWindow = [[CarbonWindowAdapter alloc] initWithCarbonWindowRef: newWindow takingOwnership: NO disableOrdering:NO carbon:YES];
+ SetWindowProperty(newWindow, NSAppKitPropertyCreator, NSCarbonWindowPropertyTag, sizeof(NSWindow *), &view->fKitWindow);
+
+ InstallWindowEventHandler( newWindow, WindowHandler, GetEventTypeCount( kWindowEvents ), kWindowEvents, newWindow, NULL );
+ }
+
+ [[view->fKitWindow contentView] addSubview:view->fWebView];
+
+ GetWindowAttributes( newWindow, &attrs );
+ view->fIsComposited = ( ( attrs & kWindowCompositingAttribute ) != 0 );
+
+ SyncFrame( view );
+ }
+ else
+ {
+ // Be sure to detach the cocoa view, too.
+ if ( view->fWebView )
+ [view->fWebView removeFromSuperview];
+
+ view->fKitWindow = NULL; // break the ties that bind
+ }
+}
+
+//-------------------------------------------------------------------------------------
+// WindowHandler
+//-------------------------------------------------------------------------------------
+// Redirect mouse events to the views beneath them. This is required for WebKit to work
+// properly. We install it once per window. We also tap into window close to release
+// the NSWindow that shadows our Carbon window.
+//
+static OSStatus
+WindowHandler( EventHandlerCallRef inCallRef, EventRef inEvent, void* inUserData )
+{
+ WindowRef window = (WindowRef)inUserData;
+ OSStatus result = eventNotHandledErr;
+
+ switch( GetEventClass( inEvent ) )
+ {
+ case kEventClassControl:
+ {
+ switch( GetEventKind( inEvent ) )
+ {
+ case kEventControlClick:
+ {
+ CarbonWindowAdapter *kitWindow;
+ OSStatus err;
+
+ err = GetWindowProperty( window, NSAppKitPropertyCreator, NSCarbonWindowPropertyTag, sizeof(NSWindow *), NULL, &kitWindow);
+
+ // We must be outside the HIWebView, relinquish focus.
+ [kitWindow relinquishFocus];
+ }
+ break;
+ }
+ }
+ break;
+
+ case kEventClassKeyboard:
+ {
+ NSWindow* kitWindow;
+ OSStatus err;
+ NSEvent* kitEvent;
+
+ // if the first responder in the kit window is something other than the
+ // window, we assume a subview of the webview is focused. we must send
+ // the event to the window so that it goes through the kit's normal TSM
+ // logic, and -- more importantly -- allows any delegates associated
+ // with the first responder to have a chance at the event.
+
+ err = GetWindowProperty( window, NSAppKitPropertyCreator, NSCarbonWindowPropertyTag, sizeof(NSWindow *), NULL, &kitWindow);
+ if ( err == noErr )
+ {
+ NSResponder* responder = [kitWindow firstResponder];
+ if ( responder != kitWindow )
+ {
+ kitEvent = WKCreateNSEventWithCarbonEvent(inEvent);
+
+ [kitWindow sendEvent:kitEvent];
+ [kitEvent release];
+
+ result = noErr;
+ }
+ }
+ }
+ break;
+
+ case kEventClassWindow:
+ {
+ NSWindow* kitWindow;
+ OSStatus err;
+
+ err = GetWindowProperty( window, NSAppKitPropertyCreator, NSCarbonWindowPropertyTag, sizeof(NSWindow *), NULL, &kitWindow);
+ if ( err == noErr )
+ {
+ [kitWindow _removeWindowRef];
+ [kitWindow close];
+ }
+
+ result = noErr;
+ }
+ break;
+
+ case kEventClassMouse:
+ switch (GetEventKind(inEvent))
+ {
+ case kEventMouseMoved:
+ {
+ Point where;
+ GetEventParameter(inEvent, kEventParamMouseLocation, typeQDPoint, NULL, sizeof(Point), NULL, &where);
+
+ WindowRef temp;
+ FindWindow(where, &temp);
+ if (temp == window)
+ {
+ Rect bounds;
+ GetWindowBounds(window, kWindowStructureRgn, &bounds);
+ where.h -= bounds.left;
+ where.v -= bounds.top;
+ SetEventParameter(inEvent, kEventParamWindowRef, typeWindowRef, sizeof(WindowRef), &window);
+ SetEventParameter(inEvent, kEventParamWindowMouseLocation, typeQDPoint, sizeof(Point), &where);
+
+ OSStatus err = noErr;
+ HIViewRef view = NULL;
+
+ err = HIViewGetViewForMouseEvent(HIViewGetRoot(window), inEvent, &view);
+ if (err == noErr && view && HIObjectIsOfClass((HIObjectRef)view, kHIWebViewClassID))
+ result = SendEventToEventTargetWithOptions(inEvent, HIObjectGetEventTarget((HIObjectRef)view), kEventTargetDontPropagate);
+ }
+ }
+ break;
+
+ case kEventMouseUp:
+ case kEventMouseDragged:
+ case kEventMouseWheelMoved:
+ {
+ OSStatus err = noErr;
+ HIViewRef view = NULL;
+
+ err = HIViewGetViewForMouseEvent(HIViewGetRoot(window), inEvent, &view);
+ if (err == noErr && view && HIObjectIsOfClass((HIObjectRef)view, kHIWebViewClassID))
+ result = SendEventToEventTargetWithOptions(inEvent, HIObjectGetEventTarget((HIObjectRef)view), kEventTargetDontPropagate);
+ }
+ break;
+ }
+ break;
+ }
+
+ return result;
+}
+
+
+//----------------------------------------------------------------------------------
+// SyncFrame
+//----------------------------------------------------------------------------------
+//
+static void
+SyncFrame( HIWebView* inView )
+{
+ HIViewRef parent = HIViewGetSuperview( inView->fViewRef );
+
+ if ( parent )
+ {
+ if ( inView->fIsComposited )
+ {
+ HIRect frame;
+ HIRect parentBounds;
+ NSPoint origin;
+
+ HIViewGetFrame( inView->fViewRef, &frame );
+ HIViewGetBounds( parent, &parentBounds );
+
+ origin.x = frame.origin.x;
+ origin.y = parentBounds.size.height - CGRectGetMaxY( frame );
+// printf( "syncing to (%g %g) (%g %g)\n", origin.x, origin.y,
+// frame.size.width, frame.size.height );
+ [inView->fWebView setFrameOrigin: origin];
+ [inView->fWebView setFrameSize: *(NSSize*)&frame.size];
+ }
+ else
+ {
+ GrafPtr port = GetWindowPort( GetControlOwner( inView->fViewRef ) );
+ PixMapHandle portPix = GetPortPixMap( port );
+ Rect bounds;
+ HIRect rootFrame;
+ HIRect frame;
+
+ GetControlBounds( inView->fViewRef, &bounds );
+ OffsetRect( &bounds, -(**portPix).bounds.left, -(**portPix).bounds.top );
+
+// printf( "control lives at %d %d %d %d in window-coords\n", bounds.top, bounds.left,
+// bounds.bottom, bounds.right );
+
+ HIViewGetFrame( HIViewGetRoot( GetControlOwner( inView->fViewRef ) ), &rootFrame );
+
+ frame.origin.x = bounds.left;
+ frame.origin.y = rootFrame.size.height - bounds.bottom;
+ frame.size.width = bounds.right - bounds.left;
+ frame.size.height = bounds.bottom - bounds.top;
+
+// printf( " before frame convert (%g %g) (%g %g)\n", frame.origin.x, frame.origin.y,
+// frame.size.width, frame.size.height );
+
+ [inView->fWebView convertRect:*(NSRect*)&frame fromView:nil];
+
+// printf( " moving web view to (%g %g) (%g %g)\n", frame.origin.x, frame.origin.y,
+// frame.size.width, frame.size.height );
+
+ [inView->fWebView setFrameOrigin: *(NSPoint*)&frame.origin];
+ [inView->fWebView setFrameSize: *(NSSize*)&frame.size];
+ }
+ }
+}
+
+//----------------------------------------------------------------------------------
+// SetFocusPart
+//----------------------------------------------------------------------------------
+//
+static OSStatus
+SetFocusPart(
+ HIWebView* view,
+ ControlPartCode desiredFocus,
+ RgnHandle invalidRgn,
+ Boolean focusEverything,
+ ControlPartCode* actualFocus )
+{
+ NSView * freshlyMadeFirstResponderView;
+ SInt32 partCodeToReturn;
+
+ // Do what Carbon is telling us to do.
+ if ( desiredFocus == kControlFocusNoPart )
+ {
+ // Relinquish the keyboard focus.
+ RelinquishFocus( view, true ); //(autodisplay ? YES : NO));
+ freshlyMadeFirstResponderView = nil;
+ partCodeToReturn = kControlFocusNoPart;
+ //NSLog(@"Relinquished the key focus because we have no choice.");
+ }
+ else if ( desiredFocus == kControlFocusNextPart || desiredFocus == kControlFocusPrevPart )
+ {
+ BOOL goForward = (desiredFocus == kControlFocusNextPart );
+
+ // Advance the keyboard focus, maybe right off of this view. Maybe a subview of this one already has the keyboard focus, maybe not.
+ freshlyMadeFirstResponderView = AdvanceFocus( view, goForward );
+ if (freshlyMadeFirstResponderView)
+ partCodeToReturn = desiredFocus;
+ else
+ partCodeToReturn = kControlFocusNoPart;
+ //NSLog(freshlyMadeFirstResponderView ? @"Advanced the key focus." : @"Relinquished the key focus.");
+ }
+ else
+ {
+ // What's this?
+ if (desiredFocus != kControlIndicatorPart) {
+ check(false);
+ }
+ freshlyMadeFirstResponderView = nil;
+ partCodeToReturn = desiredFocus;
+ }
+
+ view->fFirstResponder = freshlyMadeFirstResponderView;
+
+ *actualFocus = partCodeToReturn;
+
+ // Done.
+ return noErr;
+}
+
+//----------------------------------------------------------------------------------
+// AdvanceFocus
+//----------------------------------------------------------------------------------
+//
+static NSView*
+AdvanceFocus( HIWebView* view, bool forward )
+{
+ NSResponder* oldFirstResponder;
+ NSView* currentKeyView;
+ NSView* viewWeMadeFirstResponder;
+
+ // Focus on some part (subview) of this control (view). Maybe
+ // a subview of this one already has the keyboard focus, maybe not.
+
+ oldFirstResponder = [view->fKitWindow firstResponder];
+
+ // If we tab out of our NSView, it will no longer be the responder
+ // when we get here. We'll try this trick for now. We might need to
+ // tag the view appropriately.
+
+ if ( view->fFirstResponder && ( (NSResponder*)view->fFirstResponder != oldFirstResponder ) )
+ {
+ return NULL;
+ }
+
+ if ( [oldFirstResponder isKindOfClass:[NSView class]] )
+ {
+ NSView* tentativeNewKeyView;
+
+ // Some view in this window already has the keyboard focus. It better at least be a subview of this one.
+ NSView* oldFirstResponderView = (NSView *)oldFirstResponder;
+ check( [oldFirstResponderView isDescendantOf:view->fWebView] );
+
+ if ( oldFirstResponderView != view->fFirstResponder
+ && ![oldFirstResponderView isDescendantOf:view->fFirstResponder] )
+ {
+ // Despite our efforts to record what view we made the first responder
+ // (for use in the next paragraph) we couldn't keep up because the user
+ // has clicked in a text field to make it the key focus, instead of using
+ // the tab key. Find a control on which it's reasonable to invoke
+ // -[NSView nextValidKeyView], taking into account the fact that
+ // NSTextFields always pass on first-respondership to a temporarily-
+ // contained NSTextView.
+
+ NSView *viewBeingTested;
+ currentKeyView = oldFirstResponderView;
+ viewBeingTested = currentKeyView;
+ while ( viewBeingTested != view->fWebView )
+ {
+ if ( [viewBeingTested isKindOfClass:[NSTextField class]] )
+ {
+ currentKeyView = viewBeingTested;
+ break;
+ }
+ else
+ {
+ viewBeingTested = [viewBeingTested superview];
+ }
+ }
+ }
+ else
+ {
+ // We recorded which view we made into the first responder the
+ // last time the user hit the tab key, and nothing has invalidated
+ // our recorded value since.
+
+ currentKeyView = view->fFirstResponder;
+ }
+
+ // Try to move on to the next or previous key view. We use the laboriously
+ // recorded/figured currentKeyView instead of just oldFirstResponder as the
+ // jumping-off-point when searching for the next valid key view. This is so
+ // we don't get fooled if we recently made some view the first responder, but
+ // it passed on first-responder-ness to some temporary subview.
+
+ // You can't put normal views in a window with Carbon-control-wrapped views.
+ // Stuff like this would break. M.P. Notice - 12/2/00
+
+ tentativeNewKeyView = forward ? [currentKeyView nextValidKeyView] : [currentKeyView previousValidKeyView];
+ if ( tentativeNewKeyView && [tentativeNewKeyView isDescendantOf:view->fWebView] )
+ {
+ // The user has tabbed to another subview of this control view. Change the keyboard focus.
+ //NSLog(@"Tabbed to the next or previous key view.");
+
+ [view->fKitWindow makeFirstResponder:tentativeNewKeyView];
+ viewWeMadeFirstResponder = tentativeNewKeyView;
+ }
+ else
+ {
+ // The user has tabbed past the subviews of this control view. The window is the first responder now.
+ //NSLog(@"Tabbed past the first or last key view.");
+ [view->fKitWindow makeFirstResponder:view->fKitWindow];
+ viewWeMadeFirstResponder = nil;
+ }
+ }
+ else
+ {
+ // No view in this window has the keyboard focus. This view should
+ // try to select one of its key subviews. We're not interested in
+ // the subviews of sibling views here.
+
+ //NSLog(@"No keyboard focus in window. Attempting to set...");
+
+ NSView *tentativeNewKeyView;
+ check(oldFirstResponder==fKitWindow);
+ if ( [view->fWebView acceptsFirstResponder] )
+ tentativeNewKeyView = view->fWebView;
+ else
+ tentativeNewKeyView = [view->fWebView nextValidKeyView];
+ if ( tentativeNewKeyView && [tentativeNewKeyView isDescendantOf:view->fWebView] )
+ {
+ // This control view has at least one subview that can take the keyboard focus.
+ if ( !forward )
+ {
+ // The user has tabbed into this control view backwards. Find
+ // and select the last subview of this one that can take the
+ // keyboard focus. Watch out for loops of valid key views.
+
+ NSView *firstTentativeNewKeyView = tentativeNewKeyView;
+ NSView *nextTentativeNewKeyView = [tentativeNewKeyView nextValidKeyView];
+ while ( nextTentativeNewKeyView
+ && [nextTentativeNewKeyView isDescendantOf:view->fWebView]
+ && nextTentativeNewKeyView!=firstTentativeNewKeyView)
+ {
+ tentativeNewKeyView = nextTentativeNewKeyView;
+ nextTentativeNewKeyView = [tentativeNewKeyView nextValidKeyView];
+ }
+
+ }
+
+ // Set the keyboard focus.
+ //NSLog(@"Tabbed into the first or last key view.");
+ [view->fKitWindow makeFirstResponder:tentativeNewKeyView];
+ viewWeMadeFirstResponder = tentativeNewKeyView;
+ }
+ else
+ {
+ // This control view has no subviews that can take the keyboard focus.
+ //NSLog(@"Can't tab into this view.");
+ viewWeMadeFirstResponder = nil;
+ }
+ }
+
+ // Done.
+ return viewWeMadeFirstResponder;
+}
+
+
+//----------------------------------------------------------------------------------
+// RelinquishFocus
+//----------------------------------------------------------------------------------
+//
+static void
+RelinquishFocus( HIWebView* view, bool inAutodisplay )
+{
+ NSResponder* firstResponder;
+
+ // Apparently Carbon thinks that some subview of this control view has the keyboard focus,
+ // or we wouldn't be being asked to relinquish focus.
+
+ firstResponder = [view->fKitWindow firstResponder];
+ if ( [firstResponder isKindOfClass:[NSView class]] )
+ {
+ // Some subview of this control view really is the first responder right now.
+ check( [(NSView *)firstResponder isDescendantOf:view->fWebView] );
+
+ // Make the window the first responder, so that no view is the key view.
+ [view->fKitWindow makeFirstResponder:view->fKitWindow];
+
+ // If this control is not allowed to do autodisplay, don't let
+ // it autodisplay any just-changed focus rings or text on the
+ // next go around the event loop. I'm probably clearing more
+ // dirty rects than I have to, but it doesn't seem to hurt in
+ // the print panel accessory view case, and I don't have time
+ // to figure out exactly what -[NSCell _setKeyboardFocusRingNeedsDisplay]
+ // is doing when invoked indirectly from -makeFirstResponder up above. M.P. Notice - 12/4/00
+
+ if ( !inAutodisplay )
+ [[view->fWebView opaqueAncestor] _clearDirtyRectsForTree];
+ }
+ else
+ {
+ // The Cocoa first responder does not correspond to the Carbon
+ // control that has the keyboard focus. This can happen when
+ // you've closed a dialog by hitting return in an NSTextView
+ // that's a subview of this one; Cocoa closed the window, and
+ // now Carbon is telling this control to relinquish the focus
+ // as it's being disposed. There's nothing to do.
+
+ check(firstResponder==window);
+ }
+}
+
+//----------------------------------------------------------------------------------
+// ActiveStateChanged
+//----------------------------------------------------------------------------------
+//
+static void
+ActiveStateChanged( HIWebView* view )
+{
+ if ( [view->fWebView respondsToSelector:@selector(setEnabled)] )
+ {
+ [(NSControl*)view->fWebView setEnabled: IsControlEnabled( view->fViewRef )];
+ HIViewSetNeedsDisplay( view->fViewRef, true );
+ }
+}
+
+
+//----------------------------------------------------------------------------------
+// ProcessCommand
+//----------------------------------------------------------------------------------
+//
+static OSStatus
+ProcessCommand( HIWebView* inView, const HICommand* inCommand )
+{
+ OSStatus result = eventNotHandledErr;
+ NSResponder* resp;
+
+ resp = [inView->fKitWindow firstResponder];
+
+ if ( [resp isKindOfClass:[NSView class]] )
+ {
+ NSView* respView = (NSView*)resp;
+
+ if ( respView == inView->fWebView
+ || [respView isDescendantOf: inView->fWebView] )
+ {
+ switch ( inCommand->commandID )
+ {
+ case kHICommandCut:
+ case kHICommandCopy:
+ case kHICommandPaste:
+ case kHICommandClear:
+ case kHICommandSelectAll:
+ {
+ SEL selector = _NSSelectorForHICommand( inCommand );
+ if ( [respView respondsToSelector:selector] )
+ {
+ [respView performSelector:selector withObject:nil];
+ result = noErr;
+ }
+ }
+ break;
+ }
+ }
+ }
+
+ return result;
+}
+
+//----------------------------------------------------------------------------------
+// UpdateCommandStatus
+//----------------------------------------------------------------------------------
+//
+static OSStatus
+UpdateCommandStatus( HIWebView* inView, const HICommand* inCommand )
+{
+ OSStatus result = eventNotHandledErr;
+ MenuItemProxy* proxy = NULL;
+ NSResponder* resp;
+
+ resp = [inView->fKitWindow firstResponder];
+
+ if ( [resp isKindOfClass:[NSView class]] )
+ {
+ NSView* respView = (NSView*)resp;
+
+ if ( respView == inView->fWebView
+ || [respView isDescendantOf: inView->fWebView] )
+ {
+ if ( inCommand->attributes & kHICommandFromMenu )
+ {
+ SEL selector = _NSSelectorForHICommand( inCommand );
+
+ if ( selector )
+ {
+ if ( [resp respondsToSelector: selector] )
+ {
+ proxy = [[MenuItemProxy alloc] initWithAction: selector];
+
+ // Can't use -performSelector:withObject: here because the method we're calling returns BOOL, while
+ // -performSelector:withObject:'s return value is assumed to be an id.
+ BOOL (*validationFunction)(id, SEL, id) = (BOOL (*)(id, SEL, id))objc_msgSend;
+ if (validationFunction(resp, @selector(validateUserInterfaceItem:), proxy))
+ EnableMenuItem( inCommand->menu.menuRef, inCommand->menu.menuItemIndex );
+ else
+ DisableMenuItem( inCommand->menu.menuRef, inCommand->menu.menuItemIndex );
+
+ result = noErr;
+ }
+ }
+ }
+ }
+ }
+
+ if ( proxy )
+ [proxy release];
+
+ return result;
+}
+
+// Blatantly stolen from AppKit and cropped a bit
+
+//----------------------------------------------------------------------------------
+// _NSSelectorForHICommand
+//----------------------------------------------------------------------------------
+//
+static SEL
+_NSSelectorForHICommand( const HICommand* inCommand )
+{
+ switch ( inCommand->commandID )
+ {
+ case kHICommandUndo: return @selector(undo:);
+ case kHICommandRedo: return @selector(redo:);
+ case kHICommandCut : return @selector(cut:);
+ case kHICommandCopy : return @selector(copy:);
+ case kHICommandPaste: return @selector(paste:);
+ case kHICommandClear: return @selector(delete:);
+ case kHICommandSelectAll: return @selector(selectAll:);
+ default: return NULL;
+ }
+
+ return NULL;
+}
+
+
+//-----------------------------------------------------------------------------------
+// HIWebViewEventHandler
+//-----------------------------------------------------------------------------------
+// Our object's virtual event handler method. I'm not sure if we need this these days.
+// We used to do various things with it, but those days are long gone...
+//
+static OSStatus
+HIWebViewEventHandler(
+ EventHandlerCallRef inCallRef,
+ EventRef inEvent,
+ void * inUserData )
+{
+ OSStatus result = eventNotHandledErr;
+ HIPoint where;
+ OSType tag;
+ void * ptr;
+ Size size;
+ UInt32 features;
+ RgnHandle region = NULL;
+ ControlPartCode part;
+ HIWebView* view = (HIWebView*)inUserData;
+
+ // [NSApp setWindowsNeedUpdate:YES] must be called before events so that ActivateTSMDocument is called to set an active document.
+ // Without an active document, TSM will use a default document which uses a bottom-line input window which we don't want.
+ [NSApp setWindowsNeedUpdate:YES];
+
+ switch ( GetEventClass( inEvent ) )
+ {
+ case kEventClassHIObject:
+ switch ( GetEventKind( inEvent ) )
+ {
+ case kEventHIObjectConstruct:
+ {
+ HIObjectRef object;
+
+ result = GetEventParameter( inEvent, kEventParamHIObjectInstance,
+ typeHIObjectRef, NULL, sizeof( HIObjectRef ), NULL, &object );
+ require_noerr( result, MissingParameter );
+
+ // on entry for our construct event, we're passed the
+ // creation proc we registered with for this class.
+ // we use it now to create the instance, and then we
+ // replace the instance parameter data with said instance
+ // as type void.
+
+ view = HIWebViewConstructor( (HIViewRef)object );
+
+ if ( view )
+ {
+ SetEventParameter( inEvent, kEventParamHIObjectInstance,
+ typeVoidPtr, sizeof( void * ), &view );
+ }
+ }
+ break;
+
+ case kEventHIObjectDestruct:
+ HIWebViewDestructor( view );
+ // result is unimportant
+ break;
+ }
+ break;
+
+ case kEventClassKeyboard:
+ {
+ NSEvent* kitEvent = WKCreateNSEventWithCarbonEvent(inEvent);
+ [view->fKitWindow sendSuperEvent:kitEvent];
+ [kitEvent release];
+ result = noErr;
+ }
+ break;
+
+ case kEventClassMouse:
+ switch ( GetEventKind( inEvent ) )
+ {
+ case kEventMouseUp:
+ result = MouseUp( view, inEvent );
+ break;
+
+ case kEventMouseWheelMoved:
+ result = MouseWheelMoved( view, inEvent );
+ break;
+
+ case kEventMouseMoved:
+ result = MouseMoved( view, inEvent );
+ break;
+
+ case kEventMouseDragged:
+ result = MouseDragged( view, inEvent );
+ break;
+ }
+ break;
+
+ case kEventClassCommand:
+ {
+ HICommand command;
+
+ result = GetEventParameter( inEvent, kEventParamDirectObject, typeHICommand, NULL,
+ sizeof( HICommand ), NULL, &command );
+ require_noerr( result, MissingParameter );
+
+ switch ( GetEventKind( inEvent ) )
+ {
+ case kEventCommandProcess:
+ result = ProcessCommand( view, &command );
+ break;
+
+ case kEventCommandUpdateStatus:
+ result = UpdateCommandStatus( view, &command );
+ break;
+ }
+ }
+ break;
+
+ case kEventClassControl:
+ switch ( GetEventKind( inEvent ) )
+ {
+ case kEventControlInitialize:
+ features = GetBehaviors();
+ SetEventParameter( inEvent, kEventParamControlFeatures, typeUInt32,
+ sizeof( UInt32 ), &features );
+ result = noErr;
+ break;
+
+ case kEventControlDraw:
+ {
+ CGContextRef context = NULL;
+
+ GetEventParameter( inEvent, kEventParamRgnHandle, typeQDRgnHandle, NULL,
+ sizeof( RgnHandle ), NULL, &region );
+ GetEventParameter( inEvent, kEventParamCGContextRef, typeCGContextRef, NULL,
+ sizeof( CGContextRef ), NULL, &context );
+
+ Draw( view, region, context );
+
+ result = noErr;
+ }
+ break;
+
+ case kEventControlHitTest:
+ GetEventParameter( inEvent, kEventParamMouseLocation, typeHIPoint, NULL,
+ sizeof( HIPoint ), NULL, &where );
+ part = HitTest( view, &where );
+ SetEventParameter( inEvent, kEventParamControlPart, typeControlPartCode, sizeof( ControlPartCode ), &part );
+ result = noErr;
+ break;
+
+ case kEventControlGetPartRegion:
+ GetEventParameter( inEvent, kEventParamControlPart, typeControlPartCode, NULL,
+ sizeof( ControlPartCode ), NULL, &part );
+ GetEventParameter( inEvent, kEventParamControlRegion, typeQDRgnHandle, NULL,
+ sizeof( RgnHandle ), NULL, &region );
+ result = GetRegion( view, part, region );
+ break;
+
+ case kEventControlGetData:
+ GetEventParameter(inEvent, kEventParamControlPart, typeControlPartCode, NULL, sizeof(ControlPartCode), NULL, &part);
+ GetEventParameter(inEvent, kEventParamControlDataTag, typeEnumeration, NULL, sizeof(OSType), NULL, &tag);
+ GetEventParameter(inEvent, kEventParamControlDataBuffer, typePtr, NULL, sizeof(Ptr), NULL, &ptr);
+ GetEventParameter(inEvent, kEventParamControlDataBufferSize, typeByteCount, NULL, sizeof(Size), NULL, &size);
+
+ if (tag == kControlKindTag) {
+ Size outSize;
+ result = noErr;
+
+ if (ptr) {
+ if (size != sizeof(ControlKind))
+ result = errDataSizeMismatch;
+ else
+ (*(ControlKind *)ptr) = GetKind();
+ }
+
+ outSize = sizeof(ControlKind);
+ SetEventParameter(inEvent, kEventParamControlDataBufferSize, typeByteCount, sizeof(Size), &outSize);
+ }
+
+ break;
+
+ case kEventControlBoundsChanged:
+ {
+ HIRect prevRect, currRect;
+ UInt32 attrs;
+
+ GetEventParameter( inEvent, kEventParamAttributes, typeUInt32, NULL,
+ sizeof( UInt32 ), NULL, &attrs );
+ GetEventParameter( inEvent, kEventParamOriginalBounds, typeHIRect, NULL,
+ sizeof( HIRect ), NULL, &prevRect );
+ GetEventParameter( inEvent, kEventParamCurrentBounds, typeHIRect, NULL,
+ sizeof( HIRect ), NULL, &currRect );
+
+ BoundsChanged( view, attrs, &prevRect, &currRect );
+ result = noErr;
+ }
+ break;
+
+ case kEventControlActivate:
+ ActiveStateChanged( view );
+ result = noErr;
+ break;
+
+ case kEventControlDeactivate:
+ ActiveStateChanged( view );
+ result = noErr;
+ break;
+
+ case kEventControlOwningWindowChanged:
+ {
+ WindowRef fromWindow, toWindow;
+
+ result = GetEventParameter( inEvent, kEventParamControlOriginalOwningWindow, typeWindowRef, NULL,
+ sizeof( WindowRef ), NULL, &fromWindow );
+ require_noerr( result, MissingParameter );
+
+ result = GetEventParameter( inEvent, kEventParamControlCurrentOwningWindow, typeWindowRef, NULL,
+ sizeof( WindowRef ), NULL, &toWindow );
+ require_noerr( result, MissingParameter );
+
+ OwningWindowChanged( view, fromWindow, toWindow );
+
+ result = noErr;
+ }
+ break;
+
+ case kEventControlClick:
+ result = Click( view, inEvent );
+ break;
+
+ case kEventControlContextualMenuClick:
+ result = ContextMenuClick( view, inEvent );
+ break;
+
+ case kEventControlSetFocusPart:
+ {
+ ControlPartCode desiredFocus;
+ RgnHandle invalidRgn;
+ Boolean focusEverything;
+ ControlPartCode actualFocus;
+
+ result = GetEventParameter( inEvent, kEventParamControlPart, typeControlPartCode, NULL,
+ sizeof( ControlPartCode ), NULL, &desiredFocus );
+ require_noerr( result, MissingParameter );
+
+ GetEventParameter( inEvent, kEventParamControlInvalRgn, typeQDRgnHandle, NULL,
+ sizeof( RgnHandle ), NULL, &invalidRgn );
+
+ focusEverything = false; // a good default in case the parameter doesn't exist
+
+ GetEventParameter( inEvent, kEventParamControlFocusEverything, typeBoolean, NULL,
+ sizeof( Boolean ), NULL, &focusEverything );
+
+ result = SetFocusPart( view, desiredFocus, invalidRgn, focusEverything, &actualFocus );
+
+ if ( result == noErr )
+ verify_noerr( SetEventParameter( inEvent, kEventParamControlPart, typeControlPartCode,
+ sizeof( ControlPartCode ), &actualFocus ) );
+ }
+ break;
+
+ // some other kind of Control event
+ default:
+ break;
+ }
+ break;
+
+ // some other event class
+ default:
+ break;
+ }
+
+MissingParameter:
+ return result;
+}
+
+
+static void UpdateObserver(CFRunLoopObserverRef observer, CFRunLoopActivity activity, void *info);
+
+static void
+StartUpdateObserver( HIWebView* view )
+{
+ CFRunLoopObserverContext context;
+ CFRunLoopObserverRef observer;
+ CFRunLoopRef mainRunLoop;
+
+ check( view->fIsComposited == false );
+ check( view->fUpdateObserver == NULL );
+
+ context.version = 0;
+ context.info = view;
+ context.retain = NULL;
+ context.release = NULL;
+ context.copyDescription = NULL;
+
+ mainRunLoop = (CFRunLoopRef)GetCFRunLoopFromEventLoop( GetMainEventLoop() );
+ observer = CFRunLoopObserverCreate( NULL, kCFRunLoopEntry | kCFRunLoopBeforeWaiting, true, 0, UpdateObserver, &context );
+ CFRunLoopAddObserver( mainRunLoop, observer, kCFRunLoopCommonModes );
+
+ view->fUpdateObserver = observer;
+
+// printf( "Update observer started\n" );
+}
+
+static void
+StopUpdateObserver( HIWebView* view )
+{
+ check( view->fIsComposited == false );
+ check( view->fUpdateObserver != NULL );
+
+ CFRunLoopObserverInvalidate( view->fUpdateObserver );
+ CFRelease( view->fUpdateObserver );
+ view->fUpdateObserver = NULL;
+
+// printf( "Update observer removed\n" );
+}
+
+static void
+UpdateObserver( CFRunLoopObserverRef observer, CFRunLoopActivity activity, void *info )
+{
+ HIWebView* view = (HIWebView*)info;
+ RgnHandle region = NewRgn();
+
+// printf( "Update observer called\n" );
+
+ if ( region )
+ {
+ GetWindowRegion( GetControlOwner( view->fViewRef ), kWindowUpdateRgn, region );
+
+ if ( !EmptyRgn( region ) )
+ {
+ RgnHandle ourRgn = NewRgn();
+ Rect rect;
+
+ GetWindowBounds( GetControlOwner( view->fViewRef ), kWindowStructureRgn, &rect );
+
+// printf( "Update region is non-empty\n" );
+
+ if ( ourRgn )
+ {
+ Rect rect;
+ GrafPtr savePort, port;
+ Point offset = { 0, 0 };
+
+ port = GetWindowPort( GetControlOwner( view->fViewRef ) );
+
+ GetPort( &savePort );
+ SetPort( port );
+
+ GlobalToLocal( &offset );
+ OffsetRgn( region, offset.h, offset.v );
+
+ GetControlBounds( view->fViewRef, &rect );
+ RectRgn( ourRgn, &rect );
+
+// printf( "our control is at %d %d %d %d\n",
+// rect.top, rect.left, rect.bottom, rect.right );
+
+ GetRegionBounds( region, &rect );
+// printf( "region is at %d %d %d %d\n",
+// rect.top, rect.left, rect.bottom, rect.right );
+
+ SectRgn( ourRgn, region, ourRgn );
+
+ GetRegionBounds( ourRgn, &rect );
+// printf( "intersection is %d %d %d %d\n",
+// rect.top, rect.left, rect.bottom, rect.right );
+ if ( !EmptyRgn( ourRgn ) )
+ {
+ RgnHandle saveVis = NewRgn();
+
+// printf( "looks like we should draw\n" );
+
+ if ( saveVis )
+ {
+// RGBColor kRedColor = { 0xffff, 0, 0 };
+
+ GetPortVisibleRegion( GetWindowPort( GetControlOwner( view->fViewRef ) ), saveVis );
+ SetPortVisibleRegion( GetWindowPort( GetControlOwner( view->fViewRef ) ), ourRgn );
+
+// RGBForeColor( &kRedColor );
+// PaintRgn( ourRgn );
+// QDFlushPortBuffer( port, NULL );
+// Delay( 15, NULL );
+
+ Draw1Control( view->fViewRef );
+ ValidWindowRgn( GetControlOwner( view->fViewRef ), ourRgn );
+
+ SetPortVisibleRegion( GetWindowPort( GetControlOwner( view->fViewRef ) ), saveVis );
+ DisposeRgn( saveVis );
+ }
+ }
+
+ SetPort( savePort );
+
+ DisposeRgn( ourRgn );
+ }
+ }
+
+ DisposeRgn( region );
+ }
+}
+
+#endif
diff --git a/WebKit/mac/Configurations/Base.xcconfig b/WebKit/mac/Configurations/Base.xcconfig
new file mode 100644
index 0000000..ad1ad95
--- /dev/null
+++ b/WebKit/mac/Configurations/Base.xcconfig
@@ -0,0 +1,37 @@
+DEAD_CODE_STRIPPING = YES;
+DEBUG_INFORMATION_FORMAT = dwarf;
+GCC_C_LANGUAGE_STANDARD = gnu99;
+GCC_DEBUGGING_SYMBOLS = default;
+GCC_DYNAMIC_NO_PIC = NO;
+GCC_ENABLE_CPP_EXCEPTIONS = NO;
+GCC_ENABLE_CPP_RTTI = NO;
+GCC_ENABLE_OBJC_EXCEPTIONS = YES;
+GCC_ENABLE_OBJC_GC = supported;
+GCC_ENABLE_SYMBOL_SEPARATION = NO;
+GCC_FAST_OBJC_DISPATCH = YES;
+GCC_MODEL_TUNING = G5;
+GCC_OPTIMIZATION_LEVEL = 2;
+GCC_PRECOMPILE_PREFIX_HEADER = YES;
+GCC_THREADSAFE_STATICS = NO;
+GCC_TREAT_WARNINGS_AS_ERRORS = YES;
+GCC_WARN_ABOUT_MISSING_NEWLINE = YES;
+GCC_WARN_ABOUT_MISSING_PROTOTYPES = YES;
+GCC_WARN_NON_VIRTUAL_DESTRUCTOR = YES;
+LINKER_DISPLAYS_MANGLED_NAMES = YES;
+PREBINDING = NO;
+VALID_ARCHS = i386 ppc x86_64 ppc64;
+// FIXME: <rdar://problem/5070292> WebKit should build with -Wshorten-64-to-32
+WARNING_CFLAGS = -Wall -W -Wcast-align -Wchar-subscripts -Wformat-security -Wmissing-format-attribute -Wpointer-arith -Wwrite-strings -Wno-format-y2k -Wno-unused-parameter -Wundef;
+
+
+// <rdar://problem/5488678>: Production builds on 10.4 PowerPC need to have debugging symbols disabled to prevent a huge STABS section being generated.
+// Xcode on 10.4 does not define MAC_OS_X_VERSION_MAJOR, so the default Mac OS X version is treated as 10.4.
+GCC_GENERATE_DEBUGGING_SYMBOLS = $(GCC_GENERATE_DEBUGGING_SYMBOLS_$(CURRENT_ARCH));
+GCC_GENERATE_DEBUGGING_SYMBOLS_i386 = YES;
+GCC_GENERATE_DEBUGGING_SYMBOLS_ppc = $(GCC_GENERATE_DEBUGGING_SYMBOLS_$(CURRENT_ARCH)_$(CONFIGURATION));
+GCC_GENERATE_DEBUGGING_SYMBOLS_ppc_Debug = YES;
+GCC_GENERATE_DEBUGGING_SYMBOLS_ppc_Release = YES;
+GCC_GENERATE_DEBUGGING_SYMBOLS_ppc_Production = $(GCC_GENERATE_DEBUGGING_SYMBOLS_$(CURRENT_ARCH)_$(CONFIGURATION)_$(MAC_OS_X_VERSION_MAJOR));
+GCC_GENERATE_DEBUGGING_SYMBOLS_ppc_Production_ = NO;
+GCC_GENERATE_DEBUGGING_SYMBOLS_ppc_Production_1040 = NO;
+GCC_GENERATE_DEBUGGING_SYMBOLS_ppc_Production_1050 = YES;
diff --git a/WebKit/mac/Configurations/DebugRelease.xcconfig b/WebKit/mac/Configurations/DebugRelease.xcconfig
new file mode 100644
index 0000000..0a6dc2d
--- /dev/null
+++ b/WebKit/mac/Configurations/DebugRelease.xcconfig
@@ -0,0 +1,11 @@
+#include "Base.xcconfig"
+MACOSX_DEPLOYMENT_TARGET = $(MACOSX_DEPLOYMENT_TARGET_$(MAC_OS_X_VERSION_MAJOR));
+MACOSX_DEPLOYMENT_TARGET_ = 10.4;
+MACOSX_DEPLOYMENT_TARGET_1040 = 10.4;
+MACOSX_DEPLOYMENT_TARGET_1050 = 10.5;
+MACOSX_DEPLOYMENT_TARGET_1060 = 10.6;
+WEBKIT_SYSTEM_INTERFACE_LIBRARY = $(WEBKIT_SYSTEM_INTERFACE_LIBRARY_$(MAC_OS_X_VERSION_MAJOR));
+WEBKIT_SYSTEM_INTERFACE_LIBRARY_ = WebKitSystemInterfaceTiger;
+WEBKIT_SYSTEM_INTERFACE_LIBRARY_1040 = WebKitSystemInterfaceTiger;
+WEBKIT_SYSTEM_INTERFACE_LIBRARY_1050 = WebKitSystemInterfaceLeopard;
+WEBKIT_SYSTEM_INTERFACE_LIBRARY_1060 = WebKitSystemInterfaceLeopard;
diff --git a/WebKit/mac/Configurations/Version.xcconfig b/WebKit/mac/Configurations/Version.xcconfig
new file mode 100644
index 0000000..48128b5
--- /dev/null
+++ b/WebKit/mac/Configurations/Version.xcconfig
@@ -0,0 +1,27 @@
+MAJOR_VERSION = 526;
+MINOR_VERSION = 0;
+TINY_VERSION = 0;
+FULL_VERSION = $(MAJOR_VERSION);
+
+// The bundle version is set based on the current build configuration, see below.
+BUNDLE_VERSION = $(BUNDLE_VERSION_$(CONFIGURATION));
+
+// The local builds are always just the major version with a Plus suffix.
+BUNDLE_VERSION_Release = $(FULL_VERSION)+;
+BUNDLE_VERSION_Debug = $(BUNDLE_VERSION_Release);
+
+// The system version prefix is based on the current system version.
+SYSTEM_VERSION_PREFIX = $(SYSTEM_VERSION_PREFIX_$(MAC_OS_X_VERSION_MAJOR));
+SYSTEM_VERSION_PREFIX_ = 4; // Some Tiger versions of Xcode don't set MAC_OS_X_VERSION_MAJOR.
+SYSTEM_VERSION_PREFIX_1040 = 4;
+SYSTEM_VERSION_PREFIX_1050 = 5;
+SYSTEM_VERSION_PREFIX_1060 = 6;
+
+// The production build always uses the full version with a system version prefix.
+BUNDLE_VERSION_Production = $(SYSTEM_VERSION_PREFIX)$(FULL_VERSION);
+
+// If $(CONFIGURATION) is undefined, use the Production version.
+BUNDLE_VERSION_ = $(BUNDLE_VERSION_Production);
+
+DYLIB_COMPATIBILITY_VERSION = 1;
+DYLIB_CURRENT_VERSION = $(FULL_VERSION);
diff --git a/WebKit/mac/Configurations/WebKit.xcconfig b/WebKit/mac/Configurations/WebKit.xcconfig
new file mode 100644
index 0000000..0331798
--- /dev/null
+++ b/WebKit/mac/Configurations/WebKit.xcconfig
@@ -0,0 +1,19 @@
+#include "Version.xcconfig"
+EXPORTED_SYMBOLS_FILE = $(EXPORTED_SYMBOLS_FILE_$(CURRENT_ARCH));
+EXPORTED_SYMBOLS_FILE_ = mac/WebKit.exp;
+EXPORTED_SYMBOLS_FILE_i386 = mac/WebKit.exp;
+EXPORTED_SYMBOLS_FILE_ppc = mac/WebKit.exp;
+EXPORTED_SYMBOLS_FILE_ppc64 = $(BUILT_PRODUCTS_DIR)/DerivedSources/WebKit/WebKit.LP64.exp;
+EXPORTED_SYMBOLS_FILE_x86_64 = $(BUILT_PRODUCTS_DIR)/DerivedSources/WebKit/WebKit.LP64.exp;
+FEATURE_DEFINES = ENABLE_CROSS_DOCUMENT_MESSAGING ENABLE_DATABASE ENABLE_ICONDATABASE ENABLE_SVG ENABLE_SVG_FONTS ENABLE_SVG_AS_IMAGE ENABLE_SVG_USE ENABLE_SVG_FOREIGN_OBJECT ENABLE_XPATH ENABLE_XSLT ENABLE_VIDEO;
+FRAMEWORK_SEARCH_PATHS = $(UMBRELLA_FRAMEWORKS_DIR) $(SYSTEM_LIBRARY_DIR)/Frameworks/ApplicationServices.framework/Frameworks $(SYSTEM_LIBRARY_DIR)/Frameworks/Carbon.framework/Frameworks $(SYSTEM_LIBRARY_DIR)/Frameworks/Quartz.framework/Frameworks $(SYSTEM_LIBRARY_DIR)/PrivateFrameworks $(FRAMEWORK_SEARCH_PATHS);
+GCC_PREFIX_HEADER = mac/WebKitPrefix.h;
+GCC_PREPROCESSOR_DEFINITIONS = $(DEBUG_DEFINES) $(FEATURE_DEFINES) FRAMEWORK_NAME=WebKit $(GCC_PREPROCESSOR_DEFINITIONS);
+HEADER_SEARCH_PATHS = mac/ForwardingHeaders mac/icu "${BUILT_PRODUCTS_DIR}/usr/local/include" "${BUILT_PRODUCTS_DIR}/DerivedSources/WebKit" $(HEADER_SEARCH_PATHS);
+INFOPLIST_FILE = mac/Info.plist;
+INSTALL_PATH = $(SYSTEM_LIBRARY_DIR)/Frameworks;
+JAVASCRIPTCORE_PRIVATE_HEADERS_DIR = $(NEXT_ROOT)$(SYSTEM_LIBRARY_DIR)/Frameworks/JavaScriptCore.framework/PrivateHeaders;
+PRODUCT_NAME = WebKit;
+UMBRELLA_FRAMEWORKS_DIR = $(NEXT_ROOT)$(SYSTEM_LIBRARY_DIR)/Frameworks/WebKit.framework/Versions/A/Frameworks;
+WEBCORE_PRIVATE_HEADERS_DIR = $(UMBRELLA_FRAMEWORKS_DIR)/WebCore.framework/PrivateHeaders;
+OTHER_LDFLAGS = -sub_umbrella WebCore $(OTHER_LDFLAGS);
diff --git a/WebKit/mac/DOM/WebDOMOperations.h b/WebKit/mac/DOM/WebDOMOperations.h
new file mode 100644
index 0000000..606dd19
--- /dev/null
+++ b/WebKit/mac/DOM/WebDOMOperations.h
@@ -0,0 +1,111 @@
+/*
+ * Copyright (C) 2004, 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/DOMCore.h>
+#import <WebKit/DOMHTML.h>
+#import <WebKit/DOMRange.h>
+
+@class WebArchive;
+@class WebFrame;
+
+@interface DOMNode (WebDOMNodeOperations)
+
+/*!
+ @method webArchive
+ @result A WebArchive representing the node and the children of the node.
+*/
+- (WebArchive *)webArchive;
+
+@end
+
+@interface DOMDocument (WebDOMDocumentOperations)
+
+/*!
+ @method webFrame
+ @abstract Returns the frame of the DOM document.
+*/
+- (WebFrame *)webFrame;
+
+/*!
+ @method URLWithAttributeString:
+ @abstract Constructs a URL given an attribute string.
+ @discussion This method constructs a URL given an attribute string just as WebKit does.
+ An attribute string is the value of an attribute of an element such as the href attribute on
+ the DOMHTMLAnchorElement class. This method is only applicable to attributes that refer to URLs.
+*/
+- (NSURL *)URLWithAttributeString:(NSString *)string;
+
+@end
+
+@interface DOMRange (WebDOMRangeOperations)
+
+/*!
+ @method webArchive
+ @result A WebArchive representing the range.
+*/
+- (WebArchive *)webArchive;
+
+/*!
+ @method markupString
+ @result A markup string representing the range.
+*/
+- (NSString *)markupString;
+
+@end
+
+@interface DOMHTMLFrameElement (WebDOMHTMLFrameElementOperations)
+
+/*!
+ @method contentFrame
+ @abstract Returns the content frame of the element.
+*/
+- (WebFrame *)contentFrame;
+
+@end
+
+@interface DOMHTMLIFrameElement (WebDOMHTMLIFrameElementOperations)
+
+/*!
+ @method contentFrame
+ @abstract Returns the content frame of the element.
+*/
+- (WebFrame *)contentFrame;
+
+@end
+
+@interface DOMHTMLObjectElement (WebDOMHTMLObjectElementOperations)
+
+/*!
+ @method contentFrame
+ @abstract Returns the content frame of the element.
+ @discussion Returns non-nil only if the object represents a child frame
+ such as if the data of the object is HTML content.
+*/
+- (WebFrame *)contentFrame;
+
+@end
diff --git a/WebKit/mac/DOM/WebDOMOperations.mm b/WebKit/mac/DOM/WebDOMOperations.mm
new file mode 100644
index 0000000..ace21c3
--- /dev/null
+++ b/WebKit/mac/DOM/WebDOMOperations.mm
@@ -0,0 +1,341 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebDOMOperationsPrivate.h>
+
+#import <WebKit/DOMExtensions.h>
+#import <WebKit/DOMHTML.h>
+#import <JavaScriptCore/Assertions.h>
+#import <WebKit/WebFrameBridge.h>
+#import <WebKit/WebDataSourcePrivate.h>
+#import <WebKit/WebFramePrivate.h>
+#import <WebKit/WebKitNSStringExtras.h>
+#import <WebKit/WebArchiver.h>
+
+#if ENABLE(SVG)
+#import <WebKit/DOMSVG.h>
+#endif
+
+@implementation DOMNode (WebDOMNodeOperations)
+
+- (WebFrameBridge *)_bridge
+{
+ return (WebFrameBridge *)[WebFrameBridge bridgeForDOMDocument:[self ownerDocument]];
+}
+
+- (WebArchive *)webArchive
+{
+ return [WebArchiver archiveNode:self];
+}
+
+- (NSString *)markupString
+{
+ return [[self _bridge] markupStringFromNode:self nodes:nil];
+}
+
+- (NSArray *)_URLsFromSelectors:(SEL)firstSel, ...
+{
+ NSMutableArray *URLs = [NSMutableArray array];
+
+ va_list args;
+ va_start(args, firstSel);
+
+ SEL selector = firstSel;
+ do {
+#if ENABLE(SVG)
+ NSString *string;
+ id attributeValue = [self performSelector:selector];
+ if ([attributeValue isKindOfClass:[DOMSVGAnimatedString class]])
+ string = [(DOMSVGAnimatedString*)attributeValue animVal];
+ else
+ string = attributeValue;
+#else
+ NSString *string = [self performSelector:selector];
+#endif
+ if ([string length] > 0)
+ [URLs addObject:[[self ownerDocument] URLWithAttributeString:string]];
+ } while ((selector = va_arg(args, SEL)) != nil);
+
+ va_end(args);
+
+ return URLs;
+}
+
+- (NSArray *)_subresourceURLs
+{
+ return nil;
+}
+
+@end
+
+@implementation DOMDocument (WebDOMDocumentOperations)
+
+- (WebFrame *)webFrame
+{
+ return [[self _bridge] webFrame];
+}
+
+- (NSURL *)URLWithAttributeString:(NSString *)string
+{
+ return [[self _bridge] URLWithAttributeString:string];
+}
+
+@end
+
+@implementation DOMDocument (WebDOMDocumentOperationsPrivate)
+
+- (DOMRange *)_createRangeWithNode:(DOMNode *)node
+{
+ DOMRange *range = [self createRange];
+ [range selectNode:node];
+ return range;
+}
+
+- (DOMRange *)_documentRange
+{
+ return [self _createRangeWithNode:[self documentElement]];
+}
+
+@end
+
+@implementation DOMRange (WebDOMRangeOperations)
+
+- (WebFrameBridge *)_bridge
+{
+ return [[self startContainer] _bridge];
+}
+
+- (WebArchive *)webArchive
+{
+ return [WebArchiver archiveRange:self];
+}
+
+- (NSString *)markupString
+{
+ return [[self _bridge] markupStringFromRange:self nodes:nil];
+}
+
+@end
+
+@implementation DOMHTMLBodyElement (WebDOMHTMLBodyElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ return [self _URLsFromSelectors:@selector(background), nil];
+}
+
+@end
+
+@implementation DOMHTMLInputElement (WebDOMHTMLInputElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ return [self _URLsFromSelectors:@selector(src), nil];
+}
+
+@end
+
+@implementation DOMHTMLLinkElement (WebDOMHTMLLinkElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ NSString *relName = [self rel];
+ if ([relName _webkit_isCaseInsensitiveEqualToString:@"stylesheet"] || [relName _webkit_isCaseInsensitiveEqualToString:@"icon"]) {
+ return [self _URLsFromSelectors:@selector(href), nil];
+ }
+ return nil;
+}
+
+@end
+
+@implementation DOMHTMLScriptElement (WebDOMHTMLScriptElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ return [self _URLsFromSelectors:@selector(src), nil];
+}
+
+@end
+
+@implementation DOMHTMLImageElement (WebDOMHTMLImageElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ SEL useMapSelector = [[self useMap] hasPrefix:@"#"] ? nil : @selector(useMap);
+ return [self _URLsFromSelectors:@selector(src), useMapSelector, nil];
+}
+
+@end
+
+#if ENABLE(SVG)
+
+@implementation DOMSVGImageElement (WebDOMSVGImageElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ return [self _URLsFromSelectors:@selector(href), nil];
+}
+
+@end
+
+@implementation DOMSVGScriptElement (WebDOMSVGScriptElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ return [self _URLsFromSelectors:@selector(href), nil];
+}
+
+@end
+
+@implementation DOMSVGCursorElement (WebDOMSVGCursorElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ return [self _URLsFromSelectors:@selector(href), nil];
+}
+
+@end
+
+#if ENABLE(SVG_FILTERS)
+@implementation DOMSVGFEImageElement (WebDOMSVGFEImageElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ return [self _URLsFromSelectors:@selector(href), nil];
+}
+
+@end
+#endif
+
+#endif
+
+@implementation DOMProcessingInstruction (WebDOMProcessingInstructionOperationsPrivate)
+
+- (NSString *)_stylesheetURL
+{
+ DOMStyleSheet *styleSheet = [self sheet];
+ if (styleSheet)
+ return [styleSheet href];
+ return nil;
+}
+
+- (NSArray *)_subresourceURLs
+{
+ return [self _URLsFromSelectors:@selector(_stylesheetURL), nil];
+}
+
+@end
+
+@implementation DOMHTMLEmbedElement (WebDOMHTMLEmbedElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ return [self _URLsFromSelectors:@selector(src), nil];
+}
+
+@end
+
+@implementation DOMHTMLObjectElement (WebDOMHTMLObjectElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ SEL useMapSelector = [[self useMap] hasPrefix:@"#"] ? nil : @selector(useMap);
+ return [self _URLsFromSelectors:@selector(data), useMapSelector, nil];
+}
+
+@end
+
+@implementation DOMHTMLParamElement (WebDOMHTMLParamElementOperationsPrivate)
+
+- (NSArray *)_subresourceURLs
+{
+ NSString *paramName = [self name];
+ if ([paramName _webkit_isCaseInsensitiveEqualToString:@"data"] ||
+ [paramName _webkit_isCaseInsensitiveEqualToString:@"movie"] ||
+ [paramName _webkit_isCaseInsensitiveEqualToString:@"src"]) {
+ return [self _URLsFromSelectors:@selector(value), nil];
+ }
+ return nil;
+}
+
+@end
+
+@implementation DOMHTMLTableElement (WebDOMHTMLTableElementOperationsPrivate)
+
+- (NSString *)_web_background
+{
+ return [self getAttribute:@"background"];
+}
+
+- (NSArray *)_subresourceURLs
+{
+ return [self _URLsFromSelectors:@selector(_web_background), nil];
+}
+
+@end
+
+@implementation DOMHTMLTableCellElement (WebDOMHTMLTableCellElementOperationsPrivate)
+
+- (NSString *)_web_background
+{
+ return [self getAttribute:@"background"];
+}
+
+- (NSArray *)_subresourceURLs
+{
+ return [self _URLsFromSelectors:@selector(_web_background), nil];
+}
+
+@end
+
+@implementation DOMHTMLFrameElement (WebDOMHTMLFrameElementOperations)
+
+- (WebFrame *)contentFrame
+{
+ return [[self contentDocument] webFrame];
+}
+
+@end
+
+@implementation DOMHTMLIFrameElement (WebDOMHTMLIFrameElementOperations)
+
+- (WebFrame *)contentFrame
+{
+ return [[self contentDocument] webFrame];
+}
+
+@end
+
+@implementation DOMHTMLObjectElement (WebDOMHTMLObjectElementOperations)
+
+- (WebFrame *)contentFrame
+{
+ return [[self contentDocument] webFrame];
+}
+
+@end
diff --git a/WebKit/mac/DOM/WebDOMOperationsPrivate.h b/WebKit/mac/DOM/WebDOMOperationsPrivate.h
new file mode 100644
index 0000000..a16eee8
--- /dev/null
+++ b/WebKit/mac/DOM/WebDOMOperationsPrivate.h
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+@class WebFrameBridge;
+
+#import <WebKit/WebDOMOperations.h>
+
+@interface DOMNode (WebDOMNodeOperationsPrivate)
+- (WebFrameBridge *)_bridge;
+- (NSArray *)_URLsFromSelectors:(SEL)firstSel, ...;
+- (NSArray *)_subresourceURLs;
+@end
+
+@interface DOMRange (WebDOMRangeOperationsPrivate)
+- (WebFrameBridge *)_bridge;
+@end
+
+@interface DOMDocument (WebDOMDocumentOperationsPrivate)
+- (DOMRange *)_createRangeWithNode:(DOMNode *)node;
+- (DOMRange *)_documentRange;
+@end
diff --git a/WebKit/mac/DefaultDelegates/WebDefaultContextMenuDelegate.h b/WebKit/mac/DefaultDelegates/WebDefaultContextMenuDelegate.h
new file mode 100644
index 0000000..98ef76b
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebDefaultContextMenuDelegate.h
@@ -0,0 +1,34 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+#import <WebKit/WebDefaultUIDelegate.h>
+
+@interface WebDefaultUIDelegate (WebContextMenu)
+@end
diff --git a/WebKit/mac/DefaultDelegates/WebDefaultContextMenuDelegate.mm b/WebKit/mac/DefaultDelegates/WebDefaultContextMenuDelegate.mm
new file mode 100644
index 0000000..1624856
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebDefaultContextMenuDelegate.mm
@@ -0,0 +1,184 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebDefaultContextMenuDelegate.h"
+
+#import "WebDOMOperations.h"
+#import "WebDataSourcePrivate.h"
+#import "WebDefaultUIDelegate.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebFrameView.h"
+#import "WebHTMLViewPrivate.h"
+#import "WebLocalizableStrings.h"
+#import "WebNSPasteboardExtras.h"
+#import "WebNSURLRequestExtras.h"
+#import "WebPolicyDelegate.h"
+#import "WebUIDelegate.h"
+#import "WebUIDelegatePrivate.h"
+#import "WebViewInternal.h"
+#import <Foundation/NSURLConnection.h>
+#import <Foundation/NSURLRequest.h>
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/Editor.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/KURL.h>
+#import <WebCore/WebCoreFrameBridge.h>
+#import <WebKit/DOM.h>
+#import <WebKit/DOMPrivate.h>
+
+@implementation WebDefaultUIDelegate (WebContextMenu)
+
+- (NSMenuItem *)menuItemWithTag:(int)tag target:(id)target representedObject:(id)representedObject
+{
+ NSMenuItem *menuItem = [[[NSMenuItem alloc] init] autorelease];
+ [menuItem setTag:tag];
+ [menuItem setTarget:target]; // can be nil
+ [menuItem setRepresentedObject:representedObject];
+
+ NSString *title = nil;
+ SEL action = NULL;
+
+ switch(tag) {
+ case WebMenuItemTagCopy:
+ title = UI_STRING("Copy", "Copy context menu item");
+ action = @selector(copy:);
+ break;
+ case WebMenuItemTagGoBack:
+ title = UI_STRING("Back", "Back context menu item");
+ action = @selector(goBack:);
+ break;
+ case WebMenuItemTagGoForward:
+ title = UI_STRING("Forward", "Forward context menu item");
+ action = @selector(goForward:);
+ break;
+ case WebMenuItemTagStop:
+ title = UI_STRING("Stop", "Stop context menu item");
+ action = @selector(stopLoading:);
+ break;
+ case WebMenuItemTagReload:
+ title = UI_STRING("Reload", "Reload context menu item");
+ action = @selector(reload:);
+ break;
+ case WebMenuItemTagSearchInSpotlight:
+ title = UI_STRING("Search in Spotlight", "Search in Spotlight context menu item");
+ action = @selector(_searchWithSpotlightFromMenu:);
+ break;
+ case WebMenuItemTagSearchWeb:
+ title = UI_STRING("Search in Google", "Search in Google context menu item");
+ action = @selector(_searchWithGoogleFromMenu:);
+ break;
+ case WebMenuItemTagLookUpInDictionary:
+ title = UI_STRING("Look Up in Dictionary", "Look Up in Dictionary context menu item");
+ action = @selector(_lookUpInDictionaryFromMenu:);
+ break;
+ case WebMenuItemTagOpenFrameInNewWindow:
+ title = UI_STRING("Open Frame in New Window", "Open Frame in New Window context menu item");
+ action = @selector(_openFrameInNewWindowFromMenu:);
+ break;
+ default:
+ ASSERT_NOT_REACHED();
+ return nil;
+ }
+
+ if (title)
+ [menuItem setTitle:title];
+
+ [menuItem setAction:action];
+
+ return menuItem;
+}
+
+- (void)appendDefaultItems:(NSArray *)defaultItems toArray:(NSMutableArray *)menuItems
+{
+ ASSERT_ARG(menuItems, menuItems != nil);
+ if ([defaultItems count] > 0) {
+ ASSERT(![[menuItems lastObject] isSeparatorItem]);
+ if (![[defaultItems objectAtIndex:0] isSeparatorItem]) {
+ [menuItems addObject:[NSMenuItem separatorItem]];
+
+ NSEnumerator *e = [defaultItems objectEnumerator];
+ NSMenuItem *item;
+ while ((item = [e nextObject]) != nil) {
+ [menuItems addObject:item];
+ }
+ }
+ }
+}
+
+- (NSArray *)webView:(WebView *)wv contextMenuItemsForElement:(NSDictionary *)element defaultMenuItems:(NSArray *)defaultMenuItems
+{
+ // The defaultMenuItems here are ones supplied by the WebDocumentView protocol implementation. WebPDFView is
+ // one case that has non-nil default items here.
+ NSMutableArray *menuItems = [NSMutableArray array];
+
+ WebFrame *webFrame = [element objectForKey:WebElementFrameKey];
+
+ if ([[element objectForKey:WebElementIsSelectedKey] boolValue]) {
+ // The Spotlight and Google items are implemented in WebView, and require that the
+ // current document view conforms to WebDocumentText
+ ASSERT([[[webFrame frameView] documentView] conformsToProtocol:@protocol(WebDocumentText)]);
+ [menuItems addObject:[self menuItemWithTag:WebMenuItemTagSearchInSpotlight target:nil representedObject:element]];
+ [menuItems addObject:[self menuItemWithTag:WebMenuItemTagSearchWeb target:nil representedObject:element]];
+ [menuItems addObject:[NSMenuItem separatorItem]];
+
+ // FIXME 4184640: The Look Up in Dictionary item is only implemented in WebHTMLView, and so is present but
+ // dimmed for other cases where WebElementIsSelectedKey is present. It would probably
+ // be better not to include it in the menu if the documentView isn't a WebHTMLView, but that could break
+ // existing clients that have code that relies on it being present (unlikely for clients outside of Apple,
+ // but Safari has such code).
+ [menuItems addObject:[self menuItemWithTag:WebMenuItemTagLookUpInDictionary target:nil representedObject:element]];
+ [menuItems addObject:[NSMenuItem separatorItem]];
+ [menuItems addObject:[self menuItemWithTag:WebMenuItemTagCopy target:nil representedObject:element]];
+ } else {
+ WebView *wv = [webFrame webView];
+ if ([wv canGoBack]) {
+ [menuItems addObject:[self menuItemWithTag:WebMenuItemTagGoBack target:wv representedObject:element]];
+ }
+ if ([wv canGoForward]) {
+ [menuItems addObject:[self menuItemWithTag:WebMenuItemTagGoForward target:wv representedObject:element]];
+ }
+ if ([wv isLoading]) {
+ [menuItems addObject:[self menuItemWithTag:WebMenuItemTagStop target:wv representedObject:element]];
+ } else {
+ [menuItems addObject:[self menuItemWithTag:WebMenuItemTagReload target:wv representedObject:element]];
+ }
+
+ if (webFrame != [wv mainFrame]) {
+ [menuItems addObject:[self menuItemWithTag:WebMenuItemTagOpenFrameInNewWindow target:wv representedObject:element]];
+ }
+ }
+
+ // Add the default items at the end, if any, after a separator
+ [self appendDefaultItems:defaultMenuItems toArray:menuItems];
+
+ return menuItems;
+}
+
+@end
diff --git a/WebKit/mac/DefaultDelegates/WebDefaultEditingDelegate.h b/WebKit/mac/DefaultDelegates/WebDefaultEditingDelegate.h
new file mode 100644
index 0000000..c0f7c5b
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebDefaultEditingDelegate.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@interface WebDefaultEditingDelegate : NSObject
++ (WebDefaultEditingDelegate *)sharedEditingDelegate;
+@end
diff --git a/WebKit/mac/DefaultDelegates/WebDefaultEditingDelegate.m b/WebKit/mac/DefaultDelegates/WebDefaultEditingDelegate.m
new file mode 100644
index 0000000..bf7ee17
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebDefaultEditingDelegate.m
@@ -0,0 +1,138 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+#import <WebKit/WebDefaultEditingDelegate.h>
+
+#import <WebKit/DOM.h>
+#import <WebKit/WebEditingDelegate.h>
+#import <WebKit/WebEditingDelegatePrivate.h>
+#import <WebKit/WebView.h>
+
+@implementation WebDefaultEditingDelegate
+
+static WebDefaultEditingDelegate *sharedDelegate = nil;
+
++ (WebDefaultEditingDelegate *)sharedEditingDelegate
+{
+ if (!sharedDelegate) {
+ sharedDelegate = [[WebDefaultEditingDelegate alloc] init];
+ }
+ return sharedDelegate;
+}
+
+- (BOOL)webView:(WebView *)webView shouldShowDeleteInterfaceForElement:(DOMHTMLElement *)element
+{
+ return NO;
+}
+
+- (BOOL)webView:(WebView *)webView shouldBeginEditingInDOMRange:(DOMRange *)range
+{
+ return YES;
+}
+
+- (BOOL)webView:(WebView *)webView shouldEndEditingInDOMRange:(DOMRange *)range
+{
+ return YES;
+}
+
+- (BOOL)webView:(WebView *)webView shouldInsertNode:(DOMNode *)node replacingDOMRange:(DOMRange *)range givenAction:(WebViewInsertAction)action
+{
+ return YES;
+}
+
+- (BOOL)webView:(WebView *)webView shouldInsertText:(NSString *)text replacingDOMRange:(DOMRange *)range givenAction:(WebViewInsertAction)action
+{
+ return YES;
+}
+
+- (BOOL)webView:(WebView *)webView shouldDeleteDOMRange:(DOMRange *)range
+{
+ return YES;
+}
+
+- (BOOL)webView:(WebView *)webView shouldChangeSelectedDOMRange:(DOMRange *)currentRange toDOMRange:(DOMRange *)proposedRange affinity:(NSSelectionAffinity)selectionAffinity stillSelecting:(BOOL)flag
+{
+ return YES;
+}
+
+- (BOOL)webView:(WebView *)webView shouldApplyStyle:(DOMCSSStyleDeclaration *)style toElementsInDOMRange:(DOMRange *)range
+{
+ return YES;
+}
+
+- (BOOL)webView:(WebView *)webView shouldMoveRangeAfterDelete:(DOMRange *)range replacingRange:(DOMRange *)rangeToBeReplaced
+{
+ return YES;
+}
+
+- (BOOL)webView:(WebView *)webView shouldChangeTypingStyle:(DOMCSSStyleDeclaration *)currentStyle toStyle:(DOMCSSStyleDeclaration *)proposedStyle
+{
+ return YES;
+}
+
+- (BOOL)webView:(WebView *)webView doCommandBySelector:(SEL)selector
+{
+ return NO;
+}
+
+- (void)webView:(WebView *)webView didWriteSelectionToPasteboard:(NSPasteboard *)pasteboard
+{
+}
+
+- (void)webView:(WebView *)webView didSetSelectionTypesForPasteboard:(NSPasteboard *)pasteboard
+{
+}
+
+- (void)webViewDidBeginEditing:(NSNotification *)notification
+{
+}
+
+- (void)webViewDidChange:(NSNotification *)notification
+{
+}
+
+- (void)webViewDidEndEditing:(NSNotification *)notification
+{
+}
+
+- (void)webViewDidChangeTypingStyle:(NSNotification *)notification
+{
+}
+
+- (void)webViewDidChangeSelection:(NSNotification *)notification
+{
+}
+
+- (NSUndoManager *)undoManagerForWebView:(WebView *)webView
+{
+ return nil;
+}
+
+@end
diff --git a/WebKit/mac/DefaultDelegates/WebDefaultPolicyDelegate.h b/WebKit/mac/DefaultDelegates/WebDefaultPolicyDelegate.h
new file mode 100644
index 0000000..3796864
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebDefaultPolicyDelegate.h
@@ -0,0 +1,39 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+/*!
+ @class WebDefaultPolicyDelegate
+ @discussion WebDefaultPolicyDelegate will be used as a WebView's
+ default policy delegate. It can be subclassed to modify policies.
+*/
+@interface WebDefaultPolicyDelegate : NSObject
++ (WebDefaultPolicyDelegate *)sharedPolicyDelegate;
+@end
+
diff --git a/WebKit/mac/DefaultDelegates/WebDefaultPolicyDelegate.m b/WebKit/mac/DefaultDelegates/WebDefaultPolicyDelegate.m
new file mode 100644
index 0000000..95502da
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebDefaultPolicyDelegate.m
@@ -0,0 +1,117 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebDataSource.h>
+#import <WebKit/WebDefaultPolicyDelegate.h>
+#import <WebKit/WebFrame.h>
+#import <WebKit/WebPolicyDelegatePrivate.h>
+#import <WebKit/WebView.h>
+#import <WebKit/WebViewPrivate.h>
+
+#import <Foundation/NSURLConnection.h>
+#import <Foundation/NSURLRequest.h>
+#import <Foundation/NSURLResponse.h>
+#import <JavaScriptCore/Assertions.h>
+
+
+@implementation WebDefaultPolicyDelegate
+
+static WebDefaultPolicyDelegate *sharedDelegate = nil;
+
+// Return a object with vanilla implementations of the protocol's methods
+// Note this feature relies on our default delegate being stateless
++ (WebDefaultPolicyDelegate *)sharedPolicyDelegate
+{
+ if (!sharedDelegate) {
+ sharedDelegate = [[WebDefaultPolicyDelegate alloc] init];
+ }
+ return sharedDelegate;
+}
+
+- (void)webView: (WebView *)wv unableToImplementPolicyWithError:(NSError *)error frame:(WebFrame *)frame
+{
+ LOG_ERROR("called unableToImplementPolicyWithError:%@ inFrame:%@", error, frame);
+}
+
+
+- (void)webView: (WebView *)wv decidePolicyForMIMEType:(NSString *)type
+ request:(NSURLRequest *)request
+ frame:(WebFrame *)frame
+ decisionListener:(id <WebPolicyDecisionListener>)listener;
+{
+ if ([[request URL] isFileURL]) {
+ BOOL isDirectory = NO;
+ BOOL exists = [[NSFileManager defaultManager] fileExistsAtPath:[[request URL] path] isDirectory:&isDirectory];
+
+ if (exists && !isDirectory && [WebView canShowMIMEType:type])
+ [listener use];
+ else
+ [listener ignore];
+ } else if ([WebView canShowMIMEType:type])
+ [listener use];
+ else
+ [listener ignore];
+}
+
+- (void)webView: (WebView *)wv decidePolicyForNavigationAction:(NSDictionary *)actionInformation
+ request:(NSURLRequest *)request
+ frame:(WebFrame *)frame
+ decisionListener:(id <WebPolicyDecisionListener>)listener
+{
+ WebNavigationType navType = [[actionInformation objectForKey:WebActionNavigationTypeKey] intValue];
+
+ if ([WebView _canHandleRequest:request]) {
+ [listener use];
+ } else if (navType == WebNavigationTypePlugInRequest) {
+ [listener use];
+ } else {
+ // A file URL shouldn't fall through to here, but if it did,
+ // it would be a security risk to open it.
+ if (![[request URL] isFileURL]) {
+ [[NSWorkspace sharedWorkspace] openURL:[request URL]];
+ }
+ [listener ignore];
+ }
+}
+
+- (void)webView: (WebView *)wv decidePolicyForNewWindowAction:(NSDictionary *)actionInformation
+ request:(NSURLRequest *)request
+ newFrameName:(NSString *)frameName
+ decisionListener:(id <WebPolicyDecisionListener>)listener
+{
+ [listener use];
+}
+
+// Temporary SPI needed for <rdar://problem/3951283> can view pages from the back/forward cache that should be disallowed by Parental Controls
+- (BOOL)webView:(WebView *)webView shouldGoToHistoryItem:(WebHistoryItem *)item
+{
+ return YES;
+}
+
+@end
+
diff --git a/WebKit/mac/DefaultDelegates/WebDefaultScriptDebugDelegate.h b/WebKit/mac/DefaultDelegates/WebDefaultScriptDebugDelegate.h
new file mode 100644
index 0000000..b548212
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebDefaultScriptDebugDelegate.h
@@ -0,0 +1,34 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@interface WebDefaultScriptDebugDelegate : NSObject
++ (WebDefaultScriptDebugDelegate *)sharedScriptDebugDelegate;
+@end
+
diff --git a/WebKit/mac/DefaultDelegates/WebDefaultScriptDebugDelegate.m b/WebKit/mac/DefaultDelegates/WebDefaultScriptDebugDelegate.m
new file mode 100644
index 0000000..972f013
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebDefaultScriptDebugDelegate.m
@@ -0,0 +1,96 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebScriptDebugDelegate.h>
+#import "WebDefaultScriptDebugDelegate.h"
+
+
+@implementation WebDefaultScriptDebugDelegate
+
+static WebDefaultScriptDebugDelegate *sharedDelegate = nil;
+
++ (WebDefaultScriptDebugDelegate *)sharedScriptDebugDelegate
+{
+ if (!sharedDelegate) {
+ sharedDelegate = [[WebDefaultScriptDebugDelegate alloc] init];
+ }
+ return sharedDelegate;
+}
+
+- (void)webView:(WebView *)webView didParseSource:(NSString *)source
+ fromURL:(NSString *)url
+ sourceId:(int)sid
+ forWebFrame:(WebFrame *)webFrame
+{
+}
+
+- (void)webView:(WebView *)webView didParseSource:(NSString *)source
+ baseLineNumber:(unsigned)lineNumber
+ fromURL:(NSURL *)url
+ sourceId:(int)sid
+ forWebFrame:(WebFrame *)webFrame
+{
+}
+
+- (void)webView:(WebView *)webView failedToParseSource:(NSString *)source
+ baseLineNumber:(unsigned)lineNumber
+ fromURL:(NSURL *)url
+ withError:(NSError *)error
+ forWebFrame:(WebFrame *)webFrame
+{
+}
+
+- (void)webView:(WebView *)webView didEnterCallFrame:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame
+{
+}
+
+- (void)webView:(WebView *)webView willExecuteStatement:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame
+{
+}
+
+- (void)webView:(WebView *)webView willLeaveCallFrame:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame
+{
+}
+
+- (void)webView:(WebView *)webView exceptionWasRaised:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame
+{
+}
+
+@end
diff --git a/WebKit/mac/DefaultDelegates/WebDefaultUIDelegate.h b/WebKit/mac/DefaultDelegates/WebDefaultUIDelegate.h
new file mode 100644
index 0000000..4315121
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebDefaultUIDelegate.h
@@ -0,0 +1,36 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@interface WebDefaultUIDelegate : NSObject
+{
+ IBOutlet NSMenu *defaultMenu;
+}
++ (WebDefaultUIDelegate *)sharedUIDelegate;
+@end
diff --git a/WebKit/mac/DefaultDelegates/WebDefaultUIDelegate.m b/WebKit/mac/DefaultDelegates/WebDefaultUIDelegate.m
new file mode 100644
index 0000000..8cc8445
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebDefaultUIDelegate.m
@@ -0,0 +1,229 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+#import <Foundation/NSURLRequest.h>
+
+#import <WebKit/WebDefaultUIDelegate.h>
+#import <WebKit/WebJavaScriptTextInputPanel.h>
+#import <WebKit/WebView.h>
+#import <WebKit/WebUIDelegatePrivate.h>
+#import <WebKit/DOM.h>
+
+@interface NSApplication (DeclarationStolenFromAppKit)
+- (void)_cycleWindowsReversed:(BOOL)reversed;
+@end
+
+@implementation WebDefaultUIDelegate
+
+static WebDefaultUIDelegate *sharedDelegate = nil;
+
+// Return a object with vanilla implementations of the protocol's methods
+// Note this feature relies on our default delegate being stateless. This
+// is probably an invalid assumption for the WebUIDelegate.
+// If we add any real functionality to this default delegate we probably
+// won't be able to use a singleton.
++ (WebDefaultUIDelegate *)sharedUIDelegate
+{
+ if (!sharedDelegate) {
+ sharedDelegate = [[WebDefaultUIDelegate alloc] init];
+ }
+ return sharedDelegate;
+}
+
+- (WebView *)webView: (WebView *)wv createWebViewWithRequest:(NSURLRequest *)request windowFeatures:(NSDictionary *)features
+{
+ // If the new API method doesn't exist, fallback to the old version of createWebViewWithRequest
+ // for backwards compatability
+ if (![[wv UIDelegate] respondsToSelector:@selector(webView:createWebViewWithRequest:windowFeatures:)] && [[wv UIDelegate] respondsToSelector:@selector(webView:createWebViewWithRequest:)])
+ return [[wv UIDelegate] webView:wv createWebViewWithRequest:request];
+ return nil;
+}
+
+- (void)webViewShow: (WebView *)wv
+{
+}
+
+- (void)webViewClose: (WebView *)wv
+{
+ [[wv window] close];
+}
+
+- (void)webViewFocus: (WebView *)wv
+{
+ [[wv window] makeKeyAndOrderFront:wv];
+}
+
+- (void)webViewUnfocus: (WebView *)wv
+{
+ if ([[wv window] isKeyWindow] || [[[wv window] attachedSheet] isKeyWindow]) {
+ [NSApp _cycleWindowsReversed:FALSE];
+ }
+}
+
+- (NSResponder *)webViewFirstResponder: (WebView *)wv;
+{
+ return [[wv window] firstResponder];
+}
+
+- (void)webView: (WebView *)wv makeFirstResponder:(NSResponder *)responder
+{
+ [[wv window] makeFirstResponder:responder];
+}
+
+- (void)webView: (WebView *)wv setStatusText:(NSString *)text
+{
+}
+
+- (NSString *)webViewStatusText: (WebView *)wv
+{
+ return nil;
+}
+
+- (void)webView: (WebView *)wv mouseDidMoveOverElement:(NSDictionary *)elementInformation modifierFlags:(unsigned int)modifierFlags
+{
+}
+
+- (BOOL)webViewAreToolbarsVisible: (WebView *)wv
+{
+ return NO;
+}
+
+- (void)webView: (WebView *)wv setToolbarsVisible:(BOOL)visible
+{
+}
+
+- (BOOL)webViewIsStatusBarVisible: (WebView *)wv
+{
+ return NO;
+}
+
+- (void)webView: (WebView *)wv setStatusBarVisible:(BOOL)visible
+{
+}
+
+- (BOOL)webViewIsResizable: (WebView *)wv
+{
+ return [[wv window] showsResizeIndicator];
+}
+
+- (void)webView: (WebView *)wv setResizable:(BOOL)resizable;
+{
+ // FIXME: This doesn't actually change the resizability of the window,
+ // only visibility of the indicator.
+ [[wv window] setShowsResizeIndicator:resizable];
+}
+
+- (void)webView: (WebView *)wv setFrame:(NSRect)frame
+{
+ [[wv window] setFrame:frame display:YES];
+}
+
+- (NSRect)webViewFrame: (WebView *)wv
+{
+ NSWindow *window = [wv window];
+ return window == nil ? NSZeroRect : [window frame];
+}
+
+- (void)webView: (WebView *)wv runJavaScriptAlertPanelWithMessage:(NSString *)message initiatedByFrame:(WebFrame *)frame
+{
+ // FIXME: We want a default here, but that would add localized strings.
+}
+
+- (BOOL)webView: (WebView *)wv runJavaScriptConfirmPanelWithMessage:(NSString *)message initiatedByFrame:(WebFrame *)frame
+{
+ // FIXME: We want a default here, but that would add localized strings.
+ return NO;
+}
+
+- (NSString *)webView: (WebView *)wv runJavaScriptTextInputPanelWithPrompt:(NSString *)prompt defaultText:(NSString *)defaultText initiatedByFrame:(WebFrame *)frame
+{
+ WebJavaScriptTextInputPanel *panel = [[WebJavaScriptTextInputPanel alloc] initWithPrompt:prompt text:defaultText];
+ [panel showWindow:nil];
+ NSString *result;
+ if ([NSApp runModalForWindow:[panel window]]) {
+ result = [panel text];
+ } else {
+ result = nil;
+ }
+ [[panel window] close];
+ [panel release];
+ return result;
+}
+
+- (void)webView: (WebView *)wv runOpenPanelForFileButtonWithResultListener:(id<WebOpenPanelResultListener>)resultListener
+{
+ // FIXME: We want a default here, but that would add localized strings.
+}
+
+- (void)webView:(WebView *)sender printFrameView:(WebFrameView *)frameView
+{
+}
+
+
+- (BOOL)webView:(WebView *)webView shouldBeginDragForElement:(NSDictionary *)element dragImage:(NSImage *)dragImage mouseDownEvent:(NSEvent *)mouseDownEvent mouseDraggedEvent:(NSEvent *)mouseDraggedEvent
+{
+ return YES;
+}
+
+- (unsigned)webView:(WebView *)webView dragDestinationActionMaskForDraggingInfo:(id <NSDraggingInfo>)draggingInfo;
+{
+ return WebDragDestinationActionAny;
+}
+
+- (void)webView:(WebView *)webView willPerformDragDestinationAction:(WebDragDestinationAction)action forDraggingInfo:(id <NSDraggingInfo>)draggingInfo
+{
+}
+
+- (unsigned)webView:(WebView *)webView dragSourceActionMaskForPoint:(NSPoint)point;
+{
+ return WebDragSourceActionAny;
+}
+
+- (void)webView:(WebView *)webView willPerformDragSourceAction:(WebDragSourceAction)action fromPoint:(NSPoint)point withPasteboard:(NSPasteboard *)pasteboard;
+{
+}
+
+- (void)webView:(WebView *)sender didDrawRect:(NSRect)rect
+{
+}
+
+- (void)webView:(WebView *)sender didScrollDocumentInFrameView:(WebFrameView *)frameView
+{
+}
+
+- (void)webView:(WebView *)sender willPopupMenu:(NSMenu *)menu
+{
+}
+
+- (void)webView:(WebView *)sender contextMenuItemSelected:(NSMenuItem *)item forElement:(NSDictionary *)element
+{
+}
+
+@end
diff --git a/WebKit/mac/DefaultDelegates/WebScriptDebugServer.h b/WebKit/mac/DefaultDelegates/WebScriptDebugServer.h
new file mode 100644
index 0000000..ae93b7b
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebScriptDebugServer.h
@@ -0,0 +1,94 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebScriptDebugDelegate.h"
+
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define WebNSUInteger unsigned int
+#else
+#define WebNSUInteger NSUInteger
+#endif
+
+extern NSString *WebScriptDebugServerProcessNameKey;
+extern NSString *WebScriptDebugServerProcessBundleIdentifierKey;
+extern NSString *WebScriptDebugServerProcessIdentifierKey;
+
+extern NSString *WebScriptDebugServerQueryNotification;
+extern NSString *WebScriptDebugServerQueryReplyNotification;
+
+extern NSString *WebScriptDebugServerDidLoadNotification;
+extern NSString *WebScriptDebugServerWillUnloadNotification;
+
+@class WebDataSource;
+
+@protocol WebScriptDebugListener <NSObject>
+- (void)webView:(WebView *)webView didLoadMainResourceForDataSource:(WebDataSource *)dataSource;
+
+- (void)webView:(WebView *)webView didParseSource:(NSString *)source
+ baseLineNumber:(WebNSUInteger)lineNumber
+ fromURL:(NSURL *)url
+ sourceId:(int)sid
+ forWebFrame:(WebFrame *)webFrame;
+
+- (void)webView:(WebView *)webView failedToParseSource:(NSString *)source
+ baseLineNumber:(WebNSUInteger)lineNumber
+ fromURL:(NSURL *)url
+ withError:(NSError *)error
+ forWebFrame:(WebFrame *)webFrame;
+
+- (void)webView:(WebView *)webView didEnterCallFrame:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame;
+
+- (void)webView:(WebView *)webView willExecuteStatement:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame;
+
+- (void)webView:(WebView *)webView willLeaveCallFrame:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame;
+
+- (void)webView:(WebView *)webView exceptionWasRaised:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame;
+@end
+
+@protocol WebScriptDebugServer <NSObject>
+- (oneway void)addListener:(id<WebScriptDebugListener>)listener;
+- (oneway void)removeListener:(id<WebScriptDebugListener>)listener;
+- (oneway void)step;
+- (oneway void)pause;
+- (oneway void)resume;
+- (oneway BOOL)isPaused;
+@end
+
+#undef WebNSUInteger
diff --git a/WebKit/mac/DefaultDelegates/WebScriptDebugServer.m b/WebKit/mac/DefaultDelegates/WebScriptDebugServer.m
new file mode 100644
index 0000000..2cd0e8f
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebScriptDebugServer.m
@@ -0,0 +1,381 @@
+/*
+ * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebScriptDebugServer.h"
+#import "WebScriptDebugServerPrivate.h"
+#import "WebViewInternal.h"
+
+#import <JavaScriptCore/Assertions.h>
+
+NSString *WebScriptDebugServerProcessNameKey = @"WebScriptDebugServerProcessNameKey";
+NSString *WebScriptDebugServerProcessBundleIdentifierKey = @"WebScriptDebugServerProcessBundleIdentifierKey";
+NSString *WebScriptDebugServerProcessIdentifierKey = @"WebScriptDebugServerProcessIdentifierKey";
+
+NSString *WebScriptDebugServerQueryNotification = @"WebScriptDebugServerQueryNotification";
+NSString *WebScriptDebugServerQueryReplyNotification = @"WebScriptDebugServerQueryReplyNotification";
+
+NSString *WebScriptDebugServerDidLoadNotification = @"WebScriptDebugServerDidLoadNotification";
+NSString *WebScriptDebugServerWillUnloadNotification = @"WebScriptDebugServerWillUnloadNotification";
+
+@implementation WebScriptDebugServer
+
+static WebScriptDebugServer *sharedServer = nil;
+static unsigned listenerCount = 0;
+
++ (WebScriptDebugServer *)sharedScriptDebugServer
+{
+ if (!sharedServer)
+ sharedServer = [[WebScriptDebugServer alloc] init];
+ return sharedServer;
+}
+
++ (unsigned)listenerCount
+{
+ return listenerCount;
+}
+
+- (id)init
+{
+ self = [super init];
+
+ NSProcessInfo *processInfo = [NSProcessInfo processInfo];
+ serverName = [[NSString alloc] initWithFormat:@"WebScriptDebugServer-%@-%d", [processInfo processName], [processInfo processIdentifier]];
+
+ serverConnection = [[NSConnection alloc] init];
+ if ([serverConnection registerName:serverName]) {
+ [serverConnection setRootObject:self];
+ NSProcessInfo *processInfo = [NSProcessInfo processInfo];
+ NSDictionary *info = [[NSDictionary alloc] initWithObjectsAndKeys:[processInfo processName], WebScriptDebugServerProcessNameKey,
+ [[NSBundle mainBundle] bundleIdentifier], WebScriptDebugServerProcessBundleIdentifierKey,
+ [NSNumber numberWithInt:[processInfo processIdentifier]], WebScriptDebugServerProcessIdentifierKey, nil];
+ [[NSDistributedNotificationCenter defaultCenter] postNotificationName:WebScriptDebugServerDidLoadNotification object:serverName userInfo:info];
+ [info release];
+ } else {
+ [serverConnection release];
+ serverConnection = nil;
+ }
+
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(applicationTerminating:) name:NSApplicationWillTerminateNotification object:nil];
+ [[NSDistributedNotificationCenter defaultCenter] addObserver:self selector:@selector(serverQuery:) name:WebScriptDebugServerQueryNotification object:nil];
+
+ listeners = [[NSMutableSet alloc] init];
+
+ return self;
+}
+
+- (void)dealloc
+{
+ // FIXME: Bad to do all this work in dealloc. What about under GC?
+
+ ASSERT(listenerCount >= [listeners count]);
+ listenerCount -= [listeners count];
+ if (!listenerCount)
+ [self detachScriptDebuggerFromAllWebViews];
+ [[NSNotificationCenter defaultCenter] removeObserver:self name:NSApplicationWillTerminateNotification object:nil];
+ [[NSDistributedNotificationCenter defaultCenter] removeObserver:self name:WebScriptDebugServerQueryNotification object:nil];
+ [[NSDistributedNotificationCenter defaultCenter] postNotificationName:WebScriptDebugServerWillUnloadNotification object:serverName];
+ [[NSNotificationCenter defaultCenter] removeObserver:self name:NSConnectionDidDieNotification object:nil];
+ [serverConnection invalidate];
+ [serverConnection release];
+ [serverName release];
+ [listeners release];
+ [super dealloc];
+}
+
+- (void)applicationTerminating:(NSNotification *)notifiction
+{
+ [[NSDistributedNotificationCenter defaultCenter] postNotificationName:WebScriptDebugServerWillUnloadNotification object:serverName];
+}
+
+- (void)attachScriptDebuggerToAllWebViews
+{
+ [WebView _makeAllWebViewsPerformSelector:@selector(_attachScriptDebuggerToAllFrames)];
+}
+
+- (void)detachScriptDebuggerFromAllWebViews
+{
+ [WebView _makeAllWebViewsPerformSelector:@selector(_detachScriptDebuggerFromAllFrames)];
+}
+
+- (void)serverQuery:(NSNotification *)notification
+{
+ NSProcessInfo *processInfo = [NSProcessInfo processInfo];
+ NSDictionary *info = [[NSDictionary alloc] initWithObjectsAndKeys:[processInfo processName], WebScriptDebugServerProcessNameKey,
+ [[NSBundle mainBundle] bundleIdentifier], WebScriptDebugServerProcessBundleIdentifierKey,
+ [NSNumber numberWithInt:[processInfo processIdentifier]], WebScriptDebugServerProcessIdentifierKey, nil];
+ [[NSDistributedNotificationCenter defaultCenter] postNotificationName:WebScriptDebugServerQueryReplyNotification object:serverName userInfo:info];
+ [info release];
+}
+
+- (void)listenerConnectionDidDie:(NSNotification *)notification
+{
+ NSConnection *connection = [notification object];
+ NSMutableSet *listenersToRemove = [[NSMutableSet alloc] initWithCapacity:[listeners count]];
+ NSEnumerator *enumerator = [listeners objectEnumerator];
+ NSDistantObject *listener = nil;
+
+ [[NSNotificationCenter defaultCenter] removeObserver:self name:NSConnectionDidDieNotification object:connection];
+
+ while ((listener = [enumerator nextObject]))
+ if ([[listener connectionForProxy] isEqualTo:connection])
+ [listenersToRemove addObject:listener];
+
+ ASSERT(listenerCount >= [listenersToRemove count]);
+ listenerCount -= [listenersToRemove count];
+ [listeners minusSet:listenersToRemove];
+ [listenersToRemove release];
+
+ if (!listenerCount)
+ [self detachScriptDebuggerFromAllWebViews];
+}
+
+- (oneway void)addListener:(id<WebScriptDebugListener>)listener
+{
+ // can't use isKindOfClass: here because that will send over the wire and not check the proxy object
+ if (!listener || [listener class] != [NSDistantObject class] || ![listener conformsToProtocol:@protocol(WebScriptDebugListener)])
+ return;
+ listenerCount++;
+ [listeners addObject:listener];
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(listenerConnectionDidDie:) name:NSConnectionDidDieNotification object:[(NSDistantObject *)listener connectionForProxy]];
+ if (listenerCount == 1)
+ [self attachScriptDebuggerToAllWebViews];
+}
+
+- (oneway void)removeListener:(id<WebScriptDebugListener>)listener
+{
+ if (!listener || ![listeners containsObject:listener])
+ return;
+ ASSERT(listenerCount >= 1);
+ listenerCount--;
+ [[NSNotificationCenter defaultCenter] removeObserver:self name:NSConnectionDidDieNotification object:[(NSDistantObject *)listener connectionForProxy]];
+ [listeners removeObject:listener];
+ if (!listenerCount)
+ [self detachScriptDebuggerFromAllWebViews];
+}
+
+- (oneway void)step
+{
+ step = YES;
+ paused = NO;
+}
+
+- (oneway void)pause
+{
+ paused = YES;
+ step = NO;
+}
+
+- (oneway void)resume
+{
+ paused = NO;
+ step = NO;
+}
+
+- (oneway BOOL)isPaused
+{
+ return paused;
+}
+
+- (void)suspendProcessIfPaused
+{
+ static BOOL alreadyHere = NO;
+
+ if (alreadyHere)
+ return;
+
+ alreadyHere = YES;
+
+ // this method will suspend this process when called during the dubugging callbacks
+ // we need to do this to implement breakpoints and pausing of JavaScript
+
+ while (paused)
+ [[NSRunLoop currentRunLoop] runMode:NSConnectionReplyMode beforeDate:[NSDate distantFuture]];
+
+ if (step) {
+ step = NO;
+ paused = YES;
+ }
+
+ alreadyHere = NO;
+}
+
+- (void)webView:(WebView *)webView didLoadMainResourceForDataSource:(WebDataSource *)dataSource
+{
+ if (![listeners count] || inCallback)
+ return;
+
+ inCallback = YES;
+
+ NSEnumerator *enumerator = [listeners objectEnumerator];
+ NSDistantObject <WebScriptDebugListener> *listener = nil;
+
+ while ((listener = [enumerator nextObject])) {
+ if ([[listener connectionForProxy] isValid])
+ [listener webView:webView didLoadMainResourceForDataSource:dataSource];
+ }
+
+ inCallback = NO;
+}
+
+- (void)webView:(WebView *)webView didParseSource:(NSString *)source
+ baseLineNumber:(NSUInteger)lineNumber
+ fromURL:(NSURL *)url
+ sourceId:(int)sid
+ forWebFrame:(WebFrame *)webFrame
+{
+ if (![listeners count] || inCallback)
+ return;
+
+ inCallback = YES;
+
+ NSEnumerator *enumerator = [listeners objectEnumerator];
+ NSDistantObject <WebScriptDebugListener> *listener = nil;
+
+ while ((listener = [enumerator nextObject])) {
+ if ([[listener connectionForProxy] isValid])
+ [listener webView:webView didParseSource:source baseLineNumber:lineNumber fromURL:url sourceId:sid forWebFrame:webFrame];
+ }
+
+ inCallback = NO;
+}
+
+- (void)webView:(WebView *)webView failedToParseSource:(NSString *)source
+ baseLineNumber:(NSUInteger)lineNumber
+ fromURL:(NSURL *)url
+ withError:(NSError *)error
+ forWebFrame:(WebFrame *)webFrame
+{
+ if (![listeners count] || inCallback)
+ return;
+
+ inCallback = YES;
+
+ NSEnumerator *enumerator = [listeners objectEnumerator];
+ NSDistantObject <WebScriptDebugListener> *listener = nil;
+
+ while ((listener = [enumerator nextObject])) {
+ if ([[listener connectionForProxy] isValid])
+ [listener webView:webView failedToParseSource:source baseLineNumber:lineNumber fromURL:url withError:error forWebFrame:webFrame];
+ }
+
+ inCallback = NO;
+}
+
+- (void)webView:(WebView *)webView didEnterCallFrame:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame
+{
+ if (![listeners count] || inCallback)
+ return;
+
+ inCallback = YES;
+
+ NSEnumerator *enumerator = [listeners objectEnumerator];
+ NSDistantObject <WebScriptDebugListener> *listener = nil;
+
+ while ((listener = [enumerator nextObject])) {
+ if ([[listener connectionForProxy] isValid])
+ [listener webView:webView didEnterCallFrame:frame sourceId:sid line:lineno forWebFrame:webFrame];
+ }
+
+ [self suspendProcessIfPaused];
+
+ inCallback = NO;
+}
+
+- (void)webView:(WebView *)webView willExecuteStatement:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame
+{
+ if (![listeners count] || inCallback)
+ return;
+
+ inCallback = YES;
+
+ NSEnumerator *enumerator = [listeners objectEnumerator];
+ NSDistantObject <WebScriptDebugListener> *listener = nil;
+
+ while ((listener = [enumerator nextObject])) {
+ if ([[listener connectionForProxy] isValid])
+ [listener webView:webView willExecuteStatement:frame sourceId:sid line:lineno forWebFrame:webFrame];
+ }
+
+ [self suspendProcessIfPaused];
+
+ inCallback = NO;
+}
+
+- (void)webView:(WebView *)webView willLeaveCallFrame:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame
+{
+ if (![listeners count] || inCallback)
+ return;
+
+ inCallback = YES;
+
+ NSEnumerator *enumerator = [listeners objectEnumerator];
+ NSDistantObject <WebScriptDebugListener> *listener = nil;
+
+ while ((listener = [enumerator nextObject])) {
+ if ([[listener connectionForProxy] isValid])
+ [listener webView:webView willLeaveCallFrame:frame sourceId:sid line:lineno forWebFrame:webFrame];
+ }
+
+ [self suspendProcessIfPaused];
+
+ inCallback = NO;
+}
+
+- (void)webView:(WebView *)webView exceptionWasRaised:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame
+{
+ if (![listeners count] || inCallback)
+ return;
+
+ inCallback = YES;
+
+ NSEnumerator *enumerator = [listeners objectEnumerator];
+ NSDistantObject <WebScriptDebugListener> *listener = nil;
+
+ while ((listener = [enumerator nextObject])) {
+ if ([[listener connectionForProxy] isValid])
+ [listener webView:webView exceptionWasRaised:frame sourceId:sid line:lineno forWebFrame:webFrame];
+ }
+
+ [self suspendProcessIfPaused];
+
+ inCallback = NO;
+}
+
+@end
diff --git a/WebKit/mac/DefaultDelegates/WebScriptDebugServerPrivate.h b/WebKit/mac/DefaultDelegates/WebScriptDebugServerPrivate.h
new file mode 100644
index 0000000..081d3a9
--- /dev/null
+++ b/WebKit/mac/DefaultDelegates/WebScriptDebugServerPrivate.h
@@ -0,0 +1,82 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebScriptDebugServer.h"
+
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define WebNSUInteger unsigned int
+#else
+#define WebNSUInteger NSUInteger
+#endif
+
+@interface WebScriptDebugServer : NSObject <WebScriptDebugServer> {
+@private
+ NSConnection *serverConnection;
+ NSString *serverName;
+ NSMutableSet *listeners;
+ BOOL inCallback;
+ BOOL paused;
+ BOOL step;
+}
++ (WebScriptDebugServer *)sharedScriptDebugServer;
++ (unsigned)listenerCount;
+
+- (void)attachScriptDebuggerToAllWebViews;
+- (void)detachScriptDebuggerFromAllWebViews;
+
+- (void)webView:(WebView *)webView didLoadMainResourceForDataSource:(WebDataSource *)dataSource;
+
+- (void)webView:(WebView *)webView didParseSource:(NSString *)source
+ baseLineNumber:(WebNSUInteger)lineNumber
+ fromURL:(NSURL *)url
+ sourceId:(int)sid
+ forWebFrame:(WebFrame *)webFrame;
+
+- (void)webView:(WebView *)webView failedToParseSource:(NSString *)source
+ baseLineNumber:(WebNSUInteger)lineNumber
+ fromURL:(NSURL *)url
+ withError:(NSError *)error
+ forWebFrame:(WebFrame *)webFrame;
+
+- (void)webView:(WebView *)webView didEnterCallFrame:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame;
+
+- (void)webView:(WebView *)webView willExecuteStatement:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame;
+
+- (void)webView:(WebView *)webView willLeaveCallFrame:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame;
+@end
+
+#undef WebNSUInteger
diff --git a/WebKit/mac/ForwardingHeaders/kjs/JSLock.h b/WebKit/mac/ForwardingHeaders/kjs/JSLock.h
new file mode 100644
index 0000000..9f0a0be
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/JSLock.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/JSLock.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/SavedBuiltins.h b/WebKit/mac/ForwardingHeaders/kjs/SavedBuiltins.h
new file mode 100644
index 0000000..e380807
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/SavedBuiltins.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/SavedBuiltins.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/SymbolTable.h b/WebKit/mac/ForwardingHeaders/kjs/SymbolTable.h
new file mode 100644
index 0000000..0868c02
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/SymbolTable.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/SymbolTable.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/collector.h b/WebKit/mac/ForwardingHeaders/kjs/collector.h
new file mode 100644
index 0000000..b8ef5a1
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/collector.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/collector.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/dtoa.h b/WebKit/mac/ForwardingHeaders/kjs/dtoa.h
new file mode 100644
index 0000000..4646cf1
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/dtoa.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/dtoa.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/function.h b/WebKit/mac/ForwardingHeaders/kjs/function.h
new file mode 100644
index 0000000..3e08e6d
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/function.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/function.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/identifier.h b/WebKit/mac/ForwardingHeaders/kjs/identifier.h
new file mode 100644
index 0000000..2471c99
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/identifier.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/identifier.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/internal.h b/WebKit/mac/ForwardingHeaders/kjs/internal.h
new file mode 100644
index 0000000..a20f3f3
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/internal.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/internal.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/interpreter.h b/WebKit/mac/ForwardingHeaders/kjs/interpreter.h
new file mode 100644
index 0000000..08c2be3
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/interpreter.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/interpreter.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/lookup.h b/WebKit/mac/ForwardingHeaders/kjs/lookup.h
new file mode 100644
index 0000000..5e2ffa0
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/lookup.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/lookup.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/object.h b/WebKit/mac/ForwardingHeaders/kjs/object.h
new file mode 100644
index 0000000..3309cc1
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/object.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/object.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/operations.h b/WebKit/mac/ForwardingHeaders/kjs/operations.h
new file mode 100644
index 0000000..eb80f49
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/operations.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/operations.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/protect.h b/WebKit/mac/ForwardingHeaders/kjs/protect.h
new file mode 100644
index 0000000..e4e0499
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/protect.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/protect.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/string_object.h b/WebKit/mac/ForwardingHeaders/kjs/string_object.h
new file mode 100644
index 0000000..26f026a
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/string_object.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/string_object.h>
diff --git a/WebKit/mac/ForwardingHeaders/kjs/value.h b/WebKit/mac/ForwardingHeaders/kjs/value.h
new file mode 100644
index 0000000..cf0b9c8
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/kjs/value.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/value.h>
diff --git a/WebKit/mac/ForwardingHeaders/pcre/pcre.h b/WebKit/mac/ForwardingHeaders/pcre/pcre.h
new file mode 100644
index 0000000..47c0d3d
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/pcre/pcre.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/pcre.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/ASCIICType.h b/WebKit/mac/ForwardingHeaders/wtf/ASCIICType.h
new file mode 100644
index 0000000..f2258d2
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/ASCIICType.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/ASCIICType.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/AlwaysInline.h b/WebKit/mac/ForwardingHeaders/wtf/AlwaysInline.h
new file mode 100644
index 0000000..156bd34
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/AlwaysInline.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/AlwaysInline.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/Assertions.h b/WebKit/mac/ForwardingHeaders/wtf/Assertions.h
new file mode 100644
index 0000000..c4cc25c
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/Assertions.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/Assertions.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/DisallowCType.h b/WebKit/mac/ForwardingHeaders/wtf/DisallowCType.h
new file mode 100644
index 0000000..445944b
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/DisallowCType.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/DisallowCType.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/FastMalloc.h b/WebKit/mac/ForwardingHeaders/wtf/FastMalloc.h
new file mode 100644
index 0000000..8733b5f
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/FastMalloc.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/FastMalloc.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/Forward.h b/WebKit/mac/ForwardingHeaders/wtf/Forward.h
new file mode 100644
index 0000000..2d707ec
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/Forward.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/Forward.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/GetPtr.h b/WebKit/mac/ForwardingHeaders/wtf/GetPtr.h
new file mode 100644
index 0000000..61baf6d
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/GetPtr.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/GetPtr.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/HashCountedSet.h b/WebKit/mac/ForwardingHeaders/wtf/HashCountedSet.h
new file mode 100644
index 0000000..23120ed
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/HashCountedSet.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/HashCountedSet.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/HashMap.h b/WebKit/mac/ForwardingHeaders/wtf/HashMap.h
new file mode 100644
index 0000000..4d7d60f
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/HashMap.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/HashMap.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/HashSet.h b/WebKit/mac/ForwardingHeaders/wtf/HashSet.h
new file mode 100644
index 0000000..03b7a70
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/HashSet.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/HashSet.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/HashTraits.h b/WebKit/mac/ForwardingHeaders/wtf/HashTraits.h
new file mode 100644
index 0000000..fa2ce1c
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/HashTraits.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/HashTraits.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/ListHashSet.h b/WebKit/mac/ForwardingHeaders/wtf/ListHashSet.h
new file mode 100644
index 0000000..8ed045d
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/ListHashSet.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/ListHashSet.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/ListRefPtr.h b/WebKit/mac/ForwardingHeaders/wtf/ListRefPtr.h
new file mode 100644
index 0000000..2aa2311
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/ListRefPtr.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/ListRefPtr.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/Locker.h b/WebKit/mac/ForwardingHeaders/wtf/Locker.h
new file mode 100644
index 0000000..7718305
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/Locker.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/Locker.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/MathExtras.h b/WebKit/mac/ForwardingHeaders/wtf/MathExtras.h
new file mode 100644
index 0000000..865479e
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/MathExtras.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/MathExtras.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/Noncopyable.h b/WebKit/mac/ForwardingHeaders/wtf/Noncopyable.h
new file mode 100644
index 0000000..0508024
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/Noncopyable.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/Noncopyable.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/OwnArrayPtr.h b/WebKit/mac/ForwardingHeaders/wtf/OwnArrayPtr.h
new file mode 100644
index 0000000..f10532c
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/OwnArrayPtr.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/OwnArrayPtr.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/OwnPtr.h b/WebKit/mac/ForwardingHeaders/wtf/OwnPtr.h
new file mode 100644
index 0000000..ccf0e22
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/OwnPtr.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/OwnPtr.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/PassRefPtr.h b/WebKit/mac/ForwardingHeaders/wtf/PassRefPtr.h
new file mode 100644
index 0000000..f1eb466
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/PassRefPtr.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/PassRefPtr.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/Platform.h b/WebKit/mac/ForwardingHeaders/wtf/Platform.h
new file mode 100644
index 0000000..18eaa34
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/Platform.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/Platform.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/RefCounted.h b/WebKit/mac/ForwardingHeaders/wtf/RefCounted.h
new file mode 100644
index 0000000..02c1236
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/RefCounted.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/RefCounted.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/RefPtr.h b/WebKit/mac/ForwardingHeaders/wtf/RefPtr.h
new file mode 100644
index 0000000..33c43be
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/RefPtr.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/RefPtr.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/RetainPtr.h b/WebKit/mac/ForwardingHeaders/wtf/RetainPtr.h
new file mode 100644
index 0000000..8471d5d
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/RetainPtr.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/RetainPtr.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/Threading.h b/WebKit/mac/ForwardingHeaders/wtf/Threading.h
new file mode 100644
index 0000000..771edd1
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/Threading.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/Threading.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/Vector.h b/WebKit/mac/ForwardingHeaders/wtf/Vector.h
new file mode 100644
index 0000000..769a550
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/Vector.h
@@ -0,0 +1 @@
+#import <JavaScriptCore/Vector.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/VectorTraits.h b/WebKit/mac/ForwardingHeaders/wtf/VectorTraits.h
new file mode 100644
index 0000000..2fc1158
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/VectorTraits.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/VectorTraits.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/unicode/Unicode.h b/WebKit/mac/ForwardingHeaders/wtf/unicode/Unicode.h
new file mode 100644
index 0000000..623917f
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/unicode/Unicode.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/Unicode.h>
diff --git a/WebKit/mac/ForwardingHeaders/wtf/unicode/icu/UnicodeIcu.h b/WebKit/mac/ForwardingHeaders/wtf/unicode/icu/UnicodeIcu.h
new file mode 100644
index 0000000..6b64eb5
--- /dev/null
+++ b/WebKit/mac/ForwardingHeaders/wtf/unicode/icu/UnicodeIcu.h
@@ -0,0 +1 @@
+#include <JavaScriptCore/UnicodeIcu.h>
diff --git a/WebKit/mac/History/WebBackForwardList.h b/WebKit/mac/History/WebBackForwardList.h
new file mode 100644
index 0000000..c2750d2
--- /dev/null
+++ b/WebKit/mac/History/WebBackForwardList.h
@@ -0,0 +1,190 @@
+/*
+ * Copyright (C) 2003 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define WebNSUInteger unsigned int
+#else
+#define WebNSUInteger NSUInteger
+#endif
+
+@class WebHistoryItem;
+@class WebBackForwardListPrivate;
+
+/*!
+ @class WebBackForwardList
+ WebBackForwardList holds an ordered list of WebHistoryItems that comprises the back and
+ forward lists.
+
+ Note that the methods which modify instances of this class do not cause
+ navigation to happen in other layers of the stack; they are only for maintaining this data
+ structure.
+*/
+@interface WebBackForwardList : NSObject {
+@private
+ WebBackForwardListPrivate *_private;
+}
+
+/*!
+ @method addItem:
+ @abstract Adds an entry to the list.
+ @param entry The entry to add.
+ @discussion The added entry is inserted immediately after the current entry.
+ If the current position in the list is not at the end of the list, elements in the
+ forward list will be dropped at this point. In addition, entries may be dropped to keep
+ the size of the list within the maximum size.
+*/
+- (void)addItem:(WebHistoryItem *)item;
+
+/*!
+ @method goBack
+ @abstract Move the current pointer back to the entry before the current entry.
+*/
+- (void)goBack;
+
+/*!
+ @method goForward
+ @abstract Move the current pointer ahead to the entry after the current entry.
+*/
+- (void)goForward;
+
+/*!
+ @method goToItem:
+ @abstract Move the current pointer to the given entry.
+ @param item The history item to move the pointer to
+*/
+- (void)goToItem:(WebHistoryItem *)item;
+
+/*!
+ @method backItem
+ @abstract Returns the entry right before the current entry.
+ @result The entry right before the current entry, or nil if there isn't one.
+*/
+- (WebHistoryItem *)backItem;
+
+/*!
+ @method currentItem
+ @abstract Returns the current entry.
+ @result The current entry.
+*/
+- (WebHistoryItem *)currentItem;
+
+/*!
+ @method forwardItem
+ @abstract Returns the entry right after the current entry.
+ @result The entry right after the current entry, or nil if there isn't one.
+*/
+- (WebHistoryItem *)forwardItem;
+
+/*!
+ @method backListWithLimit:
+ @abstract Returns a portion of the list before the current entry.
+ @param limit A cap on the size of the array returned.
+ @result An array of items before the current entry, or nil if there are none. The entries are in the order that they were originally visited.
+*/
+- (NSArray *)backListWithLimit:(int)limit;
+
+/*!
+ @method forwardListWithLimit:
+ @abstract Returns a portion of the list after the current entry.
+ @param limit A cap on the size of the array returned.
+ @result An array of items after the current entry, or nil if there are none. The entries are in the order that they were originally visited.
+*/
+- (NSArray *)forwardListWithLimit:(int)limit;
+
+/*!
+ @method capacity
+ @abstract Returns the list's maximum size.
+ @result The list's maximum size.
+*/
+- (int)capacity;
+
+/*!
+ @method setCacpacity
+ @abstract Sets the list's maximum size.
+ @param size The new maximum size for the list.
+*/
+- (void)setCapacity:(int)size;
+
+/*!
+ @method backListCount
+ @abstract Returns the back list's current count.
+ @result The number of items in the list.
+*/
+- (int)backListCount;
+
+/*!
+ @method forwardListCount
+ @abstract Returns the forward list's current count.
+ @result The number of items in the list.
+*/
+- (int)forwardListCount;
+
+/*!
+ @method containsItem:
+ @param item The item that will be checked for presence in the WebBackForwardList.
+ @result Returns YES if the item is in the list.
+*/
+- (BOOL)containsItem:(WebHistoryItem *)item;
+
+/*!
+ @method itemAtIndex:
+ @abstract Returns an entry the given distance from the current entry.
+ @param index Index of the desired list item relative to the current item; 0 is current item, -1 is back item, 1 is forward item, etc.
+ @result The entry the given distance from the current entry. If index exceeds the limits of the list, nil is returned.
+*/
+- (WebHistoryItem *)itemAtIndex:(int)index;
+
+@end
+
+@interface WebBackForwardList(WebBackForwardListDeprecated)
+
+// The following methods are deprecated, and exist for backward compatibility only.
+// Use -[WebPreferences setUsesPageCache] and -[WebPreferences usesPageCache]
+// instead.
+
+/*!
+ @method setPageCacheSize:
+ @abstract The size passed to this method determines whether the WebView
+ associated with this WebBackForwardList will use the shared page cache.
+ @param size If size is 0, the WebView associated with this WebBackForwardList
+ will not use the shared page cache. Otherwise, it will.
+*/
+- (void)setPageCacheSize:(WebNSUInteger)size;
+
+/*!
+ @method pageCacheSize
+ @abstract Returns the size of the shared page cache, or 0.
+ @result The size of the shared page cache (in pages), or 0 if the WebView
+ associated with this WebBackForwardList will not use the shared page cache.
+*/
+- (WebNSUInteger)pageCacheSize;
+@end
+
+#undef WebNSUInteger
diff --git a/WebKit/mac/History/WebBackForwardList.mm b/WebKit/mac/History/WebBackForwardList.mm
new file mode 100644
index 0000000..6423830
--- /dev/null
+++ b/WebKit/mac/History/WebBackForwardList.mm
@@ -0,0 +1,279 @@
+/*
+ * Copyright (C) 2005, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebBackForwardList.h"
+#import "WebBackForwardListInternal.h"
+
+#import "WebFrameInternal.h"
+#import "WebHistoryItemInternal.h"
+#import "WebHistoryItemPrivate.h"
+#import "WebKitLogging.h"
+#import "WebNSObjectExtras.h"
+#import "WebPreferencesPrivate.h"
+#import "WebTypesInternal.h"
+#import "WebViewPrivate.h"
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/BackForwardList.h>
+#import <WebCore/HistoryItem.h>
+#import <WebCore/Page.h>
+#import <WebCore/PageCache.h>
+#import <WebCore/Settings.h>
+#import <WebCore/ThreadCheck.h>
+#import <WebCore/WebCoreObjCExtras.h>
+#import <wtf/RetainPtr.h>
+
+using namespace WebCore;
+
+static HashMap<BackForwardList*, WebBackForwardList*>& backForwardLists()
+{
+ static HashMap<BackForwardList*, WebBackForwardList*> staticBackForwardLists;
+ return staticBackForwardLists;
+}
+
+@implementation WebBackForwardList (WebBackForwardListInternal)
+
+BackForwardList* core(WebBackForwardList *webBackForwardList)
+{
+ if (!webBackForwardList)
+ return 0;
+
+ return reinterpret_cast<BackForwardList*>(webBackForwardList->_private);
+}
+
+WebBackForwardList *kit(BackForwardList* backForwardList)
+{
+ if (!backForwardList)
+ return nil;
+
+ if (WebBackForwardList *webBackForwardList = backForwardLists().get(backForwardList))
+ return webBackForwardList;
+
+ return [[[WebBackForwardList alloc] initWithBackForwardList:backForwardList] autorelease];
+}
+
+- (id)initWithBackForwardList:(PassRefPtr<BackForwardList>)backForwardList
+{
+ WebCoreThreadViolationCheck();
+ self = [super init];
+ if (!self)
+ return nil;
+
+ _private = reinterpret_cast<WebBackForwardListPrivate*>(backForwardList.releaseRef());
+ backForwardLists().set(core(self), self);
+ return self;
+}
+
+@end
+
+@implementation WebBackForwardList
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
+- (id)init
+{
+ return [self initWithBackForwardList:BackForwardList::create(0)];
+}
+
+- (void)dealloc
+{
+ WebCoreThreadViolationCheck();
+ BackForwardList* backForwardList = core(self);
+ ASSERT(backForwardList->closed());
+ backForwardLists().remove(backForwardList);
+ backForwardList->deref();
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ WebCoreThreadViolationCheck();
+ BackForwardList* backForwardList = core(self);
+ ASSERT(backForwardList->closed());
+ backForwardLists().remove(backForwardList);
+ backForwardList->deref();
+
+ [super finalize];
+}
+
+- (void)_close
+{
+ core(self)->close();
+}
+
+- (void)addItem:(WebHistoryItem *)entry;
+{
+ core(self)->addItem(core(entry));
+
+ // Since the assumed contract with WebBackForwardList is that it retains its WebHistoryItems,
+ // the following line prevents a whole class of problems where a history item will be created in
+ // a function, added to the BFlist, then used in the rest of that function.
+ [[entry retain] autorelease];
+}
+
+- (void)removeItem:(WebHistoryItem *)item
+{
+ core(self)->removeItem(core(item));
+}
+
+- (BOOL)containsItem:(WebHistoryItem *)item
+{
+ return core(self)->containsItem(core(item));
+}
+
+- (void)goBack
+{
+ core(self)->goBack();
+}
+
+- (void)goForward
+{
+ core(self)->goForward();
+}
+
+- (void)goToItem:(WebHistoryItem *)item
+{
+ core(self)->goToItem(core(item));
+}
+
+- (WebHistoryItem *)backItem
+{
+ return [[kit(core(self)->backItem()) retain] autorelease];
+}
+
+- (WebHistoryItem *)currentItem
+{
+ return [[kit(core(self)->currentItem()) retain] autorelease];
+}
+
+- (WebHistoryItem *)forwardItem
+{
+ return [[kit(core(self)->forwardItem()) retain] autorelease];
+}
+
+static NSArray* vectorToNSArray(HistoryItemVector& list)
+{
+ unsigned size = list.size();
+ NSMutableArray *result = [[[NSMutableArray alloc] initWithCapacity:size] autorelease];
+ for (unsigned i = 0; i < size; ++i)
+ [result addObject:kit(list[i].get())];
+
+ return result;
+}
+
+- (NSArray *)backListWithLimit:(int)limit;
+{
+ HistoryItemVector list;
+ core(self)->backListWithLimit(limit, list);
+ return vectorToNSArray(list);
+}
+
+- (NSArray *)forwardListWithLimit:(int)limit;
+{
+ HistoryItemVector list;
+ core(self)->forwardListWithLimit(limit, list);
+ return vectorToNSArray(list);
+}
+
+- (int)capacity
+{
+ return core(self)->capacity();
+}
+
+- (void)setCapacity:(int)size
+{
+ core(self)->setCapacity(size);
+}
+
+
+-(NSString *)description
+{
+ NSMutableString *result;
+
+ result = [NSMutableString stringWithCapacity:512];
+
+ [result appendString:@"\n--------------------------------------------\n"];
+ [result appendString:@"WebBackForwardList:\n"];
+
+ BackForwardList* backForwardList = core(self);
+ HistoryItemVector& entries = backForwardList->entries();
+
+ unsigned size = entries.size();
+ for (unsigned i = 0; i < size; ++i) {
+ if (entries[i] == backForwardList->currentItem()) {
+ [result appendString:@" >>>"];
+ } else {
+ [result appendString:@" "];
+ }
+ [result appendFormat:@"%2d) ", i];
+ int currPos = [result length];
+ [result appendString:[kit(entries[i].get()) description]];
+
+ // shift all the contents over. a bit slow, but this is for debugging
+ NSRange replRange = {currPos, [result length]-currPos};
+ [result replaceOccurrencesOfString:@"\n" withString:@"\n " options:0 range:replRange];
+
+ [result appendString:@"\n"];
+ }
+
+ [result appendString:@"\n--------------------------------------------\n"];
+
+ return result;
+}
+
+- (void)setPageCacheSize:(NSUInteger)size
+{
+ [kit(core(self)->page()) setUsesPageCache:size != 0];
+}
+
+- (NSUInteger)pageCacheSize
+{
+ return [kit(core(self)->page()) usesPageCache] ? pageCache()->capacity() : 0;
+}
+
+- (int)backListCount
+{
+ return core(self)->backListCount();
+}
+
+- (int)forwardListCount
+{
+ return core(self)->forwardListCount();
+}
+
+- (WebHistoryItem *)itemAtIndex:(int)index
+{
+ return [[kit(core(self)->itemAtIndex(index)) retain] autorelease];
+}
+
+@end
diff --git a/WebKit/mac/History/WebBackForwardListInternal.h b/WebKit/mac/History/WebBackForwardListInternal.h
new file mode 100644
index 0000000..3448647
--- /dev/null
+++ b/WebKit/mac/History/WebBackForwardListInternal.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebBackForwardList.h>
+#import <wtf/PassRefPtr.h>
+
+namespace WebCore {
+ class BackForwardList;
+}
+
+WebCore::BackForwardList* core(WebBackForwardList *);
+WebBackForwardList *kit(WebCore::BackForwardList*);
+
+@interface WebBackForwardList (WebBackForwardListInternal)
+- (id)initWithBackForwardList:(PassRefPtr<WebCore::BackForwardList>)backForwardList;
+@end
diff --git a/WebKit/mac/History/WebBackForwardListPrivate.h b/WebKit/mac/History/WebBackForwardListPrivate.h
new file mode 100644
index 0000000..7e76e9b
--- /dev/null
+++ b/WebKit/mac/History/WebBackForwardListPrivate.h
@@ -0,0 +1,42 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+#import <WebKit/WebBackForwardList.h>
+
+@interface WebBackForwardList (WebBackForwardListPrivate)
+
+/*!
+ @method removeItem:
+ @abstract Removes an entry from the list.
+ @param entry The entry to remove. Cannot be the current item.
+*/
+- (void)removeItem:(WebHistoryItem *)item;
+
+@end
diff --git a/WebKit/mac/History/WebHistory.h b/WebKit/mac/History/WebHistory.h
new file mode 100644
index 0000000..8a6ec0b
--- /dev/null
+++ b/WebKit/mac/History/WebHistory.h
@@ -0,0 +1,165 @@
+/*
+ * Copyright (C) 2003, 2004 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@class NSError;
+
+@class WebHistoryItem;
+@class WebHistoryPrivate;
+
+/*
+ @discussion Notifications sent when history is modified.
+ @constant WebHistoryItemsAddedNotification Posted from addItems:. This
+ notification comes with a userInfo dictionary that contains the array of
+ items added. The key for the array is WebHistoryItemsKey.
+ @constant WebHistoryItemsRemovedNotification Posted from removeItems:.
+ This notification comes with a userInfo dictionary that contains the array of
+ items removed. The key for the array is WebHistoryItemsKey.
+ @constant WebHistoryAllItemsRemovedNotification Posted from removeAllItems
+ @constant WebHistoryLoadedNotification Posted from loadFromURL:error:.
+*/
+extern NSString *WebHistoryItemsAddedNotification;
+extern NSString *WebHistoryItemsRemovedNotification;
+extern NSString *WebHistoryAllItemsRemovedNotification;
+extern NSString *WebHistoryLoadedNotification;
+extern NSString *WebHistorySavedNotification;
+
+extern NSString *WebHistoryItemsKey;
+
+/*!
+ @class WebHistory
+ @discussion WebHistory is used to track pages that have been loaded
+ by WebKit.
+*/
+@interface WebHistory : NSObject {
+@private
+ WebHistoryPrivate *_historyPrivate;
+}
+
+/*!
+ @method optionalSharedHistory
+ @abstract Returns a shared WebHistory instance initialized with the default history file.
+ @result A WebHistory object.
+*/
++ (WebHistory *)optionalSharedHistory;
+
+/*!
+ @method setOptionalSharedHistory:
+ @param history The history to use for the global WebHistory.
+*/
++ (void)setOptionalSharedHistory:(WebHistory *)history;
+
+/*!
+ @method loadFromURL:error:
+ @param URL The URL to use to initialize the WebHistory.
+ @param error Set to nil or an NSError instance if an error occurred.
+ @abstract The designated initializer for WebHistory.
+ @result Returns YES if successful, NO otherwise.
+*/
+- (BOOL)loadFromURL:(NSURL *)URL error:(NSError **)error;
+
+/*!
+ @method saveToURL:error:
+ @discussion Save history to URL. It is the client's responsibility to call this at appropriate times.
+ @param URL The URL to use to save the WebHistory.
+ @param error Set to nil or an NSError instance if an error occurred.
+ @result Returns YES if successful, NO otherwise.
+*/
+- (BOOL)saveToURL:(NSURL *)URL error:(NSError **)error;
+
+/*!
+ @method addItems:
+ @param newItems An array of WebHistoryItems to add to the WebHistory.
+*/
+- (void)addItems:(NSArray *)newItems;
+
+/*!
+ @method removeItems:
+ @param items An array of WebHistoryItems to remove from the WebHistory.
+*/
+- (void)removeItems:(NSArray *)items;
+
+/*!
+ @method removeAllItems
+*/
+- (void)removeAllItems;
+
+/*!
+ @method orderedLastVisitedDays
+ @discussion Get an array of NSCalendarDates, each one representing a unique day that contains one
+ or more history items, ordered from most recent to oldest.
+ @result Returns an array of NSCalendarDates for which history items exist in the WebHistory.
+*/
+- (NSArray *)orderedLastVisitedDays;
+
+/*!
+ @method orderedItemsLastVisitedOnDay:
+ @discussion Get an array of WebHistoryItem that were last visited on the day represented by the
+ specified NSCalendarDate, ordered from most recent to oldest.
+ @param calendarDate A date identifying the unique day of interest.
+ @result Returns an array of WebHistoryItems last visited on the indicated day.
+*/
+- (NSArray *)orderedItemsLastVisitedOnDay:(NSCalendarDate *)calendarDate;
+
+/*!
+ @method itemForURL:
+ @abstract Get an item for a specific URL
+ @param URL The URL of the history item to search for
+ @result Returns an item matching the URL
+*/
+- (WebHistoryItem *)itemForURL:(NSURL *)URL;
+
+/*!
+ @method setHistoryItemLimit:
+ @discussion Limits the number of items that will be stored by the WebHistory.
+ @param limit The maximum number of items that will be stored by the WebHistory.
+*/
+- (void)setHistoryItemLimit:(int)limit;
+
+/*!
+ @method historyItemLimit
+ @result The maximum number of items that will be stored by the WebHistory.
+*/
+- (int)historyItemLimit;
+
+/*!
+ @method setHistoryAgeInDaysLimit:
+ @discussion setHistoryAgeInDaysLimit: sets the maximum number of days to be read from
+ stored history.
+ @param limit The maximum number of days to be read from stored history.
+*/
+- (void)setHistoryAgeInDaysLimit:(int)limit;
+
+/*!
+ @method historyAgeInDaysLimit
+ @return Returns the maximum number of days to be read from stored history.
+*/
+- (int)historyAgeInDaysLimit;
+
+@end
diff --git a/WebKit/mac/History/WebHistory.mm b/WebKit/mac/History/WebHistory.mm
new file mode 100644
index 0000000..6d00758
--- /dev/null
+++ b/WebKit/mac/History/WebHistory.mm
@@ -0,0 +1,869 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebHistory.h"
+#import "WebHistoryPrivate.h"
+
+#import "WebHistoryItem.h"
+#import "WebHistoryItemInternal.h"
+#import "WebHistoryItemPrivate.h"
+#import "WebKitLogging.h"
+#import "WebNSURLExtras.h"
+#import <Foundation/NSError.h>
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/WebCoreHistory.h>
+#import <wtf/Vector.h>
+
+NSString *WebHistoryItemsAddedNotification = @"WebHistoryItemsAddedNotification";
+NSString *WebHistoryItemsRemovedNotification = @"WebHistoryItemsRemovedNotification";
+NSString *WebHistoryAllItemsRemovedNotification = @"WebHistoryAllItemsRemovedNotification";
+NSString *WebHistoryLoadedNotification = @"WebHistoryLoadedNotification";
+NSString *WebHistoryItemsDiscardedWhileLoadingNotification = @"WebHistoryItemsDiscardedWhileLoadingNotification";
+NSString *WebHistorySavedNotification = @"WebHistorySavedNotification";
+NSString *WebHistoryItemsKey = @"WebHistoryItems";
+
+static WebHistory *_sharedHistory = nil;
+
+NSString *FileVersionKey = @"WebHistoryFileVersion";
+NSString *DatesArrayKey = @"WebHistoryDates";
+
+#define currentFileVersion 1
+
+@implementation WebHistoryPrivate
+
+#pragma mark OBJECT FRAMEWORK
+
++ (void)initialize
+{
+ [[NSUserDefaults standardUserDefaults] registerDefaults:
+ [NSDictionary dictionaryWithObjectsAndKeys:
+ @"1000", @"WebKitHistoryItemLimit",
+ @"7", @"WebKitHistoryAgeInDaysLimit",
+ nil]];
+}
+
+- (id)init
+{
+ if (![super init]) {
+ return nil;
+ }
+
+ _entriesByURL = [[NSMutableDictionary alloc] init];
+ _entriesByDate = new DateToEntriesMap;
+
+ return self;
+}
+
+- (void)dealloc
+{
+ [_entriesByURL release];
+ [_orderedLastVisitedDays release];
+ delete _entriesByDate;
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ delete _entriesByDate;
+ [super finalize];
+}
+
+#pragma mark MODIFYING CONTENTS
+
+WebHistoryDateKey timeIntervalForBeginningOfDay(NSTimeInterval interval)
+{
+ CFTimeZoneRef timeZone = CFTimeZoneCopyDefault();
+ CFGregorianDate date = CFAbsoluteTimeGetGregorianDate(interval, timeZone);
+ date.hour = 0;
+ date.minute = 0;
+ date.second = 0;
+ NSTimeInterval result = CFGregorianDateGetAbsoluteTime(date, timeZone);
+ CFRelease(timeZone);
+
+ // Converting from double to int64_t is safe here as NSDate's useful range
+ // is -2**48 .. 2**47 which will safely fit in an int64_t.
+ return (WebHistoryDateKey)result;
+}
+
+// Returns whether the day is already in the list of days,
+// and fills in *key with the key used to access its location
+- (BOOL)findKey:(WebHistoryDateKey*)key forDay:(NSTimeInterval)date
+{
+ ASSERT_ARG(key, key != nil);
+ *key = timeIntervalForBeginningOfDay(date);
+ return _entriesByDate->contains(*key);
+}
+
+- (void)insertItem:(WebHistoryItem *)entry forDateKey:(WebHistoryDateKey)dateKey
+{
+ ASSERT_ARG(entry, entry != nil);
+ ASSERT(_entriesByDate->contains(dateKey));
+
+ NSMutableArray *entriesForDate = _entriesByDate->get(dateKey).get();
+ NSTimeInterval entryDate = [entry lastVisitedTimeInterval];
+
+ unsigned count = [entriesForDate count];
+
+ // The entries for each day are stored in a sorted array with the most recent entry first
+ // Check for the common cases of the entry being newer than all existing entries or the first entry of the day
+ if (!count || [[entriesForDate objectAtIndex:0] lastVisitedTimeInterval] < entryDate) {
+ [entriesForDate insertObject:entry atIndex:0];
+ return;
+ }
+ // .. or older than all existing entries
+ if (count > 0 && [[entriesForDate objectAtIndex:count - 1] lastVisitedTimeInterval] >= entryDate) {
+ [entriesForDate insertObject:entry atIndex:count];
+ return;
+ }
+
+ unsigned low = 0;
+ unsigned high = count;
+ while (low < high) {
+ unsigned mid = low + (high - low) / 2;
+ if ([[entriesForDate objectAtIndex:mid] lastVisitedTimeInterval] >= entryDate)
+ low = mid + 1;
+ else
+ high = mid;
+ }
+
+ // low is now the index of the first entry that is older than entryDate
+ [entriesForDate insertObject:entry atIndex:low];
+}
+
+- (BOOL)_removeItemFromDateCaches:(WebHistoryItem *)entry
+{
+ WebHistoryDateKey dateKey;
+ BOOL foundDate = [self findKey:&dateKey forDay:[entry lastVisitedTimeInterval]];
+
+ if (!foundDate)
+ return NO;
+
+ DateToEntriesMap::iterator it = _entriesByDate->find(dateKey);
+ NSMutableArray *entriesForDate = it->second.get();
+ [entriesForDate removeObjectIdenticalTo:entry];
+
+ // remove this date entirely if there are no other entries on it
+ if ([entriesForDate count] == 0) {
+ _entriesByDate->remove(it);
+ // Clear _orderedLastVisitedDays so it will be regenerated when next requested.
+ [_orderedLastVisitedDays release];
+ _orderedLastVisitedDays = nil;
+ }
+
+ return YES;
+}
+
+- (BOOL)removeItemForURLString: (NSString *)URLString
+{
+ WebHistoryItem *entry = [_entriesByURL objectForKey: URLString];
+ if (entry == nil) {
+ return NO;
+ }
+
+ [_entriesByURL removeObjectForKey: URLString];
+
+#if ASSERT_DISABLED
+ [self _removeItemFromDateCaches:entry];
+#else
+ BOOL itemWasInDateCaches = [self _removeItemFromDateCaches:entry];
+ ASSERT(itemWasInDateCaches);
+#endif
+
+ return YES;
+}
+
+- (void)_addItemToDateCaches:(WebHistoryItem *)entry
+{
+ WebHistoryDateKey dateKey;
+ if ([self findKey:&dateKey forDay:[entry lastVisitedTimeInterval]])
+ // other entries already exist for this date
+ [self insertItem:entry forDateKey:dateKey];
+ else {
+ // no other entries exist for this date
+ NSMutableArray *entries = [[NSMutableArray alloc] initWithObjects:&entry count:1];
+ _entriesByDate->set(dateKey, entries);
+ [entries release];
+ // Clear _orderedLastVisitedDays so it will be regenerated when next requested.
+ [_orderedLastVisitedDays release];
+ _orderedLastVisitedDays = nil;
+ }
+}
+
+- (void)addItem:(WebHistoryItem *)entry
+{
+ ASSERT_ARG(entry, entry);
+ ASSERT_ARG(entry, [entry lastVisitedTimeInterval] != 0);
+
+ NSString *URLString = [entry URLString];
+
+ WebHistoryItem *oldEntry = [_entriesByURL objectForKey:URLString];
+ if (oldEntry) {
+ // The last reference to oldEntry might be this dictionary, so we hold onto a reference
+ // until we're done with oldEntry.
+ [oldEntry retain];
+ [self removeItemForURLString:URLString];
+
+ // If we already have an item with this URL, we need to merge info that drives the
+ // URL autocomplete heuristics from that item into the new one.
+ [entry _mergeAutoCompleteHints:oldEntry];
+ [oldEntry release];
+ }
+
+ [self _addItemToDateCaches:entry];
+ [_entriesByURL setObject:entry forKey:URLString];
+}
+
+- (void)setLastVisitedTimeInterval:(NSTimeInterval)time forItem:(WebHistoryItem *)entry
+{
+#if ASSERT_DISABLED
+ [self _removeItemFromDateCaches:entry];
+#else
+ BOOL entryWasPresent = [self _removeItemFromDateCaches:entry];
+ ASSERT(entryWasPresent);
+#endif
+
+ [entry _setLastVisitedTimeInterval:time];
+ [self _addItemToDateCaches:entry];
+
+ // Don't send notification until entry is back in the right place in the date caches,
+ // since observers might fetch history by date when they receive the notification.
+ [[NSNotificationCenter defaultCenter]
+ postNotificationName:WebHistoryItemChangedNotification object:entry userInfo:nil];
+}
+
+- (BOOL)removeItem: (WebHistoryItem *)entry
+{
+ WebHistoryItem *matchingEntry;
+ NSString *URLString;
+
+ URLString = [entry URLString];
+
+ // If this exact object isn't stored, then make no change.
+ // FIXME: Is this the right behavior if this entry isn't present, but another entry for the same URL is?
+ // Maybe need to change the API to make something like removeEntryForURLString public instead.
+ matchingEntry = [_entriesByURL objectForKey: URLString];
+ if (matchingEntry != entry) {
+ return NO;
+ }
+
+ [self removeItemForURLString: URLString];
+
+ return YES;
+}
+
+- (BOOL)removeItems: (NSArray *)entries
+{
+ int index, count;
+
+ count = [entries count];
+ if (count == 0) {
+ return NO;
+ }
+
+ for (index = 0; index < count; ++index) {
+ [self removeItem:[entries objectAtIndex:index]];
+ }
+
+ return YES;
+}
+
+- (BOOL)removeAllItems
+{
+ if ([_entriesByURL count] == 0) {
+ return NO;
+ }
+
+ _entriesByDate->clear();
+ [_entriesByURL removeAllObjects];
+
+ // Clear _orderedLastVisitedDays so it will be regenerated when next requested.
+ [_orderedLastVisitedDays release];
+ _orderedLastVisitedDays = nil;
+
+ return YES;
+}
+
+- (void)addItems:(NSArray *)newEntries
+{
+ NSEnumerator *enumerator;
+ WebHistoryItem *entry;
+
+ // There is no guarantee that the incoming entries are in any particular
+ // order, but if this is called with a set of entries that were created by
+ // iterating through the results of orderedLastVisitedDays and orderedItemsLastVisitedOnDayy
+ // then they will be ordered chronologically from newest to oldest. We can make adding them
+ // faster (fewer compares) by inserting them from oldest to newest.
+ enumerator = [newEntries reverseObjectEnumerator];
+ while ((entry = [enumerator nextObject]) != nil) {
+ [self addItem:entry];
+ }
+}
+
+#pragma mark DATE-BASED RETRIEVAL
+
+- (NSArray *)orderedLastVisitedDays
+{
+ if (!_orderedLastVisitedDays) {
+ Vector<int> daysAsTimeIntervals;
+ daysAsTimeIntervals.reserveCapacity(_entriesByDate->size());
+ DateToEntriesMap::const_iterator end = _entriesByDate->end();
+ for (DateToEntriesMap::const_iterator it = _entriesByDate->begin(); it != end; ++it)
+ daysAsTimeIntervals.append(it->first);
+
+ std::sort(daysAsTimeIntervals.begin(), daysAsTimeIntervals.end());
+ size_t count = daysAsTimeIntervals.size();
+ _orderedLastVisitedDays = [[NSMutableArray alloc] initWithCapacity:count];
+ for (int i = count - 1; i >= 0; i--) {
+ NSTimeInterval interval = daysAsTimeIntervals[i];
+ NSCalendarDate *date = [[NSCalendarDate alloc] initWithTimeIntervalSinceReferenceDate:interval];
+ [_orderedLastVisitedDays addObject:date];
+ [date release];
+ }
+ }
+ return _orderedLastVisitedDays;
+}
+
+- (NSArray *)orderedItemsLastVisitedOnDay: (NSCalendarDate *)date
+{
+ WebHistoryDateKey dateKey;
+ if ([self findKey:&dateKey forDay:[date timeIntervalSinceReferenceDate]])
+ return _entriesByDate->get(dateKey).get();
+
+ return nil;
+}
+
+#pragma mark URL MATCHING
+
+- (WebHistoryItem *)itemForURLString:(NSString *)URLString
+{
+ return [_entriesByURL objectForKey: URLString];
+}
+
+- (BOOL)containsItemForURLString: (NSString *)URLString
+{
+ return [self itemForURLString:URLString] != nil;
+}
+
+- (BOOL)containsURL: (NSURL *)URL
+{
+ return [self itemForURLString:[URL _web_originalDataAsString]] != nil;
+}
+
+- (WebHistoryItem *)itemForURL:(NSURL *)URL
+{
+ return [self itemForURLString:[URL _web_originalDataAsString]];
+}
+
+#pragma mark ARCHIVING/UNARCHIVING
+
+- (void)setHistoryAgeInDaysLimit:(int)limit
+{
+ ageInDaysLimitSet = YES;
+ ageInDaysLimit = limit;
+}
+
+- (int)historyAgeInDaysLimit
+{
+ if (ageInDaysLimitSet)
+ return ageInDaysLimit;
+ return [[NSUserDefaults standardUserDefaults] integerForKey: @"WebKitHistoryAgeInDaysLimit"];
+}
+
+- (void)setHistoryItemLimit:(int)limit
+{
+ itemLimitSet = YES;
+ itemLimit = limit;
+}
+
+- (int)historyItemLimit
+{
+ if (itemLimitSet)
+ return itemLimit;
+ return [[NSUserDefaults standardUserDefaults] integerForKey: @"WebKitHistoryItemLimit"];
+}
+
+// Return a date that marks the age limit for history entries saved to or
+// loaded from disk. Any entry older than this item should be rejected.
+- (NSCalendarDate *)_ageLimitDate
+{
+ return [[NSCalendarDate calendarDate] dateByAddingYears:0 months:0 days:-[self historyAgeInDaysLimit]
+ hours:0 minutes:0 seconds:0];
+}
+
+// Return a flat array of WebHistoryItems. Ignores the date and item count limits; these are
+// respected when loading instead of when saving, so that clients can learn of discarded items
+// by listening to WebHistoryItemsDiscardedWhileLoadingNotification.
+- (NSArray *)arrayRepresentation
+{
+ NSMutableArray *arrayRep = [NSMutableArray array];
+
+ Vector<int> dateKeys;
+ dateKeys.reserveCapacity(_entriesByDate->size());
+ DateToEntriesMap::const_iterator end = _entriesByDate->end();
+ for (DateToEntriesMap::const_iterator it = _entriesByDate->begin(); it != end; ++it)
+ dateKeys.append(it->first);
+
+ std::sort(dateKeys.begin(), dateKeys.end());
+ for (int dateIndex = dateKeys.size() - 1; dateIndex >= 0; dateIndex--) {
+ NSArray *entries = _entriesByDate->get(dateKeys[dateIndex]).get();
+ int entryCount = [entries count];
+ for (int entryIndex = 0; entryIndex < entryCount; ++entryIndex)
+ [arrayRep addObject:[[entries objectAtIndex:entryIndex] dictionaryRepresentation]];
+ }
+
+ return arrayRep;
+}
+
+- (BOOL)_loadHistoryGutsFromURL:(NSURL *)URL savedItemsCount:(int *)numberOfItemsLoaded collectDiscardedItemsInto:(NSMutableArray *)discardedItems error:(NSError **)error
+{
+ *numberOfItemsLoaded = 0;
+ NSDictionary *dictionary = nil;
+
+ // Optimize loading from local file, which is faster than using the general URL loading mechanism
+ if ([URL isFileURL]) {
+ dictionary = [NSDictionary dictionaryWithContentsOfFile:[URL path]];
+ if (!dictionary) {
+#if !LOG_DISABLED
+ if ([[NSFileManager defaultManager] fileExistsAtPath:[URL path]])
+ LOG_ERROR("unable to read history from file %@; perhaps contents are corrupted", [URL path]);
+#endif
+ // else file doesn't exist, which is normal the first time
+ return NO;
+ }
+ } else {
+ NSData *data = [NSURLConnection sendSynchronousRequest:[NSURLRequest requestWithURL:URL] returningResponse:nil error:error];
+ if (data && [data length] > 0) {
+ dictionary = [NSPropertyListSerialization propertyListFromData:data
+ mutabilityOption:NSPropertyListImmutable
+ format:nil
+ errorDescription:nil];
+ }
+ }
+
+ // We used to support NSArrays here, but that was before Safari 1.0 shipped. We will no longer support
+ // that ancient format, so anything that isn't an NSDictionary is bogus.
+ if (![dictionary isKindOfClass:[NSDictionary class]])
+ return NO;
+
+ NSNumber *fileVersionObject = [dictionary objectForKey:FileVersionKey];
+ int fileVersion;
+ // we don't trust data obtained from elsewhere, so double-check
+ if (fileVersionObject != nil && [fileVersionObject isKindOfClass:[NSNumber class]]) {
+ fileVersion = [fileVersionObject intValue];
+ } else {
+ LOG_ERROR("history file version can't be determined, therefore not loading");
+ return NO;
+ }
+ if (fileVersion > currentFileVersion) {
+ LOG_ERROR("history file version is %d, newer than newest known version %d, therefore not loading", fileVersion, currentFileVersion);
+ return NO;
+ }
+
+ NSArray *array = [dictionary objectForKey:DatesArrayKey];
+
+ int itemCountLimit = [self historyItemLimit];
+ NSTimeInterval ageLimitDate = [[self _ageLimitDate] timeIntervalSinceReferenceDate];
+ NSEnumerator *enumerator = [array objectEnumerator];
+ BOOL ageLimitPassed = NO;
+ BOOL itemLimitPassed = NO;
+ ASSERT(*numberOfItemsLoaded == 0);
+
+ NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
+ NSDictionary *itemAsDictionary;
+ while ((itemAsDictionary = [enumerator nextObject]) != nil) {
+ WebHistoryItem *item = [[WebHistoryItem alloc] initFromDictionaryRepresentation:itemAsDictionary];
+
+ // item without URL is useless; data on disk must have been bad; ignore
+ if ([item URLString]) {
+ // Test against date limit. Since the items are ordered newest to oldest, we can stop comparing
+ // once we've found the first item that's too old.
+ if (!ageLimitPassed && [item lastVisitedTimeInterval] <= ageLimitDate)
+ ageLimitPassed = YES;
+
+ if (ageLimitPassed || itemLimitPassed)
+ [discardedItems addObject:item];
+ else {
+ [self addItem:item];
+ ++(*numberOfItemsLoaded);
+ if (*numberOfItemsLoaded == itemCountLimit)
+ itemLimitPassed = YES;
+
+ // Draining the autorelease pool every 50 iterations was found by experimentation to be optimal
+ if (*numberOfItemsLoaded % 50 == 0) {
+ [pool drain];
+ pool = [[NSAutoreleasePool alloc] init];
+ }
+ }
+ }
+ [item release];
+ }
+ [pool drain];
+
+ return YES;
+}
+
+- (BOOL)loadFromURL:(NSURL *)URL collectDiscardedItemsInto:(NSMutableArray *)discardedItems error:(NSError **)error
+{
+ int numberOfItems;
+ double start, duration;
+ BOOL result;
+
+ start = CFAbsoluteTimeGetCurrent();
+ result = [self _loadHistoryGutsFromURL:URL savedItemsCount:&numberOfItems collectDiscardedItemsInto:discardedItems error:error];
+
+ if (result) {
+ duration = CFAbsoluteTimeGetCurrent() - start;
+ LOG(Timing, "loading %d history entries from %@ took %f seconds",
+ numberOfItems, URL, duration);
+ }
+
+ return result;
+}
+
+- (BOOL)_saveHistoryGuts: (int *)numberOfItemsSaved URL:(NSURL *)URL error:(NSError **)error
+{
+ *numberOfItemsSaved = 0;
+
+ // FIXME: Correctly report error when new API is ready.
+ if (error)
+ *error = nil;
+
+ NSArray *array = [self arrayRepresentation];
+ NSDictionary *dictionary = [NSDictionary dictionaryWithObjectsAndKeys:
+ array, DatesArrayKey,
+ [NSNumber numberWithInt:currentFileVersion], FileVersionKey,
+ nil];
+ NSData *data = [NSPropertyListSerialization dataFromPropertyList:dictionary format:NSPropertyListBinaryFormat_v1_0 errorDescription:nil];
+ if (![data writeToURL:URL atomically:YES]) {
+ LOG_ERROR("attempt to save %@ to %@ failed", dictionary, URL);
+ return NO;
+ }
+
+ *numberOfItemsSaved = [array count];
+ return YES;
+}
+
+- (BOOL)saveToURL:(NSURL *)URL error:(NSError **)error
+{
+ int numberOfItems;
+ double start, duration;
+ BOOL result;
+
+ start = CFAbsoluteTimeGetCurrent();
+ result = [self _saveHistoryGuts: &numberOfItems URL:URL error:error];
+
+ if (result) {
+ duration = CFAbsoluteTimeGetCurrent() - start;
+ LOG(Timing, "saving %d history entries to %@ took %f seconds",
+ numberOfItems, URL, duration);
+ }
+
+ return result;
+}
+
+@end
+
+@interface _WebCoreHistoryProvider : NSObject <WebCoreHistoryProvider>
+{
+ WebHistory *history;
+}
+- initWithHistory: (WebHistory *)h;
+@end
+
+@implementation _WebCoreHistoryProvider
+- initWithHistory: (WebHistory *)h
+{
+ history = [h retain];
+ return self;
+}
+
+static inline bool matchLetter(char c, char lowercaseLetter)
+{
+ return (c | 0x20) == lowercaseLetter;
+}
+
+static inline bool matchUnicodeLetter(UniChar c, UniChar lowercaseLetter)
+{
+ return (c | 0x20) == lowercaseLetter;
+}
+
+#define UNICODE_BUFFER_SIZE 1024
+
+- (BOOL)containsURL:(const UniChar *)unicode length:(unsigned)length
+{
+ const UniChar *unicodeStr = unicode;
+ UniChar staticStrBuffer[UNICODE_BUFFER_SIZE];
+ UniChar *strBuffer = NULL;
+ BOOL needToAddSlash = FALSE;
+
+ if (length >= 6 &&
+ matchUnicodeLetter(unicode[0], 'h') &&
+ matchUnicodeLetter(unicode[1], 't') &&
+ matchUnicodeLetter(unicode[2], 't') &&
+ matchUnicodeLetter(unicode[3], 'p') &&
+ (unicode[4] == ':'
+ || (matchUnicodeLetter(unicode[4], 's') && unicode[5] == ':'))) {
+
+ unsigned pos = unicode[4] == ':' ? 5 : 6;
+
+ // skip possible initial two slashes
+ if (pos + 1 < length && unicode[pos] == '/' && unicode[pos + 1] == '/') {
+ pos += 2;
+ }
+
+ while (pos < length && unicode[pos] != '/') {
+ pos++;
+ }
+
+ if (pos == length) {
+ needToAddSlash = TRUE;
+ }
+ }
+
+ if (needToAddSlash) {
+ if (length + 1 <= UNICODE_BUFFER_SIZE) {
+ strBuffer = staticStrBuffer;
+ } else {
+ strBuffer = (UniChar*)malloc(sizeof(UniChar) * (length + 1));
+ }
+ memcpy(strBuffer, unicode, 2 * length);
+ strBuffer[length] = '/';
+ length++;
+
+ unicodeStr = strBuffer;
+ }
+
+ CFStringRef str = CFStringCreateWithCharactersNoCopy(NULL, unicodeStr, length, kCFAllocatorNull);
+ BOOL result = [history containsItemForURLString:(id)str];
+ CFRelease(str);
+
+ if (strBuffer != staticStrBuffer) {
+ free(strBuffer);
+ }
+
+ return result;
+}
+
+- (void)dealloc
+{
+ [history release];
+ [super dealloc];
+}
+
+@end
+
+@implementation WebHistory
+
++ (WebHistory *)optionalSharedHistory
+{
+ return _sharedHistory;
+}
+
+
++ (void)setOptionalSharedHistory: (WebHistory *)history
+{
+ // FIXME. Need to think about multiple instances of WebHistory per application
+ // and correct synchronization of history file between applications.
+ [WebCoreHistory setHistoryProvider: [[[_WebCoreHistoryProvider alloc] initWithHistory: history] autorelease]];
+ if (_sharedHistory != history){
+ [_sharedHistory release];
+ _sharedHistory = [history retain];
+ }
+}
+
+- (id)init
+{
+ if ((self = [super init]) != nil) {
+ _historyPrivate = [[WebHistoryPrivate alloc] init];
+ }
+
+ return self;
+}
+
+- (void)dealloc
+{
+ [_historyPrivate release];
+ [super dealloc];
+}
+
+#pragma mark MODIFYING CONTENTS
+
+- (void)_sendNotification:(NSString *)name entries:(NSArray *)entries
+{
+ NSDictionary *userInfo = [NSDictionary dictionaryWithObjectsAndKeys:entries, WebHistoryItemsKey, nil];
+ [[NSNotificationCenter defaultCenter]
+ postNotificationName: name object: self userInfo: userInfo];
+}
+
+- (WebHistoryItem *)addItemForURL: (NSURL *)URL
+{
+ WebHistoryItem *entry = [[WebHistoryItem alloc] initWithURL:URL title:nil];
+ [entry _setLastVisitedTimeInterval: [NSDate timeIntervalSinceReferenceDate]];
+ [self addItem: entry];
+ [entry release];
+ return entry;
+}
+
+
+- (void)addItem: (WebHistoryItem *)entry
+{
+ LOG (History, "adding %@", entry);
+ [_historyPrivate addItem: entry];
+ [self _sendNotification: WebHistoryItemsAddedNotification
+ entries: [NSArray arrayWithObject:entry]];
+}
+
+- (void)removeItem: (WebHistoryItem *)entry
+{
+ if ([_historyPrivate removeItem: entry]) {
+ [self _sendNotification: WebHistoryItemsRemovedNotification
+ entries: [NSArray arrayWithObject:entry]];
+ }
+}
+
+- (void)removeItems: (NSArray *)entries
+{
+ if ([_historyPrivate removeItems:entries]) {
+ [self _sendNotification: WebHistoryItemsRemovedNotification
+ entries: entries];
+ }
+}
+
+- (void)removeAllItems
+{
+ if ([_historyPrivate removeAllItems]) {
+ [[NSNotificationCenter defaultCenter]
+ postNotificationName: WebHistoryAllItemsRemovedNotification
+ object: self];
+ }
+}
+
+- (void)addItems:(NSArray *)newEntries
+{
+ [_historyPrivate addItems:newEntries];
+ [self _sendNotification: WebHistoryItemsAddedNotification
+ entries: newEntries];
+}
+
+- (void)setLastVisitedTimeInterval:(NSTimeInterval)time forItem:(WebHistoryItem *)entry
+{
+ [_historyPrivate setLastVisitedTimeInterval:time forItem:entry];
+}
+
+#pragma mark DATE-BASED RETRIEVAL
+
+- (NSArray *)orderedLastVisitedDays
+{
+ return [_historyPrivate orderedLastVisitedDays];
+}
+
+- (NSArray *)orderedItemsLastVisitedOnDay: (NSCalendarDate *)date
+{
+ return [_historyPrivate orderedItemsLastVisitedOnDay: date];
+}
+
+#pragma mark URL MATCHING
+
+- (BOOL)containsItemForURLString: (NSString *)URLString
+{
+ return [_historyPrivate containsItemForURLString: URLString];
+}
+
+- (BOOL)containsURL: (NSURL *)URL
+{
+ return [_historyPrivate containsURL: URL];
+}
+
+- (WebHistoryItem *)itemForURL:(NSURL *)URL
+{
+ return [_historyPrivate itemForURL:URL];
+}
+
+#pragma mark SAVING TO DISK
+
+- (BOOL)loadFromURL:(NSURL *)URL error:(NSError **)error
+{
+ NSMutableArray *discardedItems = [NSMutableArray array];
+
+ if ([_historyPrivate loadFromURL:URL collectDiscardedItemsInto:discardedItems error:error]) {
+ [[NSNotificationCenter defaultCenter]
+ postNotificationName:WebHistoryLoadedNotification
+ object:self];
+
+ if ([discardedItems count] > 0)
+ [self _sendNotification:WebHistoryItemsDiscardedWhileLoadingNotification entries:discardedItems];
+
+ return YES;
+ }
+ return NO;
+}
+
+- (BOOL)saveToURL:(NSURL *)URL error:(NSError **)error
+{
+ // FIXME: Use new foundation API to get error when ready.
+ if([_historyPrivate saveToURL:URL error:error]){
+ [[NSNotificationCenter defaultCenter]
+ postNotificationName: WebHistorySavedNotification
+ object: self];
+ return YES;
+ }
+ return NO;
+}
+
+- (WebHistoryItem *)_itemForURLString:(NSString *)URLString
+{
+ return [_historyPrivate itemForURLString: URLString];
+}
+
+- (NSCalendarDate*)ageLimitDate
+{
+ return [_historyPrivate _ageLimitDate];
+}
+
+- (void)setHistoryItemLimit:(int)limit
+{
+ [_historyPrivate setHistoryItemLimit:limit];
+}
+
+- (int)historyItemLimit
+{
+ return [_historyPrivate historyItemLimit];
+}
+
+- (void)setHistoryAgeInDaysLimit:(int)limit
+{
+ [_historyPrivate setHistoryAgeInDaysLimit:limit];
+}
+
+- (int)historyAgeInDaysLimit
+{
+ return [_historyPrivate historyAgeInDaysLimit];
+}
+
+@end
diff --git a/WebKit/mac/History/WebHistoryItem.h b/WebKit/mac/History/WebHistoryItem.h
new file mode 100644
index 0000000..4de4344
--- /dev/null
+++ b/WebKit/mac/History/WebHistoryItem.h
@@ -0,0 +1,126 @@
+/*
+ * Copyright (C) 2003 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@class WebHistoryItemPrivate;
+@class NSURL;
+
+/*
+ @discussion Notification sent when history item is modified.
+ @constant WebHistoryItemChanged Posted from whenever the value of
+ either the item's title, alternate title, url strings, or last visited interval
+ changes. The userInfo will be nil.
+*/
+extern NSString *WebHistoryItemChangedNotification;
+
+/*!
+ @class WebHistoryItem
+ @discussion WebHistoryItems are created by WebKit to represent pages visited.
+ The WebBackForwardList and WebHistory classes both use WebHistoryItems to represent
+ pages visited. With the exception of the displayTitle, the properties of
+ WebHistoryItems are set by WebKit. WebHistoryItems are normally never created directly.
+*/
+@interface WebHistoryItem : NSObject <NSCopying>
+{
+@private
+ WebHistoryItemPrivate *_private;
+}
+
+/*!
+ @method initWithURLString:title:lastVisitedTimeInterval:
+ @param URLString The URL string for the item.
+ @param title The title to use for the item. This is normally the <title> of a page.
+ @param time The time used to indicate when the item was used.
+ @abstract Initialize a new WebHistoryItem
+ @discussion WebHistoryItems are normally created for you by the WebKit.
+ You may use this method to prepopulate a WebBackForwardList, or create
+ 'artificial' items to add to a WebBackForwardList. When first initialized
+ the URLString and originalURLString will be the same.
+*/
+- (id)initWithURLString:(NSString *)URLString title:(NSString *)title lastVisitedTimeInterval:(NSTimeInterval)time;
+
+/*!
+ @method originalURLString
+ @abstract The string representation of the originial URL of this item.
+ This value is normally set by the WebKit.
+ @result The string corresponding to the initial URL of this item.
+*/
+- (NSString *)originalURLString;
+
+/*!
+ @method URLString
+ @abstract The string representation of the URL represented by this item.
+ @discussion The URLString may be different than the originalURLString if the page
+ redirected to a new location. This value is normally set by the WebKit.
+ @result The string corresponding to the final URL of this item.
+*/
+- (NSString *)URLString;
+
+
+/*!
+ @method title
+ @abstract The title of the page represented by this item.
+ @discussion This title cannot be changed by the client. This value
+ is normally set by the WebKit when a page title for the item is received.
+ @result The title of this item.
+*/
+- (NSString *)title;
+
+/*!
+ @method lastVisitedTimeInterval
+ @abstract The last time the page represented by this item was visited. The interval
+ is since the reference date as determined by NSDate. This value is normally set by
+ the WebKit.
+ @result The last time this item was visited.
+*/
+- (NSTimeInterval)lastVisitedTimeInterval;
+
+/*!
+ @method setAlternateTitle:
+ @param alternateTitle The new display title for this item.
+ @abstract A title that may be used by the client to display this item.
+*/
+- (void)setAlternateTitle:(NSString *)alternateTitle;
+
+/*
+ @method title
+ @abstract A title that may be used by the client to display this item.
+ @result The alternate title for this item.
+*/
+- (NSString *)alternateTitle;
+
+/*!
+ @method icon
+ @abstract The favorite icon of the page represented by this item.
+ @discussion This icon returned will be determined by the WebKit.
+ @result The icon associated with this item's URL.
+*/
+- (NSImage *)icon;
+
+@end
diff --git a/WebKit/mac/History/WebHistoryItem.mm b/WebKit/mac/History/WebHistoryItem.mm
new file mode 100644
index 0000000..5505e6c
--- /dev/null
+++ b/WebKit/mac/History/WebHistoryItem.mm
@@ -0,0 +1,520 @@
+/*
+ * Copyright (C) 2005, 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebHistoryItemInternal.h"
+#import "WebHistoryItemPrivate.h"
+
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebFrameView.h"
+#import "WebHTMLViewInternal.h"
+#import "WebIconDatabase.h"
+#import "WebKitLogging.h"
+#import "WebKitNSStringExtras.h"
+#import "WebNSDictionaryExtras.h"
+#import "WebNSObjectExtras.h"
+#import "WebNSURLExtras.h"
+#import "WebNSURLRequestExtras.h"
+#import "WebNSViewExtras.h"
+#import "WebPluginController.h"
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/CachedPage.h>
+#import <WebCore/HistoryItem.h>
+#import <WebCore/Image.h>
+#import <WebCore/KURL.h>
+#import <WebCore/PageCache.h>
+#import <WebCore/PlatformString.h>
+#import <WebCore/ThreadCheck.h>
+#import <WebCore/WebCoreObjCExtras.h>
+
+// Private keys used in the WebHistoryItem's dictionary representation.
+// see 3245793 for explanation of "lastVisitedDate"
+static NSString *WebLastVisitedTimeIntervalKey = @"lastVisitedDate";
+static NSString *WebVisitCountKey = @"visitCount";
+static NSString *WebTitleKey = @"title";
+static NSString *WebChildrenKey = @"children";
+static NSString *WebDisplayTitleKey = @"displayTitle";
+
+// Notification strings.
+NSString *WebHistoryItemChangedNotification = @"WebHistoryItemChangedNotification";
+
+using namespace WebCore;
+
+static inline WebHistoryItemPrivate* kitPrivate(WebCoreHistoryItem* list) { return (WebHistoryItemPrivate*)list; }
+static inline WebCoreHistoryItem* core(WebHistoryItemPrivate* list) { return (WebCoreHistoryItem*)list; }
+
+HashMap<HistoryItem*, WebHistoryItem*>& historyItemWrappers()
+{
+ static HashMap<HistoryItem*, WebHistoryItem*> historyItemWrappers;
+ return historyItemWrappers;
+}
+
+void WKNotifyHistoryItemChanged()
+{
+ [[NSNotificationCenter defaultCenter]
+ postNotificationName:WebHistoryItemChangedNotification object:nil userInfo:nil];
+}
+
+@implementation WebHistoryItem
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
+- (id)init
+{
+ return [self initWithWebCoreHistoryItem:(new HistoryItem)];
+}
+
+- (id)initWithURLString:(NSString *)URLString title:(NSString *)title lastVisitedTimeInterval:(NSTimeInterval)time
+{
+ WebCoreThreadViolationCheck();
+ return [self initWithWebCoreHistoryItem:(new HistoryItem(URLString, title, time))];
+}
+
+- (void)dealloc
+{
+ WebCoreThreadViolationCheck();
+ if (_private) {
+ HistoryItem* coreItem = core(_private);
+ coreItem->deref();
+ historyItemWrappers().remove(coreItem);
+ }
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ WebCoreThreadViolationCheck();
+ // FIXME: ~HistoryItem is what releases the history item's icon from the icon database
+ // It's probably not good to release icons from the database only when the object is garbage-collected.
+ // Need to change design so this happens at a predictable time.
+ if (_private) {
+ HistoryItem* coreItem = core(_private);
+ coreItem->deref();
+ historyItemWrappers().remove(coreItem);
+ }
+ [super finalize];
+}
+
+- (id)copyWithZone:(NSZone *)zone
+{
+ WebCoreThreadViolationCheck();
+ WebHistoryItem *copy = (WebHistoryItem *)NSCopyObject(self, 0, zone);
+ RefPtr<HistoryItem> item = core(_private)->copy();
+ copy->_private = kitPrivate(item.get());
+ historyItemWrappers().set(item.release().releaseRef(), copy);
+
+ return copy;
+}
+
+// FIXME: Need to decide if this class ever returns URLs and decide on the name of this method
+- (NSString *)URLString
+{
+ ASSERT_MAIN_THREAD();
+ return nsStringNilIfEmpty(core(_private)->urlString());
+}
+
+// The first URL we loaded to get to where this history item points. Includes both client
+// and server redirects.
+- (NSString *)originalURLString
+{
+ ASSERT_MAIN_THREAD();
+ return nsStringNilIfEmpty(core(_private)->originalURLString());
+}
+
+- (NSString *)title
+{
+ ASSERT_MAIN_THREAD();
+ return nsStringNilIfEmpty(core(_private)->title());
+}
+
+- (void)setAlternateTitle:(NSString *)alternateTitle
+{
+ core(_private)->setAlternateTitle(alternateTitle);
+}
+
+- (NSString *)alternateTitle;
+{
+ return nsStringNilIfEmpty(core(_private)->alternateTitle());
+}
+
+- (NSImage *)icon
+{
+ return [[WebIconDatabase sharedIconDatabase] iconForURL:[self URLString] withSize:WebIconSmallSize];
+
+ // FIXME: Ideally, this code should simply be the following -
+ // return core(_private)->icon()->getNSImage();
+ // Once radar -
+ // <rdar://problem/4906567> - NSImage returned from WebCore::Image may be incorrect size
+ // is resolved
+}
+
+- (NSTimeInterval)lastVisitedTimeInterval
+{
+ ASSERT_MAIN_THREAD();
+ return core(_private)->lastVisitedTime();
+}
+
+- (unsigned)hash
+{
+ return [(NSString*)core(_private)->urlString() hash];
+}
+
+- (BOOL)isEqual:(id)anObject
+{
+ ASSERT_MAIN_THREAD();
+ if (![anObject isMemberOfClass:[WebHistoryItem class]]) {
+ return NO;
+ }
+
+ return core(_private)->urlString() == core(((WebHistoryItem*)anObject)->_private)->urlString();
+}
+
+- (NSString *)description
+{
+ ASSERT_MAIN_THREAD();
+ HistoryItem* coreItem = core(_private);
+ NSMutableString *result = [NSMutableString stringWithFormat:@"%@ %@", [super description], (NSString*)coreItem->urlString()];
+ if (coreItem->target()) {
+ [result appendFormat:@" in \"%@\"", (NSString*)coreItem->target()];
+ }
+ if (coreItem->isTargetItem()) {
+ [result appendString:@" *target*"];
+ }
+ if (coreItem->formData()) {
+ [result appendString:@" *POST*"];
+ }
+
+ if (coreItem->children().size()) {
+ const HistoryItemVector& children = coreItem->children();
+ int currPos = [result length];
+ unsigned size = children.size();
+ for (unsigned i = 0; i < size; ++i) {
+ WebHistoryItem *child = kit(children[i].get());
+ [result appendString:@"\n"];
+ [result appendString:[child description]];
+ }
+ // shift all the contents over. A bit slow, but hey, this is for debugging.
+ NSRange replRange = {currPos, [result length]-currPos};
+ [result replaceOccurrencesOfString:@"\n" withString:@"\n " options:0 range:replRange];
+ }
+
+ return result;
+}
+
+@end
+
+@interface WebWindowWatcher : NSObject
+@end
+
+
+@implementation WebHistoryItem (WebInternal)
+
+HistoryItem* core(WebHistoryItem *item)
+{
+ if (!item)
+ return 0;
+ return core(item->_private);
+}
+
+WebHistoryItem *kit(HistoryItem* item)
+{
+ if (!item)
+ return nil;
+
+ WebHistoryItem *kitItem = historyItemWrappers().get(item);
+ if (kitItem)
+ return kitItem;
+
+ return [[[WebHistoryItem alloc] initWithWebCoreHistoryItem:item] autorelease];
+}
+
++ (WebHistoryItem *)entryWithURL:(NSURL *)URL
+{
+ return [[[self alloc] initWithURL:URL title:nil] autorelease];
+}
+
+static WebWindowWatcher *_windowWatcher = nil;
+
++ (void)initWindowWatcherIfNecessary
+{
+ if (_windowWatcher)
+ return;
+ _windowWatcher = [[WebWindowWatcher alloc] init];
+ [[NSNotificationCenter defaultCenter] addObserver:_windowWatcher selector:@selector(windowWillClose:)
+ name:NSWindowWillCloseNotification object:nil];
+}
+
+- (id)initWithURL:(NSURL *)URL target:(NSString *)target parent:(NSString *)parent title:(NSString *)title
+{
+ return [self initWithWebCoreHistoryItem:(new HistoryItem(URL, target, parent, title))];
+}
+
+- (id)initWithURLString:(NSString *)URLString title:(NSString *)title displayTitle:(NSString *)displayTitle lastVisitedTimeInterval:(NSTimeInterval)time
+{
+ return [self initWithWebCoreHistoryItem:(new HistoryItem(URLString, title, displayTitle, time))];
+}
+
+- (id)initWithWebCoreHistoryItem:(PassRefPtr<HistoryItem>)item
+{
+ WebCoreThreadViolationCheck();
+ // Need to tell WebCore what function to call for the
+ // "History Item has Changed" notification - no harm in doing this
+ // everytime a WebHistoryItem is created
+ // Note: We also do this in [WebFrameView initWithFrame:] where we do
+ // other "init before WebKit is used" type things
+ WebCore::notifyHistoryItemChanged = WKNotifyHistoryItemChanged;
+
+ self = [super init];
+
+ _private = kitPrivate(item.releaseRef());
+ ASSERT(!historyItemWrappers().get(core(_private)));
+ historyItemWrappers().set(core(_private), self);
+ return self;
+}
+
+- (void)setTitle:(NSString *)title
+{
+ core(_private)->setTitle(title);
+}
+
+- (void)setVisitCount:(int)count
+{
+ core(_private)->setVisitCount(count);
+}
+
+- (void)setViewState:(id)statePList;
+{
+ core(_private)->setViewState(statePList);
+}
+
+- (void)_mergeAutoCompleteHints:(WebHistoryItem *)otherItem
+{
+ ASSERT_ARG(otherItem, otherItem);
+ core(_private)->mergeAutoCompleteHints(core(otherItem->_private));
+}
+
+- (id)initFromDictionaryRepresentation:(NSDictionary *)dict
+{
+ ASSERT_MAIN_THREAD();
+ NSString *URLString = [dict _webkit_stringForKey:@""];
+ NSString *title = [dict _webkit_stringForKey:WebTitleKey];
+
+ // Do an existence check to avoid calling doubleValue on a nil string. Leave
+ // time interval at 0 if there's no value in dict.
+ NSString *timeIntervalString = [dict _webkit_stringForKey:WebLastVisitedTimeIntervalKey];
+ NSTimeInterval lastVisited = timeIntervalString == nil ? 0 : [timeIntervalString doubleValue];
+
+ self = [self initWithURLString:URLString title:title displayTitle:[dict _webkit_stringForKey:WebDisplayTitleKey] lastVisitedTimeInterval:lastVisited];
+
+ // Check if we've read a broken URL from the file that has non-Latin1 chars. If so, try to convert
+ // as if it was from user typing.
+ if (![URLString canBeConvertedToEncoding:NSISOLatin1StringEncoding]) {
+ NSURL *tempURL = [NSURL _web_URLWithUserTypedString:URLString];
+ ASSERT(tempURL);
+ NSString *newURLString = [tempURL _web_originalDataAsString];
+ core(_private)->setURLString(newURLString);
+ core(_private)->setOriginalURLString(newURLString);
+ }
+
+ core(_private)->setVisitCount([dict _webkit_intForKey:WebVisitCountKey]);
+
+ NSArray *childDicts = [dict objectForKey:WebChildrenKey];
+ if (childDicts) {
+ for (int i = [childDicts count]; i >= 0; i--) {
+ WebHistoryItem *child = [[WebHistoryItem alloc] initFromDictionaryRepresentation: [childDicts objectAtIndex:i]];
+ core(_private)->addChildItem(core(child->_private));
+ [child release];
+ }
+ }
+
+ return self;
+}
+
+- (NSPoint)scrollPoint
+{
+ ASSERT_MAIN_THREAD();
+ return core(_private)->scrollPoint();
+}
+
+@end
+
+@implementation WebHistoryItem (WebPrivate)
+
+- (id)initWithURL:(NSURL *)URL title:(NSString *)title
+{
+ return [self initWithURLString:[URL _web_originalDataAsString] title:title lastVisitedTimeInterval:0];
+}
+
+- (NSDictionary *)dictionaryRepresentation
+{
+ ASSERT_MAIN_THREAD();
+ NSMutableDictionary *dict = [NSMutableDictionary dictionaryWithCapacity:6];
+
+ HistoryItem* coreItem = core(_private);
+
+ if (!coreItem->urlString().isEmpty()) {
+ [dict setObject:(NSString*)coreItem->urlString() forKey:@""];
+ }
+ if (!coreItem->title().isEmpty()) {
+ [dict setObject:(NSString*)coreItem->title() forKey:WebTitleKey];
+ }
+ if (!coreItem->alternateTitle().isEmpty()) {
+ [dict setObject:(NSString*)coreItem->alternateTitle() forKey:WebDisplayTitleKey];
+ }
+ if (coreItem->lastVisitedTime() != 0.0) {
+ // store as a string to maintain backward compatibility (see 3245793)
+ [dict setObject:[NSString stringWithFormat:@"%.1lf", coreItem->lastVisitedTime()]
+ forKey:WebLastVisitedTimeIntervalKey];
+ }
+ if (coreItem->visitCount()) {
+ [dict setObject:[NSNumber numberWithInt:coreItem->visitCount()] forKey:WebVisitCountKey];
+ }
+ if (coreItem->children().size()) {
+ const HistoryItemVector& children = coreItem->children();
+ NSMutableArray *childDicts = [NSMutableArray arrayWithCapacity:children.size()];
+
+ for (int i = children.size(); i >= 0; i--)
+ [childDicts addObject:[kit(children[i].get()) dictionaryRepresentation]];
+ [dict setObject: childDicts forKey:WebChildrenKey];
+ }
+
+ return dict;
+}
+
+- (NSString *)target
+{
+ ASSERT_MAIN_THREAD();
+ return nsStringNilIfEmpty(core(_private)->target());
+}
+
+- (BOOL)isTargetItem
+{
+ return core(_private)->isTargetItem();
+}
+
+- (int)visitCount
+{
+ ASSERT_MAIN_THREAD();
+ return core(_private)->visitCount();
+}
+
+- (NSString *)RSSFeedReferrer
+{
+ return nsStringNilIfEmpty(core(_private)->rssFeedReferrer());
+}
+
+- (void)setRSSFeedReferrer:(NSString *)referrer
+{
+ core(_private)->setRSSFeedReferrer(referrer);
+}
+
+- (NSArray *)children
+{
+ ASSERT_MAIN_THREAD();
+ const HistoryItemVector& children = core(_private)->children();
+ if (!children.size())
+ return nil;
+
+ unsigned size = children.size();
+ NSMutableArray *result = [[[NSMutableArray alloc] initWithCapacity:size] autorelease];
+
+ for (unsigned i = 0; i < size; ++i)
+ [result addObject:kit(children[i].get())];
+
+ return result;
+}
+
+- (void)setAlwaysAttemptToUsePageCache:(BOOL)flag
+{
+ // Safari 2.0 uses this for SnapBack, so we stub it out to avoid a crash.
+}
+
+- (NSURL *)URL
+{
+ ASSERT_MAIN_THREAD();
+ KURL url = core(_private)->url();
+ if (url.isEmpty())
+ return nil;
+ return url;
+}
+
+// This should not be called directly for WebHistoryItems that are already included
+// in WebHistory. Use -[WebHistory setLastVisitedTimeInterval:forItem:] instead.
+- (void)_setLastVisitedTimeInterval:(NSTimeInterval)time
+{
+ core(_private)->setLastVisitedTime(time);
+}
+
+// FIXME: <rdar://problem/4880065> - Push Global History into WebCore
+// Once that task is complete, this accessor can go away
+- (NSCalendarDate *)_lastVisitedDate
+{
+ ASSERT_MAIN_THREAD();
+ return [[[NSCalendarDate alloc] initWithTimeIntervalSinceReferenceDate:core(_private)->lastVisitedTime()] autorelease];
+}
+
+- (WebHistoryItem *)targetItem
+{
+ ASSERT_MAIN_THREAD();
+ HistoryItem* coreItem = core(_private);
+ if (coreItem->isTargetItem() || !coreItem->hasChildren())
+ return self;
+ return kit(coreItem->recurseToFindTargetItem());
+}
+
++ (void)_releaseAllPendingPageCaches
+{
+ pageCache()->releaseAutoreleasedPagesNow();
+}
+
+- (id)_transientPropertyForKey:(NSString *)key
+{
+ return core(_private)->getTransientProperty(key);
+}
+
+- (void)_setTransientProperty:(id)property forKey:(NSString *)key
+{
+ core(_private)->setTransientProperty(key, property);
+}
+
+@end
+
+
+// FIXME: <rdar://problem/4886761>
+// This is a bizarre policy - we flush the page caches ANY time ANY window is closed?
+@implementation WebWindowWatcher
+-(void)windowWillClose:(NSNotification *)notification
+{
+ pageCache()->releaseAutoreleasedPagesNow();
+}
+@end
diff --git a/WebKit/mac/History/WebHistoryItemInternal.h b/WebKit/mac/History/WebHistoryItemInternal.h
new file mode 100644
index 0000000..b2658ff
--- /dev/null
+++ b/WebKit/mac/History/WebHistoryItemInternal.h
@@ -0,0 +1,63 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+#import <WebKit/WebBackForwardList.h>
+#import <WebKit/WebHistoryItem.h>
+#import <wtf/PassRefPtr.h>
+
+namespace WebCore {
+ class HistoryItem;
+}
+
+WebCore::HistoryItem* core(WebHistoryItem *item);
+WebHistoryItem *kit(WebCore::HistoryItem* item);
+
+extern void WKNotifyHistoryItemChanged();
+
+@interface WebHistoryItem (WebInternal)
+
++ (WebHistoryItem *)entryWithURL:(NSURL *)URL;
++ (void)initWindowWatcherIfNecessary;
+
+- (id)initWithURL:(NSURL *)URL target:(NSString *)target parent:(NSString *)parent title:(NSString *)title;
+- (id)initWithURLString:(NSString *)URLString title:(NSString *)title displayTitle:(NSString *)displayTitle lastVisitedTimeInterval:(NSTimeInterval)time;
+- (id)initFromDictionaryRepresentation:(NSDictionary *)dict;
+- (id)initWithWebCoreHistoryItem:(PassRefPtr<WebCore::HistoryItem>)item;
+
+- (void)_mergeAutoCompleteHints:(WebHistoryItem *)otherItem;
+- (void)setTitle:(NSString *)title;
+
+@end
+
+@interface WebBackForwardList (WebPrivate)
+- (void)_close;
+@end
+
+
diff --git a/WebKit/mac/History/WebHistoryItemPrivate.h b/WebKit/mac/History/WebHistoryItemPrivate.h
new file mode 100644
index 0000000..bc75d1b
--- /dev/null
+++ b/WebKit/mac/History/WebHistoryItemPrivate.h
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+#import <WebKit/WebBackForwardList.h>
+#import <WebKit/WebHistoryItem.h>
+
+@interface WebHistoryItem (WebPrivate)
++ (void)_releaseAllPendingPageCaches;
+
+- (id)initWithURL:(NSURL *)URL title:(NSString *)title;
+
+- (NSURL *)URL;
+- (int)visitCount;
+
+- (NSString *)RSSFeedReferrer;
+- (void)setRSSFeedReferrer:(NSString *)referrer;
+- (NSCalendarDate *)_lastVisitedDate;
+
+- (WebHistoryItem *)targetItem;
+- (NSString *)target;
+- (BOOL)isTargetItem;
+- (NSArray *)children;
+- (NSDictionary *)dictionaryRepresentation;
+
+// This should not be called directly for WebHistoryItems that are already included
+// in WebHistory. Use -[WebHistory setLastVisitedTimeInterval:forItem:] instead.
+- (void)_setLastVisitedTimeInterval:(NSTimeInterval)time;
+// Transient properties may be of any ObjC type. They are intended to be used to store state per back/forward list entry.
+// The properties will not be persisted; when the history item is removed, the properties will be lost.
+- (id)_transientPropertyForKey:(NSString *)key;
+- (void)_setTransientProperty:(id)property forKey:(NSString *)key;
+
+@end
diff --git a/WebKit/mac/History/WebHistoryPrivate.h b/WebKit/mac/History/WebHistoryPrivate.h
new file mode 100644
index 0000000..724c4e5
--- /dev/null
+++ b/WebKit/mac/History/WebHistoryPrivate.h
@@ -0,0 +1,113 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+#import <WebKit/WebHistory.h>
+
+@class WebHistoryItem;
+@class NSError;
+
+#ifdef __cplusplus
+#include <wtf/HashMap.h>
+#include <wtf/RetainPtr.h>
+
+typedef int64_t WebHistoryDateKey;
+typedef HashMap<WebHistoryDateKey, RetainPtr<NSMutableArray> > DateToEntriesMap;
+#else
+typedef struct DateToEntriesMap DateToEntriesMap;
+#endif
+
+/*
+ @constant WebHistoryItemsDiscardedWhileLoadingNotification Posted from loadFromURL:error:.
+ This notification comes with a userInfo dictionary that contains the array of
+ items discarded due to the date limit or item limit. The key for the array is WebHistoryItemsKey.
+*/
+// FIXME: This notification should become API in WebHistory.h
+extern NSString *WebHistoryItemsDiscardedWhileLoadingNotification;
+
+// FIXME: The WebHistoryPrivate interface should be in WebHistoryInternal.h or inside WebHistory.m
+@interface WebHistoryPrivate : NSObject {
+@private
+ NSMutableDictionary *_entriesByURL;
+ DateToEntriesMap* _entriesByDate;
+ NSMutableArray *_orderedLastVisitedDays;
+ BOOL itemLimitSet;
+ int itemLimit;
+ BOOL ageInDaysLimitSet;
+ int ageInDaysLimit;
+}
+
+- (void)addItem:(WebHistoryItem *)entry;
+- (void)addItems:(NSArray *)newEntries;
+- (BOOL)removeItem:(WebHistoryItem *)entry;
+- (BOOL)removeItems:(NSArray *)entries;
+- (BOOL)removeAllItems;
+- (void)setLastVisitedTimeInterval:(NSTimeInterval)time forItem:(WebHistoryItem *)item;
+
+- (NSArray *)orderedLastVisitedDays;
+- (NSArray *)orderedItemsLastVisitedOnDay:(NSCalendarDate *)calendarDate;
+- (BOOL)containsItemForURLString:(NSString *)URLString;
+- (BOOL)containsURL:(NSURL *)URL;
+- (WebHistoryItem *)itemForURL:(NSURL *)URL;
+- (WebHistoryItem *)itemForURLString:(NSString *)URLString;
+
+- (BOOL)loadFromURL:(NSURL *)URL collectDiscardedItemsInto:(NSMutableArray *)discardedItems error:(NSError **)error;
+- (BOOL)saveToURL:(NSURL *)URL error:(NSError **)error;
+
+- (NSCalendarDate*)_ageLimitDate;
+
+- (void)setHistoryItemLimit:(int)limit;
+- (int)historyItemLimit;
+- (void)setHistoryAgeInDaysLimit:(int)limit;
+- (int)historyAgeInDaysLimit;
+
+@end
+
+@interface WebHistory (WebPrivate)
+
+// FIXME: The following SPI is used by Safari. Should it be made into public API?
+- (WebHistoryItem *)_itemForURLString:(NSString *)URLString;
+
+// FIXME: Safari doesn't use the following SPI, and it's used in WebKit only inside WebHistory.m.
+// Should we move it into a FileInternal category inside WebHistory.m, or do we need it for other
+// clients?
+- (void)removeItem:(WebHistoryItem *)entry;
+- (void)addItem:(WebHistoryItem *)entry;
+- (BOOL)containsItemForURLString:(NSString *)URLString;
+
+// FIXME: Safari doesn't use the following SPI, but other WebKit classes do. Should we move it into
+// a WebHistoryInternal.h, or do we need it for other clients?
+- (WebHistoryItem *)addItemForURL:(NSURL *)URL;
+// Change date on existing item
+- (void)setLastVisitedTimeInterval:(NSTimeInterval)time forItem:(WebHistoryItem *)item;
+
+// FIXME: neither Safari nor WebKit use the following SPI -- do we still need it?
+- (NSCalendarDate*)ageLimitDate;
+
+@end
diff --git a/WebKit/mac/History/WebURLsWithTitles.h b/WebKit/mac/History/WebURLsWithTitles.h
new file mode 100644
index 0000000..905588e
--- /dev/null
+++ b/WebKit/mac/History/WebURLsWithTitles.h
@@ -0,0 +1,55 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+#define WebURLsWithTitlesPboardType @"WebURLsWithTitlesPboardType"
+
+// Convenience class for getting URLs and associated titles on and off an NSPasteboard
+
+@interface WebURLsWithTitles : NSObject
+
+// Writes parallel arrays of URLs and titles to the pasteboard. These items can be retrieved by
+// calling URLsFromPasteboard and titlesFromPasteboard. URLs must consist of NSURL objects.
+// titles must consist of NSStrings, or be nil. If titles is nil, or if titles is a different
+// length than URLs, empty strings will be used for all titles. If URLs is nil, this method
+// returns without doing anything. You must declare an WebURLsWithTitlesPboardType data type
+// for pasteboard before invoking this method, or it will return without doing anything.
++ (void)writeURLs:(NSArray *)URLs andTitles:(NSArray *)titles toPasteboard:(NSPasteboard *)pasteboard;
+
+// Reads an array of NSURLs off the pasteboard. Returns nil if pasteboard does not contain
+// data of type WebURLsWithTitlesPboardType. This array consists of the URLs that correspond to
+// the titles returned from titlesFromPasteboard.
++ (NSArray *)URLsFromPasteboard:(NSPasteboard *)pasteboard;
+
+// Reads an array of NSStrings off the pasteboard. Returns nil if pasteboard does not contain
+// data of type WebURLsWithTitlesPboardType. This array consists of the titles that correspond to
+// the URLs returned from URLsFromPasteboard.
++ (NSArray *)titlesFromPasteboard:(NSPasteboard *)pasteboard;
+
+@end
diff --git a/WebKit/mac/History/WebURLsWithTitles.m b/WebKit/mac/History/WebURLsWithTitles.m
new file mode 100644
index 0000000..df9ef75
--- /dev/null
+++ b/WebKit/mac/History/WebURLsWithTitles.m
@@ -0,0 +1,107 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebURLsWithTitles.h"
+
+#import <WebKit/WebNSURLExtras.h>
+#import <WebKit/WebKitNSStringExtras.h>
+
+@implementation WebURLsWithTitles
+
++ (NSArray *)arrayWithIFURLsWithTitlesPboardType
+{
+ // Make a canned array so we don't construct it on the fly over and over.
+ static NSArray *cannedArray = nil;
+
+ if (cannedArray == nil) {
+ cannedArray = [[NSArray arrayWithObject:WebURLsWithTitlesPboardType] retain];
+ }
+
+ return cannedArray;
+}
+
++(void)writeURLs:(NSArray *)URLs andTitles:(NSArray *)titles toPasteboard:(NSPasteboard *)pasteboard
+{
+ NSMutableArray *URLStrings;
+ NSMutableArray *titlesOrEmptyStrings;
+ unsigned index, count;
+
+ count = [URLs count];
+ if (count == 0) {
+ return;
+ }
+
+ if ([pasteboard availableTypeFromArray:[self arrayWithIFURLsWithTitlesPboardType]] == nil) {
+ return;
+ }
+
+ if (count != [titles count]) {
+ titles = nil;
+ }
+
+ URLStrings = [NSMutableArray arrayWithCapacity:count];
+ titlesOrEmptyStrings = [NSMutableArray arrayWithCapacity:count];
+ for (index = 0; index < count; ++index) {
+ [URLStrings addObject:[[URLs objectAtIndex:index] _web_originalDataAsString]];
+ [titlesOrEmptyStrings addObject:(titles == nil) ? @"" : [[titles objectAtIndex:index] _webkit_stringByTrimmingWhitespace]];
+ }
+
+ [pasteboard setPropertyList:[NSArray arrayWithObjects:URLStrings, titlesOrEmptyStrings, nil]
+ forType:WebURLsWithTitlesPboardType];
+}
+
++(NSArray *)titlesFromPasteboard:(NSPasteboard *)pasteboard
+{
+ if ([pasteboard availableTypeFromArray:[self arrayWithIFURLsWithTitlesPboardType]] == nil) {
+ return nil;
+ }
+
+ return [[pasteboard propertyListForType:WebURLsWithTitlesPboardType] objectAtIndex:1];
+}
+
++(NSArray *)URLsFromPasteboard:(NSPasteboard *)pasteboard
+{
+ NSArray *URLStrings;
+ NSMutableArray *URLs;
+ unsigned index, count;
+
+ if ([pasteboard availableTypeFromArray:[self arrayWithIFURLsWithTitlesPboardType]] == nil) {
+ return nil;
+ }
+
+ URLStrings = [[pasteboard propertyListForType:WebURLsWithTitlesPboardType] objectAtIndex:0];
+ count = [URLStrings count];
+ URLs = [NSMutableArray arrayWithCapacity:count];
+ for (index = 0; index < count; ++index) {
+ [URLs addObject:[NSURL _web_URLWithDataAsString:[URLStrings objectAtIndex:index]]];
+ }
+
+ return URLs;
+}
+
+@end
diff --git a/WebKit/mac/Info.plist b/WebKit/mac/Info.plist
new file mode 100644
index 0000000..635fbe5
--- /dev/null
+++ b/WebKit/mac/Info.plist
@@ -0,0 +1,24 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+ <key>CFBundleDevelopmentRegion</key>
+ <string>English</string>
+ <key>CFBundleExecutable</key>
+ <string>${PRODUCT_NAME}</string>
+ <key>CFBundleGetInfoString</key>
+ <string>${BUNDLE_VERSION}, Copyright 2003-2007 Apple Inc.</string>
+ <key>CFBundleIdentifier</key>
+ <string>com.apple.${PRODUCT_NAME}</string>
+ <key>CFBundleInfoDictionaryVersion</key>
+ <string>6.0</string>
+ <key>CFBundleName</key>
+ <string>${PRODUCT_NAME}</string>
+ <key>CFBundlePackageType</key>
+ <string>FMWK</string>
+ <key>CFBundleShortVersionString</key>
+ <string>${BUNDLE_VERSION}</string>
+ <key>CFBundleVersion</key>
+ <string>${BUNDLE_VERSION}</string>
+</dict>
+</plist>
diff --git a/WebKit/mac/MigrateHeaders.make b/WebKit/mac/MigrateHeaders.make
new file mode 100644
index 0000000..624197f
--- /dev/null
+++ b/WebKit/mac/MigrateHeaders.make
@@ -0,0 +1,503 @@
+# Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved.
+# Copyright (C) 2006 Samuel Weinig <sam.weinig@gmail.com>
+#
+# Redistribution and use in source and binary forms, with or without
+# modification, are permitted provided that the following conditions
+# are met:
+#
+# 1. Redistributions of source code must retain the above copyright
+# notice, this list of conditions and the following disclaimer.
+# 2. Redistributions in binary form must reproduce the above copyright
+# notice, this list of conditions and the following disclaimer in the
+# documentation and/or other materials provided with the distribution.
+# 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+# its contributors may be used to endorse or promote products derived
+# from this software without specific prior written permission.
+#
+# THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+# EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+# WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+# DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+# DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+# (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+# LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+# ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+# (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+# THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+VPATH = $(WEBCORE_PRIVATE_HEADERS_DIR) $(JAVASCRIPTCORE_PRIVATE_HEADERS_DIR)
+
+INTERNAL_HEADERS_DIR = $(BUILT_PRODUCTS_DIR)/DerivedSources/WebKit
+PUBLIC_HEADERS_DIR = $(TARGET_BUILD_DIR)/$(PUBLIC_HEADERS_FOLDER_PATH)
+PRIVATE_HEADERS_DIR = $(TARGET_BUILD_DIR)/$(PRIVATE_HEADERS_FOLDER_PATH)
+
+.PHONY : all
+all : \
+ $(PUBLIC_HEADERS_DIR)/DOM.h \
+ $(PUBLIC_HEADERS_DIR)/DOMAbstractView.h \
+ $(PUBLIC_HEADERS_DIR)/DOMAttr.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCDATASection.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSS.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSCharsetRule.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSFontFaceRule.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSImportRule.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSMediaRule.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSPageRule.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSPrimitiveValue.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSRule.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSRuleList.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSStyleDeclaration.h \
+ $(INTERNAL_HEADERS_DIR)/DOMCSSStyleDeclarationInternal.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSStyleRule.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSStyleSheet.h \
+ $(PRIVATE_HEADERS_DIR)/DOMCSSStyleSheetPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSUnknownRule.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSValue.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCSSValueList.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCharacterData.h \
+ $(PUBLIC_HEADERS_DIR)/DOMComment.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCore.h \
+ $(PUBLIC_HEADERS_DIR)/DOMCounter.h \
+ $(PUBLIC_HEADERS_DIR)/DOMImplementation.h \
+ $(PUBLIC_HEADERS_DIR)/DOMDocument.h \
+ $(INTERNAL_HEADERS_DIR)/DOMDocumentInternal.h \
+ $(PUBLIC_HEADERS_DIR)/DOMDocumentFragment.h \
+ $(PRIVATE_HEADERS_DIR)/DOMDocumentPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMDocumentType.h \
+ $(PUBLIC_HEADERS_DIR)/DOMElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMEntity.h \
+ $(PUBLIC_HEADERS_DIR)/DOMEntityReference.h \
+ $(PUBLIC_HEADERS_DIR)/DOMEvent.h \
+ $(PUBLIC_HEADERS_DIR)/DOMEventException.h \
+ $(PUBLIC_HEADERS_DIR)/DOMEventListener.h \
+ $(PRIVATE_HEADERS_DIR)/DOMEventPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMEventTarget.h \
+ $(PUBLIC_HEADERS_DIR)/DOMEvents.h \
+ $(PUBLIC_HEADERS_DIR)/DOMException.h \
+ $(PUBLIC_HEADERS_DIR)/DOMExtensions.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTML.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLAnchorElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLAnchorElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLAppletElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLAreaElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLAreaElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLBRElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLBaseElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLBaseFontElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLBodyElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLBodyElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLButtonElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLButtonElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLCollection.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLCollectionPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLDListElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLDirectoryElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLDivElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLDocument.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLDocumentPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMHTMLElementInternal.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLEmbedElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLEmbedElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLFieldSetElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLFontElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLFormElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLFormElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLFrameElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLFrameElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLFrameSetElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLHRElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLHeadElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLHeadingElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLHtmlElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLIFrameElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLIFrameElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLImageElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLImageElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLInputElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLInputElementPrivate.h \
+ $(INTERNAL_HEADERS_DIR)/DOMHTMLInputElementInternal.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLIsIndexElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLLIElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLLabelElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLLabelElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLLegendElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLLegendElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLLinkElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLLinkElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLMapElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLMarqueeElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLMenuElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLMetaElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLModElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLOListElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLObjectElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLObjectElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLOptGroupElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLOptionElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLOptionsCollection.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLOptionsCollectionPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLParagraphElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLParamElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLPreElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLPreElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLQuoteElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLScriptElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLSelectElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLSelectElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLStyleElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLStyleElementPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLTableCaptionElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLTableCellElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLTableColElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLTableElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLTableRowElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLTableSectionElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLTextAreaElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMHTMLTextAreaElementPrivate.h \
+ $(INTERNAL_HEADERS_DIR)/DOMHTMLTextAreaElementInternal.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLTitleElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMHTMLUListElement.h \
+ $(PUBLIC_HEADERS_DIR)/DOMKeyboardEvent.h \
+ $(PRIVATE_HEADERS_DIR)/DOMKeyboardEventPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMMediaList.h \
+ $(PUBLIC_HEADERS_DIR)/DOMMouseEvent.h \
+ $(PRIVATE_HEADERS_DIR)/DOMMouseEventPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMMutationEvent.h \
+ $(PUBLIC_HEADERS_DIR)/DOMNamedNodeMap.h \
+ $(PUBLIC_HEADERS_DIR)/DOMNode.h \
+ $(INTERNAL_HEADERS_DIR)/DOMNodeInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMNodePrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMNodeFilter.h \
+ $(PUBLIC_HEADERS_DIR)/DOMNodeIterator.h \
+ $(PRIVATE_HEADERS_DIR)/DOMNodeIteratorPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMNodeList.h \
+ $(PUBLIC_HEADERS_DIR)/DOMNotation.h \
+ $(PUBLIC_HEADERS_DIR)/DOMObject.h \
+ $(PUBLIC_HEADERS_DIR)/DOMOverflowEvent.h \
+ $(PRIVATE_HEADERS_DIR)/DOMPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMProcessingInstruction.h \
+ $(PRIVATE_HEADERS_DIR)/DOMProcessingInstructionPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMProgressEvent.h \
+ $(PUBLIC_HEADERS_DIR)/DOMRGBColor.h \
+ $(PUBLIC_HEADERS_DIR)/DOMRange.h \
+ $(INTERNAL_HEADERS_DIR)/DOMRangeInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMRangePrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMRangeException.h \
+ $(PUBLIC_HEADERS_DIR)/DOMRanges.h \
+ $(PUBLIC_HEADERS_DIR)/DOMRect.h \
+ $(PUBLIC_HEADERS_DIR)/DOMStyleSheet.h \
+ $(PUBLIC_HEADERS_DIR)/DOMStyleSheetList.h \
+ $(PUBLIC_HEADERS_DIR)/DOMStylesheets.h \
+ $(PUBLIC_HEADERS_DIR)/DOMText.h \
+ $(PRIVATE_HEADERS_DIR)/DOMTextPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMTraversal.h \
+ $(PUBLIC_HEADERS_DIR)/DOMTreeWalker.h \
+ $(PUBLIC_HEADERS_DIR)/DOMUIEvent.h \
+ $(PRIVATE_HEADERS_DIR)/DOMUIEventPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMViews.h \
+ $(PUBLIC_HEADERS_DIR)/DOMWheelEvent.h \
+ $(PRIVATE_HEADERS_DIR)/DOMWheelEventPrivate.h \
+ $(PUBLIC_HEADERS_DIR)/DOMXPath.h \
+ $(PUBLIC_HEADERS_DIR)/DOMXPathException.h \
+ $(PUBLIC_HEADERS_DIR)/DOMXPathExpression.h \
+ $(PUBLIC_HEADERS_DIR)/DOMXPathNSResolver.h \
+ $(PUBLIC_HEADERS_DIR)/DOMXPathResult.h \
+ $(PRIVATE_HEADERS_DIR)/WebDashboardRegion.h \
+ $(PUBLIC_HEADERS_DIR)/WebScriptObject.h \
+ $(PUBLIC_HEADERS_DIR)/npapi.h \
+ $(PUBLIC_HEADERS_DIR)/npruntime.h \
+#
+
+ifeq ($(findstring ENABLE_SVG,$(FEATURE_DEFINES)), ENABLE_SVG)
+
+all : \
+ $(PRIVATE_HEADERS_DIR)/DOMSVG.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAngle.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAngleInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimateColorElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimateColorElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimateElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimateElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimateTransformElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimateTransformElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedAngle.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedAngleInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedBoolean.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedBooleanInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedEnumeration.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedEnumerationInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedInteger.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedIntegerInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedLength.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedLengthInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedLengthList.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedLengthListInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedNumber.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedNumberInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedNumberList.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedNumberListInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedPathData.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedPoints.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedPreserveAspectRatio.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedPreserveAspectRatioInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedRect.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedRectInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedString.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedStringInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimatedTransformList.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimatedTransformListInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGAnimationElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGAnimationElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGCircleElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGCircleElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGClipPathElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGClipPathElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGColor.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGColorInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGComponentTransferFunctionElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGComponentTransferFunctionElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGCursorElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGCursorElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGDefsElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGDefsElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGDefinitionSrcElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGDescElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGDescElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGDocument.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGDocumentInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGElementInstance.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGElementInstanceInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGElementInstanceList.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGElementInstanceListInternal.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGEllipseElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGEllipseElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGException.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGExternalResourcesRequired.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEBlendElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEBlendElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEColorMatrixElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEColorMatrixElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEComponentTransferElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEComponentTransferElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFECompositeElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFECompositeElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEDiffuseLightingElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEDiffuseLightingElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEDisplacementMapElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEDisplacementMapElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEDistantLightElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEDistantLightElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEFloodElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEFloodElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEFuncAElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEFuncAElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEFuncBElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEFuncBElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEFuncGElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEFuncGElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEFuncRElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEFuncRElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEGaussianBlurElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEGaussianBlurElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEImageElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEImageElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEMergeElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEMergeElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEMergeNodeElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEMergeNodeElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEOffsetElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEOffsetElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFEPointLightElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFEPointLightElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFESpecularLightingElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFESpecularLightingElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFESpotLightElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFESpotLightElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFETileElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFETileElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFETurbulenceElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFETurbulenceElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFilterElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGFilterElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFilterPrimitiveStandardAttributes.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFitToViewBox.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFontElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFontFaceElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFontFaceFormatElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFontFaceNameElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFontFaceSrcElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGFontFaceUriElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGForeignObjectElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGForeignObjectElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGGElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGGElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGGlyphElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGGradientElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGGradientElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGImageElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGImageElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGLangSpace.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGLength.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGLengthInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGLengthList.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGLengthListInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGLineElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGLineElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGLinearGradientElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGLinearGradientElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGLocatable.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGMarkerElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGMarkerElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGMaskElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGMaskElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGMatrix.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGMatrixInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGMetadataElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGMetadataElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGMissingGlyphElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGNumber.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGNumberList.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGNumberListInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPaint.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPaintInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSeg.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegArcAbs.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegArcAbsInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegArcRel.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegArcRelInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegClosePath.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegClosePathInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegCurvetoCubicAbs.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegCurvetoCubicAbsInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegCurvetoCubicRel.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegCurvetoCubicRelInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegCurvetoCubicSmoothAbs.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegCurvetoCubicSmoothAbsInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegCurvetoCubicSmoothRel.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegCurvetoCubicSmoothRelInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegCurvetoQuadraticAbs.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegCurvetoQuadraticAbsInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegCurvetoQuadraticRel.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegCurvetoQuadraticRelInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegCurvetoQuadraticSmoothAbs.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegCurvetoQuadraticSmoothAbsInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegCurvetoQuadraticSmoothRel.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegCurvetoQuadraticSmoothRelInternal.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegLinetoAbs.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegLinetoAbsInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegLinetoHorizontalAbs.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegLinetoHorizontalAbsInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegLinetoHorizontalRel.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegLinetoHorizontalRelInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegLinetoRel.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegLinetoRelInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegLinetoVerticalAbs.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegLinetoVerticalAbsInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegLinetoVerticalRel.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegLinetoVerticalRelInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegList.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegListInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegMovetoAbs.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegMovetoAbsInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPathSegMovetoRel.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPathSegMovetoRelInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPatternElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPatternElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPoint.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPointList.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPointListInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPolygonElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPolygonElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPolylineElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPolylineElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGPreserveAspectRatio.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGPreserveAspectRatioInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGRadialGradientElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGRadialGradientElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGRect.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGRectElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGRectElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGRenderingIntent.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGRenderingIntentInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGSVGElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGSVGElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGScriptElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGScriptElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGSetElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGSetElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGStopElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGStopElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGStringList.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGStringListInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGStylable.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGStyleElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGStyleElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGSwitchElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGSwitchElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGSymbolElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGSymbolElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGTRefElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGTRefElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGTSpanElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGTSpanElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGTests.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGTextContentElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGTextContentElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGTextElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGTextElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGTextPathElement.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGTextPositioningElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGTextPositioningElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGTitleElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGTitleElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGTransform.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGTransformInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGTransformList.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGTransformListInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGTransformable.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGURIReference.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGUnitTypes.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGUnitTypesInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGUseElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGUseElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGViewElement.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGViewElementInternal.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGZoomAndPan.h \
+ $(PRIVATE_HEADERS_DIR)/DOMSVGZoomEvent.h \
+ $(INTERNAL_HEADERS_DIR)/DOMSVGZoomEventInternal.h \
+
+endif
+
+REPLACE_RULES = -e s/\<WebCore/\<WebKit/ -e s/\<JavaScriptCore/\<WebKit/ -e s/DOMDOMImplementation/DOMImplementation/ -e 's/\<WebKit\/JSBase.h/\<JavaScriptCore\/JSBase.h/'
+HEADER_MIGRATE_CMD = sed $(REPLACE_RULES) $< $(PROCESS_HEADER_FOR_MACOSX_TARGET_CMD) > $@
+
+ifeq ($(MACOSX_DEPLOYMENT_TARGET),10.4)
+PROCESS_HEADER_FOR_MACOSX_TARGET_CMD = | ( unifdef -DBUILDING_ON_TIGER || exit 0 )
+else
+PROCESS_HEADER_FOR_MACOSX_TARGET_CMD = | ( unifdef -UBUILDING_ON_TIGER || exit 0 )
+endif
+
+$(PUBLIC_HEADERS_DIR)/DOM% : DOMDOM% MigrateHeaders.make
+ $(HEADER_MIGRATE_CMD)
+
+$(PRIVATE_HEADERS_DIR)/DOM% : DOMDOM% MigrateHeaders.make
+ $(HEADER_MIGRATE_CMD)
+
+$(PUBLIC_HEADERS_DIR)/% : % MigrateHeaders.make
+ $(HEADER_MIGRATE_CMD)
+
+$(PRIVATE_HEADERS_DIR)/% : % MigrateHeaders.make
+ $(HEADER_MIGRATE_CMD)
+
+$(INTERNAL_HEADERS_DIR)/% : % MigrateHeaders.make
+ $(HEADER_MIGRATE_CMD)
diff --git a/WebKit/mac/Misc/OldWebAssertions.c b/WebKit/mac/Misc/OldWebAssertions.c
new file mode 100644
index 0000000..b84cdbc
--- /dev/null
+++ b/WebKit/mac/Misc/OldWebAssertions.c
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/* These functions are not used anymore, but need to stay for binary compatibility <rdar://problem/4841432>. */
+/* You should use <wtf/Assertions.h>. */
+
+void WebReportAssertionFailure(const char *file, int line, const char *function, const char *assertion);
+void WebReportError(const char *file, int line, const char *function, const char *format, ...);
+
+void WebReportAssertionFailure(const char *file, int line, const char *function, const char *assertion)
+{
+}
+
+void WebReportError(const char *file, int line, const char *function, const char *format, ...)
+{
+}
diff --git a/WebKit/mac/Misc/WebAssertions.h b/WebKit/mac/Misc/WebAssertions.h
new file mode 100644
index 0000000..4824090
--- /dev/null
+++ b/WebKit/mac/Misc/WebAssertions.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/* This header is needed only for backwards-compatibility with internal clients
+ * which have yet to move away from it: <rdar://problem/5141290>.
+ */
+
+#warning <WebKit/WebAssertions.h> is deprecated. Please move away from this SPI as soon as is possible.
+
+#define ASSERT(...) ((void)0)
+#define ASSERT_NOT_REACHED(...) ((void)0)
+#define ASSERT_ARG(...) ((void)0)
+#define ERROR(...) ((void)0)
diff --git a/WebKit/mac/Misc/WebCache.h b/WebKit/mac/Misc/WebCache.h
new file mode 100644
index 0000000..1b5662b
--- /dev/null
+++ b/WebKit/mac/Misc/WebCache.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+@interface WebCache : NSObject
+{
+}
+
++ (NSArray *)statistics;
++ (void)empty;
++ (void)setDisabled:(BOOL)disabled;
++ (BOOL)isDisabled;
+
+@end
diff --git a/WebKit/mac/Misc/WebCache.mm b/WebKit/mac/Misc/WebCache.mm
new file mode 100644
index 0000000..1c1850b
--- /dev/null
+++ b/WebKit/mac/Misc/WebCache.mm
@@ -0,0 +1,85 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebCache.h"
+
+#import "WebPreferences.h"
+#import "WebView.h"
+#import "WebViewInternal.h"
+#import <WebCore/Cache.h>
+
+@implementation WebCache
+
++ (NSArray *)statistics
+{
+ WebCore::Cache::Statistics s = WebCore::cache()->getStatistics();
+
+ return [NSArray arrayWithObjects:
+ [NSDictionary dictionaryWithObjectsAndKeys:
+ [NSNumber numberWithInt:s.images.count], @"Images",
+ [NSNumber numberWithInt:s.cssStyleSheets.count], @"CSS",
+ [NSNumber numberWithInt:s.xslStyleSheets.count], @"XSL",
+ [NSNumber numberWithInt:s.scripts.count], @"JavaScript",
+ nil],
+ [NSDictionary dictionaryWithObjectsAndKeys:
+ [NSNumber numberWithInt:s.images.size], @"Images",
+ [NSNumber numberWithInt:s.cssStyleSheets.size] ,@"CSS",
+ [NSNumber numberWithInt:s.xslStyleSheets.size], @"XSL",
+ [NSNumber numberWithInt:s.scripts.size], @"JavaScript",
+ nil],
+ [NSDictionary dictionaryWithObjectsAndKeys:
+ [NSNumber numberWithInt:s.images.liveSize], @"Images",
+ [NSNumber numberWithInt:s.cssStyleSheets.liveSize] ,@"CSS",
+ [NSNumber numberWithInt:s.xslStyleSheets.liveSize], @"XSL",
+ [NSNumber numberWithInt:s.scripts.liveSize], @"JavaScript",
+ nil],
+ [NSDictionary dictionaryWithObjectsAndKeys:
+ [NSNumber numberWithInt:s.images.decodedSize], @"Images",
+ [NSNumber numberWithInt:s.cssStyleSheets.decodedSize] ,@"CSS",
+ [NSNumber numberWithInt:s.xslStyleSheets.decodedSize], @"XSL",
+ [NSNumber numberWithInt:s.scripts.decodedSize], @"JavaScript",
+ nil],
+ nil];
+}
+
++ (void)empty
+{
+ // Toggling the cache model like this forces the cache to evict all its in-memory resources.
+ WebCacheModel cacheModel = [WebView _cacheModel];
+ [WebView _setCacheModel:WebCacheModelDocumentViewer];
+ [WebView _setCacheModel:cacheModel];
+}
+
++ (void)setDisabled:(BOOL)disabled
+{
+ WebCore::cache()->setDisabled(disabled);
+}
+
++ (BOOL)isDisabled
+{
+ return WebCore::cache()->disabled();
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebCoreStatistics.h b/WebKit/mac/Misc/WebCoreStatistics.h
new file mode 100644
index 0000000..7585ec0
--- /dev/null
+++ b/WebKit/mac/Misc/WebCoreStatistics.h
@@ -0,0 +1,72 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+#import <WebKit/WebFrame.h>
+
+@interface WebCoreStatistics : NSObject
+{
+}
+
++ (NSArray *)statistics;
+
++ (size_t)javaScriptObjectsCount;
++ (size_t)javaScriptGlobalObjectsCount;
++ (size_t)javaScriptProtectedObjectsCount;
++ (size_t)javaScriptProtectedGlobalObjectsCount;
++ (NSCountedSet *)javaScriptProtectedObjectTypeCounts;
+
++ (void)garbageCollectJavaScriptObjects;
++ (void)garbageCollectJavaScriptObjectsOnAlternateThreadForDebugging:(BOOL)waitUntilDone;
+
++ (size_t)iconPageURLMappingCount;
++ (size_t)iconRetainedPageURLCount;
++ (size_t)iconRecordCount;
++ (size_t)iconsWithDataCount;
+
++ (BOOL)shouldPrintExceptions;
++ (void)setShouldPrintExceptions:(BOOL)print;
+
++ (void)startIgnoringWebCoreNodeLeaks;
++ (void)stopIgnoringWebCoreNodeLeaks;
+
+// Deprecated, but used by older versions of Safari.
++ (void)emptyCache;
++ (void)setCacheDisabled:(BOOL)disabled;
++ (size_t)javaScriptNoGCAllowedObjectsCount;
++ (size_t)javaScriptReferencedObjectsCount;
++ (NSSet *)javaScriptRootObjectClasses;
++ (NSCountedSet *)javaScriptRootObjectTypeCounts;
++ (size_t)javaScriptInterpretersCount;
+
+@end
+
+@interface WebFrame (WebKitDebug)
+- (NSString *)renderTreeAsExternalRepresentation;
+@end
diff --git a/WebKit/mac/Misc/WebCoreStatistics.mm b/WebKit/mac/Misc/WebCoreStatistics.mm
new file mode 100644
index 0000000..1dc553f
--- /dev/null
+++ b/WebKit/mac/Misc/WebCoreStatistics.mm
@@ -0,0 +1,187 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebCoreStatistics.h"
+
+#import "WebCache.h"
+#import <JavaScriptCore/collector.h>
+#import <JavaScriptCore/interpreter.h>
+#import <WebCore/GCController.h>
+#import <WebCore/IconDatabase.h>
+#import <WebCore/Node.h>
+#import <WebKit/WebFrameBridge.h>
+#import <WebKit/WebFrameInternal.h>
+
+using namespace KJS;
+using namespace WebCore;
+
+@implementation WebCoreStatistics
+
++ (NSArray *)statistics
+{
+ return [WebCache statistics];
+}
+
++ (size_t)javaScriptObjectsCount
+{
+ JSLock lock;
+ return Collector::size();
+}
+
++ (size_t)javaScriptGlobalObjectsCount
+{
+ JSLock lock;
+ return Collector::globalObjectCount();
+}
+
++ (size_t)javaScriptProtectedObjectsCount
+{
+ JSLock lock;
+ return Collector::protectedObjectCount();
+}
+
++ (size_t)javaScriptProtectedGlobalObjectsCount
+{
+ JSLock lock;
+ return Collector::protectedGlobalObjectCount();
+}
+
++ (NSCountedSet *)javaScriptProtectedObjectTypeCounts
+{
+ JSLock lock;
+
+ NSCountedSet *result = [NSCountedSet set];
+
+ OwnPtr<HashCountedSet<const char*> > counts(Collector::protectedObjectTypeCounts());
+ HashCountedSet<const char*>::iterator end = counts->end();
+ for (HashCountedSet<const char*>::iterator it = counts->begin(); it != end; ++it)
+ for (unsigned i = 0; i < it->second; ++i)
+ [result addObject:[NSString stringWithUTF8String:it->first]];
+
+ return result;
+}
+
++ (void)garbageCollectJavaScriptObjects
+{
+ gcController().garbageCollectNow();
+}
+
++ (void)garbageCollectJavaScriptObjectsOnAlternateThreadForDebugging:(BOOL)waitUntilDone;
+{
+ gcController().garbageCollectOnAlternateThreadForDebugging(waitUntilDone);
+}
+
++ (size_t)iconPageURLMappingCount
+{
+ return iconDatabase()->pageURLMappingCount();
+}
+
++ (size_t)iconRetainedPageURLCount
+{
+ return iconDatabase()->retainedPageURLCount();
+}
+
++ (size_t)iconRecordCount
+{
+ return iconDatabase()->iconRecordCount();
+}
+
++ (size_t)iconsWithDataCount
+{
+ return iconDatabase()->iconRecordCountWithData();
+}
+
++ (BOOL)shouldPrintExceptions
+{
+ JSLock lock;
+ return Interpreter::shouldPrintExceptions();
+}
+
++ (void)setShouldPrintExceptions:(BOOL)print
+{
+ JSLock lock;
+ Interpreter::setShouldPrintExceptions(print);
+}
+
++ (void)emptyCache
+{
+ [WebCache empty];
+}
+
++ (void)setCacheDisabled:(BOOL)disabled
+{
+ [WebCache setDisabled:disabled];
+}
+
++ (void)startIgnoringWebCoreNodeLeaks
+{
+ WebCore::Node::startIgnoringLeaks();
+}
+
++ (void)stopIgnoringWebCoreNodeLeaks;
+{
+ WebCore::Node::stopIgnoringLeaks();
+}
+
+// Deprecated
++ (size_t)javaScriptNoGCAllowedObjectsCount
+{
+ return 0;
+}
+
++ (size_t)javaScriptReferencedObjectsCount
+{
+ JSLock lock;
+ return Collector::protectedObjectCount();
+}
+
++ (NSSet *)javaScriptRootObjectClasses
+{
+ return [self javaScriptRootObjectTypeCounts];
+}
+
++ (size_t)javaScriptInterpretersCount
+{
+ return [self javaScriptProtectedGlobalObjectsCount];
+}
+
++ (NSCountedSet *)javaScriptRootObjectTypeCounts
+{
+ return [self javaScriptProtectedObjectTypeCounts];
+}
+
+@end
+
+@implementation WebFrame (WebKitDebug)
+
+- (NSString *)renderTreeAsExternalRepresentation
+{
+ return [[self _bridge] renderTreeAsExternalRepresentation];
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebDownload.h b/WebKit/mac/Misc/WebDownload.h
new file mode 100644
index 0000000..68dfda9
--- /dev/null
+++ b/WebKit/mac/Misc/WebDownload.h
@@ -0,0 +1,67 @@
+/*
+ * Copyright (C) 2003 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/NSURLDownload.h>
+
+@class WebDownloadInternal;
+
+/*!
+ @class WebDownload
+ @discussion A WebDownload works just like an NSURLDownload, with
+ one extra feature: if you do not implement the
+ authentication-related delegate methods, it will automatically
+ prompt for authentication using the standard WebKit authentication
+ panel, as either a sheet or window. It provides no extra methods,
+ but does have one additional delegate method.
+*/
+
+
+@interface WebDownload : NSURLDownload
+{
+@private
+ WebDownloadInternal *_webInternal;
+}
+
+@end
+
+/*!
+ @protocol WebDownloadDelegate
+ @discussion The WebDownloadDelegate delegate has one extra method used to choose
+ the right window when automatically prompting with a sheet.
+*/
+@interface NSObject (WebDownloadDelegate)
+
+/*!
+ @method downloadWindowForAuthenticationSheet:
+ @abstract
+ @param
+ @result
+*/
+- (NSWindow *)downloadWindowForAuthenticationSheet:(WebDownload *)download;
+
+@end
diff --git a/WebKit/mac/Misc/WebDownload.m b/WebKit/mac/Misc/WebDownload.m
new file mode 100644
index 0000000..50a5777
--- /dev/null
+++ b/WebKit/mac/Misc/WebDownload.m
@@ -0,0 +1,240 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebDownload.h>
+
+#import <Foundation/NSURLAuthenticationChallenge.h>
+#import <Foundation/NSURLDownload.h>
+#import <JavaScriptCore/Assertions.h>
+#import <WebKit/WebPanelAuthenticationHandler.h>
+
+#import "WebTypesInternal.h"
+
+@class NSURLConnectionDelegateProxy;
+
+// FIXME: The following are NSURLDownload SPI - it would be nice to not have to override them at
+// some point in the future
+@interface NSURLDownload (WebDownloadCapability)
+- (id)_initWithLoadingConnection:(NSURLConnection *)connection
+ request:(NSURLRequest *)request
+ response:(NSURLResponse *)response
+ delegate:(id)delegate
+ proxy:(NSURLConnectionDelegateProxy *)proxy;
+- (id)_initWithRequest:(NSURLRequest *)request
+ delegate:(id)delegate
+ directory:(NSString *)directory;
+@end
+
+@interface WebDownloadInternal : NSObject
+{
+@public
+ id realDelegate;
+}
+
+- (void)setRealDelegate:(id)rd;
+
+@end
+
+@implementation WebDownloadInternal
+
+- (void)dealloc
+{
+ [realDelegate release];
+ [super dealloc];
+}
+
+- (void)setRealDelegate:(id)rd
+{
+ [rd retain];
+ [realDelegate release];
+ realDelegate = rd;
+}
+
+- (BOOL)respondsToSelector:(SEL)selector
+{
+ if (selector == @selector(downloadDidBegin:) ||
+ selector == @selector(download:willSendRequest:redirectResponse:) ||
+ selector == @selector(download:didReceiveResponse:) ||
+ selector == @selector(download:didReceiveDataOfLength:) ||
+ selector == @selector(download:shouldDecodeSourceDataOfMIMEType:) ||
+ selector == @selector(download:decideDestinationWithSuggestedFilename:) ||
+ selector == @selector(download:didCreateDestination:) ||
+ selector == @selector(downloadDidFinish:) ||
+ selector == @selector(download:didFailWithError:) ||
+ selector == @selector(download:shouldBeginChildDownloadOfSource:delegate:) ||
+ selector == @selector(download:didBeginChildDownload:)) {
+ return [realDelegate respondsToSelector:selector];
+ }
+
+ return [super respondsToSelector:selector];
+}
+
+- (void)downloadDidBegin:(NSURLDownload *)download
+{
+ [realDelegate downloadDidBegin:download];
+}
+
+- (NSURLRequest *)download:(NSURLDownload *)download willSendRequest:(NSURLRequest *)request redirectResponse:(NSURLResponse *)redirectResponse
+{
+ return [realDelegate download:download willSendRequest:request redirectResponse:redirectResponse];
+}
+
+- (void)download:(NSURLDownload *)download didReceiveAuthenticationChallenge:(NSURLAuthenticationChallenge *)challenge
+{
+ if ([realDelegate respondsToSelector:@selector(download:didReceiveAuthenticationChallenge:)]) {
+ [realDelegate download:download didReceiveAuthenticationChallenge:challenge];
+ } else {
+ NSWindow *window = nil;
+ if ([realDelegate respondsToSelector:@selector(downloadWindowForAuthenticationSheet:)]) {
+ window = [realDelegate downloadWindowForAuthenticationSheet:(WebDownload *)download];
+ }
+
+ [[WebPanelAuthenticationHandler sharedHandler] startAuthentication:challenge window:window];
+ }
+}
+
+- (void)download:(NSURLDownload *)download didCancelAuthenticationChallenge:(NSURLAuthenticationChallenge *)challenge
+{
+ if ([realDelegate respondsToSelector:@selector(download:didCancelAuthenticationChallenge:)]) {
+ [realDelegate download:download didCancelAuthenticationChallenge:challenge];
+ } else {
+ [[WebPanelAuthenticationHandler sharedHandler] cancelAuthentication:challenge];
+ }
+}
+
+- (void)download:(NSURLDownload *)download didReceiveResponse:(NSURLResponse *)response
+{
+ [realDelegate download:download didReceiveResponse:response];
+}
+
+- (void)download:(NSURLDownload *)download didReceiveDataOfLength:(NSUInteger)length
+{
+ [realDelegate download:download didReceiveDataOfLength:length];
+}
+
+- (BOOL)download:(NSURLDownload *)download shouldDecodeSourceDataOfMIMEType:(NSString *)encodingType
+{
+ return [realDelegate download:download shouldDecodeSourceDataOfMIMEType:encodingType];
+}
+
+- (void)download:(NSURLDownload *)download decideDestinationWithSuggestedFilename:(NSString *)filename
+{
+ [realDelegate download:download decideDestinationWithSuggestedFilename:filename];
+}
+
+- (void)download:(NSURLDownload *)download didCreateDestination:(NSString *)path
+{
+ [realDelegate download:download didCreateDestination:path];
+}
+
+- (void)downloadDidFinish:(NSURLDownload *)download
+{
+ [realDelegate downloadDidFinish:download];
+}
+
+- (void)download:(NSURLDownload *)download didFailWithError:(NSError *)error
+{
+ [realDelegate download:download didFailWithError:error];
+}
+
+- (NSURLRequest *)download:(NSURLDownload *)download shouldBeginChildDownloadOfSource:(NSURLRequest *)child delegate:(id *)childDelegate
+{
+ return [realDelegate download:download shouldBeginChildDownloadOfSource:child delegate:childDelegate];
+}
+
+- (void)download:(NSURLDownload *)parent didBeginChildDownload:(NSURLDownload *)child
+{
+ [realDelegate download:parent didBeginChildDownload:child];
+}
+
+@end
+
+@implementation WebDownload
+
+- (void)_setRealDelegate:(id)delegate
+{
+ if (_webInternal == nil) {
+ _webInternal = [[WebDownloadInternal alloc] init];
+ [_webInternal setRealDelegate:delegate];
+ } else {
+ ASSERT(_webInternal == delegate);
+ }
+}
+
+- (id)init
+{
+ self = [super init];
+ if (self != nil) {
+ // _webInternal can be set up before init by _setRealDelegate
+ if (_webInternal == nil) {
+ _webInternal = [[WebDownloadInternal alloc] init];
+ }
+ }
+ return self;
+}
+
+- (void)dealloc
+{
+ [_webInternal release];
+ [super dealloc];
+}
+
+- (id)initWithRequest:(NSURLRequest *)request delegate:(id)delegate
+{
+ [self _setRealDelegate:delegate];
+ return [super initWithRequest:request delegate:_webInternal];
+}
+
+- (id)_initWithLoadingConnection:(NSURLConnection *)connection
+ request:(NSURLRequest *)request
+ response:(NSURLResponse *)response
+ delegate:(id)delegate
+ proxy:(NSURLConnectionDelegateProxy *)proxy
+{
+ [self _setRealDelegate:delegate];
+ return [super _initWithLoadingConnection:connection request:request response:response delegate:_webInternal proxy:proxy];
+}
+
+- (id)_initWithRequest:(NSURLRequest *)request
+ delegate:(id)delegate
+ directory:(NSString *)directory
+{
+ [self _setRealDelegate:delegate];
+ return [super _initWithRequest:request delegate:_webInternal directory:directory];
+}
+
+- (void)connection:(NSURLConnection *)connection willStopBufferingData:(NSData *)data
+{
+ // NSURLConnection calls this method even if it is not implemented.
+ // This happens because NSURLConnection caches the results of respondsToSelector.
+ // Those results become invalid when the delegate of NSURLConnectionDelegateProxy is changed.
+ // This is a workaround since this problem needs to be fixed in NSURLConnectionDelegateProxy.
+ // <rdar://problem/3913270> NSURLConnection calls unimplemented delegate method in WebDownload
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebDownloadInternal.h b/WebKit/mac/Misc/WebDownloadInternal.h
new file mode 100644
index 0000000..aaed445
--- /dev/null
+++ b/WebKit/mac/Misc/WebDownloadInternal.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+* THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+*/
+
+#import <WebKit/WebDownload.h>
+
+@interface WebDownload (WebDownloadCreation)
++(id)_downloadWithLoadingConnection:(NSURLConnection *)connection
+ request:(NSURLRequest *)request
+ response:(NSURLResponse *)r
+ delegate:(id)delegate
+ proxy:(id)proxy;
+
++(id)_downloadWithRequest:(NSURLRequest *)request
+ delegate:(id)delegate
+ directory:(NSString *)directory;
+@end
diff --git a/WebKit/mac/Misc/WebElementDictionary.h b/WebKit/mac/Misc/WebElementDictionary.h
new file mode 100644
index 0000000..b835b5c
--- /dev/null
+++ b/WebKit/mac/Misc/WebElementDictionary.h
@@ -0,0 +1,42 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/NSDictionary.h>
+
+namespace WebCore {
+ class HitTestResult;
+}
+
+@interface WebElementDictionary : NSDictionary {
+ WebCore::HitTestResult* _result;
+ NSMutableDictionary *_cache;
+ NSMutableSet *_nilValues;
+ BOOL _cacheComplete;
+}
+- (id)initWithHitTestResult:(const WebCore::HitTestResult&)result;
+@end
diff --git a/WebKit/mac/Misc/WebElementDictionary.mm b/WebKit/mac/Misc/WebElementDictionary.mm
new file mode 100644
index 0000000..51101d0
--- /dev/null
+++ b/WebKit/mac/Misc/WebElementDictionary.mm
@@ -0,0 +1,250 @@
+/*
+ * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebElementDictionary.h"
+
+#import "WebDOMOperations.h"
+#import "WebFrame.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebKitLogging.h"
+#import "WebView.h"
+#import "WebViewPrivate.h"
+#import <WebCore/Frame.h>
+#import <WebCore/HitTestResult.h>
+#import <WebCore/Image.h>
+#import <WebCore/KURL.h>
+#import <WebCore/WebCoreObjCExtras.h>
+#import <WebKit/DOMCore.h>
+#import <WebKit/DOMExtensions.h>
+
+using namespace WebCore;
+
+static CFMutableDictionaryRef lookupTable = NULL;
+
+static void addLookupKey(NSString *key, SEL selector)
+{
+ CFDictionaryAddValue(lookupTable, key, selector);
+}
+
+static void cacheValueForKey(const void *key, const void *value, void *self)
+{
+ // calling objectForKey will cache the value in our _cache dictionary
+ [(WebElementDictionary *)self objectForKey:(NSString *)key];
+}
+
+@implementation WebElementDictionary
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
++ (void)initializeLookupTable
+{
+ if (lookupTable)
+ return;
+
+ lookupTable = CFDictionaryCreateMutable(kCFAllocatorDefault, 0, &kCFCopyStringDictionaryKeyCallBacks, NULL);
+
+ addLookupKey(WebElementDOMNodeKey, @selector(_domNode));
+ addLookupKey(WebElementFrameKey, @selector(_webFrame));
+ addLookupKey(WebElementImageAltStringKey, @selector(_altDisplayString));
+ addLookupKey(WebElementImageKey, @selector(_image));
+ addLookupKey(WebElementImageRectKey, @selector(_imageRect));
+ addLookupKey(WebElementImageURLKey, @selector(_absoluteImageURL));
+ addLookupKey(WebElementIsSelectedKey, @selector(_isSelected));
+ addLookupKey(WebElementSpellingToolTipKey, @selector(_spellingToolTip));
+ addLookupKey(WebElementTitleKey, @selector(_title));
+ addLookupKey(WebElementLinkURLKey, @selector(_absoluteLinkURL));
+ addLookupKey(WebElementLinkTargetFrameKey, @selector(_targetWebFrame));
+ addLookupKey(WebElementLinkTitleKey, @selector(_titleDisplayString));
+ addLookupKey(WebElementLinkLabelKey, @selector(_textContent));
+ addLookupKey(WebElementLinkIsLiveKey, @selector(_isLiveLink));
+ addLookupKey(WebElementIsContentEditableKey, @selector(_isContentEditable));
+}
+
+- (id)initWithHitTestResult:(const HitTestResult&)result
+{
+ [[self class] initializeLookupTable];
+ [super init];
+ _result = new HitTestResult(result);
+ return self;
+}
+
+- (void)dealloc
+{
+ delete _result;
+ [_cache release];
+ [_nilValues release];
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+ delete _result;
+ [super finalize];
+}
+
+- (void)_fillCache
+{
+ CFDictionaryApplyFunction(lookupTable, cacheValueForKey, self);
+ _cacheComplete = YES;
+}
+
+- (unsigned)count
+{
+ if (!_cacheComplete)
+ [self _fillCache];
+ return [_cache count];
+}
+
+- (NSEnumerator *)keyEnumerator
+{
+ if (!_cacheComplete)
+ [self _fillCache];
+ return [_cache keyEnumerator];
+}
+
+- (id)objectForKey:(id)key
+{
+ id value = [_cache objectForKey:key];
+ if (value || _cacheComplete || [_nilValues containsObject:key])
+ return value;
+
+ SEL selector = (SEL)CFDictionaryGetValue(lookupTable, key);
+ if (!selector)
+ return nil;
+ value = [self performSelector:selector];
+
+ unsigned lookupTableCount = CFDictionaryGetCount(lookupTable);
+ if (value) {
+ if (!_cache)
+ _cache = [[NSMutableDictionary alloc] initWithCapacity:lookupTableCount];
+ [_cache setObject:value forKey:key];
+ } else {
+ if (!_nilValues)
+ _nilValues = [[NSMutableSet alloc] initWithCapacity:lookupTableCount];
+ [_nilValues addObject:key];
+ }
+
+ _cacheComplete = ([_cache count] + [_nilValues count]) == lookupTableCount;
+
+ return value;
+}
+
+- (DOMNode *)_domNode
+{
+ return kit(_result->innerNonSharedNode());
+}
+
+- (WebFrame *)_webFrame
+{
+ return [[[self _domNode] ownerDocument] webFrame];
+}
+
+// String's NSString* operator converts null Strings to empty NSStrings for compatibility
+// with AppKit. We need to work around that here.
+static NSString* NSStringOrNil(String coreString)
+{
+ if (coreString.isNull())
+ return nil;
+ return coreString;
+}
+
+- (NSString *)_altDisplayString
+{
+ return NSStringOrNil(_result->altDisplayString());
+}
+
+- (NSString *)_spellingToolTip
+{
+ return NSStringOrNil(_result->spellingToolTip());
+}
+
+- (NSImage *)_image
+{
+ Image* image = _result->image();
+ return image ? image->getNSImage() : nil;
+}
+
+- (NSValue *)_imageRect
+{
+ IntRect rect = _result->imageRect();
+ return rect.isEmpty() ? nil : [NSValue valueWithRect:rect];
+}
+
+- (NSURL *)_absoluteImageURL
+{
+ return _result->absoluteImageURL();
+}
+
+- (NSNumber *)_isSelected
+{
+ return [NSNumber numberWithBool:_result->isSelected()];
+}
+
+- (NSString *)_title
+{
+ return NSStringOrNil(_result->title());
+}
+
+- (NSURL *)_absoluteLinkURL
+{
+ return _result->absoluteLinkURL();
+}
+
+- (WebFrame *)_targetWebFrame
+{
+ return kit(_result->targetFrame());
+}
+
+- (NSString *)_titleDisplayString
+{
+ return NSStringOrNil(_result->titleDisplayString());
+}
+
+- (NSString *)_textContent
+{
+ return NSStringOrNil(_result->textContent());
+}
+
+- (NSNumber *)_isLiveLink
+{
+ return [NSNumber numberWithBool:_result->isLiveLink()];
+}
+
+- (NSNumber *)_isContentEditable
+{
+ return [NSNumber numberWithBool:_result->isContentEditable()];
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebGraphicsExtras.c b/WebKit/mac/Misc/WebGraphicsExtras.c
new file mode 100644
index 0000000..0832c6c
--- /dev/null
+++ b/WebKit/mac/Misc/WebGraphicsExtras.c
@@ -0,0 +1,57 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebGraphicsExtras.h"
+
+#import <Accelerate/Accelerate.h>
+#import <JavaScriptCore/Assertions.h>
+#import <dlfcn.h>
+
+unsigned WebConvertBGRAToARGB(unsigned char *offscreenBuffer, int rowBytes, int x, int y, int width, int height)
+{
+
+ static vImage_Error (*softLink_vImagePermuteChannels_ARGB8888)(const vImage_Buffer *src, const vImage_Buffer *dest, const uint8_t permuteMap[4], vImage_Flags flags) = NULL;
+
+ if (!softLink_vImagePermuteChannels_ARGB8888) {
+ void *framework = dlopen("/System/Library/Frameworks/Accelerate.framework/Accelerate", RTLD_NOW);
+ ASSERT(framework);
+ softLink_vImagePermuteChannels_ARGB8888 = dlsym(framework, "vImagePermuteChannels_ARGB8888");
+ ASSERT(softLink_vImagePermuteChannels_ARGB8888);
+ }
+
+ void *swizzleImageBase = offscreenBuffer + y * rowBytes + x * 4;
+ vImage_Buffer vImage = { swizzleImageBase, height, width, rowBytes };
+ uint8_t vImagePermuteMap[4] = { 3, 2, 1, 0 }; // Where { 0, 1, 2, 3 } would leave the channels unchanged; this map converts BGRA to ARGB
+ vImage_Error vImageError = softLink_vImagePermuteChannels_ARGB8888(&vImage, &vImage, vImagePermuteMap, 0);
+ if (vImageError) {
+ LOG_ERROR("Could not convert BGRA image to ARGB: %zd", vImageError);
+ return FALSE;
+ }
+
+ return TRUE;
+}
diff --git a/WebKit/mac/Misc/WebGraphicsExtras.h b/WebKit/mac/Misc/WebGraphicsExtras.h
new file mode 100644
index 0000000..9232303
--- /dev/null
+++ b/WebKit/mac/Misc/WebGraphicsExtras.h
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+unsigned WebConvertBGRAToARGB(unsigned char *offscreenBuffer, int rowBytes, int x, int y, int width, int height);
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/WebKit/mac/Misc/WebIconDatabase.h b/WebKit/mac/Misc/WebIconDatabase.h
new file mode 100644
index 0000000..8dc3d45
--- /dev/null
+++ b/WebKit/mac/Misc/WebIconDatabase.h
@@ -0,0 +1,146 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+// Sent whenever a site icon has changed. The object of the notification is the icon database.
+// The userInfo contains the site URL whose icon has changed.
+// It can be accessed with the key WebIconNotificationUserInfoURLKey.
+extern NSString *WebIconDatabaseDidAddIconNotification;
+
+extern NSString *WebIconNotificationUserInfoURLKey;
+
+extern NSString *WebIconDatabaseDirectoryDefaultsKey;
+extern NSString *WebIconDatabaseEnabledDefaultsKey;
+
+extern NSSize WebIconSmallSize; // 16 x 16
+extern NSSize WebIconMediumSize; // 32 x 32
+extern NSSize WebIconLargeSize; // 128 x 128
+
+@class WebIconDatabasePrivate;
+
+/*!
+ @class WebIconDatabase
+ @discussion Features:
+ - memory cache icons at different sizes
+ - disk storage
+ - icon update notification
+
+ Uses:
+ - UI elements to retrieve icons that represent site URLs.
+ - Save icons to disk for later use.
+
+ Every icon in the database has a retain count. If an icon has a retain count greater than 0, it will be written to disk for later use. If an icon's retain count equals zero it will be removed from disk. The retain count is not persistent across launches. If the WebKit client wishes to retain an icon it should retain the icon once for every launch. This is best done at initialization time before the database begins removing icons. To make sure that the database does not remove unretained icons prematurely, call delayDatabaseCleanup until all desired icons are retained. Once all are retained, call allowDatabaseCleanup.
+
+ Note that an icon can be retained after the database clean-up has begun. This just has to be done before the icon is removed. Icons are removed from the database whenever new icons are added to it.
+
+ Retention methods can be called for icons that are not yet in the database.
+*/
+@interface WebIconDatabase : NSObject {
+
+@private
+ WebIconDatabasePrivate *_private;
+ BOOL _isClosing;
+}
+
+
+/*!
+ @method sharedIconDatabase
+ @abstract Returns a shared instance of the icon database
+*/
++ (WebIconDatabase *)sharedIconDatabase;
+
+/*!
+ @method iconForURL:withSize:
+ @discussion Calls iconForURL:withSize:cache: with YES for cache.
+ @param URL
+ @param size
+*/
+- (NSImage *)iconForURL:(NSString *)URL withSize:(NSSize)size;
+
+/*!
+ @method iconForURL:withSize:cache:
+ @discussion Returns an icon for a web site URL from memory or disk. nil if none is found.
+ Usually called by a UI element to determine if a site URL has an associated icon.
+ Often called by the observer of WebIconChangedNotification after the notification is sent.
+ @param URL
+ @param size
+ @param cache If yes, caches the returned image in memory if not already cached
+*/
+- (NSImage *)iconForURL:(NSString *)URL withSize:(NSSize)size cache:(BOOL)cache;
+
+/*!
+ @method iconURLForURL:withSize:cache:
+ @discussion Returns an icon URL for a web site URL from memory or disk. nil if none is found.
+ @param URL
+*/
+- (NSString *)iconURLForURL:(NSString *)URL;
+
+/*!
+ @method defaultIconWithSize:
+ @param size
+*/
+- (NSImage *)defaultIconWithSize:(NSSize)size;
+- (NSImage *)defaultIconForURL:(NSString *)URL withSize:(NSSize)size;
+
+/*!
+ @method retainIconForURL:
+ @abstract Increments the retain count of the icon.
+ @param URL
+*/
+- (void)retainIconForURL:(NSString *)URL;
+
+/*!
+ @method releaseIconForURL:
+ @abstract Decrements the retain count of the icon.
+ @param URL
+*/
+- (void)releaseIconForURL:(NSString *)URL;
+
+/*!
+ @method delayDatabaseCleanup:
+ @discussion Only effective if called before the database begins removing icons.
+ delayDatabaseCleanUp increments an internal counter that when 0 begins the database clean-up.
+ The counter equals 0 at initialization.
+*/
++ (void)delayDatabaseCleanup;
+
+/*!
+ @method allowDatabaseCleanup:
+ @discussion Informs the database that it now can begin removing icons.
+ allowDatabaseCleanup decrements an internal counter that when 0 begins the database clean-up.
+ The counter equals 0 at initialization.
+*/
++ (void)allowDatabaseCleanup;
+
+- (void)setDelegate:(id)delegate;
+- (id)delegate;
+
+@end
+
+
diff --git a/WebKit/mac/Misc/WebIconDatabase.mm b/WebKit/mac/Misc/WebIconDatabase.mm
new file mode 100644
index 0000000..39dbcac
--- /dev/null
+++ b/WebKit/mac/Misc/WebIconDatabase.mm
@@ -0,0 +1,669 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebIconDatabaseInternal.h"
+
+#import "WebIconDatabaseClient.h"
+#import "WebIconDatabaseDelegate.h"
+#import "WebKitLogging.h"
+#import "WebKitNSStringExtras.h"
+#import "WebNSNotificationCenterExtras.h"
+#import "WebNSURLExtras.h"
+#import "WebPreferences.h"
+#import "WebTypesInternal.h"
+#import <WebCore/FoundationExtras.h>
+#import <WebCore/IconDatabase.h>
+#import <WebCore/Image.h>
+#import <WebCore/IntSize.h>
+#import <WebCore/ThreadCheck.h>
+
+using namespace WebCore;
+
+NSString * const WebIconDatabaseVersionKey = @"WebIconDatabaseVersion";
+NSString * const WebURLToIconURLKey = @"WebSiteURLToIconURLKey";
+
+NSString *WebIconDatabaseDidAddIconNotification = @"WebIconDatabaseDidAddIconNotification";
+NSString *WebIconNotificationUserInfoURLKey = @"WebIconNotificationUserInfoURLKey";
+NSString *WebIconDatabaseDidRemoveAllIconsNotification = @"WebIconDatabaseDidRemoveAllIconsNotification";
+
+NSString *WebIconDatabaseDirectoryDefaultsKey = @"WebIconDatabaseDirectoryDefaultsKey";
+NSString *WebIconDatabaseImportDirectoryDefaultsKey = @"WebIconDatabaseImportDirectoryDefaultsKey";
+NSString *WebIconDatabaseEnabledDefaultsKey = @"WebIconDatabaseEnabled";
+
+NSString *WebIconDatabasePath = @"~/Library/Icons";
+
+NSSize WebIconSmallSize = {16, 16};
+NSSize WebIconMediumSize = {32, 32};
+NSSize WebIconLargeSize = {128, 128};
+
+#define UniqueFilePathSize (34)
+
+static WebIconDatabaseClient* defaultClient()
+{
+ static WebIconDatabaseClient* defaultClient = new WebIconDatabaseClient();
+ return defaultClient;
+}
+
+@interface WebIconDatabase (WebReallyInternal)
+- (BOOL)_isEnabled;
+- (void)_sendNotificationForURL:(NSString *)URL;
+- (void)_sendDidRemoveAllIconsNotification;
+- (NSImage *)_iconForFileURL:(NSString *)fileURL withSize:(NSSize)size;
+- (void)_resetCachedWebPreferences:(NSNotification *)notification;
+- (NSImage *)_largestIconFromDictionary:(NSMutableDictionary *)icons;
+- (NSMutableDictionary *)_iconsBySplittingRepresentationsOfIcon:(NSImage *)icon;
+- (NSImage *)_iconFromDictionary:(NSMutableDictionary *)icons forSize:(NSSize)size cache:(BOOL)cache;
+- (void)_scaleIcon:(NSImage *)icon toSize:(NSSize)size;
+- (NSString *)_databaseDirectory;
+@end
+
+@implementation WebIconDatabase
+
++ (WebIconDatabase *)sharedIconDatabase
+{
+ static WebIconDatabase *database = nil;
+ if (!database)
+ database = [[WebIconDatabase alloc] init];
+ return database;
+}
+
+- init
+{
+ [super init];
+ WebCoreThreadViolationCheck();
+
+ _private = [[WebIconDatabasePrivate alloc] init];
+
+ // Check the user defaults and see if the icon database should even be enabled.
+ // Inform the bridge and, if we're disabled, bail from init right here
+ NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
+ // <rdar://problem/4741419> - IconDatabase should be disabled by default
+ NSDictionary *initialDefaults = [[NSDictionary alloc] initWithObjectsAndKeys:[NSNumber numberWithBool:YES], WebIconDatabaseEnabledDefaultsKey, nil];
+ [defaults registerDefaults:initialDefaults];
+ [initialDefaults release];
+ BOOL enabled = [defaults boolForKey:WebIconDatabaseEnabledDefaultsKey];
+ iconDatabase()->setEnabled(enabled);
+ if (!enabled)
+ return self;
+ iconDatabase()->setClient(defaultClient());
+
+ // Figure out the directory we should be using for the icon.db
+ NSString *databaseDirectory = [self _databaseDirectory];
+
+ // Rename legacy icon database files to the new icon database name
+ BOOL isDirectory = NO;
+ NSString *legacyDB = [databaseDirectory stringByAppendingPathComponent:@"icon.db"];
+ NSFileManager *defaultManager = [NSFileManager defaultManager];
+ if ([defaultManager fileExistsAtPath:legacyDB isDirectory:&isDirectory] && !isDirectory) {
+ NSString *newDB = [databaseDirectory stringByAppendingPathComponent:iconDatabase()->defaultDatabaseFilename()];
+ if (![defaultManager fileExistsAtPath:newDB])
+ rename([legacyDB fileSystemRepresentation], [newDB fileSystemRepresentation]);
+ }
+
+ // Set the private browsing pref then open the WebCore icon database
+ iconDatabase()->setPrivateBrowsingEnabled([[WebPreferences standardPreferences] privateBrowsingEnabled]);
+ if (!iconDatabase()->open(databaseDirectory))
+ LOG_ERROR("Unable to open icon database");
+
+ // Register for important notifications
+ [[NSNotificationCenter defaultCenter] addObserver:self
+ selector:@selector(_applicationWillTerminate:)
+ name:NSApplicationWillTerminateNotification
+ object:NSApp];
+ [[NSNotificationCenter defaultCenter]
+ addObserver:self selector:@selector(_resetCachedWebPreferences:)
+ name:WebPreferencesChangedNotification object:nil];
+
+ return self;
+}
+
+- (NSImage *)iconForURL:(NSString *)URL withSize:(NSSize)size cache:(BOOL)cache
+{
+ ASSERT_MAIN_THREAD();
+ ASSERT(size.width);
+ ASSERT(size.height);
+
+ if (!URL || ![self _isEnabled])
+ return [self defaultIconForURL:URL withSize:size];
+
+ // FIXME - <rdar://problem/4697934> - Move the handling of FileURLs to WebCore and implement in ObjC++
+ if ([URL _webkit_isFileURL])
+ return [self _iconForFileURL:URL withSize:size];
+
+ if (Image* image = iconDatabase()->iconForPageURL(URL, IntSize(size)))
+ if (NSImage *icon = webGetNSImage(image, size))
+ return icon;
+ return [self defaultIconForURL:URL withSize:size];
+}
+
+- (NSImage *)iconForURL:(NSString *)URL withSize:(NSSize)size
+{
+ return [self iconForURL:URL withSize:size cache:YES];
+}
+
+- (NSString *)iconURLForURL:(NSString *)URL
+{
+ if (![self _isEnabled])
+ return nil;
+ ASSERT_MAIN_THREAD();
+
+ return iconDatabase()->iconURLForPageURL(URL);
+}
+
+- (NSImage *)defaultIconWithSize:(NSSize)size
+{
+ ASSERT_MAIN_THREAD();
+ ASSERT(size.width);
+ ASSERT(size.height);
+
+ Image* image = iconDatabase()->defaultIcon(IntSize(size));
+ return image ? image->getNSImage() : nil;
+}
+
+- (NSImage *)defaultIconForURL:(NSString *)URL withSize:(NSSize)size
+{
+ if (_private->delegateImplementsDefaultIconForURL)
+ return [_private->delegate webIconDatabase:self defaultIconForURL:URL withSize:size];
+ return [self defaultIconWithSize:size];
+}
+
+- (void)retainIconForURL:(NSString *)URL
+{
+ ASSERT_MAIN_THREAD();
+ ASSERT(URL);
+ if (![self _isEnabled])
+ return;
+
+ iconDatabase()->retainIconForPageURL(URL);
+}
+
+- (void)releaseIconForURL:(NSString *)pageURL
+{
+ ASSERT_MAIN_THREAD();
+ ASSERT(pageURL);
+ if (![self _isEnabled])
+ return;
+
+ iconDatabase()->releaseIconForPageURL(pageURL);
+}
+
++ (void)delayDatabaseCleanup
+{
+ ASSERT_MAIN_THREAD();
+
+ IconDatabase::delayDatabaseCleanup();
+}
+
++ (void)allowDatabaseCleanup
+{
+ ASSERT_MAIN_THREAD();
+
+ IconDatabase::allowDatabaseCleanup();
+}
+
+- (void)setDelegate:(id)delegate
+{
+ _private->delegate = delegate;
+ _private->delegateImplementsDefaultIconForURL = [delegate respondsToSelector:@selector(webIconDatabase:defaultIconForURL:withSize:)];
+}
+
+- (id)delegate
+{
+ return _private->delegate;
+}
+
+@end
+
+
+@implementation WebIconDatabase (WebPendingPublic)
+
+- (void)removeAllIcons
+{
+ ASSERT_MAIN_THREAD();
+ if (![self _isEnabled])
+ return;
+
+ // Via the IconDatabaseClient interface, removeAllIcons() will send the WebIconDatabaseDidRemoveAllIconsNotification
+ iconDatabase()->removeAllIcons();
+}
+
+@end
+
+@implementation WebIconDatabase (WebPrivate)
+
++ (void)_checkIntegrityBeforeOpening
+{
+ iconDatabase()->checkIntegrityBeforeOpening();
+}
+
+@end
+
+@implementation WebIconDatabase (WebInternal)
+
+- (BOOL)_isEnabled
+{
+ return iconDatabase()->isEnabled();
+}
+
+- (void)_sendNotificationForURL:(NSString *)URL
+{
+ ASSERT(URL);
+
+ NSDictionary *userInfo = [NSDictionary dictionaryWithObject:URL
+ forKey:WebIconNotificationUserInfoURLKey];
+
+ [[NSNotificationCenter defaultCenter] postNotificationOnMainThreadWithName:WebIconDatabaseDidAddIconNotification
+ object:self
+ userInfo:userInfo];
+}
+
+- (void)_sendDidRemoveAllIconsNotification
+{
+ [[NSNotificationCenter defaultCenter] postNotificationOnMainThreadWithName:WebIconDatabaseDidRemoveAllIconsNotification
+ object:self
+ userInfo:nil];
+}
+
+- (void)_applicationWillTerminate:(NSNotification *)notification
+{
+ iconDatabase()->close();
+}
+
+- (NSImage *)_iconForFileURL:(NSString *)file withSize:(NSSize)size
+{
+ ASSERT_MAIN_THREAD();
+ ASSERT(size.width);
+ ASSERT(size.height);
+
+ NSWorkspace *workspace = [NSWorkspace sharedWorkspace];
+ NSString *path = [[NSURL _web_URLWithDataAsString:file] path];
+ NSString *suffix = [path pathExtension];
+ NSImage *icon = nil;
+
+ if ([suffix _webkit_isCaseInsensitiveEqualToString:@"htm"] || [suffix _webkit_isCaseInsensitiveEqualToString:@"html"]) {
+ if (!_private->htmlIcons) {
+ icon = [workspace iconForFileType:@"html"];
+ _private->htmlIcons = [[self _iconsBySplittingRepresentationsOfIcon:icon] retain];
+ }
+ icon = [self _iconFromDictionary:_private->htmlIcons forSize:size cache:YES];
+ } else {
+ if (!path || ![path isAbsolutePath]) {
+ // Return the generic icon when there is no path.
+ icon = [workspace iconForFileType:NSFileTypeForHFSTypeCode(kGenericDocumentIcon)];
+ } else {
+ icon = [workspace iconForFile:path];
+ }
+ [self _scaleIcon:icon toSize:size];
+ }
+
+ return icon;
+}
+
+- (void)_resetCachedWebPreferences:(NSNotification *)notification
+{
+ BOOL privateBrowsingEnabledNow = [[WebPreferences standardPreferences] privateBrowsingEnabled];
+ iconDatabase()->setPrivateBrowsingEnabled(privateBrowsingEnabledNow);
+}
+
+- (NSImage *)_largestIconFromDictionary:(NSMutableDictionary *)icons
+{
+ ASSERT(icons);
+
+ NSEnumerator *enumerator = [icons keyEnumerator];
+ NSValue *currentSize, *largestSize=nil;
+ float largestSizeArea=0;
+
+ while ((currentSize = [enumerator nextObject]) != nil) {
+ NSSize currentSizeSize = [currentSize sizeValue];
+ float currentSizeArea = currentSizeSize.width * currentSizeSize.height;
+ if(!largestSizeArea || (currentSizeArea > largestSizeArea)){
+ largestSize = currentSize;
+ largestSizeArea = currentSizeArea;
+ }
+ }
+
+ return [icons objectForKey:largestSize];
+}
+
+- (NSMutableDictionary *)_iconsBySplittingRepresentationsOfIcon:(NSImage *)icon
+{
+ ASSERT(icon);
+
+ NSMutableDictionary *icons = [NSMutableDictionary dictionary];
+ NSEnumerator *enumerator = [[icon representations] objectEnumerator];
+ NSImageRep *rep;
+
+ while ((rep = [enumerator nextObject]) != nil) {
+ NSSize size = [rep size];
+ NSImage *subIcon = [[NSImage alloc] initWithSize:size];
+ [subIcon addRepresentation:rep];
+ [icons setObject:subIcon forKey:[NSValue valueWithSize:size]];
+ [subIcon release];
+ }
+
+ if([icons count] > 0)
+ return icons;
+
+ LOG_ERROR("icon has no representations");
+
+ return nil;
+}
+
+- (NSImage *)_iconFromDictionary:(NSMutableDictionary *)icons forSize:(NSSize)size cache:(BOOL)cache
+{
+ ASSERT(size.width);
+ ASSERT(size.height);
+
+ NSImage *icon = [icons objectForKey:[NSValue valueWithSize:size]];
+
+ if(!icon){
+ icon = [[[self _largestIconFromDictionary:icons] copy] autorelease];
+ [self _scaleIcon:icon toSize:size];
+
+ if(cache){
+ [icons setObject:icon forKey:[NSValue valueWithSize:size]];
+ }
+ }
+
+ return icon;
+}
+
+- (void)_scaleIcon:(NSImage *)icon toSize:(NSSize)size
+{
+ ASSERT(size.width);
+ ASSERT(size.height);
+
+#if !LOG_DISABLED
+ double start = CFAbsoluteTimeGetCurrent();
+#endif
+
+ [icon setScalesWhenResized:YES];
+ [icon setSize:size];
+
+#if !LOG_DISABLED
+ double duration = CFAbsoluteTimeGetCurrent() - start;
+ LOG(Timing, "scaling icon took %f seconds.", duration);
+#endif
+}
+
+// This hashing String->filename algorithm came from WebFileDatabase.m and is what was used in the
+// WebKit Icon Database
+static void legacyIconDatabaseFilePathForKey(id key, char *buffer)
+{
+ const char *s;
+ UInt32 hash1;
+ UInt32 hash2;
+ CFIndex len;
+ CFIndex cnt;
+
+ s = [[[[key description] lowercaseString] stringByStandardizingPath] UTF8String];
+ len = strlen(s);
+
+ // compute first hash
+ hash1 = len;
+ for (cnt = 0; cnt < len; cnt++) {
+ hash1 += (hash1 << 8) + s[cnt];
+ }
+ hash1 += (hash1 << (len & 31));
+
+ // compute second hash
+ hash2 = len;
+ for (cnt = 0; cnt < len; cnt++) {
+ hash2 = (37 * hash2) ^ s[cnt];
+ }
+
+#ifdef __LP64__
+ snprintf(buffer, UniqueFilePathSize, "%.2u/%.2u/%.10u-%.10u.cache", ((hash1 & 0xff) >> 4), ((hash2 & 0xff) >> 4), hash1, hash2);
+#else
+ snprintf(buffer, UniqueFilePathSize, "%.2lu/%.2lu/%.10lu-%.10lu.cache", ((hash1 & 0xff) >> 4), ((hash2 & 0xff) >> 4), hash1, hash2);
+#endif
+}
+
+// This method of getting an object from the filesystem is taken from the old
+// WebKit Icon Database
+static id objectFromPathForKey(NSString *databasePath, id key)
+{
+ ASSERT(key);
+ id result = nil;
+
+ // Use the key->filename hashing the old WebKit IconDatabase used
+ char uniqueKey[UniqueFilePathSize];
+ legacyIconDatabaseFilePathForKey(key, uniqueKey);
+
+ // Get the data from this file and setup for the un-archiving
+ NSString *filePath = [[NSString alloc] initWithFormat:@"%@/%s", databasePath, uniqueKey];
+ NSData *data = [[NSData alloc] initWithContentsOfFile:filePath];
+ NSUnarchiver *unarchiver = nil;
+
+ @try {
+ if (data) {
+ unarchiver = [[NSUnarchiver alloc] initForReadingWithData:data];
+ if (unarchiver) {
+ id fileKey = [unarchiver decodeObject];
+ if ([fileKey isEqual:key]) {
+ id object = [unarchiver decodeObject];
+ if (object) {
+ // Decoded objects go away when the unarchiver does, so we need to
+ // retain this so we can return it to our caller.
+ result = [[object retain] autorelease];
+ LOG(IconDatabase, "read disk cache file - %@", key);
+ }
+ }
+ }
+ }
+ } @catch (NSException *localException) {
+ LOG(IconDatabase, "cannot unarchive cache file - %@", key);
+ result = nil;
+ }
+
+ [unarchiver release];
+ [data release];
+ [filePath release];
+
+ return result;
+}
+
+static NSData* iconDataFromPathForIconURL(NSString *databasePath, NSString *iconURLString)
+{
+ ASSERT(iconURLString);
+ ASSERT(databasePath);
+
+ NSData *iconData = objectFromPathForKey(databasePath, iconURLString);
+
+ if ((id)iconData == (id)[NSNull null])
+ return nil;
+
+ return iconData;
+}
+
+- (NSString *)_databaseDirectory
+{
+ NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
+
+ // Figure out the directory we should be using for the icon.db
+ NSString *databaseDirectory = [defaults objectForKey:WebIconDatabaseDirectoryDefaultsKey];
+ if (!databaseDirectory) {
+ databaseDirectory = WebIconDatabasePath;
+ [defaults setObject:databaseDirectory forKey:WebIconDatabaseDirectoryDefaultsKey];
+ }
+
+ return [[databaseDirectory stringByExpandingTildeInPath] stringByStandardizingPath];
+}
+
+@end
+
+@implementation WebIconDatabasePrivate
+@end
+
+@interface ThreadEnabler : NSObject {
+}
++ (void)enableThreading;
+
+- (void)threadEnablingSelector:(id)arg;
+@end
+
+@implementation ThreadEnabler
+
+- (void)threadEnablingSelector:(id)arg
+{
+ return;
+}
+
++ (void)enableThreading
+{
+ ThreadEnabler *enabler = [[ThreadEnabler alloc] init];
+ [NSThread detachNewThreadSelector:@selector(threadEnablingSelector:) toTarget:enabler withObject:nil];
+ [enabler release];
+}
+
+@end
+
+bool importToWebCoreFormat()
+{
+ // Since this is running on a secondary POSIX thread and Cocoa cannot be used multithreaded unless an NSThread has been detached,
+ // make sure that happens here for all WebKit clients
+ if (![NSThread isMultiThreaded])
+ [ThreadEnabler enableThreading];
+ ASSERT([NSThread isMultiThreaded]);
+
+#ifndef BUILDING_ON_TIGER
+ // Tell backup software (i.e., Time Machine) to never back up the icon database, because
+ // it's a large file that changes frequently, thus using a lot of backup disk space, and
+ // it's unlikely that many users would be upset about it not being backed up. We do this
+ // here because this code is only executed once for each icon database instance. We could
+ // make this configurable on a per-client basis someday if that seemed useful.
+ // See <rdar://problem/5320208>.
+ CFStringRef databasePath = iconDatabase()->databasePath().createCFString();
+ if (databasePath) {
+ CFURLRef databasePathURL = CFURLCreateWithFileSystemPath(0, databasePath, kCFURLPOSIXPathStyle, FALSE);
+ CFRelease(databasePath);
+ CSBackupSetItemExcluded(databasePathURL, true, true);
+ CFRelease(databasePathURL);
+ }
+#endif
+
+ // Get the directory the old icon database *should* be in
+ NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
+ NSString *databaseDirectory = [defaults objectForKey:WebIconDatabaseImportDirectoryDefaultsKey];
+
+ if (!databaseDirectory)
+ databaseDirectory = [defaults objectForKey:WebIconDatabaseDirectoryDefaultsKey];
+
+ if (!databaseDirectory) {
+ databaseDirectory = WebIconDatabasePath;
+ [defaults setObject:databaseDirectory forKey:WebIconDatabaseDirectoryDefaultsKey];
+ }
+ databaseDirectory = [databaseDirectory stringByExpandingTildeInPath];
+
+ // With this directory, get the PageURLToIconURL map that was saved to disk
+ NSMutableDictionary *pageURLToIconURL = objectFromPathForKey(databaseDirectory, WebURLToIconURLKey);
+
+ // If the retrieved object was not a valid NSMutableDictionary, then we have no valid
+ // icons to import
+ if (![pageURLToIconURL isKindOfClass:[NSMutableDictionary class]])
+ pageURLToIconURL = nil;
+
+ NSEnumerator *enumerator = [pageURLToIconURL keyEnumerator];
+ NSString *url, *iconURL;
+
+ // First, we'll iterate through the PageURL->IconURL map
+ while ((url = [enumerator nextObject]) != nil) {
+ iconURL = [pageURLToIconURL objectForKey:url];
+ if (!iconURL)
+ continue;
+ iconDatabase()->importIconURLForPageURL(iconURL, url);
+ if (iconDatabase()->shouldStopThreadActivity())
+ return false;
+ }
+
+ // Second, we'll get a list of the unique IconURLs we have
+ NSMutableSet *iconsOnDiskWithURLs = [NSMutableSet setWithArray:[pageURLToIconURL allValues]];
+ enumerator = [iconsOnDiskWithURLs objectEnumerator];
+ NSData *iconData;
+
+ // And iterate through them, adding the icon data to the new icon database
+ while ((url = [enumerator nextObject]) != nil) {
+ iconData = iconDataFromPathForIconURL(databaseDirectory, url);
+ if (iconData)
+ iconDatabase()->importIconDataForIconURL(SharedBuffer::wrapNSData(iconData), url);
+ else {
+ // This really *shouldn't* happen, so it'd be good to track down why it might happen in a debug build
+ // however, we do know how to handle it gracefully in release
+ LOG_ERROR("%@ is marked as having an icon on disk, but we couldn't get the data for it", url);
+ iconDatabase()->importIconDataForIconURL(0, url);
+ }
+ if (iconDatabase()->shouldStopThreadActivity())
+ return false;
+ }
+
+ // After we're done importing old style icons over to webcore icons, we delete the entire directory hierarchy
+ // for the old icon DB (skipping the new iconDB if it is in the same directory)
+ NSFileManager *fileManager = [NSFileManager defaultManager];
+ enumerator = [[fileManager directoryContentsAtPath:databaseDirectory] objectEnumerator];
+
+ NSString *databaseFilename = iconDatabase()->defaultDatabaseFilename();
+
+ BOOL foundIconDB = NO;
+ NSString *file;
+ while ((file = [enumerator nextObject]) != nil) {
+ if ([file caseInsensitiveCompare:databaseFilename] == NSOrderedSame) {
+ foundIconDB = YES;
+ continue;
+ }
+ NSString *filePath = [databaseDirectory stringByAppendingPathComponent:file];
+ if (![fileManager removeFileAtPath:filePath handler:nil])
+ LOG_ERROR("Failed to delete %@ from old icon directory", filePath);
+ }
+
+ // If the new iconDB wasn't in that directory, we can delete the directory itself
+ if (!foundIconDB)
+ rmdir([databaseDirectory fileSystemRepresentation]);
+
+ return true;
+}
+
+NSImage *webGetNSImage(Image* image, NSSize size)
+{
+ ASSERT_MAIN_THREAD();
+ ASSERT(size.width);
+ ASSERT(size.height);
+
+ // FIXME: We're doing the resize here for now because WebCore::Image doesn't yet support resizing/multiple representations
+ // This makes it so there's effectively only one size of a particular icon in the system at a time. We should move this
+ // to WebCore::Image at some point.
+ if (!image)
+ return nil;
+ NSImage* nsImage = image->getNSImage();
+ if (!nsImage)
+ return nil;
+ if (!NSEqualSizes([nsImage size], size)) {
+ [nsImage setScalesWhenResized:YES];
+ [nsImage setSize:size];
+ }
+ return nsImage;
+}
diff --git a/WebKit/mac/Misc/WebIconDatabaseDelegate.h b/WebKit/mac/Misc/WebIconDatabaseDelegate.h
new file mode 100644
index 0000000..ad6aed2
--- /dev/null
+++ b/WebKit/mac/Misc/WebIconDatabaseDelegate.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+@interface NSObject (WebIconDatabaseDelegate)
+
+- (NSImage *)webIconDatabase:(WebIconDatabase *)webIconDatabase defaultIconForURL:(NSString *)URL withSize:(NSSize)size;
+
+@end
+
+
diff --git a/WebKit/mac/Misc/WebIconDatabaseInternal.h b/WebKit/mac/Misc/WebIconDatabaseInternal.h
new file mode 100644
index 0000000..b7b01ec
--- /dev/null
+++ b/WebKit/mac/Misc/WebIconDatabaseInternal.h
@@ -0,0 +1,49 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebIconDatabasePrivate.h"
+
+namespace WebCore {
+ class Image;
+}
+
+@interface WebIconDatabasePrivate : NSObject {
+@public
+ id delegate;
+ BOOL delegateImplementsDefaultIconForURL;
+ NSMutableDictionary *htmlIcons;
+}
+@end
+
+@interface WebIconDatabase (WebInternal)
+- (void)_sendNotificationForURL:(NSString *)URL;
+- (void)_sendDidRemoveAllIconsNotification;
+@end
+
+extern bool importToWebCoreFormat();
+NSImage *webGetNSImage(WebCore::Image*, NSSize);
diff --git a/WebKit/mac/Misc/WebIconDatabasePrivate.h b/WebKit/mac/Misc/WebIconDatabasePrivate.h
new file mode 100644
index 0000000..aff923e
--- /dev/null
+++ b/WebKit/mac/Misc/WebIconDatabasePrivate.h
@@ -0,0 +1,59 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebIconDatabase.h>
+
+// FIXME: Some of the following is not API and should be moved
+// either inside WebIconDatabase.mm, or to WebIconDatabaseInternal.h.
+
+// Sent when all icons are removed from the database. The object of the notification is
+// the icon database. There is no userInfo. Clients should react by removing any cached
+// icon images from the user interface. Clients need not and should not call
+// releaseIconForURL: in response to this notification.
+extern NSString *WebIconDatabaseDidRemoveAllIconsNotification;
+
+// Key to store the path to look for old style icons in to convert to the new icon db
+extern NSString *WebIconDatabaseImportDirectoryDefaultsKey;
+
+@interface WebIconDatabase (WebPendingPublic)
+
+/*!
+ @method removeAllIcons:
+ @discussion Causes the icon database to delete all of the images that it has stored,
+ and to send out the notification WebIconDatabaseDidRemoveAllIconsNotification.
+*/
+- (void)removeAllIcons;
+
+@end
+
+@interface WebIconDatabase (WebPrivate)
+
++ (void)_checkIntegrityBeforeOpening;
+
+@end
+
diff --git a/WebKit/mac/Misc/WebKit.h b/WebKit/mac/Misc/WebKit.h
new file mode 100644
index 0000000..84bfd37
--- /dev/null
+++ b/WebKit/mac/Misc/WebKit.h
@@ -0,0 +1,52 @@
+/*
+ * Copyright (C) 2003, 2004 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/DOM.h>
+#import <WebKit/WebArchive.h>
+#import <WebKit/WebBackForwardList.h>
+#import <WebKit/WebDataSource.h>
+#import <WebKit/WebDocument.h>
+#import <WebKit/WebDOMOperations.h>
+#import <WebKit/WebDownload.h>
+#import <WebKit/WebEditingDelegate.h>
+#import <WebKit/WebFrame.h>
+#import <WebKit/WebFrameLoadDelegate.h>
+#import <WebKit/WebFrameView.h>
+#import <WebKit/WebHistory.h>
+#import <WebKit/WebHistoryItem.h>
+#import <WebKit/WebKitErrors.h>
+#import <WebKit/WebPlugin.h>
+#import <WebKit/WebPluginContainer.h>
+#import <WebKit/WebPluginViewFactory.h>
+#import <WebKit/WebPolicyDelegate.h>
+#import <WebKit/WebPreferences.h>
+#import <WebKit/WebResource.h>
+#import <WebKit/WebResourceLoadDelegate.h>
+#import <WebKit/WebScriptObject.h>
+#import <WebKit/WebUIDelegate.h>
+#import <WebKit/WebView.h>
diff --git a/WebKit/mac/Misc/WebKitErrors.h b/WebKit/mac/Misc/WebKitErrors.h
new file mode 100644
index 0000000..e4cbdcc
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitErrors.h
@@ -0,0 +1,59 @@
+/*
+ * Copyright (C) 2003 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+extern NSString *WebKitErrorDomain;
+
+extern NSString * const WebKitErrorMIMETypeKey;
+extern NSString * const WebKitErrorPlugInNameKey;
+extern NSString * const WebKitErrorPlugInPageURLStringKey;
+
+/*!
+ @enum
+ @abstract Policy errors
+ @constant WebKitErrorCannotShowMIMEType
+ @constant WebKitErrorCannotShowURL
+ @constant WebKitErrorFrameLoadInterruptedByPolicyChange
+*/
+enum {
+ WebKitErrorCannotShowMIMEType = 100,
+ WebKitErrorCannotShowURL = 101,
+ WebKitErrorFrameLoadInterruptedByPolicyChange = 102,
+};
+
+/*!
+ @enum
+ @abstract Plug-in and java errors
+ @constant WebKitErrorCannotFindPlugIn
+ @constant WebKitErrorCannotLoadPlugIn
+ @constant WebKitErrorJavaUnavailable
+*/
+enum {
+ WebKitErrorCannotFindPlugIn = 200,
+ WebKitErrorCannotLoadPlugIn = 201,
+ WebKitErrorJavaUnavailable = 202,
+};
diff --git a/WebKit/mac/Misc/WebKitErrors.m b/WebKit/mac/Misc/WebKitErrors.m
new file mode 100644
index 0000000..59561f3
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitErrors.m
@@ -0,0 +1,163 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebKitErrors.h>
+
+#import <WebKit/WebKitErrorsPrivate.h>
+#import <WebKit/WebLocalizableStrings.h>
+#import <WebKit/WebNSURLExtras.h>
+
+#import <pthread.h>
+
+NSString *WebKitErrorDomain = @"WebKitErrorDomain";
+
+NSString * const WebKitErrorMIMETypeKey = @"WebKitErrorMIMETypeKey";
+NSString * const WebKitErrorPlugInNameKey = @"WebKitErrorPlugInNameKey";
+NSString * const WebKitErrorPlugInPageURLStringKey = @"WebKitErrorPlugInPageURLStringKey";
+
+// Policy errors
+#define WebKitErrorDescriptionCannotShowMIMEType UI_STRING("Cannot show content with specified mime type", "WebKitErrorCannotShowMIMEType description")
+#define WebKitErrorDescriptionCannotShowURL UI_STRING("Cannot show URL", "WebKitErrorCannotShowURL description")
+#define WebKitErrorDescriptionFrameLoadInterruptedByPolicyChange UI_STRING("Frame load interrupted", "WebKitErrorFrameLoadInterruptedByPolicyChange description")
+#define WebKitErrorDescriptionCannotUseRestrictedPort UI_STRING("Not allowed to use restricted network port", "WebKitErrorCannotUseRestrictedPort description")
+
+// Plug-in and java errors
+#define WebKitErrorDescriptionCannotFindPlugin UI_STRING("Cannot find plug-in", "WebKitErrorCannotFindPlugin description")
+#define WebKitErrorDescriptionCannotLoadPlugin UI_STRING("Cannot load plug-in", "WebKitErrorCannotLoadPlugin description")
+#define WebKitErrorDescriptionJavaUnavailable UI_STRING("Java is unavailable", "WebKitErrorJavaUnavailable description")
+#define WebKitErrorDescriptionPlugInCancelledConnection UI_STRING("Plug-in cancelled", "WebKitErrorPlugInCancelledConnection description")
+#define WebKitErrorDescriptionPlugInWillHandleLoad UI_STRING("Plug-in handled load", "WebKitErrorPlugInWillHandleLoad description")
+
+static pthread_once_t registerErrorsControl = PTHREAD_ONCE_INIT;
+static void registerErrors(void);
+
+@implementation NSError (WebKitExtras)
+
+static NSMutableDictionary *descriptions = nil;
+
++ (void)_registerWebKitErrors
+{
+ pthread_once(&registerErrorsControl, registerErrors);
+}
+
+-(id)_webkit_initWithDomain:(NSString *)domain code:(int)code URL:(NSURL *)URL
+{
+ NSDictionary *descriptionsDict;
+ NSString *localizedDesc;
+ NSDictionary *dict;
+ // insert a localized string here for those folks not savvy to our category methods
+ descriptionsDict = [descriptions objectForKey:domain];
+ localizedDesc = descriptionsDict ? [descriptionsDict objectForKey:[NSNumber numberWithInt:code]] : nil;
+ dict = [NSDictionary dictionaryWithObjectsAndKeys:
+ URL, @"NSErrorFailingURLKey",
+ [URL absoluteString], @"NSErrorFailingURLStringKey",
+ localizedDesc, NSLocalizedDescriptionKey,
+ nil];
+ return [self initWithDomain:domain code:code userInfo:dict];
+}
+
++(id)_webkit_errorWithDomain:(NSString *)domain code:(int)code URL:(NSURL *)URL
+{
+ return [[[self alloc] _webkit_initWithDomain:domain code:code URL:URL] autorelease];
+}
+
++ (NSError *)_webKitErrorWithDomain:(NSString *)domain code:(int)code URL:(NSURL *)URL
+{
+ [self _registerWebKitErrors];
+ return [self _webkit_errorWithDomain:domain code:code URL:URL];
+}
+
++ (NSError *)_webKitErrorWithCode:(int)code failingURL:(NSString *)URLString
+{
+ return [self _webKitErrorWithDomain:WebKitErrorDomain code:code URL:[NSURL _web_URLWithUserTypedString:URLString]];
+}
+
+- (id)_initWithPluginErrorCode:(int)code
+ contentURL:(NSURL *)contentURL
+ pluginPageURL:(NSURL *)pluginPageURL
+ pluginName:(NSString *)pluginName
+ MIMEType:(NSString *)MIMEType
+{
+ [[self class] _registerWebKitErrors];
+
+ NSMutableDictionary *userInfo = [[NSMutableDictionary alloc] init];
+ if (contentURL) {
+ [userInfo setObject:contentURL forKey:@"NSErrorFailingURLKey"];
+ [userInfo setObject:[contentURL _web_userVisibleString] forKey:NSErrorFailingURLStringKey];
+ }
+ if (pluginPageURL) {
+ [userInfo setObject:[pluginPageURL _web_userVisibleString] forKey:WebKitErrorPlugInPageURLStringKey];
+ }
+ if (pluginName) {
+ [userInfo setObject:pluginName forKey:WebKitErrorPlugInNameKey];
+ }
+ if (MIMEType) {
+ [userInfo setObject:MIMEType forKey:WebKitErrorMIMETypeKey];
+ }
+
+ NSDictionary *userInfoCopy = [userInfo count] > 0 ? [[NSDictionary alloc] initWithDictionary:userInfo] : nil;
+ [userInfo release];
+ NSError *error = [self initWithDomain:WebKitErrorDomain code:code userInfo:userInfoCopy];
+ [userInfoCopy release];
+
+ return error;
+}
+
++ (void)_webkit_addErrorsWithCodesAndDescriptions:(NSDictionary *)dictionary inDomain:(NSString *)domain
+{
+ if (!descriptions)
+ descriptions = [[NSMutableDictionary alloc] init];
+
+ [descriptions setObject:dictionary forKey:domain];
+}
+
+static void registerErrors()
+{
+ NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
+
+ NSDictionary *dict = [NSDictionary dictionaryWithObjectsAndKeys:
+ // Policy errors
+ WebKitErrorDescriptionCannotShowMIMEType, [NSNumber numberWithInt: WebKitErrorCannotShowMIMEType],
+ WebKitErrorDescriptionCannotShowURL, [NSNumber numberWithInt: WebKitErrorCannotShowURL],
+ WebKitErrorDescriptionFrameLoadInterruptedByPolicyChange, [NSNumber numberWithInt: WebKitErrorFrameLoadInterruptedByPolicyChange],
+ WebKitErrorDescriptionCannotUseRestrictedPort, [NSNumber numberWithInt: WebKitErrorCannotUseRestrictedPort],
+
+ // Plug-in and java errors
+ WebKitErrorDescriptionCannotFindPlugin, [NSNumber numberWithInt: WebKitErrorCannotFindPlugIn],
+ WebKitErrorDescriptionCannotLoadPlugin, [NSNumber numberWithInt: WebKitErrorCannotLoadPlugIn],
+ WebKitErrorDescriptionJavaUnavailable, [NSNumber numberWithInt: WebKitErrorJavaUnavailable],
+ WebKitErrorDescriptionPlugInCancelledConnection, [NSNumber numberWithInt: WebKitErrorPlugInCancelledConnection],
+ WebKitErrorDescriptionPlugInWillHandleLoad, [NSNumber numberWithInt: WebKitErrorPlugInWillHandleLoad],
+ nil];
+
+ [NSError _webkit_addErrorsWithCodesAndDescriptions:dict inDomain:WebKitErrorDomain];
+
+ [pool drain];
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebKitErrorsPrivate.h b/WebKit/mac/Misc/WebKitErrorsPrivate.h
new file mode 100644
index 0000000..6a98c4e
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitErrorsPrivate.h
@@ -0,0 +1,53 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebKitErrors.h>
+
+#define WebKitErrorPlugInCancelledConnection 203
+// FIXME: WebKitErrorPlugInWillHandleLoad is used for the cancel we do to prevent loading plugin content twice. See <rdar://problem/4258008>
+#define WebKitErrorPlugInWillHandleLoad 204
+
+/*!
+ @enum
+ @abstract Policy errors - Pending Public API Review
+ @constant WebKitErrorCannotUseRestrictedPort
+*/
+enum {
+ WebKitErrorCannotUseRestrictedPort = 103,
+};
+
+@interface NSError (WebKitExtras)
++ (NSError *)_webKitErrorWithCode:(int)code failingURL:(NSString *)URL;
++ (NSError *)_webKitErrorWithDomain:(NSString *)domain code:(int)code URL:(NSURL *)URL;
+
+- (id)_initWithPluginErrorCode:(int)code
+ contentURL:(NSURL *)contentURL
+ pluginPageURL:(NSURL *)pluginPageURL
+ pluginName:(NSString *)pluginName
+ MIMEType:(NSString *)MIMEType;
+@end
diff --git a/WebKit/mac/Misc/WebKitLogging.h b/WebKit/mac/Misc/WebKitLogging.h
new file mode 100644
index 0000000..0bf791c
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitLogging.h
@@ -0,0 +1,85 @@
+/*
+ * Copyright (C) 2005, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <JavaScriptCore/Assertions.h>
+
+#ifndef LOG_CHANNEL_PREFIX
+#define LOG_CHANNEL_PREFIX WebKitLog
+#endif
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+extern WTFLogChannel WebKitLogTiming;
+extern WTFLogChannel WebKitLogLoading;
+extern WTFLogChannel WebKitLogFontCache;
+extern WTFLogChannel WebKitLogFontSubstitution;
+extern WTFLogChannel WebKitLogFontSelection;
+extern WTFLogChannel WebKitLogDownload;
+extern WTFLogChannel WebKitLogDocumentLoad;
+extern WTFLogChannel WebKitLogPlugins;
+extern WTFLogChannel WebKitLogEvents;
+extern WTFLogChannel WebKitLogView;
+extern WTFLogChannel WebKitLogRedirect;
+extern WTFLogChannel WebKitLogPageCache;
+extern WTFLogChannel WebKitLogCacheSizes;
+extern WTFLogChannel WebKitLogFormDelegate;
+extern WTFLogChannel WebKitLogFileDatabaseActivity;
+extern WTFLogChannel WebKitLogHistory;
+extern WTFLogChannel WebKitLogBindings;
+extern WTFLogChannel WebKitLogEncoding;
+extern WTFLogChannel WebKitLogLiveConnect;
+extern WTFLogChannel WebKitLogBackForward;
+extern WTFLogChannel WebKitLogProgress;
+extern WTFLogChannel WebKitLogPluginEvents;
+extern WTFLogChannel WebKitLogIconDatabase;
+extern WTFLogChannel WebKitLogTextInput;
+
+void WebKitInitializeLoggingChannelsIfNecessary(void);
+
+BOOL WebKitRunningOnMainThread(void);
+
+// The ASSERT_MAIN_THREAD() check should be on by default in DEBUG builds
+// To disable it, even in a debug build, define DISABLE_THREAD_CHECK in your project file (or elsewhere globally)
+#if !defined(NDEBUG) && !defined(DISABLE_THREAD_CHECK)
+#define ASSERT_MAIN_THREAD() do \
+ if (!WebKitRunningOnMainThread()) { \
+ WTFReportAssertionFailure(__FILE__, __LINE__, WTF_PRETTY_FUNCTION, "<not running on main thread>"); \
+ CRASH(); \
+ } \
+while (0)
+#else
+#define ASSERT_MAIN_THREAD() ((void)0)
+#endif
+
+void ReportDiscardedDelegateException(SEL delegateSelector, id exception);
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/WebKit/mac/Misc/WebKitLogging.m b/WebKit/mac/Misc/WebKitLogging.m
new file mode 100644
index 0000000..4e4294f
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitLogging.m
@@ -0,0 +1,115 @@
+/*
+ * Copyright (C) 2005, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebKitLogging.h"
+
+WTFLogChannel WebKitLogTextInput = { 0x00000010, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogTiming = { 0x00000020, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogLoading = { 0x00000040, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogFontCache = { 0x00000100, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogFontSubstitution = { 0x00000200, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogDownload = { 0x00000800, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogDocumentLoad = { 0x00001000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogPlugins = { 0x00002000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogEvents = { 0x00010000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogView = { 0x00020000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogRedirect = { 0x00040000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogPageCache = { 0x00080000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogCacheSizes = { 0x00100000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogFormDelegate = { 0x00200000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogFileDatabaseActivity = { 0x00400000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogHistory = { 0x00800000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogBindings = { 0x01000000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogFontSelection = { 0x02000000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogEncoding = { 0x04000000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogLiveConnect = { 0x08000000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogBackForward = { 0x10000000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogProgress = { 0x20000000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogPluginEvents = { 0x40000000, "WebKitLogLevel", WTFLogChannelOff };
+WTFLogChannel WebKitLogIconDatabase = { 0x80000000, "WebKitLogLevel", WTFLogChannelOff };
+
+static void initializeLogChannel(WTFLogChannel *channel)
+{
+ channel->state = WTFLogChannelOff;
+ NSString *logLevelString = [[NSUserDefaults standardUserDefaults] objectForKey:[NSString stringWithUTF8String:channel->defaultName]];
+ if (logLevelString) {
+ unsigned logLevel;
+ if (![[NSScanner scannerWithString:logLevelString] scanHexInt:&logLevel])
+ NSLog(@"unable to parse hex value for %s (%@), logging is off", channel->defaultName, logLevelString);
+ if ((logLevel & channel->mask) == channel->mask)
+ channel->state = WTFLogChannelOn;
+ }
+}
+
+void WebKitInitializeLoggingChannelsIfNecessary()
+{
+ static bool haveInitializedLoggingChannels = false;
+ if (haveInitializedLoggingChannels)
+ return;
+ haveInitializedLoggingChannels = true;
+
+ initializeLogChannel(&WebKitLogTiming);
+ initializeLogChannel(&WebKitLogLoading);
+ initializeLogChannel(&WebKitLogFontCache);
+ initializeLogChannel(&WebKitLogFontSubstitution);
+ initializeLogChannel(&WebKitLogDownload);
+ initializeLogChannel(&WebKitLogDocumentLoad);
+ initializeLogChannel(&WebKitLogPlugins);
+ initializeLogChannel(&WebKitLogEvents);
+ initializeLogChannel(&WebKitLogView);
+ initializeLogChannel(&WebKitLogRedirect);
+ initializeLogChannel(&WebKitLogPageCache);
+ initializeLogChannel(&WebKitLogCacheSizes);
+ initializeLogChannel(&WebKitLogFormDelegate);
+ initializeLogChannel(&WebKitLogFileDatabaseActivity);
+ initializeLogChannel(&WebKitLogHistory);
+ initializeLogChannel(&WebKitLogBindings);
+ initializeLogChannel(&WebKitLogFontSelection);
+ initializeLogChannel(&WebKitLogEncoding);
+ initializeLogChannel(&WebKitLogLiveConnect);
+ initializeLogChannel(&WebKitLogBackForward);
+ initializeLogChannel(&WebKitLogProgress);
+ initializeLogChannel(&WebKitLogPluginEvents);
+ initializeLogChannel(&WebKitLogIconDatabase);
+ initializeLogChannel(&WebKitLogTextInput);
+}
+
+BOOL WebKitRunningOnMainThread()
+{
+ return pthread_main_np() != 0;
+}
+
+void ReportDiscardedDelegateException(SEL delegateSelector, id exception)
+{
+ if ([exception isKindOfClass:[NSException class]])
+ NSLog(@"*** WebKit discarded an uncaught exception in the %s delegate: <%@> %@",
+ sel_getName(delegateSelector), [exception name], [exception reason]);
+ else
+ NSLog(@"*** WebKit discarded an uncaught exception in the %s delegate: %@",
+ sel_getName(delegateSelector), exception);
+}
diff --git a/WebKit/mac/Misc/WebKitNSStringExtras.h b/WebKit/mac/Misc/WebKitNSStringExtras.h
new file mode 100644
index 0000000..d7fe47c
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitNSStringExtras.h
@@ -0,0 +1,57 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@interface NSString (WebKitExtras)
+
+- (void)_web_drawAtPoint:(NSPoint)point font:(NSFont *)font textColor:(NSColor *)textColor;
+- (void)_web_drawDoubledAtPoint:(NSPoint)textPoint withTopColor:(NSColor *)topColor bottomColor:(NSColor *)bottomColor font:(NSFont *)font;
+
+- (float)_web_widthWithFont:(NSFont *)font;
+
+// Handles home directories that have symlinks in their paths.
+// This works around 2774250.
+- (NSString *)_web_stringByAbbreviatingWithTildeInPath;
+
+- (NSString *)_web_stringByStrippingReturnCharacters;
+
++ (NSStringEncoding)_web_encodingForResource:(Handle)resource;
+
+- (BOOL)_webkit_isCaseInsensitiveEqualToString:(NSString *)string;
+- (BOOL)_webkit_hasCaseInsensitivePrefix:(NSString *)suffix;
+- (BOOL)_webkit_hasCaseInsensitiveSuffix:(NSString *)suffix;
+- (BOOL)_webkit_hasCaseInsensitiveSubstring:(NSString *)substring;
+- (NSString *)_webkit_filenameByFixingIllegalCharacters;
+
+- (NSString *)_webkit_stringByTrimmingWhitespace;
+- (NSString *)_webkit_stringByCollapsingNonPrintingCharacters;
+- (NSString *)_webkit_stringByCollapsingWhitespaceCharacters;
+- (NSString *)_webkit_fixedCarbonPOSIXPath;
+
+@end
diff --git a/WebKit/mac/Misc/WebKitNSStringExtras.m b/WebKit/mac/Misc/WebKitNSStringExtras.m
new file mode 100644
index 0000000..940e63c
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitNSStringExtras.m
@@ -0,0 +1,343 @@
+/*
+ * Copyright (C) 2005, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebKitNSStringExtras.h"
+
+#import <WebKit/WebNSObjectExtras.h>
+#import <WebKit/WebNSFileManagerExtras.h>
+
+#import <WebCore/WebCoreNSStringExtras.h>
+#import <WebCore/WebCoreTextRenderer.h>
+
+#import <unicode/uchar.h>
+
+@implementation NSString (WebKitExtras)
+
+static BOOL canUseFastRenderer(const UniChar *buffer, unsigned length)
+{
+ unsigned i;
+ for (i = 0; i < length; i++) {
+ UCharDirection direction = u_charDirection(buffer[i]);
+ if (direction == U_RIGHT_TO_LEFT || direction > U_OTHER_NEUTRAL)
+ return NO;
+ }
+ return YES;
+}
+
+- (void)_web_drawAtPoint:(NSPoint)point font:(NSFont *)font textColor:(NSColor *)textColor;
+{
+ // FIXME: Would be more efficient to change this to C++ and use Vector<UChar, 2048>.
+ unsigned length = [self length];
+ UniChar *buffer = malloc(sizeof(UniChar) * length);
+
+ [self getCharacters:buffer];
+
+ if (canUseFastRenderer(buffer, length)) {
+ // The following is a half-assed attempt to match AppKit's rounding rules for drawAtPoint.
+ // It's probably incorrect for high DPI.
+ // If you change this, be sure to test all the text drawn this way in Safari, including
+ // the status bar, bookmarks bar, tab bar, and activity window.
+ point.y = ceilf(point.y);
+ WebCoreDrawTextAtPoint(buffer, length, point, font, textColor);
+ } else {
+ // WebTextRenderer assumes drawing from baseline.
+ if ([[NSView focusView] isFlipped])
+ point.y -= [font ascender];
+ else {
+ point.y += [font descender];
+ }
+ [self drawAtPoint:point withAttributes:[NSDictionary dictionaryWithObjectsAndKeys:font, NSFontAttributeName, textColor, NSForegroundColorAttributeName, nil]];
+ }
+
+ free(buffer);
+}
+
+- (void)_web_drawDoubledAtPoint:(NSPoint)textPoint
+ withTopColor:(NSColor *)topColor
+ bottomColor:(NSColor *)bottomColor
+ font:(NSFont *)font
+{
+ // turn off font smoothing so translucent text draws correctly (Radar 3118455)
+ [NSGraphicsContext saveGraphicsState];
+ CGContextSetShouldSmoothFonts([[NSGraphicsContext currentContext] graphicsPort], false);
+ [self _web_drawAtPoint:textPoint
+ font:font
+ textColor:bottomColor];
+
+ textPoint.y += 1;
+ [self _web_drawAtPoint:textPoint
+ font:font
+ textColor:topColor];
+ [NSGraphicsContext restoreGraphicsState];
+}
+
+- (float)_web_widthWithFont:(NSFont *)font
+{
+ unsigned length = [self length];
+ float width;
+ UniChar *buffer = (UniChar *)malloc(sizeof(UniChar) * length);
+
+ [self getCharacters:buffer];
+
+ if (canUseFastRenderer(buffer, length))
+ width = WebCoreTextFloatWidth(buffer, length, font);
+ else
+ width = [self sizeWithAttributes:[NSDictionary dictionaryWithObjectsAndKeys:font, NSFontAttributeName, nil]].width;
+
+ free(buffer);
+
+ return width;
+}
+
+- (NSString *)_web_stringByAbbreviatingWithTildeInPath
+{
+ NSString *resolvedHomeDirectory = [NSHomeDirectory() stringByResolvingSymlinksInPath];
+ NSString *path;
+
+ if ([self hasPrefix:resolvedHomeDirectory]) {
+ NSString *relativePath = [self substringFromIndex:[resolvedHomeDirectory length]];
+ path = [NSHomeDirectory() stringByAppendingPathComponent:relativePath];
+ } else {
+ path = self;
+ }
+
+ return [path stringByAbbreviatingWithTildeInPath];
+}
+
+- (NSString *)_web_stringByStrippingReturnCharacters
+{
+ NSMutableString *newString = [[self mutableCopy] autorelease];
+ [newString replaceOccurrencesOfString:@"\r" withString:@"" options:NSLiteralSearch range:NSMakeRange(0, [newString length])];
+ [newString replaceOccurrencesOfString:@"\n" withString:@"" options:NSLiteralSearch range:NSMakeRange(0, [newString length])];
+ return newString;
+}
+
++ (NSStringEncoding)_web_encodingForResource:(Handle)resource
+{
+ short resRef = HomeResFile(resource);
+ if (ResError() != noErr) {
+ return NSMacOSRomanStringEncoding;
+ }
+
+ // Get the FSRef for the current resource file
+ FSRef fref;
+ OSStatus error = FSGetForkCBInfo(resRef, 0, NULL, NULL, NULL, &fref, NULL);
+ if (error != noErr) {
+ return NSMacOSRomanStringEncoding;
+ }
+
+ CFURLRef URL = CFURLCreateFromFSRef(NULL, &fref);
+ if (URL == NULL) {
+ return NSMacOSRomanStringEncoding;
+ }
+
+ NSString *path = [(NSURL *)URL path];
+ CFRelease(URL);
+
+ // Get the lproj directory name
+ path = [path stringByDeletingLastPathComponent];
+ if (![[path pathExtension] _webkit_isCaseInsensitiveEqualToString:@"lproj"]) {
+ return NSMacOSRomanStringEncoding;
+ }
+
+ NSString *directoryName = [[path stringByDeletingPathExtension] lastPathComponent];
+ CFStringRef locale = CFLocaleCreateCanonicalLocaleIdentifierFromString(NULL, (CFStringRef)directoryName);
+ if (locale == NULL) {
+ return NSMacOSRomanStringEncoding;
+ }
+
+ LangCode lang;
+ RegionCode region;
+ error = LocaleStringToLangAndRegionCodes([(NSString *)locale UTF8String], &lang, &region);
+ CFRelease(locale);
+ if (error != noErr) {
+ return NSMacOSRomanStringEncoding;
+ }
+
+ TextEncoding encoding;
+ error = UpgradeScriptInfoToTextEncoding(kTextScriptDontCare, lang, region, NULL, &encoding);
+ if (error != noErr) {
+ return NSMacOSRomanStringEncoding;
+ }
+
+ return CFStringConvertEncodingToNSStringEncoding(encoding);
+}
+
+- (BOOL)_webkit_isCaseInsensitiveEqualToString:(NSString *)string
+{
+ return [self compare:string options:(NSCaseInsensitiveSearch|NSLiteralSearch)] == NSOrderedSame;
+}
+
+-(BOOL)_webkit_hasCaseInsensitivePrefix:(NSString *)prefix
+{
+ return [self rangeOfString:prefix options:(NSCaseInsensitiveSearch | NSAnchoredSearch)].location != NSNotFound;
+}
+
+-(BOOL)_webkit_hasCaseInsensitiveSuffix:(NSString *)suffix
+{
+ return hasCaseInsensitiveSuffix(self, suffix);
+}
+
+-(BOOL)_webkit_hasCaseInsensitiveSubstring:(NSString *)substring
+{
+ return hasCaseInsensitiveSubstring(self, substring);
+}
+
+-(NSString *)_webkit_filenameByFixingIllegalCharacters
+{
+ return filenameByFixingIllegalCharacters(self);
+}
+
+-(NSString *)_webkit_stringByTrimmingWhitespace
+{
+ NSMutableString *trimmed = [[self mutableCopy] autorelease];
+ CFStringTrimWhitespace((CFMutableStringRef)trimmed);
+ return trimmed;
+}
+
+- (NSString *)_webkit_stringByCollapsingNonPrintingCharacters
+{
+ NSMutableString *result = [NSMutableString string];
+ static NSCharacterSet *charactersToTurnIntoSpaces = nil;
+ static NSCharacterSet *charactersToNotTurnIntoSpaces = nil;
+
+ if (charactersToTurnIntoSpaces == nil) {
+ NSMutableCharacterSet *set = [[NSMutableCharacterSet alloc] init];
+ [set addCharactersInRange:NSMakeRange(0x00, 0x21)];
+ [set addCharactersInRange:NSMakeRange(0x7F, 0x01)];
+ charactersToTurnIntoSpaces = [set copy];
+ [set release];
+ charactersToNotTurnIntoSpaces = [[charactersToTurnIntoSpaces invertedSet] retain];
+ }
+
+ unsigned length = [self length];
+ unsigned position = 0;
+ while (position != length) {
+ NSRange nonSpace = [self rangeOfCharacterFromSet:charactersToNotTurnIntoSpaces
+ options:0 range:NSMakeRange(position, length - position)];
+ if (nonSpace.location == NSNotFound) {
+ break;
+ }
+
+ NSRange space = [self rangeOfCharacterFromSet:charactersToTurnIntoSpaces
+ options:0 range:NSMakeRange(nonSpace.location, length - nonSpace.location)];
+ if (space.location == NSNotFound) {
+ space.location = length;
+ }
+
+ if (space.location > nonSpace.location) {
+ if (position != 0) {
+ [result appendString:@" "];
+ }
+ [result appendString:[self substringWithRange:
+ NSMakeRange(nonSpace.location, space.location - nonSpace.location)]];
+ }
+
+ position = space.location;
+ }
+
+ return result;
+}
+
+- (NSString *)_webkit_stringByCollapsingWhitespaceCharacters
+{
+ NSMutableString *result = [[NSMutableString alloc] initWithCapacity:[self length]];
+ NSCharacterSet *spaces = [NSCharacterSet whitespaceAndNewlineCharacterSet];
+ static NSCharacterSet *notSpaces = nil;
+
+ if (notSpaces == nil)
+ notSpaces = [[spaces invertedSet] retain];
+
+ unsigned length = [self length];
+ unsigned position = 0;
+ while (position != length) {
+ NSRange nonSpace = [self rangeOfCharacterFromSet:notSpaces options:0 range:NSMakeRange(position, length - position)];
+ if (nonSpace.location == NSNotFound)
+ break;
+
+ NSRange space = [self rangeOfCharacterFromSet:spaces options:0 range:NSMakeRange(nonSpace.location, length - nonSpace.location)];
+ if (space.location == NSNotFound)
+ space.location = length;
+
+ if (space.location > nonSpace.location) {
+ if (position != 0)
+ [result appendString:@" "];
+ [result appendString:[self substringWithRange:NSMakeRange(nonSpace.location, space.location - nonSpace.location)]];
+ }
+
+ position = space.location;
+ }
+
+ return [result autorelease];
+}
+
+-(NSString *)_webkit_fixedCarbonPOSIXPath
+{
+ NSFileManager *fileManager = [NSFileManager defaultManager];
+ if ([fileManager fileExistsAtPath:self]) {
+ // Files exists, no need to fix.
+ return self;
+ }
+
+ NSMutableArray *pathComponents = [[[self pathComponents] mutableCopy] autorelease];
+ NSString *volumeName = [pathComponents objectAtIndex:1];
+ if ([volumeName isEqualToString:@"Volumes"]) {
+ // Path starts with "/Volumes", so the volume name is the next path component.
+ volumeName = [pathComponents objectAtIndex:2];
+ // Remove "Volumes" from the path because it may incorrectly be part of the path (3163647).
+ // We'll add it back if we have to.
+ [pathComponents removeObjectAtIndex:1];
+ }
+
+ if (!volumeName) {
+ // Should only happen if self == "/", so this shouldn't happen because that always exists.
+ return self;
+ }
+
+ if ([[fileManager _webkit_startupVolumeName] isEqualToString:volumeName]) {
+ // Startup volume name is included in path, remove it.
+ [pathComponents removeObjectAtIndex:1];
+ } else if ([[fileManager directoryContentsAtPath:@"/Volumes"] containsObject:volumeName]) {
+ // Path starts with other volume name, prepend "/Volumes".
+ [pathComponents insertObject:@"Volumes" atIndex:1];
+ } else {
+ // It's valid.
+ return self;
+ }
+
+ NSString *path = [NSString pathWithComponents:pathComponents];
+
+ if (![fileManager fileExistsAtPath:path]) {
+ // File at canonicalized path doesn't exist, return original.
+ return self;
+ }
+
+ return path;
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebKitStatistics.h b/WebKit/mac/Misc/WebKitStatistics.h
new file mode 100644
index 0000000..32241b5
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitStatistics.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@interface WebKitStatistics : NSObject
+
++ (int)webViewCount;
+
++ (int)frameCount;
++ (int)dataSourceCount;
++ (int)viewCount;
++ (int)HTMLRepresentationCount;
++ (int)bridgeCount;
+
+@end
diff --git a/WebKit/mac/Misc/WebKitStatistics.m b/WebKit/mac/Misc/WebKitStatistics.m
new file mode 100644
index 0000000..9b4cd4f
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitStatistics.m
@@ -0,0 +1,72 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebKitStatistics.h"
+
+#import "WebKitStatisticsPrivate.h"
+
+int WebBridgeCount;
+int WebViewCount;
+int WebDataSourceCount;
+int WebFrameCount;
+int WebHTMLRepresentationCount;
+int WebFrameViewCount;
+
+@implementation WebKitStatistics
+
++ (int)webViewCount
+{
+ return WebViewCount;
+}
+
++ (int)frameCount
+{
+ return WebFrameCount;
+}
+
++ (int)dataSourceCount
+{
+ return WebDataSourceCount;
+}
+
++ (int)viewCount
+{
+ return WebFrameViewCount;
+}
+
++ (int)bridgeCount
+{
+ return WebBridgeCount;
+}
+
++ (int)HTMLRepresentationCount
+{
+ return WebHTMLRepresentationCount;
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebKitStatisticsPrivate.h b/WebKit/mac/Misc/WebKitStatisticsPrivate.h
new file mode 100644
index 0000000..ed8ce6a
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitStatisticsPrivate.h
@@ -0,0 +1,34 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+extern int WebBridgeCount;
+extern int WebViewCount;
+extern int WebDataSourceCount;
+extern int WebFrameCount;
+extern int WebHTMLRepresentationCount;
+extern int WebFrameViewCount;
diff --git a/WebKit/mac/Misc/WebKitSystemBits.h b/WebKit/mac/Misc/WebKitSystemBits.h
new file mode 100644
index 0000000..99370e0
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitSystemBits.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+vm_size_t WebMemorySize(void);
+unsigned long long WebVolumeFreeSize(NSString *path);
+int WebNumberOfCPUs(void);
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/WebKit/mac/Misc/WebKitSystemBits.m b/WebKit/mac/Misc/WebKitSystemBits.m
new file mode 100644
index 0000000..afa54f2
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitSystemBits.m
@@ -0,0 +1,85 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebKitSystemBits.h>
+
+#import <JavaScriptCore/Assertions.h>
+
+#include <mach/mach.h>
+#include <mach/host_info.h>
+#include <mach/mach_error.h>
+
+#include <sys/types.h>
+#include <sys/sysctl.h>
+
+static host_basic_info_data_t gHostBasicInfo;
+static pthread_once_t initControl = PTHREAD_ONCE_INIT;
+
+static void initCapabilities(void)
+{
+ mach_msg_type_number_t count;
+ kern_return_t r;
+ mach_port_t host;
+
+ /* Discover our CPU type */
+ host = mach_host_self();
+ count = HOST_BASIC_INFO_COUNT;
+ r = host_info(host, HOST_BASIC_INFO, (host_info_t) &gHostBasicInfo, &count);
+ mach_port_deallocate(mach_task_self(), host);
+ if (r != KERN_SUCCESS) {
+ LOG_ERROR("%s : host_info(%d) : %s.\n", __FUNCTION__, r, mach_error_string(r));
+ }
+}
+
+vm_size_t WebMemorySize(void)
+{
+ pthread_once(&initControl, initCapabilities);
+ return gHostBasicInfo.memory_size;
+}
+
+int WebNumberOfCPUs(void)
+{
+ static int numCPUs = 0;
+
+ if (numCPUs == 0) {
+ int mib[2];
+ size_t len;
+
+ mib[0] = CTL_HW;
+ mib[1] = HW_NCPU;
+ len = sizeof(numCPUs);
+ sysctl(mib, 2, &numCPUs, &len, NULL, 0);
+ }
+ return numCPUs;
+}
+
+unsigned long long WebVolumeFreeSize(NSString *path)
+{
+ NSDictionary *fileSystemAttributesDictionary = [[NSFileManager defaultManager] fileSystemAttributesAtPath:path];
+ return [[fileSystemAttributesDictionary objectForKey:NSFileSystemFreeSize] unsignedLongLongValue];
+}
diff --git a/WebKit/mac/Misc/WebKitVersionChecks.h b/WebKit/mac/Misc/WebKitVersionChecks.h
new file mode 100644
index 0000000..5e3ed90
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitVersionChecks.h
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/*
+ Version numbers are based on the 'current library version' specified in the WebKit build rules.
+ All of these methods return or take version numbers with each part shifted to the left 2 bytes.
+ For example the version 1.2.3 is returned as 0x00010203 and version 200.3.5 is returned as 0x00C80305
+ A version of -1 is returned if the main executable did not link against WebKit (should never happen).
+
+ Please use the current WebKit version number, available in WebKit/Configurations/Version.xcconfig,
+ when adding a new version constant.
+*/
+
+#define WEBKIT_FIRST_VERSION_WITH_3_0_CONTEXT_MENU_TAGS 0x020A0000 // 522.0.0
+#define WEBKIT_FIRST_VERSION_WITH_LOCAL_RESOURCE_SECURITY_RESTRICTION 0x020A0000 // 522.0.0
+#define WEBKIT_FIRST_VERSION_WITHOUT_APERTURE_QUIRK 0x020A0000 // 522.0.0
+#define WEBKIT_FIRST_VERSION_WITHOUT_QUICKBOOKS_QUIRK 0x020A0000 // 522.0.0
+#define WEBKIT_FIRST_VERSION_WITH_MAIN_THREAD_EXCEPTIONS 0x020A0000 // 522.0.0
+#define WEBKIT_FIRST_VERSION_WITHOUT_ADOBE_INSTALLER_QUIRK 0x020A0000 // 522.0.0
+#define WEBKIT_FIRST_VERSION_WITH_INSPECT_ELEMENT_MENU_TAG 0x020A0C00 // 522.12.0
+#define WEBKIT_FIRST_VERSION_WITH_CACHE_MODEL_API 0x020B0500 // 523.5.0
+#define WEBKIT_FIRST_VERSION_WITHOUT_JAVASCRIPT_RETURN_QUIRK 0x020D0100 // 525.1.0
+#define WEBKIT_FIRST_VERSION_WITH_IE_COMPATIBLE_KEYBOARD_EVENT_DISPATCH 0x020D0100 // 525.1.0
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+BOOL WebKitLinkedOnOrAfter(int version);
+int WebKitLinkTimeVersion(void);
+int WebKitRunTimeVersion(void);
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/WebKit/mac/Misc/WebKitVersionChecks.m b/WebKit/mac/Misc/WebKitVersionChecks.m
new file mode 100644
index 0000000..5659273
--- /dev/null
+++ b/WebKit/mac/Misc/WebKitVersionChecks.m
@@ -0,0 +1,45 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebKitVersionChecks.h"
+#import <mach-o/dyld.h>
+
+BOOL WebKitLinkedOnOrAfter(int version)
+{
+ return (WebKitLinkTimeVersion() >= version);
+}
+
+int WebKitLinkTimeVersion(void)
+{
+ return NSVersionOfLinkTimeLibrary("WebKit");
+}
+
+int WebKitRunTimeVersion(void)
+{
+ return NSVersionOfRunTimeLibrary("WebKit");
+}
diff --git a/WebKit/mac/Misc/WebLocalizableStrings.h b/WebKit/mac/Misc/WebLocalizableStrings.h
new file mode 100644
index 0000000..ecad83d
--- /dev/null
+++ b/WebKit/mac/Misc/WebLocalizableStrings.h
@@ -0,0 +1,68 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#if __OBJC__
+@class NSBundle;
+#else
+typedef struct NSBundle NSBundle;
+#endif
+
+typedef struct {
+ const char *identifier;
+ NSBundle *bundle;
+} WebLocalizableStringsBundle;
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+#if __OBJC__
+NSString *WebLocalizedString(WebLocalizableStringsBundle *bundle, const char *key);
+#else
+CFStringRef WebLocalizedString(WebLocalizableStringsBundle *bundle, const char *key);
+#endif
+
+#ifdef __cplusplus
+}
+#endif
+
+#ifdef FRAMEWORK_NAME
+
+#define LOCALIZABLE_STRINGS_BUNDLE(F) LOCALIZABLE_STRINGS_BUNDLE_HELPER(F)
+#define LOCALIZABLE_STRINGS_BUNDLE_HELPER(F) F ## LocalizableStringsBundle
+extern WebLocalizableStringsBundle LOCALIZABLE_STRINGS_BUNDLE(FRAMEWORK_NAME);
+
+#define UI_STRING(string, comment) WebLocalizedString(&LOCALIZABLE_STRINGS_BUNDLE(FRAMEWORK_NAME), string)
+#define UI_STRING_KEY(string, key, comment) WebLocalizedString(&LOCALIZABLE_STRINGS_BUNDLE(FRAMEWORK_NAME), key)
+
+#else
+
+#define UI_STRING(string, comment) WebLocalizedString(0, string)
+#define UI_STRING_KEY(string, key, comment) WebLocalizedString(0, key)
+
+#endif
diff --git a/WebKit/mac/Misc/WebLocalizableStrings.m b/WebKit/mac/Misc/WebLocalizableStrings.m
new file mode 100644
index 0000000..6e95be1
--- /dev/null
+++ b/WebKit/mac/Misc/WebLocalizableStrings.m
@@ -0,0 +1,60 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebLocalizableStrings.h>
+
+#import <JavaScriptCore/Assertions.h>
+
+WebLocalizableStringsBundle WebKitLocalizableStringsBundle = { "com.apple.WebKit", 0 };
+
+NSString *WebLocalizedString(WebLocalizableStringsBundle *stringsBundle, const char *key)
+{
+ NSBundle *bundle;
+ if (stringsBundle == NULL) {
+ static NSBundle *mainBundle;
+ if (mainBundle == nil) {
+ mainBundle = [NSBundle mainBundle];
+ ASSERT(mainBundle);
+ CFRetain(mainBundle);
+ }
+ bundle = mainBundle;
+ } else {
+ bundle = stringsBundle->bundle;
+ if (bundle == nil) {
+ bundle = [NSBundle bundleWithIdentifier:[NSString stringWithUTF8String:stringsBundle->identifier]];
+ ASSERT(bundle);
+ stringsBundle->bundle = bundle;
+ }
+ }
+ NSString *notFound = @"localized string not found";
+ CFStringRef keyString = CFStringCreateWithCStringNoCopy(NULL, key, kCFStringEncodingUTF8, kCFAllocatorNull);
+ NSString *result = [bundle localizedStringForKey:(NSString *)keyString value:notFound table:nil];
+ CFRelease(keyString);
+ ASSERT_WITH_MESSAGE(result != notFound, "could not find localizable string %s in bundle", key);
+ return result;
+}
diff --git a/WebKit/mac/Misc/WebNSArrayExtras.h b/WebKit/mac/Misc/WebNSArrayExtras.h
new file mode 100644
index 0000000..5e3294d
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSArrayExtras.h
@@ -0,0 +1,36 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+
+@interface NSMutableArray (WebNSArrayExtras)
+
+- (void)_webkit_removeUselessMenuItemSeparators;
+
+@end
diff --git a/WebKit/mac/Misc/WebNSArrayExtras.m b/WebKit/mac/Misc/WebNSArrayExtras.m
new file mode 100644
index 0000000..efc655e
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSArrayExtras.m
@@ -0,0 +1,58 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNSArrayExtras.h"
+
+#import <JavaScriptCore/Assertions.h>
+
+@implementation NSMutableArray (WebExtras)
+
+- (void)_webkit_removeUselessMenuItemSeparators
+{
+ // Starting with a mutable array of NSMenuItems, removes any separators at the start,
+ // removes any separators at the end, and collapses any other adjacent separators to
+ // a single separator.
+
+ int index;
+ // Start this with YES so very last item will be removed if it's a separator.
+ BOOL removePreviousItemIfSeparator = YES;
+ for (index = [self count] - 1; index >= 0; --index) {
+ NSMenuItem *item = [self objectAtIndex:index];
+ ASSERT([item isKindOfClass:[NSMenuItem class]]);
+ BOOL itemIsSeparator = [item isSeparatorItem];
+ if (itemIsSeparator && (removePreviousItemIfSeparator || index == 0))
+ [self removeObjectAtIndex:index];
+ removePreviousItemIfSeparator = itemIsSeparator;
+ }
+
+ // This could leave us with one initial separator; kill it off too
+ if ([self count] && [[self objectAtIndex:0] isSeparatorItem])
+ [self removeObjectAtIndex:0];
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSAttributedStringExtras.h b/WebKit/mac/Misc/WebNSAttributedStringExtras.h
new file mode 100644
index 0000000..a4ee9fc
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSAttributedStringExtras.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+namespace WebCore {
+ class Range;
+}
+
+@interface NSAttributedString (WebKitExtras)
+
++ (NSAttributedString *)_web_attributedStringFromRange:(WebCore::Range*)range;
+- (NSAttributedString *)_web_attributedStringByStrippingAttachmentCharacters;
+
+@end
diff --git a/WebKit/mac/Misc/WebNSAttributedStringExtras.mm b/WebKit/mac/Misc/WebNSAttributedStringExtras.mm
new file mode 100644
index 0000000..5e50109
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSAttributedStringExtras.mm
@@ -0,0 +1,556 @@
+/*
+ * Copyright (C) 2005, 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNSAttributedStringExtras.h"
+
+#import "DOMRangeInternal.h"
+#import "WebDataSourcePrivate.h"
+#import "WebFrame.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import <WebCore/BlockExceptions.h>
+#import <WebCore/ColorMac.h>
+#import <WebCore/CSSHelper.h>
+#import <WebCore/Document.h>
+#import <WebCore/Element.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/HTMLNames.h>
+#import <WebCore/Image.h>
+#import <WebCore/InlineTextBox.h>
+#import <WebCore/KURL.h>
+#import <WebCore/Range.h>
+#import <WebCore/RenderImage.h>
+#import <WebCore/RenderListItem.h>
+#import <WebCore/RenderObject.h>
+#import <WebCore/RenderStyle.h>
+#import <WebCore/RenderText.h>
+#import <WebCore/SimpleFontData.h>
+#import <WebCore/Text.h>
+
+using namespace WebCore;
+using namespace HTMLNames;
+
+struct ListItemInfo {
+ unsigned start;
+ unsigned end;
+};
+
+static Element* listParent(Element* item)
+{
+ while (!item->hasTagName(ulTag) && !item->hasTagName(olTag)) {
+ item = static_cast<Element*>(item->parentNode());
+ if (!item)
+ break;
+ }
+ return item;
+}
+
+static Node* isTextFirstInListItem(Node* e)
+{
+ if (!e->isTextNode())
+ return 0;
+ Node* par = e->parentNode();
+ while (par) {
+ if (par->firstChild() != e)
+ return 0;
+ if (par->hasTagName(liTag))
+ return par;
+ e = par;
+ par = par->parentNode();
+ }
+ return 0;
+}
+
+static NSFileWrapper *fileWrapperForElement(Element* e)
+{
+ NSFileWrapper *wrapper = nil;
+ BEGIN_BLOCK_OBJC_EXCEPTIONS;
+
+ const AtomicString& attr = e->getAttribute(srcAttr);
+ if (!attr.isEmpty()) {
+ NSURL *URL = e->document()->completeURL(attr);
+ wrapper = [[kit(e->document()->frame()) _dataSource] _fileWrapperForURL:URL];
+ }
+ if (!wrapper) {
+ RenderImage* renderer = static_cast<RenderImage*>(e->renderer());
+ if (renderer->cachedImage() && !renderer->cachedImage()->errorOccurred()) {
+ wrapper = [[NSFileWrapper alloc] initRegularFileWithContents:(NSData *)(renderer->cachedImage()->image()->getTIFFRepresentation())];
+ [wrapper setPreferredFilename:@"image.tiff"];
+ [wrapper autorelease];
+ }
+ }
+
+ return wrapper;
+
+ END_BLOCK_OBJC_EXCEPTIONS;
+
+ return nil;
+}
+
+@implementation NSAttributedString (WebKitExtras)
+
+- (NSAttributedString *)_web_attributedStringByStrippingAttachmentCharacters
+{
+ // This code was originally copied from NSTextView
+ NSRange attachmentRange;
+ NSString *originalString = [self string];
+ static NSString *attachmentCharString = nil;
+
+ if (!attachmentCharString) {
+ unichar chars[2];
+ if (!attachmentCharString) {
+ chars[0] = NSAttachmentCharacter;
+ chars[1] = 0;
+ attachmentCharString = [[NSString alloc] initWithCharacters:chars length:1];
+ }
+ }
+
+ attachmentRange = [originalString rangeOfString:attachmentCharString];
+ if (attachmentRange.location != NSNotFound && attachmentRange.length > 0) {
+ NSMutableAttributedString *newAttributedString = [[self mutableCopyWithZone:NULL] autorelease];
+
+ while (attachmentRange.location != NSNotFound && attachmentRange.length > 0) {
+ [newAttributedString replaceCharactersInRange:attachmentRange withString:@""];
+ attachmentRange = [[newAttributedString string] rangeOfString:attachmentCharString];
+ }
+ return newAttributedString;
+ }
+
+ return self;
+}
+
+// FIXME: Use WebCore::TextIterator to iterate text runs.
+
++ (NSAttributedString *)_web_attributedStringFromRange:(Range*)range
+{
+ ListItemInfo info;
+ ExceptionCode ec = 0; // dummy variable -- we ignore DOM exceptions
+ NSMutableAttributedString *result;
+ BEGIN_BLOCK_OBJC_EXCEPTIONS;
+
+ if (!range || !range->boundaryPointsValid())
+ return nil;
+
+ Node* firstNode = range->startNode();
+ if (!firstNode)
+ return nil;
+ Node* pastEndNode = range->pastEndNode();
+
+ int startOffset = range->startOffset(ec);
+ int endOffset = range->endOffset(ec);
+ Node* endNode = range->endContainer(ec);
+
+ result = [[[NSMutableAttributedString alloc] init] autorelease];
+
+ bool hasNewLine = true;
+ bool addedSpace = true;
+ NSAttributedString *pendingStyledSpace = nil;
+ bool hasParagraphBreak = true;
+ const Element *linkStartNode = 0;
+ unsigned linkStartLocation = 0;
+ Vector<Element*> listItems;
+ Vector<ListItemInfo> listItemLocations;
+ float maxMarkerWidth = 0;
+
+ Node *currentNode = firstNode;
+
+ // If the first item is the entire text of a list item, use the list item node as the start of the
+ // selection, not the text node. The user's intent was probably to select the list.
+ if (currentNode->isTextNode() && startOffset == 0) {
+ Node *startListNode = isTextFirstInListItem(firstNode);
+ if (startListNode){
+ firstNode = startListNode;
+ currentNode = firstNode;
+ }
+ }
+
+ while (currentNode && currentNode != pastEndNode) {
+ RenderObject *renderer = currentNode->renderer();
+ if (renderer) {
+ RenderStyle *style = renderer->style();
+ NSFont *font = style->font().primaryFont()->getNSFont();
+ bool needSpace = pendingStyledSpace != nil;
+ if (currentNode->isTextNode()) {
+ if (hasNewLine) {
+ addedSpace = true;
+ needSpace = false;
+ [pendingStyledSpace release];
+ pendingStyledSpace = nil;
+ hasNewLine = false;
+ }
+ String text;
+ String str = currentNode->nodeValue();
+ int start = (currentNode == firstNode) ? startOffset : -1;
+ int end = (currentNode == endNode) ? endOffset : -1;
+ if (renderer->isText()) {
+ if (!style->collapseWhiteSpace()) {
+ if (needSpace && !addedSpace) {
+ if (text.isEmpty() && linkStartLocation == [result length])
+ ++linkStartLocation;
+ [result appendAttributedString:pendingStyledSpace];
+ }
+ int runStart = (start == -1) ? 0 : start;
+ int runEnd = (end == -1) ? str.length() : end;
+ text += str.substring(runStart, runEnd-runStart);
+ [pendingStyledSpace release];
+ pendingStyledSpace = nil;
+ addedSpace = u_charDirection(str.characters()[runEnd - 1]) == U_WHITE_SPACE_NEUTRAL;
+ }
+ else {
+ RenderText* textObj = static_cast<RenderText*>(renderer);
+ if (!textObj->firstTextBox() && str.length() > 0 && !addedSpace) {
+ // We have no runs, but we do have a length. This means we must be
+ // whitespace that collapsed away at the end of a line.
+ text.append(' ');
+ addedSpace = true;
+ }
+ else {
+ addedSpace = false;
+ for (InlineTextBox* box = textObj->firstTextBox(); box; box = box->nextTextBox()) {
+ int runStart = (start == -1) ? box->m_start : start;
+ int runEnd = (end == -1) ? box->m_start + box->m_len : end;
+ if (runEnd > box->m_start + box->m_len)
+ runEnd = box->m_start + box->m_len;
+ if (runStart >= box->m_start &&
+ runStart < box->m_start + box->m_len) {
+ if (box == textObj->firstTextBox() && box->m_start == runStart && runStart > 0)
+ needSpace = true; // collapsed space at the start
+ if (needSpace && !addedSpace) {
+ if (pendingStyledSpace != nil) {
+ if (text.isEmpty() && linkStartLocation == [result length])
+ ++linkStartLocation;
+ [result appendAttributedString:pendingStyledSpace];
+ } else
+ text.append(' ');
+ }
+ String runText = str.substring(runStart, runEnd - runStart);
+ runText.replace('\n', ' ');
+ text += runText;
+ int nextRunStart = box->nextTextBox() ? box->nextTextBox()->m_start : str.length(); // collapsed space between runs or at the end
+ needSpace = nextRunStart > runEnd;
+ [pendingStyledSpace release];
+ pendingStyledSpace = nil;
+ addedSpace = u_charDirection(str.characters()[runEnd - 1]) == U_WHITE_SPACE_NEUTRAL;
+ start = -1;
+ }
+ if (end != -1 && runEnd >= end)
+ break;
+ }
+ }
+ }
+ }
+
+ text.replace('\\', renderer->backslashAsCurrencySymbol());
+
+ if (text.length() > 0 || needSpace) {
+ NSMutableDictionary *attrs = [[NSMutableDictionary alloc] init];
+ [attrs setObject:font forKey:NSFontAttributeName];
+ if (style && style->color().isValid() && style->color().alpha() != 0)
+ [attrs setObject:nsColor(style->color()) forKey:NSForegroundColorAttributeName];
+ if (style && style->backgroundColor().isValid() && style->backgroundColor().alpha() != 0)
+ [attrs setObject:nsColor(style->backgroundColor()) forKey:NSBackgroundColorAttributeName];
+
+ if (text.length() > 0) {
+ hasParagraphBreak = false;
+ NSAttributedString *partialString = [[NSAttributedString alloc] initWithString:text attributes:attrs];
+ [result appendAttributedString: partialString];
+ [partialString release];
+ }
+
+ if (needSpace) {
+ [pendingStyledSpace release];
+ pendingStyledSpace = [[NSAttributedString alloc] initWithString:@" " attributes:attrs];
+ }
+
+ [attrs release];
+ }
+ } else {
+ // This is our simple HTML -> ASCII transformation:
+ String text;
+ if (currentNode->hasTagName(aTag)) {
+ // Note the start of the <a> element. We will add the NSLinkAttributeName
+ // attribute to the attributed string when navigating to the next sibling
+ // of this node.
+ linkStartLocation = [result length];
+ linkStartNode = static_cast<Element*>(currentNode);
+ } else if (currentNode->hasTagName(brTag)) {
+ text.append('\n');
+ hasNewLine = true;
+ } else if (currentNode->hasTagName(liTag)) {
+ String listText;
+ Element *itemParent = listParent(static_cast<Element*>(currentNode));
+
+ if (!hasNewLine)
+ listText.append('\n');
+ hasNewLine = true;
+
+ listItems.append(static_cast<Element*>(currentNode));
+ info.start = [result length];
+ info.end = 0;
+ listItemLocations.append (info);
+
+ listText.append('\t');
+ if (itemParent && renderer->isListItem()) {
+ RenderListItem* listRenderer = static_cast<RenderListItem*>(renderer);
+
+ maxMarkerWidth = MAX([font pointSize], maxMarkerWidth);
+
+ String marker = listRenderer->markerText();
+ if (!marker.isEmpty()) {
+ listText.append(marker);
+ // Use AppKit metrics, since this will be rendered by AppKit.
+ NSString *markerNSString = marker;
+ float markerWidth = [markerNSString sizeWithAttributes:[NSDictionary dictionaryWithObject:font forKey:NSFontAttributeName]].width;
+ maxMarkerWidth = MAX(markerWidth, maxMarkerWidth);
+ }
+
+ listText.append(' ');
+ listText.append('\t');
+
+ NSMutableDictionary *attrs = [[NSMutableDictionary alloc] init];
+ [attrs setObject:font forKey:NSFontAttributeName];
+ if (style && style->color().isValid())
+ [attrs setObject:nsColor(style->color()) forKey:NSForegroundColorAttributeName];
+ if (style && style->backgroundColor().isValid())
+ [attrs setObject:nsColor(style->backgroundColor()) forKey:NSBackgroundColorAttributeName];
+
+ NSAttributedString *partialString = [[NSAttributedString alloc] initWithString:listText attributes:attrs];
+ [attrs release];
+ [result appendAttributedString: partialString];
+ [partialString release];
+ }
+ } else if (currentNode->hasTagName(olTag) || currentNode->hasTagName(ulTag)) {
+ if (!hasNewLine)
+ text.append('\n');
+ hasNewLine = true;
+ } else if (currentNode->hasTagName(blockquoteTag)
+ || currentNode->hasTagName(ddTag)
+ || currentNode->hasTagName(divTag)
+ || currentNode->hasTagName(dlTag)
+ || currentNode->hasTagName(dtTag)
+ || currentNode->hasTagName(hrTag)
+ || currentNode->hasTagName(listingTag)
+ || currentNode->hasTagName(preTag)
+ || currentNode->hasTagName(tdTag)
+ || currentNode->hasTagName(thTag)) {
+ if (!hasNewLine)
+ text.append('\n');
+ hasNewLine = true;
+ } else if (currentNode->hasTagName(h1Tag)
+ || currentNode->hasTagName(h2Tag)
+ || currentNode->hasTagName(h3Tag)
+ || currentNode->hasTagName(h4Tag)
+ || currentNode->hasTagName(h5Tag)
+ || currentNode->hasTagName(h6Tag)
+ || currentNode->hasTagName(pTag)
+ || currentNode->hasTagName(trTag)) {
+ if (!hasNewLine)
+ text.append('\n');
+
+ // In certain cases, emit a paragraph break.
+ int bottomMargin = renderer->collapsedMarginBottom();
+ int fontSize = style->fontDescription().computedPixelSize();
+ if (bottomMargin * 2 >= fontSize) {
+ if (!hasParagraphBreak) {
+ text.append('\n');
+ hasParagraphBreak = true;
+ }
+ }
+
+ hasNewLine = true;
+ } else if (currentNode->hasTagName(imgTag)) {
+ if (pendingStyledSpace != nil) {
+ if (linkStartLocation == [result length])
+ ++linkStartLocation;
+ [result appendAttributedString:pendingStyledSpace];
+ [pendingStyledSpace release];
+ pendingStyledSpace = nil;
+ }
+ NSFileWrapper *fileWrapper = fileWrapperForElement(static_cast<Element*>(currentNode));
+ NSTextAttachment *attachment = [[NSTextAttachment alloc] initWithFileWrapper:fileWrapper];
+ NSAttributedString *iString = [NSAttributedString attributedStringWithAttachment:attachment];
+ [result appendAttributedString: iString];
+ [attachment release];
+ }
+
+ NSAttributedString *partialString = [[NSAttributedString alloc] initWithString:text];
+ [result appendAttributedString: partialString];
+ [partialString release];
+ }
+ }
+
+ Node* nextNode = currentNode->firstChild();
+ if (!nextNode)
+ nextNode = currentNode->nextSibling();
+
+ while (!nextNode && currentNode->parentNode()) {
+ String text;
+ currentNode = currentNode->parentNode();
+ if (currentNode == pastEndNode)
+ break;
+ nextNode = currentNode->nextSibling();
+
+ if (currentNode->hasTagName(aTag)) {
+ // End of a <a> element. Create an attributed string NSLinkAttributeName attribute
+ // for the range of the link. Note that we create the attributed string from the DOM, which
+ // will have corrected any illegally nested <a> elements.
+ if (linkStartNode && currentNode == linkStartNode) {
+ NSURL *URL = linkStartNode->document()->frame()->loader()->completeURL(parseURL(linkStartNode->getAttribute(hrefAttr)));
+ NSRange tempRange = { linkStartLocation, [result length]-linkStartLocation }; // workaround for 4213314
+ [result addAttribute:NSLinkAttributeName value:URL range:tempRange];
+ linkStartNode = 0;
+ }
+ } else if (currentNode->hasTagName(olTag) || currentNode->hasTagName(ulTag)) {
+ if (!hasNewLine)
+ text.append('\n');
+ hasNewLine = true;
+ } else if (currentNode->hasTagName(liTag)) {
+
+ int i, count = listItems.size();
+ for (i = 0; i < count; i++){
+ if (listItems[i] == currentNode){
+ listItemLocations[i].end = [result length];
+ break;
+ }
+ }
+ if (!hasNewLine)
+ text.append('\n');
+ hasNewLine = true;
+ } else if (currentNode->hasTagName(blockquoteTag) ||
+ currentNode->hasTagName(ddTag) ||
+ currentNode->hasTagName(divTag) ||
+ currentNode->hasTagName(dlTag) ||
+ currentNode->hasTagName(dtTag) ||
+ currentNode->hasTagName(hrTag) ||
+ currentNode->hasTagName(listingTag) ||
+ currentNode->hasTagName(preTag) ||
+ currentNode->hasTagName(tdTag) ||
+ currentNode->hasTagName(thTag)) {
+ if (!hasNewLine)
+ text.append('\n');
+ hasNewLine = true;
+ } else if (currentNode->hasTagName(pTag) ||
+ currentNode->hasTagName(trTag) ||
+ currentNode->hasTagName(h1Tag) ||
+ currentNode->hasTagName(h2Tag) ||
+ currentNode->hasTagName(h3Tag) ||
+ currentNode->hasTagName(h4Tag) ||
+ currentNode->hasTagName(h5Tag) ||
+ currentNode->hasTagName(h6Tag)) {
+ if (!hasNewLine)
+ text.append('\n');
+ // An extra newline is needed at the start, not the end, of these types of tags,
+ // so don't add another here.
+ hasNewLine = true;
+ }
+
+ NSAttributedString *partialString = [[NSAttributedString alloc] initWithString:text];
+ [result appendAttributedString:partialString];
+ [partialString release];
+ }
+
+ currentNode = nextNode;
+ }
+
+ [pendingStyledSpace release];
+
+ // Apply paragraph styles from outside in. This ensures that nested lists correctly
+ // override their parent's paragraph style.
+ {
+ unsigned i, count = listItems.size();
+ Element *e;
+
+#ifdef POSITION_LIST
+ Node *containingBlock;
+ int containingBlockX, containingBlockY;
+
+ // Determine the position of the outermost containing block. All paragraph
+ // styles and tabs should be relative to this position. So, the horizontal position of
+ // each item in the list (in the resulting attributed string) will be relative to position
+ // of the outermost containing block.
+ if (count > 0){
+ containingBlock = firstNode;
+ while (containingBlock->renderer()->isInline()){
+ containingBlock = containingBlock->parentNode();
+ }
+ containingBlock->renderer()->absolutePosition(containingBlockX, containingBlockY);
+ }
+#endif
+
+ for (i = 0; i < count; i++){
+ e = listItems[i];
+ info = listItemLocations[i];
+
+ if (info.end < info.start)
+ info.end = [result length];
+
+ RenderObject *r = e->renderer();
+ RenderStyle *style = r->style();
+
+ int rx;
+ NSFont *font = style->font().primaryFont()->getNSFont();
+ float pointSize = [font pointSize];
+
+#ifdef POSITION_LIST
+ int ry;
+ r->absolutePosition(rx, ry);
+ rx -= containingBlockX;
+
+ // Ensure that the text is indented at least enough to allow for the markers.
+ rx = MAX(rx, (int)maxMarkerWidth);
+#else
+ rx = (int)MAX(maxMarkerWidth, pointSize);
+#endif
+
+ // The bullet text will be right aligned at the first tab marker, followed
+ // by a space, followed by the list item text. The space is arbitrarily
+ // picked as pointSize*2/3. The space on the first line of the text item
+ // is established by a left aligned tab, on subsequent lines it's established
+ // by the head indent.
+ NSMutableParagraphStyle *mps = [[NSMutableParagraphStyle alloc] init];
+ [mps setFirstLineHeadIndent: 0];
+ [mps setHeadIndent: rx];
+ [mps setTabStops:[NSArray arrayWithObjects:
+ [[[NSTextTab alloc] initWithType:NSRightTabStopType location:rx-(pointSize*2/3)] autorelease],
+ [[[NSTextTab alloc] initWithType:NSLeftTabStopType location:rx] autorelease],
+ nil]];
+ NSRange tempRange = { info.start, info.end-info.start }; // workaround for 4213314
+ [result addAttribute:NSParagraphStyleAttributeName value:mps range:tempRange];
+ [mps release];
+ }
+ }
+
+ return result;
+
+ END_BLOCK_OBJC_EXCEPTIONS;
+
+ return nil;
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSControlExtras.h b/WebKit/mac/Misc/WebNSControlExtras.h
new file mode 100644
index 0000000..cf4cfa6
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSControlExtras.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@interface NSControl (WebExtras)
+- (void)sizeToFitAndAdjustWindowHeight;
+@end
diff --git a/WebKit/mac/Misc/WebNSControlExtras.m b/WebKit/mac/Misc/WebNSControlExtras.m
new file mode 100644
index 0000000..733269b
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSControlExtras.m
@@ -0,0 +1,50 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNSControlExtras.h"
+
+@implementation NSControl (WebExtras)
+
+- (void)sizeToFitAndAdjustWindowHeight
+{
+ NSRect frame = [self frame];
+
+ NSSize bestSize = [[self cell] cellSizeForBounds:NSMakeRect(0.0f, 0.0f, frame.size.width, 10000.0f)];
+
+ float heightDelta = bestSize.height - frame.size.height;
+
+ frame.size.height += heightDelta;
+ frame.origin.y -= heightDelta;
+ [self setFrame:frame];
+
+ NSRect windowFrame = [[self window] frame];
+ windowFrame.size.height += heightDelta;
+ [[self window] setFrame:windowFrame display:NO];
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSDataExtras.h b/WebKit/mac/Misc/WebNSDataExtras.h
new file mode 100644
index 0000000..d6ce829
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSDataExtras.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+#define WEB_GUESS_MIME_TYPE_PEEK_LENGTH 1024
+
+@interface NSData (WebNSDataExtras)
+
+-(BOOL)_web_isCaseInsensitiveEqualToCString:(const char *)string;
+-(NSMutableDictionary *)_webkit_parseRFC822HeaderFields;
+
+@end
diff --git a/WebKit/mac/Misc/WebNSDataExtras.m b/WebKit/mac/Misc/WebNSDataExtras.m
new file mode 100644
index 0000000..a10efcd
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSDataExtras.m
@@ -0,0 +1,395 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebNSDataExtras.h>
+#import <WebKit/WebNSDataExtrasPrivate.h>
+
+#import <JavaScriptCore/Assertions.h>
+
+@interface NSString (WebNSDataExtrasInternal)
+- (NSString *)_web_capitalizeRFC822HeaderFieldName;
+@end
+
+@implementation NSString (WebNSDataExtrasInternal)
+
+-(NSString *)_web_capitalizeRFC822HeaderFieldName
+{
+ CFStringRef name = (CFStringRef)self;
+ NSString *result = nil;
+
+ CFIndex i;
+ CFIndex len = CFStringGetLength(name);
+ char *charPtr = NULL;
+ UniChar *uniCharPtr = NULL;
+ Boolean useUniCharPtr = FALSE;
+ Boolean shouldCapitalize = TRUE;
+ Boolean somethingChanged = FALSE;
+
+ for (i = 0; i < len; i ++) {
+ UniChar ch = CFStringGetCharacterAtIndex(name, i);
+ Boolean replace = FALSE;
+ if (shouldCapitalize && ch >= 'a' && ch <= 'z') {
+ ch = ch + 'A' - 'a';
+ replace = TRUE;
+ }
+ else if (!shouldCapitalize && ch >= 'A' && ch <= 'Z') {
+ ch = ch + 'a' - 'A';
+ replace = TRUE;
+ }
+ if (replace) {
+ if (!somethingChanged) {
+ somethingChanged = TRUE;
+ if (CFStringGetBytes(name, CFRangeMake(0, len), kCFStringEncodingISOLatin1, 0, FALSE, NULL, 0, NULL) == len) {
+ // Can be encoded in ISOLatin1
+ useUniCharPtr = FALSE;
+ charPtr = CFAllocatorAllocate(NULL, len + 1, 0);
+ CFStringGetCString(name, charPtr, len+1, kCFStringEncodingISOLatin1);
+ }
+ else {
+ useUniCharPtr = TRUE;
+ uniCharPtr = CFAllocatorAllocate(NULL, len * sizeof(UniChar), 0);
+ CFStringGetCharacters(name, CFRangeMake(0, len), uniCharPtr);
+ }
+ }
+ if (useUniCharPtr) {
+ uniCharPtr[i] = ch;
+ }
+ else {
+ charPtr[i] = ch;
+ }
+ }
+ if (ch == '-') {
+ shouldCapitalize = TRUE;
+ }
+ else {
+ shouldCapitalize = FALSE;
+ }
+ }
+ if (somethingChanged) {
+ if (useUniCharPtr) {
+ result = (NSString *)CFMakeCollectable(CFStringCreateWithCharactersNoCopy(NULL, uniCharPtr, len, NULL));
+ }
+ else {
+ result = (NSString *)CFMakeCollectable(CFStringCreateWithCStringNoCopy(NULL, charPtr, kCFStringEncodingISOLatin1, NULL));
+ }
+ }
+ else {
+ result = [self retain];
+ }
+
+ return [result autorelease];
+}
+
+@end
+
+@implementation NSData (WebKitExtras)
+
+-(NSString *)_webkit_guessedMIMETypeForXML
+{
+ int length = [self length];
+ const UInt8 *bytes = [self bytes];
+
+#define CHANNEL_TAG_LENGTH 7
+
+ const char *p = (const char *)bytes;
+ int remaining = MIN(length, WEB_GUESS_MIME_TYPE_PEEK_LENGTH) - (CHANNEL_TAG_LENGTH - 1);
+
+ BOOL foundRDF = false;
+
+ while (remaining > 0) {
+ // Look for a "<".
+ const char *hit = memchr(p, '<', remaining);
+ if (!hit) {
+ break;
+ }
+
+ // We are trying to identify RSS or Atom. RSS has a top-level
+ // element of either <rss> or <rdf>. However, there are
+ // non-RSS RDF files, so in the case of <rdf> we further look
+ // for a <channel> element. In the case of an Atom file, a
+ // top-level <feed> element is all we need to see. Only tags
+ // starting with <? or <! can precede the root element. We
+ // bail if we don't find an <rss>, <feed> or <rdf> element
+ // right after those.
+
+ if (foundRDF) {
+ if (strncasecmp(hit, "<channel", strlen("<channel")) == 0) {
+ return @"application/rss+xml";
+ }
+ } else if (strncasecmp(hit, "<rdf", strlen("<rdf")) == 0) {
+ foundRDF = TRUE;
+ } else if (strncasecmp(hit, "<rss", strlen("<rss")) == 0) {
+ return @"application/rss+xml";
+ } else if (strncasecmp(hit, "<feed", strlen("<feed")) == 0) {
+ return @"application/atom+xml";
+ } else if (strncasecmp(hit, "<?", strlen("<?")) != 0 && strncasecmp(hit, "<!", strlen("<!")) != 0) {
+ return nil;
+ }
+
+ // Skip the "<" and continue.
+ remaining -= (hit + 1) - p;
+ p = hit + 1;
+ }
+
+ return nil;
+}
+
+-(NSString *)_webkit_guessedMIMEType
+{
+#define JPEG_MAGIC_NUMBER_LENGTH 4
+#define SCRIPT_TAG_LENGTH 7
+#define TEXT_HTML_LENGTH 9
+#define VCARD_HEADER_LENGTH 11
+#define VCAL_HEADER_LENGTH 15
+
+ NSString *MIMEType = [self _webkit_guessedMIMETypeForXML];
+ if ([MIMEType length])
+ return MIMEType;
+
+ int length = [self length];
+ const char *bytes = [self bytes];
+
+ const char *p = bytes;
+ int remaining = MIN(length, WEB_GUESS_MIME_TYPE_PEEK_LENGTH) - (SCRIPT_TAG_LENGTH - 1);
+ while (remaining > 0) {
+ // Look for a "<".
+ const char *hit = memchr(p, '<', remaining);
+ if (!hit) {
+ break;
+ }
+
+ // If we found a "<", look for "<html>" or "<a " or "<script".
+ if (strncasecmp(hit, "<html>", strlen("<html>")) == 0 ||
+ strncasecmp(hit, "<a ", strlen("<a ")) == 0 ||
+ strncasecmp(hit, "<script", strlen("<script")) == 0 ||
+ strncasecmp(hit, "<title>", strlen("<title>")) == 0) {
+ return @"text/html";
+ }
+
+ // Skip the "<" and continue.
+ remaining -= (hit + 1) - p;
+ p = hit + 1;
+ }
+
+ // Test for a broken server which has sent the content type as part of the content.
+ // This code could be improved to look for other mime types.
+ p = bytes;
+ remaining = MIN(length, WEB_GUESS_MIME_TYPE_PEEK_LENGTH) - (TEXT_HTML_LENGTH - 1);
+ while (remaining > 0) {
+ // Look for a "t" or "T".
+ const char *hit = NULL;
+ const char *lowerhit = memchr(p, 't', remaining);
+ const char *upperhit = memchr(p, 'T', remaining);
+ if (!lowerhit && !upperhit) {
+ break;
+ }
+ if (!lowerhit) {
+ hit = upperhit;
+ }
+ else if (!upperhit) {
+ hit = lowerhit;
+ }
+ else {
+ hit = MIN(lowerhit, upperhit);
+ }
+
+ // If we found a "t/T", look for "text/html".
+ if (strncasecmp(hit, "text/html", TEXT_HTML_LENGTH) == 0) {
+ return @"text/html";
+ }
+
+ // Skip the "t/T" and continue.
+ remaining -= (hit + 1) - p;
+ p = hit + 1;
+ }
+
+ if ((length >= VCARD_HEADER_LENGTH) && strncmp(bytes, "BEGIN:VCARD", VCARD_HEADER_LENGTH) == 0) {
+ return @"text/vcard";
+ }
+ if ((length >= VCAL_HEADER_LENGTH) && strncmp(bytes, "BEGIN:VCALENDAR", VCAL_HEADER_LENGTH) == 0) {
+ return @"text/calendar";
+ }
+
+ // Test for plain text.
+ int i;
+ for(i=0; i<length; i++){
+ char c = bytes[i];
+ if ((c < 0x20 || c > 0x7E) && (c != '\t' && c != '\r' && c != '\n')) {
+ break;
+ }
+ }
+ if (i == length) {
+ // Didn't encounter any bad characters, looks like plain text.
+ return @"text/plain";
+ }
+
+ // Looks like this is a binary file.
+
+ // Sniff for the JPEG magic number.
+ if ((length >= JPEG_MAGIC_NUMBER_LENGTH) && strncmp(bytes, "\xFF\xD8\xFF\xE0", JPEG_MAGIC_NUMBER_LENGTH) == 0) {
+ return @"image/jpeg";
+ }
+
+#undef JPEG_MAGIC_NUMBER_LENGTH
+#undef SCRIPT_TAG_LENGTH
+#undef TEXT_HTML_LENGTH
+#undef VCARD_HEADER_LENGTH
+#undef VCAL_HEADER_LENGTH
+
+ return nil;
+}
+
+@end
+
+@implementation NSData (WebNSDataExtras)
+
+-(BOOL)_web_isCaseInsensitiveEqualToCString:(const char *)string
+{
+ ASSERT(string);
+
+ const char *bytes = [self bytes];
+ return strncasecmp(bytes, string, [self length]) == 0;
+}
+
+static const UInt8 *_findEOL(const UInt8 *bytes, CFIndex len) {
+
+ // According to the HTTP specification EOL is defined as
+ // a CRLF pair. Unfortunately, some servers will use LF
+ // instead. Worse yet, some servers will use a combination
+ // of both (e.g. <header>CRLFLF<body>), so findEOL needs
+ // to be more forgiving. It will now accept CRLF, LF, or
+ // CR.
+ //
+ // It returns NULL if EOL is not found or it will return
+ // a pointer to the first terminating character.
+ CFIndex i;
+ for (i = 0; i < len; i++)
+ {
+ UInt8 c = bytes[i];
+ if ('\n' == c) return bytes + i;
+ if ('\r' == c)
+ {
+ // Check to see if spanning buffer bounds
+ // (CRLF is across reads). If so, wait for
+ // next read.
+ if (i + 1 == len) break;
+
+ return bytes + i;
+ }
+ }
+
+ return NULL;
+}
+
+-(NSMutableDictionary *)_webkit_parseRFC822HeaderFields
+{
+ NSMutableDictionary *headerFields = [NSMutableDictionary dictionary];
+
+ const UInt8 *bytes = [self bytes];
+ unsigned length = [self length];
+ NSString *lastKey = nil;
+ const UInt8 *eol;
+
+ // Loop over lines until we're past the header, or we can't find any more end-of-lines
+ while ((eol = _findEOL(bytes, length))) {
+ const UInt8 *line = bytes;
+ SInt32 lineLength = eol - bytes;
+
+ // Move bytes to the character after the terminator as returned by _findEOL.
+ bytes = eol + 1;
+ if (('\r' == *eol) && ('\n' == *bytes)) {
+ bytes++; // Safe since _findEOL won't return a spanning CRLF.
+ }
+
+ length -= (bytes - line);
+ if (lineLength == 0) {
+ // Blank line; we're at the end of the header
+ break;
+ }
+ else if (*line == ' ' || *line == '\t') {
+ // Continuation of the previous header
+ if (!lastKey) {
+ // malformed header; ignore it and continue
+ continue;
+ }
+ else {
+ // Merge the continuation of the previous header
+ NSString *currentValue = [headerFields objectForKey:lastKey];
+ NSString *newValue = (NSString *)CFMakeCollectable(CFStringCreateWithBytes(NULL, line, lineLength, kCFStringEncodingISOLatin1, FALSE));
+ ASSERT(currentValue);
+ ASSERT(newValue);
+ NSString *mergedValue = [[NSString alloc] initWithFormat:@"%@%@", currentValue, newValue];
+ [headerFields setObject:(NSString *)mergedValue forKey:lastKey];
+ [newValue release];
+ [mergedValue release];
+ // Note: currentValue is autoreleased
+ }
+ }
+ else {
+ // Brand new header
+ const UInt8 *colon;
+ for (colon = line; *colon != ':' && colon != eol; colon ++) {
+ // empty loop
+ }
+ if (colon == eol) {
+ // malformed header; ignore it and continue
+ continue;
+ }
+ else {
+ lastKey = (NSString *)CFMakeCollectable(CFStringCreateWithBytes(NULL, line, colon - line, kCFStringEncodingISOLatin1, FALSE));
+ [lastKey autorelease];
+ NSString *value = [lastKey _web_capitalizeRFC822HeaderFieldName];
+ lastKey = value;
+ for (colon++; colon != eol; colon++) {
+ if (*colon != ' ' && *colon != '\t') {
+ break;
+ }
+ }
+ if (colon == eol) {
+ value = [[NSString alloc] initWithString:@""];
+ [value autorelease];
+ }
+ else {
+ value = (NSString *)CFMakeCollectable(CFStringCreateWithBytes(NULL, colon, eol-colon, kCFStringEncodingISOLatin1, FALSE));
+ [value autorelease];
+ }
+ NSString *oldValue = [headerFields objectForKey:lastKey];
+ if (oldValue) {
+ NSString *newValue = [[NSString alloc] initWithFormat:@"%@, %@", oldValue, value];
+ value = newValue;
+ [newValue autorelease];
+ }
+ [headerFields setObject:(NSString *)value forKey:lastKey];
+ }
+ }
+ }
+
+ return headerFields;
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSDataExtrasPrivate.h b/WebKit/mac/Misc/WebNSDataExtrasPrivate.h
new file mode 100644
index 0000000..5f5ea68
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSDataExtrasPrivate.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@interface NSData (WebKitExtras)
+
+-(NSString *)_webkit_guessedMIMEType;
+
+@end
diff --git a/WebKit/mac/Misc/WebNSDictionaryExtras.h b/WebKit/mac/Misc/WebNSDictionaryExtras.h
new file mode 100644
index 0000000..57d868a
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSDictionaryExtras.h
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@interface NSDictionary (WebNSDictionaryExtras)
+- (int)_webkit_intForKey:(id)key;
+- (NSString *)_webkit_stringForKey:(id)key; // Returns nil if the value is not an NSString.
+
+// Searches for the full MIME type, then the prefix (e.g., "text/" for "text/html")
+- (id)_webkit_objectForMIMEType:(NSString *)MIMEType;
+@end
+
+@interface NSMutableDictionary (WebNSDictionaryExtras)
+- (void)_webkit_setObject:(id)object forUncopiedKey:(id)key;
+- (void)_webkit_setInt:(int)value forKey:(id)key;
+- (void)_webkit_setFloat:(float)value forKey:(id)key;
+- (void)_webkit_setBool:(BOOL)value forKey:(id)key;
+- (void)_webkit_setUnsignedLongLong:(unsigned long long)value forKey:(id)key;
+@end
+
diff --git a/WebKit/mac/Misc/WebNSDictionaryExtras.m b/WebKit/mac/Misc/WebNSDictionaryExtras.m
new file mode 100644
index 0000000..86df63a
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSDictionaryExtras.m
@@ -0,0 +1,107 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebNSDataExtras.h>
+
+#import <JavaScriptCore/Assertions.h>
+
+@implementation NSDictionary (WebNSDictionaryExtras)
+-(NSNumber *)_webkit_numberForKey:(id)key
+{
+ id object = [self objectForKey:key];
+ return [object isKindOfClass:[NSNumber class]] ? object : nil;
+}
+
+-(int)_webkit_intForKey:(NSString *)key
+{
+ NSNumber *number = [self _webkit_numberForKey:key];
+ return number == nil ? 0 : [number intValue];
+}
+
+-(NSString *)_webkit_stringForKey:(id)key
+{
+ id object = [self objectForKey:key];
+ return [object isKindOfClass:[NSString class]] ? object : nil;
+}
+
+-(id)_webkit_objectForMIMEType:(NSString *)MIMEType
+{
+ id result;
+ NSRange slashRange;
+
+ result = [self objectForKey:MIMEType];
+ if (result) {
+ return result;
+ }
+
+ slashRange = [MIMEType rangeOfString:@"/"];
+ if (slashRange.location == NSNotFound) {
+ return nil;
+ }
+
+ return [self objectForKey:[MIMEType substringToIndex:slashRange.location + 1]];
+}
+
+@end
+
+@implementation NSMutableDictionary (WebNSDictionaryExtras)
+-(void)_webkit_setObject:(id)object forUncopiedKey:(id)key
+{
+ CFDictionarySetValue((CFMutableDictionaryRef)self, key, object);
+}
+
+-(void)_webkit_setInt:(int)value forKey:(id)key
+{
+ NSNumber *object = [[NSNumber alloc] initWithInt:value];
+ [self setObject:object forKey:key];
+ [object release];
+}
+
+-(void)_webkit_setFloat:(float)value forKey:(id)key
+{
+ NSNumber *object = [[NSNumber alloc] initWithFloat:value];
+ [self setObject:object forKey:key];
+ [object release];
+}
+
+-(void)_webkit_setBool:(BOOL)value forKey:(id)key
+{
+ NSNumber *object = [[NSNumber alloc] initWithBool:value];
+ [self setObject:object forKey:key];
+ [object release];
+}
+
+- (void)_webkit_setUnsignedLongLong:(unsigned long long)value forKey:(id)key
+{
+ NSNumber *object = [[NSNumber alloc] initWithUnsignedLongLong:value];
+ [self setObject:object forKey:key];
+ [object release];
+}
+
+@end
+
diff --git a/WebKit/mac/Misc/WebNSEventExtras.h b/WebKit/mac/Misc/WebNSEventExtras.h
new file mode 100644
index 0000000..e35ff52
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSEventExtras.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <AppKit/AppKit.h>
+
+@interface NSEvent (WebExtras)
+
+-(BOOL)_web_isKeyEvent:(unichar)key;
+
+-(BOOL)_web_isDeleteKeyEvent;
+-(BOOL)_web_isEscapeKeyEvent;
+-(BOOL)_web_isOptionTabKeyEvent;
+-(BOOL)_web_isReturnOrEnterKeyEvent;
+-(BOOL)_web_isTabKeyEvent;
+
+@end
diff --git a/WebKit/mac/Misc/WebNSEventExtras.m b/WebKit/mac/Misc/WebNSEventExtras.m
new file mode 100644
index 0000000..60fb3cf
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSEventExtras.m
@@ -0,0 +1,82 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebNSEventExtras.h>
+
+@implementation NSEvent (WebExtras)
+
+-(BOOL)_web_isKeyEvent:(unichar)key
+{
+ int type = [self type];
+ if (type != NSKeyDown && type != NSKeyUp)
+ return NO;
+
+ NSString *chars = [self charactersIgnoringModifiers];
+ if ([chars length] != 1)
+ return NO;
+
+ unichar c = [chars characterAtIndex:0];
+ if (c != key)
+ return NO;
+
+ return YES;
+}
+
+- (BOOL)_web_isDeleteKeyEvent
+{
+ const unichar deleteKey = NSDeleteCharacter;
+ const unichar deleteForwardKey = NSDeleteFunctionKey;
+ return [self _web_isKeyEvent:deleteKey] || [self _web_isKeyEvent:deleteForwardKey];
+}
+
+- (BOOL)_web_isEscapeKeyEvent
+{
+ const unichar escapeKey = 0x001b;
+ return [self _web_isKeyEvent:escapeKey];
+}
+
+- (BOOL)_web_isOptionTabKeyEvent
+{
+ return ([self modifierFlags] & NSAlternateKeyMask) && [self _web_isTabKeyEvent];
+}
+
+- (BOOL)_web_isReturnOrEnterKeyEvent
+{
+ const unichar enterKey = NSEnterCharacter;
+ const unichar returnKey = NSCarriageReturnCharacter;
+ return [self _web_isKeyEvent:enterKey] || [self _web_isKeyEvent:returnKey];
+}
+
+- (BOOL)_web_isTabKeyEvent
+{
+ const unichar tabKey = 0x0009;
+ const unichar shiftTabKey = 0x0019;
+ return [self _web_isKeyEvent:tabKey] || [self _web_isKeyEvent:shiftTabKey];
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSFileManagerExtras.h b/WebKit/mac/Misc/WebNSFileManagerExtras.h
new file mode 100644
index 0000000..aaaf0a7
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSFileManagerExtras.h
@@ -0,0 +1,47 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+#define WEB_UREAD (00400) /* Read by owner */
+#define WEB_UWRITE (00200) /* Write by owner */
+#define WEB_UEXEC (00100) /* Execute/Search by owner */
+
+@interface NSFileManager (WebNSFileManagerExtras)
+
+- (BOOL)_webkit_createDirectoryAtPathWithIntermediateDirectories:(NSString *)path attributes:(NSDictionary *)attributes;
+- (BOOL)_webkit_createFileAtPathWithIntermediateDirectories:(NSString *)path contents:(NSData *)contents attributes:(NSDictionary *)attributes directoryAttributes:(NSDictionary *)directoryAttributes;
+- (void)_webkit_backgroundRemoveFileAtPath:(NSString *)path;
+- (void)_webkit_backgroundRemoveLeftoverFiles:(NSString *)path;
+- (BOOL)_webkit_removeFileOnlyAtPath:(NSString *)path;
+- (void)_webkit_setMetadataURL:(NSString *)URLString referrer:(NSString *)referrer atPath:(NSString *)path;
+- (NSString *)_webkit_startupVolumeName;
+- (NSString *)_webkit_pathWithUniqueFilenameForPath:(NSString *)path;
+
+@end
+
diff --git a/WebKit/mac/Misc/WebNSFileManagerExtras.m b/WebKit/mac/Misc/WebNSFileManagerExtras.m
new file mode 100644
index 0000000..ae45afe
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSFileManagerExtras.m
@@ -0,0 +1,346 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebNSFileManagerExtras.h>
+
+#import <JavaScriptCore/Assertions.h>
+#import <WebKit/WebKitNSStringExtras.h>
+#import <WebKitSystemInterface.h>
+
+#import <sys/mount.h>
+
+@implementation NSFileManager (WebNSFileManagerExtras)
+
+- (BOOL)_webkit_fileExistsAtPath:(NSString *)path isDirectory:(BOOL *)isDirectory traverseLink:(BOOL)flag
+{
+ BOOL result;
+ NSDictionary *attributes;
+
+ result = NO;
+ if (isDirectory) {
+ *isDirectory = NO;
+ }
+
+ attributes = [self fileAttributesAtPath:path traverseLink:flag];
+
+ if (attributes) {
+ result = YES;
+ if ([[attributes objectForKey:NSFileType] isEqualToString:NSFileTypeDirectory]) {
+ if (isDirectory) {
+ *isDirectory = YES;
+ }
+ }
+ }
+
+ return result;
+}
+
+- (BOOL)_webkit_createIntermediateDirectoriesForPath:(NSString *)path attributes:(NSDictionary *)attributes
+{
+ BOOL result;
+ NSArray *pathComponents;
+ BOOL isDir;
+ unsigned count;
+ unsigned i;
+ NSString *checkPath;
+ NSMutableString *subpath;
+
+ if (!path || [path length] == 0 || ![path isAbsolutePath]) {
+ return NO;
+ }
+
+ result = NO;
+
+ // check to see if the path to the file already exists
+ if ([self _webkit_fileExistsAtPath:[path stringByDeletingLastPathComponent] isDirectory:&isDir traverseLink:YES]) {
+ if (isDir) {
+ result = YES;
+ }
+ else {
+ result = NO;
+ }
+ }
+ else {
+ // create the path to the file
+ result = YES;
+
+ // assume that most of the path exists, look backwards until we find an existing subpath
+ checkPath = path;
+ while (![checkPath isEqualToString:@"/"]) {
+ checkPath = [checkPath stringByDeletingLastPathComponent];
+ if ([self _webkit_fileExistsAtPath:checkPath isDirectory:&isDir traverseLink:YES]) {
+ if (isDir) {
+ break;
+ }
+ else {
+ // found a leaf node, can't continue
+ result = NO;
+ break;
+ }
+ }
+ }
+
+ if (result) {
+ // now build up the path to the point where we found existing paths
+ subpath = [[NSMutableString alloc] initWithCapacity:[path length]];
+ pathComponents = [path componentsSeparatedByString:@"/"];
+ count = [pathComponents count];
+ i = 0;
+ while (i < count - 1 && ![subpath isEqualToString:checkPath]) {
+ if (i > 0) {
+ [subpath appendString:@"/"];
+ }
+ [subpath appendString:[pathComponents objectAtIndex:i]];
+ i++;
+ }
+
+ // now create the parts of the path that did not yet exist
+ while (i < count - 1) {
+ if ([(NSString *)[pathComponents objectAtIndex:i] length] == 0) {
+ continue;
+ }
+ if (i > 0) {
+ [subpath appendString:@"/"];
+ }
+ [subpath appendString:[pathComponents objectAtIndex:i]];
+
+ // does this directory exist?
+ if ([self _webkit_fileExistsAtPath:subpath isDirectory:&isDir traverseLink:YES]) {
+ if (!isDir) {
+ // ran into a leaf node of some sort
+ result = NO;
+ break;
+ }
+ }
+ else {
+ // subpath does not exist - create it
+ if (![self createDirectoryAtPath:subpath attributes:attributes]) {
+ // failed to create subpath
+ result = NO;
+ break;
+ }
+ }
+ i++;
+ }
+
+ [subpath release];
+ }
+
+ }
+
+ return result;
+}
+
+- (BOOL)_webkit_createDirectoryAtPathWithIntermediateDirectories:(NSString *)path attributes:(NSDictionary *)attributes
+{
+ // Be really optimistic - assume that in the common case, the directory exists.
+ BOOL isDirectory;
+ if ([self fileExistsAtPath:path isDirectory:&isDirectory] && isDirectory) {
+ return YES;
+ }
+
+ // Assume the next most common case is that the parent directory already exists
+ if ([self createDirectoryAtPath:path attributes:attributes]) {
+ return YES;
+ }
+
+ // Do it the hard way
+ return [self _webkit_createIntermediateDirectoriesForPath:path attributes:attributes] && [self createDirectoryAtPath:path attributes:attributes];
+}
+
+- (BOOL)_webkit_createFileAtPathWithIntermediateDirectories:(NSString *)path contents:(NSData *)contents attributes:(NSDictionary *)attributes directoryAttributes:(NSDictionary *)directoryAttributes
+{
+ // Be optimistic - try just creating the file first, assuming intermediate directories exist.
+ if ([self createFileAtPath:path contents:contents attributes:attributes]) {
+ return YES;
+ }
+
+ return ([self _webkit_createIntermediateDirectoriesForPath:path attributes:directoryAttributes] && [self createFileAtPath:path contents:contents attributes:attributes]);
+}
+
+- (BOOL)_webkit_removeFileOnlyAtPath:(NSString *)path
+{
+ struct statfs buf;
+ BOOL result = unlink([path fileSystemRepresentation]) == 0;
+
+ // For mysterious reasons, MNT_DOVOLFS is the flag for "supports resource fork"
+ if ((statfs([path fileSystemRepresentation], &buf) == 0) && !(buf.f_flags & MNT_DOVOLFS)) {
+ NSString *lastPathComponent = [path lastPathComponent];
+ if ([lastPathComponent length] != 0 && ![lastPathComponent isEqualToString:@"/"]) {
+ NSString *resourcePath = [[path stringByDeletingLastPathComponent] stringByAppendingString:[@"._" stringByAppendingString:lastPathComponent]];
+ if (unlink([resourcePath fileSystemRepresentation]) != 0) {
+ result = NO;
+ }
+ }
+ }
+
+ return result;
+}
+
+- (void)_webkit_backgroundRemoveFileAtPath:(NSString *)path
+{
+ NSFileManager *manager;
+ NSString *moveToSubpath;
+ NSString *moveToPath;
+ int i;
+
+ manager = [NSFileManager defaultManager];
+
+ i = 0;
+ moveToSubpath = [path stringByDeletingLastPathComponent];
+ do {
+ moveToPath = [NSString stringWithFormat:@"%@/.tmp%d", moveToSubpath, i];
+ i++;
+ } while ([manager fileExistsAtPath:moveToPath]);
+
+ if ([manager movePath:path toPath:moveToPath handler:nil]) {
+ [NSThread detachNewThreadSelector:@selector(_performRemoveFileAtPath:) toTarget:self withObject:moveToPath];
+ }
+
+}
+
+- (void)_webkit_backgroundRemoveLeftoverFiles:(NSString *)path
+{
+ NSFileManager *manager;
+ NSString *leftoverSubpath;
+ NSString *leftoverPath;
+ int i;
+
+ manager = [NSFileManager defaultManager];
+ leftoverSubpath = [path stringByDeletingLastPathComponent];
+
+ i = 0;
+ while (1) {
+ leftoverPath = [NSString stringWithFormat:@"%@/.tmp%d", leftoverSubpath, i];
+ if (![manager fileExistsAtPath:leftoverPath]) {
+ break;
+ }
+ [NSThread detachNewThreadSelector:@selector(_performRemoveFileAtPath:) toTarget:self withObject:leftoverPath];
+ i++;
+ }
+}
+
+- (NSString *)_webkit_carbonPathForPath:(NSString *)posixPath
+{
+ OSStatus error;
+ FSRef ref, rootRef, parentRef;
+ FSCatalogInfo info;
+ NSMutableArray *carbonPathPieces;
+ HFSUniStr255 nameString;
+
+ // Make an FSRef.
+ error = FSPathMakeRef((const UInt8 *)[posixPath fileSystemRepresentation], &ref, NULL);
+ if (error != noErr) {
+ return nil;
+ }
+
+ // Get volume refNum.
+ error = FSGetCatalogInfo(&ref, kFSCatInfoVolume, &info, NULL, NULL, NULL);
+ if (error != noErr) {
+ return nil;
+ }
+
+ // Get root directory FSRef.
+ error = FSGetVolumeInfo(info.volume, 0, NULL, kFSVolInfoNone, NULL, NULL, &rootRef);
+ if (error != noErr) {
+ return nil;
+ }
+
+ // Get the pieces of the path.
+ carbonPathPieces = [NSMutableArray array];
+ for (;;) {
+ error = FSGetCatalogInfo(&ref, kFSCatInfoNone, NULL, &nameString, NULL, &parentRef);
+ if (error != noErr) {
+ return nil;
+ }
+ [carbonPathPieces insertObject:[NSString stringWithCharacters:nameString.unicode length:nameString.length] atIndex:0];
+ if (FSCompareFSRefs(&ref, &rootRef) == noErr) {
+ break;
+ }
+ ref = parentRef;
+ }
+
+ // Volume names need trailing : character.
+ if ([carbonPathPieces count] == 1) {
+ [carbonPathPieces addObject:@""];
+ }
+
+ return [carbonPathPieces componentsJoinedByString:@":"];
+}
+
+- (void)_webkit_setMetadataURL:(NSString *)URLString referrer:(NSString *)referrer atPath:(NSString *)path
+{
+ ASSERT(URLString);
+ ASSERT(path);
+ WKSetMetadataURL(URLString, referrer, path);
+}
+
+- (NSString *)_webkit_startupVolumeName
+{
+ NSString *path = [self _webkit_carbonPathForPath:@"/"];
+ return [path substringToIndex:[path length]-1];
+}
+
+- (NSString *)_webkit_pathWithUniqueFilenameForPath:(NSString *)path
+{
+ // "Fix" the filename of the path.
+ NSString *filename = [[path lastPathComponent] _webkit_filenameByFixingIllegalCharacters];
+ path = [[path stringByDeletingLastPathComponent] stringByAppendingPathComponent:filename];
+
+ NSFileManager *fileManager = [NSFileManager defaultManager];
+ if ([fileManager fileExistsAtPath:path]) {
+ // Don't overwrite existing file by appending "-n", "-n.ext" or "-n.ext.ext" to the filename.
+ NSString *extensions = nil;
+ NSString *pathWithoutExtensions;
+ NSString *lastPathComponent = [path lastPathComponent];
+ NSRange periodRange = [lastPathComponent rangeOfString:@"."];
+
+ if (periodRange.location == NSNotFound) {
+ pathWithoutExtensions = path;
+ } else {
+ extensions = [lastPathComponent substringFromIndex:periodRange.location + 1];
+ lastPathComponent = [lastPathComponent substringToIndex:periodRange.location];
+ pathWithoutExtensions = [[path stringByDeletingLastPathComponent] stringByAppendingPathComponent:lastPathComponent];
+ }
+
+ NSString *pathWithAppendedNumber;
+ unsigned i;
+
+ for (i = 1; 1; i++) {
+ pathWithAppendedNumber = [NSString stringWithFormat:@"%@-%d", pathWithoutExtensions, i];
+ path = [extensions length] ? [pathWithAppendedNumber stringByAppendingPathExtension:extensions] : pathWithAppendedNumber;
+ if (![fileManager fileExistsAtPath:path]) {
+ break;
+ }
+ }
+ }
+
+ return path;
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSImageExtras.h b/WebKit/mac/Misc/WebNSImageExtras.h
new file mode 100644
index 0000000..b8ac5b5
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSImageExtras.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@interface NSImage (WebExtras)
+
+- (void)_web_scaleToMaxSize:(NSSize)size;
+
+- (void)_web_dissolveToFraction:(float)delta;
+
+// Debug method. Saves an image and opens it in the preferred TIFF viewing application.
+- (void)_web_saveAndOpen;
+
+@end
diff --git a/WebKit/mac/Misc/WebNSImageExtras.m b/WebKit/mac/Misc/WebNSImageExtras.m
new file mode 100644
index 0000000..7124f85
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSImageExtras.m
@@ -0,0 +1,91 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebNSImageExtras.h>
+
+#import <WebKit/WebKitLogging.h>
+
+@implementation NSImage (WebExtras)
+
+- (void)_web_scaleToMaxSize:(NSSize)size
+{
+ float heightResizeDelta = 0.0f, widthResizeDelta = 0.0f, resizeDelta = 0.0f;
+ NSSize originalSize = [self size];
+
+ if(originalSize.width > size.width){
+ widthResizeDelta = size.width / originalSize.width;
+ resizeDelta = widthResizeDelta;
+ }
+
+ if(originalSize.height > size.height){
+ heightResizeDelta = size.height / originalSize.height;
+ if((resizeDelta == 0.0) || (resizeDelta > heightResizeDelta)){
+ resizeDelta = heightResizeDelta;
+ }
+ }
+
+ if(resizeDelta > 0.0){
+ NSSize newSize = NSMakeSize((originalSize.width * resizeDelta), (originalSize.height * resizeDelta));
+ [self setScalesWhenResized:YES];
+ [self setSize:newSize];
+ }
+}
+
+- (void)_web_dissolveToFraction:(float)delta
+{
+ NSImage *dissolvedImage = [[NSImage alloc] initWithSize:[self size]];
+
+ NSPoint point = [self isFlipped] ? NSMakePoint(0, [self size].height) : NSZeroPoint;
+
+ // In this case the dragging image is always correct.
+ [dissolvedImage setFlipped:[self isFlipped]];
+
+ [dissolvedImage lockFocus];
+ [self dissolveToPoint:point fraction: delta];
+ [dissolvedImage unlockFocus];
+
+ [self lockFocus];
+ [dissolvedImage compositeToPoint:point operation:NSCompositeCopy];
+ [self unlockFocus];
+
+ [dissolvedImage release];
+}
+
+- (void)_web_saveAndOpen
+{
+ char path[] = "/tmp/XXXXXX.tiff";
+ int fd = mkstemps(path, 5);
+ if (fd != -1) {
+ NSData *data = [self TIFFRepresentation];
+ write(fd, [data bytes], [data length]);
+ close(fd);
+ [[NSWorkspace sharedWorkspace] openFile:[NSString stringWithUTF8String:path]];
+ }
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSNotificationCenterExtras.h b/WebKit/mac/Misc/WebNSNotificationCenterExtras.h
new file mode 100644
index 0000000..1a2e16c
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSNotificationCenterExtras.h
@@ -0,0 +1,39 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNSNotificationCenterExtras.h"
+
+@interface NSNotificationCenter (WebNSNotificationCenterExtras)
+
+- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object;
+- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object userInfo:(NSDictionary *)userInfo;
+- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object userInfo:(NSDictionary *)userInfo waitUntilDone:(BOOL)wait;
+
++ (void)_postNotificationName:(NSDictionary *)info;
+
+@end
diff --git a/WebKit/mac/Misc/WebNSNotificationCenterExtras.m b/WebKit/mac/Misc/WebNSNotificationCenterExtras.m
new file mode 100644
index 0000000..bc5b4ed
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSNotificationCenterExtras.m
@@ -0,0 +1,69 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNSNotificationCenterExtras.h"
+
+@implementation NSNotificationCenter (WebNSNotificationCenterExtras)
+
+- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object
+{
+ [self postNotificationOnMainThreadWithName:name object:object userInfo:nil waitUntilDone:NO];
+}
+
+- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object userInfo:(NSDictionary *)userInfo
+{
+ [self postNotificationOnMainThreadWithName:name object:object userInfo:userInfo waitUntilDone:NO];
+}
+
+- (void)postNotificationOnMainThreadWithName:(NSString *)name object:(id)object userInfo:(NSDictionary *)userInfo waitUntilDone:(BOOL)wait
+{
+ NSMutableDictionary *info = [[NSMutableDictionary alloc] initWithCapacity:3];
+ if (name)
+ [info setObject:name forKey:@"name"];
+
+ if (object)
+ [info setObject:object forKey:@"object"];
+
+ if (userInfo)
+ [info setObject:userInfo forKey:@"userInfo"];
+
+ [[self class] performSelectorOnMainThread:@selector(_postNotificationName:) withObject:info waitUntilDone:wait];
+}
+
++ (void)_postNotificationName:(NSDictionary *)info
+{
+ NSString *name = [info objectForKey:@"name"];
+ id object = [info objectForKey:@"object"];
+ NSDictionary *userInfo = [info objectForKey:@"userInfo"];
+
+ [[self defaultCenter] postNotificationName:name object:object userInfo:userInfo];
+
+ [info release];
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSObjectExtras.h b/WebKit/mac/Misc/WebNSObjectExtras.h
new file mode 100644
index 0000000..8029825
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSObjectExtras.h
@@ -0,0 +1,54 @@
+/*
+ * Copyright (C) 2005, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+#import <objc/objc-class.h>
+#import <objc/objc.h>
+
+// Use WebCFAutorelease to return an object made by a CoreFoundation
+// "create" or "copy" function as an autoreleased and garbage collected
+// object. CF objects need to be "made collectable" for autorelease to work
+// properly under GC.
+static inline id WebCFAutorelease(CFTypeRef obj)
+{
+ if (obj)
+ CFMakeCollectable(obj);
+ [(id)obj autorelease];
+ return (id)obj;
+}
+
+#if !(defined(OBJC_API_VERSION) && OBJC_API_VERSION > 0)
+
+static inline IMP method_setImplementation(Method m, IMP i)
+{
+ IMP oi = m->method_imp;
+ m->method_imp = i;
+ return oi;
+}
+
+#endif
diff --git a/WebKit/mac/Misc/WebNSPasteboardExtras.h b/WebKit/mac/Misc/WebNSPasteboardExtras.h
new file mode 100644
index 0000000..b994512
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSPasteboardExtras.h
@@ -0,0 +1,89 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@class DOMElement;
+@class WebArchive;
+@class WebHTMLView;
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+extern NSString *WebURLPboardType;
+extern NSString *WebURLNamePboardType;
+
+@interface NSPasteboard (WebExtras)
+
+// Returns the array of types that _web_writeURL:andTitle: handles.
++ (NSArray *)_web_writableTypesForURL;
+
+// Returns the array of types that _web_writeImage handles.
++ (NSArray *)_web_writableTypesForImageIncludingArchive:(BOOL)hasArchive;
+
+// Returns the array of drag types that _web_bestURL handles; note that the presence
+// of one or more of these drag types on the pasteboard is not a guarantee that
+// _web_bestURL will return a non-nil result.
++ (NSArray *)_web_dragTypesForURL;
+
+// Finds the best URL from the data on the pasteboard, giving priority to http and https URLs
+- (NSURL *)_web_bestURL;
+
+// Writes the URL to the pasteboard with the passed types.
+- (void)_web_writeURL:(NSURL *)URL andTitle:(NSString *)title types:(NSArray *)types;
+
+// Sets the text on the NSFindPboard. Returns the new changeCount for the NSFindPboard.
++ (int)_web_setFindPasteboardString:(NSString *)string withOwner:(id)owner;
+
+// Writes a file wrapper to the pasteboard as an RTFD attachment.
+// NSRTFDPboardType must be declared on the pasteboard before calling this method.
+- (void)_web_writeFileWrapperAsRTFDAttachment:(NSFileWrapper *)wrapper;
+
+// Writes an image, URL and other optional types to the pasteboard.
+- (void)_web_writeImage:(NSImage *)image
+ element:(DOMElement*)element
+ URL:(NSURL *)URL
+ title:(NSString *)title
+ archive:(WebArchive *)archive
+ types:(NSArray *)types
+ source:(WebHTMLView *)source;
+
+- (id)_web_declareAndWriteDragImageForElement:(DOMElement *)element
+ URL:(NSURL *)URL
+ title:(NSString *)title
+ archive:(WebArchive *)archive
+ source:(WebHTMLView *)source;
+
+- (void)_web_writePromisedRTFDFromArchive:(WebArchive*)archive containsImage:(BOOL)containsImage;
+
+@end
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/WebKit/mac/Misc/WebNSPasteboardExtras.mm b/WebKit/mac/Misc/WebNSPasteboardExtras.mm
new file mode 100644
index 0000000..cdf47cc
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSPasteboardExtras.mm
@@ -0,0 +1,282 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNSPasteboardExtras.h"
+
+#import "WebArchive.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebHTMLViewInternal.h"
+#import "WebNSURLExtras.h"
+#import "WebResourcePrivate.h"
+#import "WebURLsWithTitles.h"
+#import "WebViewPrivate.h"
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/Element.h>
+#import <WebCore/MIMETypeRegistry.h>
+#import <WebCore/RenderImage.h>
+#import <WebKit/DOMExtensions.h>
+#import <WebKit/DOMPrivate.h>
+#import <wtf/RetainPtr.h>
+#import <WebKitSystemInterface.h>
+
+@interface NSFilePromiseDragSource : NSObject
+- initWithSource:(id)draggingSource;
+- (void)setTypes:(NSArray *)types onPasteboard:(NSPasteboard *)pboard;
+@end
+
+using namespace WebCore;
+
+NSString *WebURLPboardType = @"public.url";
+NSString *WebURLNamePboardType = @"public.url-name";
+
+@implementation NSPasteboard (WebExtras)
+
++ (NSArray *)_web_writableTypesForURL
+{
+ static RetainPtr<NSArray> types;
+ if (!types) {
+ types = [[NSArray alloc] initWithObjects:
+ WebURLsWithTitlesPboardType,
+ NSURLPboardType,
+ WebURLPboardType,
+ WebURLNamePboardType,
+ NSStringPboardType,
+ nil];
+ }
+ return types.get();
+}
+
+static NSArray *_writableTypesForImageWithoutArchive (void)
+{
+ static RetainPtr<NSMutableArray> types;
+ if (types == nil) {
+ types = [[NSMutableArray alloc] initWithObjects:NSTIFFPboardType, nil];
+ [types.get() addObjectsFromArray:[NSPasteboard _web_writableTypesForURL]];
+ }
+ return types.get();
+}
+
+static NSArray *_writableTypesForImageWithArchive (void)
+{
+ static RetainPtr<NSMutableArray> types;
+ if (types == nil) {
+ types = [_writableTypesForImageWithoutArchive() mutableCopy];
+ [types.get() addObject:NSRTFDPboardType];
+ [types.get() addObject:WebArchivePboardType];
+ }
+ return types.get();
+}
+
++ (NSArray *)_web_writableTypesForImageIncludingArchive:(BOOL)hasArchive
+{
+ return hasArchive
+ ? _writableTypesForImageWithArchive()
+ : _writableTypesForImageWithoutArchive();
+}
+
++ (NSArray *)_web_dragTypesForURL
+{
+ return [NSArray arrayWithObjects:
+ WebURLsWithTitlesPboardType,
+ NSURLPboardType,
+ WebURLPboardType,
+ WebURLNamePboardType,
+ NSStringPboardType,
+ NSFilenamesPboardType,
+ nil];
+}
+
+- (NSURL *)_web_bestURL
+{
+ NSArray *types = [self types];
+
+ if ([types containsObject:NSURLPboardType]) {
+ NSURL *URLFromPasteboard = [NSURL URLFromPasteboard:self];
+ NSString *scheme = [URLFromPasteboard scheme];
+ if ([scheme isEqualToString:@"http"] || [scheme isEqualToString:@"https"]) {
+ return [URLFromPasteboard _webkit_canonicalize];
+ }
+ }
+
+ if ([types containsObject:NSStringPboardType]) {
+ NSString *URLString = [self stringForType:NSStringPboardType];
+ if ([URLString _webkit_looksLikeAbsoluteURL]) {
+ NSURL *URL = [[NSURL _web_URLWithUserTypedString:URLString] _webkit_canonicalize];
+ if (URL) {
+ return URL;
+ }
+ }
+ }
+
+ if ([types containsObject:NSFilenamesPboardType]) {
+ NSArray *files = [self propertyListForType:NSFilenamesPboardType];
+ if ([files count] == 1) {
+ NSString *file = [files objectAtIndex:0];
+ BOOL isDirectory;
+ if([[NSFileManager defaultManager] fileExistsAtPath:file isDirectory:&isDirectory] && !isDirectory){
+ return [[NSURL fileURLWithPath:file] _webkit_canonicalize];
+ }
+ }
+ }
+
+ return nil;
+}
+
+- (void)_web_writeURL:(NSURL *)URL andTitle:(NSString *)title types:(NSArray *)types
+{
+ ASSERT(URL);
+
+ if ([title length] == 0) {
+ title = [[URL path] lastPathComponent];
+ if ([title length] == 0)
+ title = [URL _web_userVisibleString];
+ }
+
+ if ([types containsObject:NSURLPboardType])
+ [URL writeToPasteboard:self];
+ if ([types containsObject:WebURLPboardType])
+ [self setString:[URL _web_originalDataAsString] forType:WebURLPboardType];
+ if ([types containsObject:WebURLNamePboardType])
+ [self setString:title forType:WebURLNamePboardType];
+ if ([types containsObject:NSStringPboardType])
+ [self setString:[URL _web_userVisibleString] forType:NSStringPboardType];
+ if ([types containsObject:WebURLsWithTitlesPboardType])
+ [WebURLsWithTitles writeURLs:[NSArray arrayWithObject:URL] andTitles:[NSArray arrayWithObject:title] toPasteboard:self];
+}
+
++ (int)_web_setFindPasteboardString:(NSString *)string withOwner:(id)owner
+{
+ NSPasteboard *findPasteboard = [NSPasteboard pasteboardWithName:NSFindPboard];
+ [findPasteboard declareTypes:[NSArray arrayWithObject:NSStringPboardType] owner:owner];
+ [findPasteboard setString:string forType:NSStringPboardType];
+ return [findPasteboard changeCount];
+}
+
+- (void)_web_writeFileWrapperAsRTFDAttachment:(NSFileWrapper *)wrapper
+{
+ NSTextAttachment *attachment = [[NSTextAttachment alloc] initWithFileWrapper:wrapper];
+
+ NSAttributedString *string = [NSAttributedString attributedStringWithAttachment:attachment];
+ [attachment release];
+
+ NSData *RTFDData = [string RTFDFromRange:NSMakeRange(0, [string length]) documentAttributes:nil];
+ [self setData:RTFDData forType:NSRTFDPboardType];
+}
+
+
+- (void)_web_writePromisedRTFDFromArchive:(WebArchive*)archive containsImage:(BOOL)containsImage
+{
+ ASSERT(archive);
+ // This image data is either the only subresource of an archive (HTML image case)
+ // or the main resource (standalone image case).
+ NSArray *subresources = [archive subresources];
+ WebResource *resource = [archive mainResource];
+ if (containsImage && [subresources count] > 0
+ && MIMETypeRegistry::isSupportedImageResourceMIMEType([[subresources objectAtIndex:0] MIMEType]))
+ resource = (WebResource *)[subresources objectAtIndex:0];
+ ASSERT(resource != nil);
+
+ ASSERT(!containsImage || MIMETypeRegistry::isSupportedImageResourceMIMEType([resource MIMEType]));
+ if (!containsImage || MIMETypeRegistry::isSupportedImageResourceMIMEType([resource MIMEType]))
+ [self _web_writeFileWrapperAsRTFDAttachment:[resource _fileWrapperRepresentation]];
+
+}
+
+CachedImage* imageFromElement(DOMElement *domElement) {
+ Element* element = core(domElement);
+ if (!element)
+ return 0;
+
+ RenderObject* renderer = element->renderer();
+ RenderImage* imageRenderer = static_cast<RenderImage*>(renderer);
+ if (!imageRenderer->cachedImage() || imageRenderer->cachedImage()->errorOccurred())
+ return 0;
+ return imageRenderer->cachedImage();
+}
+
+- (void)_web_writeImage:(NSImage *)image
+ element:(DOMElement *)element
+ URL:(NSURL *)URL
+ title:(NSString *)title
+ archive:(WebArchive *)archive
+ types:(NSArray *)types
+ source:(WebHTMLView *)source
+{
+ ASSERT(image || element);
+ ASSERT(URL);
+
+ [self _web_writeURL:URL andTitle:title types:types];
+
+ if ([types containsObject:NSTIFFPboardType]) {
+ if (image)
+ [self setData:[image TIFFRepresentation] forType:NSTIFFPboardType];
+ else if (source && element)
+ [source setPromisedDragTIFFDataSource:imageFromElement(element)];
+ else if (element)
+ [self setData:[element _imageTIFFRepresentation] forType:NSTIFFPboardType];
+ }
+
+ if (archive)
+ if ([types containsObject:WebArchivePboardType])
+ [self setData:[archive data] forType:WebArchivePboardType];
+ else {
+ // We should not have declared types that we aren't going to write (4031826).
+ ASSERT(![types containsObject:NSRTFDPboardType]);
+ ASSERT(![types containsObject:WebArchivePboardType]);
+ }
+}
+
+- (id)_web_declareAndWriteDragImageForElement:(DOMElement *)element
+ URL:(NSURL *)URL
+ title:(NSString *)title
+ archive:(WebArchive *)archive
+ source:(WebHTMLView *)source
+{
+ ASSERT(self == [NSPasteboard pasteboardWithName:NSDragPboard]);
+
+ NSMutableArray *types = [[NSMutableArray alloc] initWithObjects:NSFilesPromisePboardType, nil];
+ [types addObjectsFromArray:[NSPasteboard _web_writableTypesForImageIncludingArchive:(archive != nil)]];
+ [self declareTypes:types owner:source];
+ [self _web_writeImage:nil element:element URL:URL title:title archive:archive types:types source:source];
+ [types release];
+
+ NSString *extension = @"";
+ if (RenderObject* renderer = core(element)->renderer())
+ if (renderer->isImage())
+ if (CachedImage* image = static_cast<RenderImage*>(renderer)->cachedImage())
+ extension = WKGetPreferredExtensionForMIMEType(image->response().mimeType());
+
+ NSArray *extensions = [[NSArray alloc] initWithObjects:extension, nil];
+ [self setPropertyList:extensions forType:NSFilesPromisePboardType];
+ [extensions release];
+
+ return source;
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSPrintOperationExtras.h b/WebKit/mac/Misc/WebNSPrintOperationExtras.h
new file mode 100644
index 0000000..44eb3df
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSPrintOperationExtras.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@interface NSPrintOperation (WebKitExtras)
+
+- (float)_web_pageSetupScaleFactor;
+
+@end
diff --git a/WebKit/mac/Misc/WebNSPrintOperationExtras.m b/WebKit/mac/Misc/WebNSPrintOperationExtras.m
new file mode 100644
index 0000000..4c45f17
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSPrintOperationExtras.m
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNSPrintOperationExtras.h"
+
+@implementation NSPrintOperation (WebKitExtras)
+
+- (float)_web_pageSetupScaleFactor
+{
+ return [[[[self printInfo] dictionary] objectForKey:NSPrintScalingFactor] floatValue];
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSURLExtras.h b/WebKit/mac/Misc/WebNSURLExtras.h
new file mode 100644
index 0000000..f8823b9
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSURLExtras.h
@@ -0,0 +1,95 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@interface NSURL (WebNSURLExtras)
+
++ (NSURL *)_web_URLWithUserTypedString:(NSString *)string;
++ (NSURL *)_web_URLWithUserTypedString:(NSString *)string relativeToURL:(NSURL *)URL;
+
++ (NSURL *)_web_URLWithDataAsString:(NSString *)string;
++ (NSURL *)_web_URLWithDataAsString:(NSString *)string relativeToURL:(NSURL *)baseURL;
+
++ (NSURL *)_web_URLWithData:(NSData *)data;
++ (NSURL *)_web_URLWithData:(NSData *)data relativeToURL:(NSURL *)baseURL;
+
+- (NSURL *)_web_URLWithLowercasedScheme;
+
+- (NSData *)_web_originalData;
+- (NSString *)_web_originalDataAsString;
+- (const char *)_web_URLCString;
+
+- (NSData *)_web_hostData;
+- (NSString *)_web_hostString;
+
+- (NSString *)_web_userVisibleString;
+
+- (BOOL)_web_isEmpty;
+
+// FIXME: change these names back to _web_ when identically-named
+// methods are removed from Foundation
+
+- (NSURL *)_webkit_canonicalize;
+- (NSURL *)_webkit_URLByRemovingFragment;
+- (NSURL *)_webkit_URLByRemovingResourceSpecifier;
+
+- (BOOL)_webkit_isJavaScriptURL;
+- (NSString *)_webkit_scriptIfJavaScriptURL;
+- (BOOL)_webkit_isFTPDirectoryURL;
+
+- (BOOL)_webkit_shouldLoadAsEmptyDocument;
+
+- (NSString *)_webkit_suggestedFilenameWithMIMEType:(NSString *)MIMEType;
+
+@end
+
+@interface NSString (WebNSURLExtras)
+
+- (BOOL)_web_isUserVisibleURL;
+
+- (BOOL)_web_hostNameNeedsDecodingWithRange:(NSRange)range; // returns NO if decodeHostNameWithRange: would return nil, but more efficient
+- (BOOL)_web_hostNameNeedsEncodingWithRange:(NSRange)range; // returns NO if encodeHostNameWithRange: would return nil, but more efficient
+
+- (NSString *)_web_decodeHostNameWithRange:(NSRange)range; // turns funny-looking ASCII form into Unicode, returns nil if no decoding needed
+- (NSString *)_web_encodeHostNameWithRange:(NSRange)range; // turns Unicode into funny-looking ASCII form, returns nil if no decoding needed
+
+- (NSString *)_web_decodeHostName; // turns funny-looking ASCII form into Unicode, returns self if no decoding needed, convenient cover
+- (NSString *)_web_encodeHostName; // turns Unicode into funny-looking ASCII form, returns self if no decoding needed, convenient cover
+
+// FIXME: change these names back to _web_ when identically-named
+// methods are removed from or renamed in Foundation
+- (BOOL)_webkit_isJavaScriptURL;
+- (BOOL)_webkit_isFTPDirectoryURL;
+- (BOOL)_webkit_isFileURL;
+- (BOOL)_webkit_looksLikeAbsoluteURL;
+- (NSRange)_webkit_rangeOfURLScheme;
+- (NSString *)_webkit_URLFragment;
+- (NSString *)_webkit_scriptIfJavaScriptURL;
+
+@end
diff --git a/WebKit/mac/Misc/WebNSURLExtras.mm b/WebKit/mac/Misc/WebNSURLExtras.mm
new file mode 100644
index 0000000..df1f9da
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSURLExtras.mm
@@ -0,0 +1,1098 @@
+/*
+ * Copyright (C) 2005, 2007, 2008 Apple Inc. All rights reserved.
+ * Copyright (C) 2006 Alexey Proskuryakov (ap@nypop.com)
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNSURLExtras.h"
+
+#import "WebKitNSStringExtras.h"
+#import "WebLocalizableStrings.h"
+#import "WebNSDataExtras.h"
+#import "WebNSObjectExtras.h"
+#import "WebSystemInterface.h"
+#import <Foundation/NSURLRequest.h>
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/KURL.h>
+#import <WebCore/LoaderNSURLExtras.h>
+#import <WebKitSystemInterface.h>
+#import <unicode/uchar.h>
+#import <unicode/uidna.h>
+#import <unicode/uscript.h>
+
+using namespace WebCore;
+using namespace WTF;
+
+typedef void (* StringRangeApplierFunction)(NSString *string, NSRange range, void *context);
+
+// Needs to be big enough to hold an IDN-encoded name.
+// For host names bigger than this, we won't do IDN encoding, which is almost certainly OK.
+#define HOST_NAME_BUFFER_LENGTH 2048
+
+#define URL_BYTES_BUFFER_LENGTH 2048
+
+static pthread_once_t IDNScriptWhiteListFileRead = PTHREAD_ONCE_INIT;
+static uint32_t IDNScriptWhiteList[(USCRIPT_CODE_LIMIT + 31) / 32];
+
+static inline BOOL isLookalikeCharacter(int charCode)
+{
+// FIXME: Move this code down into WebCore so it can be shared with other platforms.
+
+// This function treats the following as unsafe, lookalike characters:
+// any non-printable character, any character considered as whitespace that isn't already converted to a space by ICU,
+// and any ignorable character.
+
+// We also considered the characters in Mozilla's blacklist (http://kb.mozillazine.org/Network.IDN.blacklist_chars),
+// and included all of these characters that ICU can encode.
+
+ if (!u_isprint(charCode) || u_isUWhiteSpace(charCode) || u_hasBinaryProperty(charCode, UCHAR_DEFAULT_IGNORABLE_CODE_POINT))
+ return YES;
+
+ switch (charCode) {
+ case 0x01C3: /* LATIN LETTER RETROFLEX CLICK */
+ case 0x0337: /* COMBINING SHORT SOLIDUS OVERLAY */
+ case 0x0338: /* COMBINING LONG SOLIDUS OVERLAY */
+ case 0x05B4: /* HEBREW POINT HIRIQ */
+ case 0x05BC: /* HEBREW POINT DAGESH OR MAPIQ */
+ case 0x05C3: /* HEBREW PUNCTUATION SOF PASUQ */
+ case 0x05F4: /* HEBREW PUNCTUATION GERSHAYIM */
+ case 0x0660: /* ARABIC INDIC DIGIT ZERO */
+ case 0x06D4: /* ARABIC FULL STOP */
+ case 0x06F0: /* EXTENDED ARABIC INDIC DIGIT ZERO */
+ case 0x2027: /* HYPHENATION POINT */
+ case 0x2039: /* SINGLE LEFT-POINTING ANGLE QUOTATION MARK */
+ case 0x203A: /* SINGLE RIGHT-POINTING ANGLE QUOTATION MARK */
+ case 0x2044: /* FRACTION SLASH */
+ case 0x2215: /* DIVISION SLASH */
+ case 0x23ae: /* INTEGRAL EXTENSION */
+ case 0x2571: /* BOX DRAWINGS LIGHT DIAGONAL UPPER RIGHT TO LOWER LEFT */
+ case 0x29F8: /* BIG SOLIDUS */
+ case 0x29f6: /* SOLIDUS WITH OVERBAR */
+ case 0x2AFB: /* TRIPLE SOLIDUS BINARY RELATION */
+ case 0x2AFD: /* DOUBLE SOLIDUS OPERATOR */
+ case 0x3008: /* LEFT ANGLE BRACKET */
+ case 0x3014: /* LEFT TORTOISE SHELL BRACKET */
+ case 0x3015: /* RIGHT TORTOISE SHELL BRACKET */
+ case 0x3033: /* VERTICAL KANA REPEAT MARK UPPER HALF */
+ case 0x321D: /* PARENTHESIZED KOREAN CHARACTER OJEON */
+ case 0x321E: /* PARENTHESIZED KOREAN CHARACTER O HU */
+ case 0x33DF: /* SQUARE A OVER M */
+ case 0xFE14: /* PRESENTATION FORM FOR VERTICAL SEMICOLON */
+ case 0xFE15: /* PRESENTATION FORM FOR VERTICAL EXCLAMATION MARK */
+ case 0xFE3F: /* PRESENTATION FORM FOR VERTICAL LEFT ANGLE BRACKET */
+ case 0xFE5D: /* SMALL LEFT TORTOISE SHELL BRACKET */
+ case 0xFE5E: /* SMALL RIGHT TORTOISE SHELL BRACKET */
+ return YES;
+ default:
+ return NO;
+ }
+}
+
+static char hexDigit(int i)
+{
+ if (i < 0 || i > 16) {
+ LOG_ERROR("illegal hex digit");
+ return '0';
+ }
+ int h = i;
+ if (h >= 10) {
+ h = h - 10 + 'A';
+ }
+ else {
+ h += '0';
+ }
+ return h;
+}
+
+static BOOL isHexDigit(char c)
+{
+ return (c >= '0' && c <= '9') || (c >= 'A' && c <= 'F') || (c >= 'a' && c <= 'f');
+}
+
+static int hexDigitValue(char c)
+{
+ if (c >= '0' && c <= '9') {
+ return c - '0';
+ }
+ if (c >= 'A' && c <= 'F') {
+ return c - 'A' + 10;
+ }
+ if (c >= 'a' && c <= 'f') {
+ return c - 'a' + 10;
+ }
+ LOG_ERROR("illegal hex digit");
+ return 0;
+}
+
+static void applyHostNameFunctionToMailToURLString(NSString *string, StringRangeApplierFunction f, void *context)
+{
+ // In a mailto: URL, host names come after a '@' character and end with a '>' or ',' or '?' character.
+ // Skip quoted strings so that characters in them don't confuse us.
+ // When we find a '?' character, we are past the part of the URL that contains host names.
+
+ static NSCharacterSet *hostNameOrStringStartCharacters;
+ if (hostNameOrStringStartCharacters == nil) {
+ hostNameOrStringStartCharacters = [NSCharacterSet characterSetWithCharactersInString:@"\"@?"];
+ CFRetain(hostNameOrStringStartCharacters);
+ }
+ static NSCharacterSet *hostNameEndCharacters;
+ if (hostNameEndCharacters == nil) {
+ hostNameEndCharacters = [NSCharacterSet characterSetWithCharactersInString:@">,?"];
+ CFRetain(hostNameEndCharacters);
+ }
+ static NSCharacterSet *quotedStringCharacters;
+ if (quotedStringCharacters == nil) {
+ quotedStringCharacters = [NSCharacterSet characterSetWithCharactersInString:@"\"\\"];
+ CFRetain(quotedStringCharacters);
+ }
+
+ unsigned stringLength = [string length];
+ NSRange remaining = NSMakeRange(0, stringLength);
+
+ while (1) {
+ // Find start of host name or of quoted string.
+ NSRange hostNameOrStringStart = [string rangeOfCharacterFromSet:hostNameOrStringStartCharacters options:0 range:remaining];
+ if (hostNameOrStringStart.location == NSNotFound) {
+ return;
+ }
+ unichar c = [string characterAtIndex:hostNameOrStringStart.location];
+ remaining.location = NSMaxRange(hostNameOrStringStart);
+ remaining.length = stringLength - remaining.location;
+
+ if (c == '?') {
+ return;
+ }
+
+ if (c == '@') {
+ // Find end of host name.
+ unsigned hostNameStart = remaining.location;
+ NSRange hostNameEnd = [string rangeOfCharacterFromSet:hostNameEndCharacters options:0 range:remaining];
+ BOOL done;
+ if (hostNameEnd.location == NSNotFound) {
+ hostNameEnd.location = stringLength;
+ done = YES;
+ } else {
+ remaining.location = hostNameEnd.location;
+ remaining.length = stringLength - remaining.location;
+ done = NO;
+ }
+
+ // Process host name range.
+ f(string, NSMakeRange(hostNameStart, hostNameEnd.location - hostNameStart), context);
+
+ if (done) {
+ return;
+ }
+ } else {
+ // Skip quoted string.
+ ASSERT(c == '"');
+ while (1) {
+ NSRange escapedCharacterOrStringEnd = [string rangeOfCharacterFromSet:quotedStringCharacters options:0 range:remaining];
+ if (escapedCharacterOrStringEnd.location == NSNotFound) {
+ return;
+ }
+ c = [string characterAtIndex:escapedCharacterOrStringEnd.location];
+ remaining.location = NSMaxRange(escapedCharacterOrStringEnd);
+ remaining.length = stringLength - remaining.location;
+
+ // If we are the end of the string, then break from the string loop back to the host name loop.
+ if (c == '"') {
+ break;
+ }
+
+ // Skip escaped character.
+ ASSERT(c == '\\');
+ if (remaining.length == 0) {
+ return;
+ }
+ remaining.location += 1;
+ remaining.length -= 1;
+ }
+ }
+ }
+}
+
+static void applyHostNameFunctionToURLString(NSString *string, StringRangeApplierFunction f, void *context)
+{
+ // Find hostnames. Too bad we can't use any real URL-parsing code to do this,
+ // but we have to do it before doing all the %-escaping, and this is the only
+ // code we have that parses mailto URLs anyway.
+
+ // Maybe we should implement this using a character buffer instead?
+
+ if ([string _webkit_hasCaseInsensitivePrefix:@"mailto:"]) {
+ applyHostNameFunctionToMailToURLString(string, f, context);
+ return;
+ }
+
+ // Find the host name in a hierarchical URL.
+ // It comes after a "://" sequence, with scheme characters preceding.
+ // If ends with the end of the string or a ":", "/", or a "?".
+ // If there is a "@" character, the host part is just the part after the "@".
+ NSRange separatorRange = [string rangeOfString:@"://"];
+ if (separatorRange.location == NSNotFound) {
+ return;
+ }
+
+ // Check that all characters before the :// are valid scheme characters.
+ static NSCharacterSet *nonSchemeCharacters;
+ if (nonSchemeCharacters == nil) {
+ nonSchemeCharacters = [[NSCharacterSet characterSetWithCharactersInString:@"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+-."] invertedSet];
+ CFRetain(nonSchemeCharacters);
+ }
+ if ([string rangeOfCharacterFromSet:nonSchemeCharacters options:0 range:NSMakeRange(0, separatorRange.location)].location != NSNotFound) {
+ return;
+ }
+
+ unsigned stringLength = [string length];
+
+ static NSCharacterSet *hostTerminators;
+ if (hostTerminators == nil) {
+ hostTerminators = [NSCharacterSet characterSetWithCharactersInString:@":/?#"];
+ CFRetain(hostTerminators);
+ }
+
+ // Start after the separator.
+ unsigned authorityStart = NSMaxRange(separatorRange);
+
+ // Find terminating character.
+ NSRange hostNameTerminator = [string rangeOfCharacterFromSet:hostTerminators options:0 range:NSMakeRange(authorityStart, stringLength - authorityStart)];
+ unsigned hostNameEnd = hostNameTerminator.location == NSNotFound ? stringLength : hostNameTerminator.location;
+
+ // Find "@" for the start of the host name.
+ NSRange userInfoTerminator = [string rangeOfString:@"@" options:0 range:NSMakeRange(authorityStart, hostNameEnd - authorityStart)];
+ unsigned hostNameStart = userInfoTerminator.location == NSNotFound ? authorityStart : NSMaxRange(userInfoTerminator);
+
+ f(string, NSMakeRange(hostNameStart, hostNameEnd - hostNameStart), context);
+}
+
+@implementation NSURL (WebNSURLExtras)
+
+static void collectRangesThatNeedMapping(NSString *string, NSRange range, void *context, BOOL encode)
+{
+ BOOL needsMapping = encode
+ ? [string _web_hostNameNeedsEncodingWithRange:range]
+ : [string _web_hostNameNeedsDecodingWithRange:range];
+ if (!needsMapping) {
+ return;
+ }
+
+ NSMutableArray **array = (NSMutableArray **)context;
+ if (*array == nil) {
+ *array = [[NSMutableArray alloc] init];
+ }
+
+ [*array addObject:[NSValue valueWithRange:range]];
+}
+
+static void collectRangesThatNeedEncoding(NSString *string, NSRange range, void *context)
+{
+ return collectRangesThatNeedMapping(string, range, context, YES);
+}
+
+static void collectRangesThatNeedDecoding(NSString *string, NSRange range, void *context)
+{
+ return collectRangesThatNeedMapping(string, range, context, NO);
+}
+
+static NSString *mapHostNames(NSString *string, BOOL encode)
+{
+ // Generally, we want to optimize for the case where there is one host name that does not need mapping.
+
+ if (encode && [string canBeConvertedToEncoding:NSASCIIStringEncoding])
+ return string;
+
+ // Make a list of ranges that actually need mapping.
+ NSMutableArray *hostNameRanges = nil;
+ StringRangeApplierFunction f = encode
+ ? collectRangesThatNeedEncoding
+ : collectRangesThatNeedDecoding;
+ applyHostNameFunctionToURLString(string, f, &hostNameRanges);
+ if (hostNameRanges == nil)
+ return string;
+
+ // Do the mapping.
+ NSMutableString *mutableCopy = [string mutableCopy];
+ unsigned i = [hostNameRanges count];
+ while (i-- != 0) {
+ NSRange hostNameRange = [[hostNameRanges objectAtIndex:i] rangeValue];
+ NSString *mappedHostName = encode
+ ? [string _web_encodeHostNameWithRange:hostNameRange]
+ : [string _web_decodeHostNameWithRange:hostNameRange];
+ [mutableCopy replaceCharactersInRange:hostNameRange withString:mappedHostName];
+ }
+ [hostNameRanges release];
+ return [mutableCopy autorelease];
+}
+
++ (NSURL *)_web_URLWithUserTypedString:(NSString *)string relativeToURL:(NSURL *)URL
+{
+ if (string == nil) {
+ return nil;
+ }
+ string = mapHostNames([string _webkit_stringByTrimmingWhitespace], YES);
+
+ NSData *userTypedData = [string dataUsingEncoding:NSUTF8StringEncoding];
+ ASSERT(userTypedData);
+
+ const UInt8 *inBytes = static_cast<const UInt8 *>([userTypedData bytes]);
+ int inLength = [userTypedData length];
+ if (inLength == 0) {
+ return [NSURL URLWithString:@""];
+ }
+
+ char *outBytes = static_cast<char *>(malloc(inLength * 3)); // large enough to %-escape every character
+ char *p = outBytes;
+ int outLength = 0;
+ int i;
+ for (i = 0; i < inLength; i++) {
+ UInt8 c = inBytes[i];
+ if (c <= 0x20 || c >= 0x7f) {
+ *p++ = '%';
+ *p++ = hexDigit(c >> 4);
+ *p++ = hexDigit(c & 0xf);
+ outLength += 3;
+ }
+ else {
+ *p++ = c;
+ outLength++;
+ }
+ }
+
+ NSData *data = [NSData dataWithBytesNoCopy:outBytes length:outLength]; // adopts outBytes
+ return [self _web_URLWithData:data relativeToURL:URL];
+}
+
++ (NSURL *)_web_URLWithUserTypedString:(NSString *)string
+{
+ return [self _web_URLWithUserTypedString:string relativeToURL:nil];
+}
+
++ (NSURL *)_web_URLWithDataAsString:(NSString *)string
+{
+ if (string == nil) {
+ return nil;
+ }
+ return [self _web_URLWithDataAsString:string relativeToURL:nil];
+}
+
++ (NSURL *)_web_URLWithDataAsString:(NSString *)string relativeToURL:(NSURL *)baseURL
+{
+ if (string == nil) {
+ return nil;
+ }
+ string = [string _webkit_stringByTrimmingWhitespace];
+ NSData *data = [string dataUsingEncoding:NSISOLatin1StringEncoding];
+ return [self _web_URLWithData:data relativeToURL:baseURL];
+}
+
++ (NSURL *)_web_URLWithData:(NSData *)data
+{
+ return [NSURL _web_URLWithData:data relativeToURL:nil];
+}
+
++ (NSURL *)_web_URLWithData:(NSData *)data relativeToURL:(NSURL *)baseURL
+{
+ if (data == nil)
+ return nil;
+
+ NSURL *result = nil;
+ size_t length = [data length];
+ if (length > 0) {
+ // work around <rdar://4470771>: CFURLCreateAbsoluteURLWithBytes(.., TRUE) doesn't remove non-path components.
+ baseURL = [baseURL _webkit_URLByRemovingResourceSpecifier];
+
+ const UInt8 *bytes = static_cast<const UInt8*>([data bytes]);
+ // NOTE: We use UTF-8 here since this encoding is used when computing strings when returning URL components
+ // (e.g calls to NSURL -path). However, this function is not tolerant of illegal UTF-8 sequences, which
+ // could either be a malformed string or bytes in a different encoding, like shift-jis, so we fall back
+ // onto using ISO Latin 1 in those cases.
+ result = WebCFAutorelease(CFURLCreateAbsoluteURLWithBytes(NULL, bytes, length, kCFStringEncodingUTF8, (CFURLRef)baseURL, YES));
+ if (!result)
+ result = WebCFAutorelease(CFURLCreateAbsoluteURLWithBytes(NULL, bytes, length, kCFStringEncodingISOLatin1, (CFURLRef)baseURL, YES));
+ } else
+ result = [NSURL URLWithString:@""];
+
+ return result;
+}
+
+- (NSData *)_web_originalData
+{
+ UInt8 *buffer = (UInt8 *)malloc(URL_BYTES_BUFFER_LENGTH);
+ CFIndex bytesFilled = CFURLGetBytes((CFURLRef)self, buffer, URL_BYTES_BUFFER_LENGTH);
+ if (bytesFilled == -1) {
+ CFIndex bytesToAllocate = CFURLGetBytes((CFURLRef)self, NULL, 0);
+ buffer = (UInt8 *)realloc(buffer, bytesToAllocate);
+ bytesFilled = CFURLGetBytes((CFURLRef)self, buffer, bytesToAllocate);
+ ASSERT(bytesFilled == bytesToAllocate);
+ }
+
+ // buffer is adopted by the NSData
+ NSData *data = [NSData dataWithBytesNoCopy:buffer length:bytesFilled freeWhenDone:YES];
+
+ NSURL *baseURL = (NSURL *)CFURLGetBaseURL((CFURLRef)self);
+ if (baseURL)
+ return [[NSURL _web_URLWithData:data relativeToURL:baseURL] _web_originalData];
+ return data;
+}
+
+- (NSString *)_web_originalDataAsString
+{
+ return [[[NSString alloc] initWithData:[self _web_originalData] encoding:NSISOLatin1StringEncoding] autorelease];
+}
+
+- (NSString *)_web_userVisibleString
+{
+ NSData *data = [self _web_originalData];
+ const unsigned char *before = static_cast<const unsigned char*>([data bytes]);
+ int length = [data length];
+
+ bool needsHostNameDecoding = false;
+
+ const unsigned char *p = before;
+ int bufferLength = (length * 3) + 1;
+ char *after = static_cast<char *>(malloc(bufferLength)); // large enough to %-escape every character
+ char *q = after;
+ int i;
+ for (i = 0; i < length; i++) {
+ unsigned char c = p[i];
+ // escape control characters, space, and delete
+ if (c <= 0x20 || c == 0x7f) {
+ *q++ = '%';
+ *q++ = hexDigit(c >> 4);
+ *q++ = hexDigit(c & 0xf);
+ }
+ // unescape escape sequences that indicate bytes greater than 0x7f
+ else if (c == '%' && (i + 1 < length && isHexDigit(p[i + 1])) && i + 2 < length && isHexDigit(p[i + 2])) {
+ unsigned char u = (hexDigitValue(p[i + 1]) << 4) | hexDigitValue(p[i + 2]);
+ if (u > 0x7f) {
+ // unescape
+ *q++ = u;
+ }
+ else {
+ // do not unescape
+ *q++ = p[i];
+ *q++ = p[i + 1];
+ *q++ = p[i + 2];
+ }
+ i += 2;
+ }
+ else {
+ *q++ = c;
+
+ // Check for "xn--" in an efficient, non-case-sensitive, way.
+ if (c == '-' && i >= 3 && !needsHostNameDecoding && (q[-4] | 0x20) == 'x' && (q[-3] | 0x20) == 'n' && q[-2] == '-')
+ needsHostNameDecoding = true;
+ }
+ }
+ *q = '\0';
+
+ // Check string to see if it can be converted to display using UTF-8
+ NSString *result = [NSString stringWithUTF8String:after];
+ if (!result) {
+ // Could not convert to UTF-8.
+ // Convert characters greater than 0x7f to escape sequences.
+ // Shift current string to the end of the buffer
+ // then we will copy back bytes to the start of the buffer
+ // as we convert.
+ int afterlength = q - after;
+ char *p = after + bufferLength - afterlength - 1;
+ memmove(p, after, afterlength + 1); // copies trailing '\0'
+ char *q = after;
+ while (*p) {
+ unsigned char c = *p;
+ if (c > 0x7f) {
+ *q++ = '%';
+ *q++ = hexDigit(c >> 4);
+ *q++ = hexDigit(c & 0xf);
+ }
+ else {
+ *q++ = *p;
+ }
+ p++;
+ }
+ *q = '\0';
+ result = [NSString stringWithUTF8String:after];
+ }
+
+ free(after);
+
+ // As an optimization, only do host name decoding if we have "xn--" somewhere.
+ return needsHostNameDecoding ? mapHostNames(result, NO) : result;
+}
+
+- (BOOL)_web_isEmpty
+{
+ if (!CFURLGetBaseURL((CFURLRef)self))
+ return CFURLGetBytes((CFURLRef)self, NULL, 0) == 0;
+ return [[self _web_originalData] length] == 0;
+}
+
+- (const char *)_web_URLCString
+{
+ NSMutableData *data = [NSMutableData data];
+ [data appendData:[self _web_originalData]];
+ [data appendBytes:"\0" length:1];
+ return (const char *)[data bytes];
+ }
+
+- (NSURL *)_webkit_canonicalize
+{
+ NSURLRequest *request = [[NSURLRequest alloc] initWithURL:self];
+ Class concreteClass = WKNSURLProtocolClassForRequest(request);
+ if (!concreteClass) {
+ [request release];
+ return self;
+ }
+
+ // This applies NSURL's concept of canonicalization, but not KURL's concept. It would
+ // make sense to apply both, but when we tried that it caused a performance degradation
+ // (see 5315926). It might make sense to apply only the KURL concept and not the NSURL
+ // concept, but it's too risky to make that change for WebKit 3.0.
+ NSURLRequest *newRequest = [concreteClass canonicalRequestForRequest:request];
+ NSURL *newURL = [newRequest URL];
+ NSURL *result = [[newURL retain] autorelease];
+ [request release];
+
+ return result;
+}
+
+typedef struct {
+ NSString *scheme;
+ NSString *user;
+ NSString *password;
+ NSString *host;
+ CFIndex port; // kCFNotFound means ignore/omit
+ NSString *path;
+ NSString *query;
+ NSString *fragment;
+} WebKitURLComponents;
+
+- (NSURL *)_webkit_URLByRemovingComponent:(CFURLComponentType)component
+{
+ CFRange fragRg = CFURLGetByteRangeForComponent((CFURLRef)self, component, NULL);
+ // Check to see if a fragment exists before decomposing the URL.
+ if (fragRg.location == kCFNotFound)
+ return self;
+
+ UInt8 *urlBytes, buffer[2048];
+ CFIndex numBytes = CFURLGetBytes((CFURLRef)self, buffer, 2048);
+ if (numBytes == -1) {
+ numBytes = CFURLGetBytes((CFURLRef)self, NULL, 0);
+ urlBytes = static_cast<UInt8*>(malloc(numBytes));
+ CFURLGetBytes((CFURLRef)self, urlBytes, numBytes);
+ } else
+ urlBytes = buffer;
+
+ NSURL *result = (NSURL *)CFMakeCollectable(CFURLCreateWithBytes(NULL, urlBytes, fragRg.location - 1, kCFStringEncodingUTF8, NULL));
+ if (!result)
+ result = (NSURL *)CFMakeCollectable(CFURLCreateWithBytes(NULL, urlBytes, fragRg.location - 1, kCFStringEncodingISOLatin1, NULL));
+
+ if (urlBytes != buffer) free(urlBytes);
+ return result ? [result autorelease] : self;
+}
+
+- (NSURL *)_webkit_URLByRemovingFragment
+{
+ return [self _webkit_URLByRemovingComponent:kCFURLComponentFragment];
+}
+
+- (NSURL *)_webkit_URLByRemovingResourceSpecifier
+{
+ return [self _webkit_URLByRemovingComponent:kCFURLComponentResourceSpecifier];
+}
+
+- (BOOL)_webkit_isJavaScriptURL
+{
+ return [[self _web_originalDataAsString] _webkit_isJavaScriptURL];
+}
+
+- (NSString *)_webkit_scriptIfJavaScriptURL
+{
+ return [[self absoluteString] _webkit_scriptIfJavaScriptURL];
+}
+
+- (BOOL)_webkit_isFileURL
+{
+ return [[self _web_originalDataAsString] _webkit_isFileURL];
+}
+
+- (BOOL)_webkit_isFTPDirectoryURL
+{
+ return [[self _web_originalDataAsString] _webkit_isFTPDirectoryURL];
+}
+
+- (BOOL)_webkit_shouldLoadAsEmptyDocument
+{
+ return [[self _web_originalDataAsString] _webkit_hasCaseInsensitivePrefix:@"about:"] || [self _web_isEmpty];
+}
+
+- (NSURL *)_web_URLWithLowercasedScheme
+{
+ CFRange range;
+ CFURLGetByteRangeForComponent((CFURLRef)self, kCFURLComponentScheme, &range);
+ if (range.location == kCFNotFound) {
+ return self;
+ }
+
+ UInt8 static_buffer[URL_BYTES_BUFFER_LENGTH];
+ UInt8 *buffer = static_buffer;
+ CFIndex bytesFilled = CFURLGetBytes((CFURLRef)self, buffer, URL_BYTES_BUFFER_LENGTH);
+ if (bytesFilled == -1) {
+ CFIndex bytesToAllocate = CFURLGetBytes((CFURLRef)self, NULL, 0);
+ buffer = static_cast<UInt8 *>(malloc(bytesToAllocate));
+ bytesFilled = CFURLGetBytes((CFURLRef)self, buffer, bytesToAllocate);
+ ASSERT(bytesFilled == bytesToAllocate);
+ }
+
+ int i;
+ BOOL changed = NO;
+ for (i = 0; i < range.length; ++i) {
+ char c = buffer[range.location + i];
+ char lower = toASCIILower(c);
+ if (c != lower) {
+ buffer[range.location + i] = lower;
+ changed = YES;
+ }
+ }
+
+ NSURL *result = changed
+ ? (NSURL *)WebCFAutorelease(CFURLCreateAbsoluteURLWithBytes(NULL, buffer, bytesFilled, kCFStringEncodingUTF8, nil, YES))
+ : (NSURL *)self;
+
+ if (buffer != static_buffer) {
+ free(buffer);
+ }
+
+ return result;
+}
+
+
+-(BOOL)_web_hasQuestionMarkOnlyQueryString
+{
+ CFRange rangeWithSeparators;
+ CFURLGetByteRangeForComponent((CFURLRef)self, kCFURLComponentQuery, &rangeWithSeparators);
+ if (rangeWithSeparators.location != kCFNotFound && rangeWithSeparators.length == 1) {
+ return YES;
+ }
+ return NO;
+}
+
+-(NSData *)_web_schemeSeparatorWithoutColon
+{
+ NSData *result = nil;
+ CFRange rangeWithSeparators;
+ CFRange range = CFURLGetByteRangeForComponent((CFURLRef)self, kCFURLComponentScheme, &rangeWithSeparators);
+ if (rangeWithSeparators.location != kCFNotFound) {
+ NSString *absoluteString = [self absoluteString];
+ NSRange separatorsRange = NSMakeRange(range.location + range.length + 1, rangeWithSeparators.length - range.length - 1);
+ if (separatorsRange.location + separatorsRange.length <= [absoluteString length]) {
+ NSString *slashes = [absoluteString substringWithRange:separatorsRange];
+ result = [slashes dataUsingEncoding:NSISOLatin1StringEncoding];
+ }
+ }
+ return result;
+}
+
+#define completeURL (CFURLComponentType)-1
+
+-(NSData *)_web_dataForURLComponentType:(CFURLComponentType)componentType
+{
+ static int URLComponentTypeBufferLength = 2048;
+
+ UInt8 staticAllBytesBuffer[URLComponentTypeBufferLength];
+ UInt8 *allBytesBuffer = staticAllBytesBuffer;
+
+ CFIndex bytesFilled = CFURLGetBytes((CFURLRef)self, allBytesBuffer, URLComponentTypeBufferLength);
+ if (bytesFilled == -1) {
+ CFIndex bytesToAllocate = CFURLGetBytes((CFURLRef)self, NULL, 0);
+ allBytesBuffer = static_cast<UInt8 *>(malloc(bytesToAllocate));
+ bytesFilled = CFURLGetBytes((CFURLRef)self, allBytesBuffer, bytesToAllocate);
+ }
+
+ CFRange range;
+ if (componentType != completeURL) {
+ range = CFURLGetByteRangeForComponent((CFURLRef)self, componentType, NULL);
+ if (range.location == kCFNotFound) {
+ return nil;
+ }
+ }
+ else {
+ range.location = 0;
+ range.length = bytesFilled;
+ }
+
+ NSData *componentData = [NSData dataWithBytes:allBytesBuffer + range.location length:range.length];
+
+ const unsigned char *bytes = static_cast<const unsigned char *>([componentData bytes]);
+ NSMutableData *resultData = [NSMutableData data];
+ // NOTE: add leading '?' to query strings non-zero length query strings.
+ // NOTE: retain question-mark only query strings.
+ if (componentType == kCFURLComponentQuery) {
+ if (range.length > 0 || [self _web_hasQuestionMarkOnlyQueryString]) {
+ [resultData appendBytes:"?" length:1];
+ }
+ }
+ int i;
+ for (i = 0; i < range.length; i++) {
+ unsigned char c = bytes[i];
+ if (c <= 0x20 || c >= 0x7f) {
+ char escaped[3];
+ escaped[0] = '%';
+ escaped[1] = hexDigit(c >> 4);
+ escaped[2] = hexDigit(c & 0xf);
+ [resultData appendBytes:escaped length:3];
+ }
+ else {
+ char b[1];
+ b[0] = c;
+ [resultData appendBytes:b length:1];
+ }
+ }
+
+ if (staticAllBytesBuffer != allBytesBuffer) {
+ free(allBytesBuffer);
+ }
+
+ return resultData;
+}
+
+-(NSData *)_web_schemeData
+{
+ return [self _web_dataForURLComponentType:kCFURLComponentScheme];
+}
+
+-(NSData *)_web_hostData
+{
+ NSData *result = [self _web_dataForURLComponentType:kCFURLComponentHost];
+ NSData *scheme = [self _web_schemeData];
+ // Take off localhost for file
+ if ([scheme _web_isCaseInsensitiveEqualToCString:"file"]) {
+ return ([result _web_isCaseInsensitiveEqualToCString:"localhost"]) ? nil : result;
+ }
+ return result;
+}
+
+- (NSString *)_web_hostString
+{
+ NSData *data = [self _web_hostData];
+ if (!data) {
+ data = [NSData data];
+ }
+ return [[[NSString alloc] initWithData:[self _web_hostData] encoding:NSUTF8StringEncoding] autorelease];
+}
+
+- (NSString *)_webkit_suggestedFilenameWithMIMEType:(NSString *)MIMEType
+{
+ return suggestedFilenameWithMIMEType(self, MIMEType);
+}
+
+@end
+
+@implementation NSString (WebNSURLExtras)
+
+- (BOOL)_web_isUserVisibleURL
+{
+ BOOL valid = YES;
+ // get buffer
+
+ char static_buffer[1024];
+ const char *p;
+ BOOL success = CFStringGetCString((CFStringRef)self, static_buffer, 1023, kCFStringEncodingUTF8);
+ if (success) {
+ p = static_buffer;
+ } else {
+ p = [self UTF8String];
+ }
+
+ int length = strlen(p);
+
+ // check for characters <= 0x20 or >=0x7f, %-escape sequences of %7f, and xn--, these
+ // are the things that will lead _web_userVisibleString to actually change things.
+ int i;
+ for (i = 0; i < length; i++) {
+ unsigned char c = p[i];
+ // escape control characters, space, and delete
+ if (c <= 0x20 || c == 0x7f) {
+ valid = NO;
+ break;
+ } else if (c == '%' && (i + 1 < length && isHexDigit(p[i + 1])) && i + 2 < length && isHexDigit(p[i + 2])) {
+ unsigned char u = (hexDigitValue(p[i + 1]) << 4) | hexDigitValue(p[i + 2]);
+ if (u > 0x7f) {
+ valid = NO;
+ break;
+ }
+ i += 2;
+ } else {
+ // Check for "xn--" in an efficient, non-case-sensitive, way.
+ if (c == '-' && i >= 3 && (p[i - 3] | 0x20) == 'x' && (p[i - 2] | 0x20) == 'n' && p[i - 1] == '-') {
+ valid = NO;
+ break;
+ }
+ }
+ }
+
+ return valid;
+}
+
+
+- (BOOL)_webkit_isJavaScriptURL
+{
+ return [self _webkit_hasCaseInsensitivePrefix:@"javascript:"];
+}
+
+- (BOOL)_webkit_isFileURL
+{
+ return [self rangeOfString:@"file:" options:(NSCaseInsensitiveSearch | NSAnchoredSearch)].location != NSNotFound;
+}
+
+- (NSString *)_webkit_stringByReplacingValidPercentEscapes
+{
+ return decodeURLEscapeSequences(self);
+}
+
+- (NSString *)_webkit_scriptIfJavaScriptURL
+{
+ if (![self _webkit_isJavaScriptURL]) {
+ return nil;
+ }
+ return [[self substringFromIndex:11] _webkit_stringByReplacingValidPercentEscapes];
+}
+
+- (BOOL)_webkit_isFTPDirectoryURL
+{
+ int length = [self length];
+ if (length < 5) { // 5 is length of "ftp:/"
+ return NO;
+ }
+ unichar lastChar = [self characterAtIndex:length - 1];
+ return lastChar == '/' && [self _webkit_hasCaseInsensitivePrefix:@"ftp:"];
+}
+
+
+static BOOL readIDNScriptWhiteListFile(NSString *filename)
+{
+ if (!filename) {
+ return NO;
+ }
+ FILE *file = fopen([filename fileSystemRepresentation], "r");
+ if (file == NULL) {
+ return NO;
+ }
+
+ // Read a word at a time.
+ // Allow comments, starting with # character to the end of the line.
+ while (1) {
+ // Skip a comment if present.
+ int result = fscanf(file, " #%*[^\n\r]%*[\n\r]");
+ if (result == EOF) {
+ break;
+ }
+
+ // Read a script name if present.
+ char word[33];
+ result = fscanf(file, " %32[^# \t\n\r]%*[^# \t\n\r] ", word);
+ if (result == EOF) {
+ break;
+ }
+ if (result == 1) {
+ // Got a word, map to script code and put it into the array.
+ int32_t script = u_getPropertyValueEnum(UCHAR_SCRIPT, word);
+ if (script >= 0 && script < USCRIPT_CODE_LIMIT) {
+ size_t index = script / 32;
+ uint32_t mask = 1 << (script % 32);
+ IDNScriptWhiteList[index] |= mask;
+ }
+ }
+ }
+ fclose(file);
+ return YES;
+}
+
+static void readIDNScriptWhiteList(void)
+{
+ // Read white list from library.
+ NSArray *dirs = NSSearchPathForDirectoriesInDomains(NSLibraryDirectory, NSAllDomainsMask, YES);
+ int i, numDirs = [dirs count];
+ for (i = 0; i < numDirs; i++) {
+ NSString *dir = [dirs objectAtIndex:i];
+ if (readIDNScriptWhiteListFile([dir stringByAppendingPathComponent:@"IDNScriptWhiteList.txt"])) {
+ return;
+ }
+ }
+
+ // Fall back on white list inside bundle.
+ NSBundle *bundle = [NSBundle bundleWithIdentifier:@"com.apple.WebKit"];
+ readIDNScriptWhiteListFile([bundle pathForResource:@"IDNScriptWhiteList" ofType:@"txt"]);
+}
+
+static BOOL allCharactersInIDNScriptWhiteList(const UChar *buffer, int32_t length)
+{
+ pthread_once(&IDNScriptWhiteListFileRead, readIDNScriptWhiteList);
+
+ int32_t i = 0;
+ while (i < length) {
+ UChar32 c;
+ U16_NEXT(buffer, i, length, c)
+ UErrorCode error = U_ZERO_ERROR;
+ UScriptCode script = uscript_getScript(c, &error);
+ if (error != U_ZERO_ERROR) {
+ LOG_ERROR("got ICU error while trying to look at scripts: %d", error);
+ return NO;
+ }
+ if (script < 0) {
+ LOG_ERROR("got negative number for script code from ICU: %d", script);
+ return NO;
+ }
+ if (script >= USCRIPT_CODE_LIMIT) {
+ return NO;
+ }
+ size_t index = script / 32;
+ uint32_t mask = 1 << (script % 32);
+ if (!(IDNScriptWhiteList[index] & mask)) {
+ return NO;
+ }
+
+ if (isLookalikeCharacter(c))
+ return NO;
+ }
+ return YES;
+}
+
+// Return value of nil means no mapping is necessary.
+// If makeString is NO, then return value is either nil or self to indicate mapping is necessary.
+// If makeString is YES, then return value is either nil or the mapped string.
+- (NSString *)_web_mapHostNameWithRange:(NSRange)range encode:(BOOL)encode makeString:(BOOL)makeString
+{
+ if (range.length > HOST_NAME_BUFFER_LENGTH) {
+ return nil;
+ }
+
+ if ([self length] == 0)
+ return nil;
+
+ UChar sourceBuffer[HOST_NAME_BUFFER_LENGTH];
+ UChar destinationBuffer[HOST_NAME_BUFFER_LENGTH];
+
+ NSString *string = self;
+ if (encode && [self rangeOfString:@"%" options:NSLiteralSearch range:range].location != NSNotFound) {
+ NSString *substring = [self substringWithRange:range];
+ substring = WebCFAutorelease(CFURLCreateStringByReplacingPercentEscapes(NULL, (CFStringRef)substring, CFSTR("")));
+ if (substring != nil) {
+ string = substring;
+ range = NSMakeRange(0, [string length]);
+ }
+ }
+
+ int length = range.length;
+ [string getCharacters:sourceBuffer range:range];
+
+ UErrorCode error = U_ZERO_ERROR;
+ int32_t numCharactersConverted = (encode ? uidna_IDNToASCII : uidna_IDNToUnicode)
+ (sourceBuffer, length, destinationBuffer, HOST_NAME_BUFFER_LENGTH, UIDNA_ALLOW_UNASSIGNED, NULL, &error);
+ if (error != U_ZERO_ERROR) {
+ return nil;
+ }
+ if (numCharactersConverted == length && memcmp(sourceBuffer, destinationBuffer, length * sizeof(UChar)) == 0) {
+ return nil;
+ }
+ if (!encode && !allCharactersInIDNScriptWhiteList(destinationBuffer, numCharactersConverted)) {
+ return nil;
+ }
+ return makeString ? (NSString *)[NSString stringWithCharacters:destinationBuffer length:numCharactersConverted] : (NSString *)self;
+}
+
+- (BOOL)_web_hostNameNeedsDecodingWithRange:(NSRange)range
+{
+ return [self _web_mapHostNameWithRange:range encode:NO makeString:NO] != nil;
+}
+
+- (BOOL)_web_hostNameNeedsEncodingWithRange:(NSRange)range
+{
+ return [self _web_mapHostNameWithRange:range encode:YES makeString:NO] != nil;
+}
+
+- (NSString *)_web_decodeHostNameWithRange:(NSRange)range
+{
+ return [self _web_mapHostNameWithRange:range encode:NO makeString:YES];
+}
+
+- (NSString *)_web_encodeHostNameWithRange:(NSRange)range
+{
+ return [self _web_mapHostNameWithRange:range encode:YES makeString:YES];
+}
+
+- (NSString *)_web_decodeHostName
+{
+ NSString *name = [self _web_mapHostNameWithRange:NSMakeRange(0, [self length]) encode:NO makeString:YES];
+ return name == nil ? self : name;
+}
+
+- (NSString *)_web_encodeHostName
+{
+ NSString *name = [self _web_mapHostNameWithRange:NSMakeRange(0, [self length]) encode:YES makeString:YES];
+ return name == nil ? self : name;
+}
+
+-(NSRange)_webkit_rangeOfURLScheme
+{
+ NSRange colon = [self rangeOfString:@":"];
+ if (colon.location != NSNotFound && colon.location > 0) {
+ NSRange scheme = {0, colon.location};
+ static NSCharacterSet *InverseSchemeCharacterSet = nil;
+ if (!InverseSchemeCharacterSet) {
+ /*
+ This stuff is very expensive. 10-15 msec on a 2x1.2GHz. If not cached it swamps
+ everything else when adding items to the autocomplete DB. Makes me wonder if we
+ even need to enforce the character set here.
+ */
+ NSString *acceptableCharacters = @"ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz0123456789+.-";
+ InverseSchemeCharacterSet = [[[NSCharacterSet characterSetWithCharactersInString:acceptableCharacters] invertedSet] retain];
+ }
+ NSRange illegals = [self rangeOfCharacterFromSet:InverseSchemeCharacterSet options:0 range:scheme];
+ if (illegals.location == NSNotFound)
+ return scheme;
+ }
+ return NSMakeRange(NSNotFound, 0);
+}
+
+-(BOOL)_webkit_looksLikeAbsoluteURL
+{
+ // Trim whitespace because _web_URLWithString allows whitespace.
+ return [[self _webkit_stringByTrimmingWhitespace] _webkit_rangeOfURLScheme].location != NSNotFound;
+}
+
+- (NSString *)_webkit_URLFragment
+{
+ NSRange fragmentRange;
+
+ fragmentRange = [self rangeOfString:@"#" options:NSLiteralSearch];
+ if (fragmentRange.location == NSNotFound)
+ return nil;
+ return [self substringFromIndex:fragmentRange.location + 1];
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSURLRequestExtras.h b/WebKit/mac/Misc/WebNSURLRequestExtras.h
new file mode 100644
index 0000000..5dc30a2
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSURLRequestExtras.h
@@ -0,0 +1,44 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@interface NSURLRequest (WebNSURLRequestExtras)
+
+- (NSString *)_web_HTTPReferrer;
+- (NSString *)_web_HTTPContentType;
+- (BOOL)_web_isConditionalRequest;
+@end
+
+@interface NSMutableURLRequest (WebNSURLRequestExtras)
+
+- (void)_web_setHTTPContentType:(NSString *)contentType;
+- (void)_web_setHTTPReferrer:(NSString *)theReferrer;
+- (void)_web_setHTTPUserAgent:(NSString *)theUserAgent;
+
+@end
diff --git a/WebKit/mac/Misc/WebNSURLRequestExtras.m b/WebKit/mac/Misc/WebNSURLRequestExtras.m
new file mode 100644
index 0000000..770ff8f
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSURLRequestExtras.m
@@ -0,0 +1,88 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNSURLRequestExtras.h"
+
+#import "WebNSURLExtras.h"
+
+#define WebContentType (@"Content-Type")
+#define WebUserAgent (@"User-Agent")
+#define WebReferrer (@"Referer")
+
+@implementation NSURLRequest (WebNSURLRequestExtras)
+
+- (NSString *)_web_HTTPReferrer
+{
+ return [self valueForHTTPHeaderField:WebReferrer];
+}
+
+- (NSString *)_web_HTTPContentType
+{
+ return [self valueForHTTPHeaderField:WebContentType];
+}
+
+- (BOOL)_web_isConditionalRequest
+{
+ if ([self valueForHTTPHeaderField:@"If-Match"] ||
+ [self valueForHTTPHeaderField:@"If-Modified-Since"] ||
+ [self valueForHTTPHeaderField:@"If-None-Match"] ||
+ [self valueForHTTPHeaderField:@"If-Range"] ||
+ [self valueForHTTPHeaderField:@"If-Unmodified-Since"])
+ return YES;
+ return NO;
+}
+
+@end
+
+@implementation NSMutableURLRequest (WebNSURLRequestExtras)
+
+- (void)_web_setHTTPContentType:(NSString *)contentType
+{
+ [self setValue:contentType forHTTPHeaderField:WebContentType];
+}
+
+- (void)_web_setHTTPReferrer:(NSString *)referrer
+{
+ // Do not set the referrer to a string that refers to a file URL.
+ // That is a potential security hole.
+ if ([referrer _webkit_isFileURL])
+ return;
+
+ // Don't allow empty Referer: headers; some servers refuse them
+ if ([referrer length] == 0)
+ return;
+
+ [self setValue:referrer forHTTPHeaderField:WebReferrer];
+}
+
+- (void)_web_setHTTPUserAgent:(NSString *)userAgent
+{
+ [self setValue:userAgent forHTTPHeaderField:WebUserAgent];
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSUserDefaultsExtras.h b/WebKit/mac/Misc/WebNSUserDefaultsExtras.h
new file mode 100644
index 0000000..487fbc0
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSUserDefaultsExtras.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@interface NSUserDefaults (WebNSUserDefaultsExtras)
++ (NSString *)_webkit_preferredLanguageCode;
+@end
diff --git a/WebKit/mac/Misc/WebNSUserDefaultsExtras.m b/WebKit/mac/Misc/WebNSUserDefaultsExtras.m
new file mode 100644
index 0000000..b7d297a
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSUserDefaultsExtras.m
@@ -0,0 +1,130 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebNSUserDefaultsExtras.h>
+
+#import <JavaScriptCore/Assertions.h>
+#import <WebKitSystemInterface.h>
+
+@implementation NSString (WebNSUserDefaultsPrivate)
+
+- (NSString *)_webkit_HTTPStyleLanguageCode
+{
+ // Look up the language code using CFBundle.
+ NSString *languageCode = self;
+ NSString *preferredLanguageCode = [(id)WKCopyCFLocalizationPreferredName((CFStringRef)self) autorelease];
+
+ if (preferredLanguageCode)
+ languageCode = preferredLanguageCode;
+
+ // Make the string lowercase.
+ NSString *lowercaseLanguageCode = [languageCode lowercaseString];
+
+ // Turn a '_' into a '-' if it appears after a 2-letter language code.
+ if ([lowercaseLanguageCode length] < 3 || [lowercaseLanguageCode characterAtIndex:2] != '_') {
+ return lowercaseLanguageCode;
+ }
+ NSMutableString *result = [lowercaseLanguageCode mutableCopy];
+ [result replaceCharactersInRange:NSMakeRange(2, 1) withString:@"-"];
+ return [result autorelease];
+}
+
+@end
+
+@implementation NSUserDefaults (WebNSUserDefaultsExtras)
+
+static NSString *preferredLanguageCode = nil;
+static NSLock *preferredLanguageLock = nil;
+static pthread_once_t preferredLanguageLockOnce = PTHREAD_ONCE_INIT;
+static pthread_once_t addDefaultsChangeObserverOnce = PTHREAD_ONCE_INIT;
+
+static void makeLock(void)
+{
+ preferredLanguageLock = [[NSLock alloc] init];
+}
+
++ (void)_webkit_ensureAndLockPreferredLanguageLock
+{
+ pthread_once(&preferredLanguageLockOnce, makeLock);
+ [preferredLanguageLock lock];
+}
+
++ (void)_webkit_defaultsDidChange
+{
+ [self _webkit_ensureAndLockPreferredLanguageLock];
+
+ [preferredLanguageCode release];
+ preferredLanguageCode = nil;
+
+ [preferredLanguageLock unlock];
+}
+
+static void addDefaultsChangeObserver(void)
+{
+ [[NSNotificationCenter defaultCenter] addObserver:[NSUserDefaults class]
+ selector:@selector(_webkit_defaultsDidChange)
+ name:NSUserDefaultsDidChangeNotification
+ object:[NSUserDefaults standardUserDefaults]];
+}
+
++ (void)_webkit_addDefaultsChangeObserver
+{
+ pthread_once(&addDefaultsChangeObserverOnce, addDefaultsChangeObserver);
+}
+
++ (NSString *)_webkit_preferredLanguageCode
+{
+ // Get this outside the lock since it might block on the defaults lock, while we are inside registerDefaults:.
+ NSUserDefaults *standardDefaults = [self standardUserDefaults];
+
+ BOOL addObserver = NO;
+
+ [self _webkit_ensureAndLockPreferredLanguageLock];
+
+ if (!preferredLanguageCode) {
+ NSArray *languages = [standardDefaults stringArrayForKey:@"AppleLanguages"];
+ if ([languages count] == 0) {
+ preferredLanguageCode = [@"en" retain];
+ } else {
+ preferredLanguageCode = [[[languages objectAtIndex:0] _webkit_HTTPStyleLanguageCode] copy];
+ }
+ addObserver = YES;
+ }
+
+ NSString *code = [[preferredLanguageCode retain] autorelease];
+
+ [preferredLanguageLock unlock];
+
+ if (addObserver) {
+ [self _webkit_addDefaultsChangeObserver];
+ }
+
+ return code;
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSViewExtras.h b/WebKit/mac/Misc/WebNSViewExtras.h
new file mode 100644
index 0000000..a9c2717
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSViewExtras.h
@@ -0,0 +1,73 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <AppKit/AppKit.h>
+
+#define WebDragImageAlpha 0.75f
+
+@class DOMElement;
+@class WebFrameView;
+@class WebView;
+
+@interface NSView (WebExtras)
+
+// Returns the nearest enclosing view of the given class, or nil if none.
+- (NSView *)_web_superviewOfClass:(Class)viewClass;
+- (WebFrameView *)_web_parentWebFrameView;
+- (WebView *)_webView;
+
+// returns whether a drag should begin starting with mouseDownEvent; if the time
+// passes expiration or the mouse moves less than the hysteresis before the mouseUp event,
+// returns NO, else returns YES.
+- (BOOL)_web_dragShouldBeginFromMouseDown:(NSEvent *)mouseDownEvent
+ withExpiration:(NSDate *)expiration
+ xHysteresis:(float)xHysteresis
+ yHysteresis:(float)yHysteresis;
+
+// Calls _web_dragShouldBeginFromMouseDown:withExpiration:xHysteresis:yHysteresis: with
+// the default values for xHysteresis and yHysteresis
+- (BOOL)_web_dragShouldBeginFromMouseDown:(NSEvent *)mouseDownEvent
+ withExpiration:(NSDate *)expiration;
+
+// Convenience method. Returns NSDragOperationCopy if _web_bestURLFromPasteboard doesn't return nil.
+// Returns NSDragOperationNone otherwise.
+- (NSDragOperation)_web_dragOperationForDraggingInfo:(id <NSDraggingInfo>)sender;
+
+// Resizes and applies alpha to image and drags it.
+- (void)_web_DragImageForElement:(DOMElement *)element
+ rect:(NSRect)rect
+ event:(NSEvent *)event
+ pasteboard:(NSPasteboard *)pasteboard
+ source:(id)source
+ offset:(NSPoint *)dragImageOffset;
+
+- (BOOL)_web_firstResponderIsSelfOrDescendantView;
+
+- (NSRect)_web_convertRect:(NSRect)aRect toView:(NSView *)aView;
+
+@end
diff --git a/WebKit/mac/Misc/WebNSViewExtras.m b/WebKit/mac/Misc/WebNSViewExtras.m
new file mode 100644
index 0000000..70ff68a
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSViewExtras.m
@@ -0,0 +1,243 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebNSViewExtras.h>
+
+#import <WebKit/DOMExtensions.h>
+#import <WebKit/WebDataSource.h>
+#import <WebKit/WebFramePrivate.h>
+#import <WebKit/WebFrameViewInternal.h>
+#import <WebKit/WebNSImageExtras.h>
+#import <WebKit/WebNSPasteboardExtras.h>
+#import <WebKit/WebNSURLExtras.h>
+#import <WebKit/WebView.h>
+
+#define WebDragStartHysteresisX 5.0f
+#define WebDragStartHysteresisY 5.0f
+#define WebMaxDragImageSize NSMakeSize(400.0f, 400.0f)
+#define WebMaxOriginalImageArea (1500.0f * 1500.0f)
+#define WebDragIconRightInset 7.0f
+#define WebDragIconBottomInset 3.0f
+
+@implementation NSView (WebExtras)
+
+- (NSView *)_web_superviewOfClass:(Class)class
+{
+ NSView *view = [self superview];
+ while (view && ![view isKindOfClass:class])
+ view = [view superview];
+ return view;
+}
+
+- (WebFrameView *)_web_parentWebFrameView
+{
+ return (WebFrameView *)[self _web_superviewOfClass:[WebFrameView class]];
+}
+
+// FIXME: Mail is the only client of _webView, remove this method once no versions of Mail need it.
+- (WebView *)_webView
+{
+ return (WebView *)[self _web_superviewOfClass:[WebView class]];
+}
+
+/* Determine whether a mouse down should turn into a drag; started as copy of NSTableView code */
+- (BOOL)_web_dragShouldBeginFromMouseDown:(NSEvent *)mouseDownEvent
+ withExpiration:(NSDate *)expiration
+ xHysteresis:(float)xHysteresis
+ yHysteresis:(float)yHysteresis
+{
+ NSEvent *nextEvent, *firstEvent, *dragEvent, *mouseUp;
+ BOOL dragIt;
+
+ if ([mouseDownEvent type] != NSLeftMouseDown) {
+ return NO;
+ }
+
+ nextEvent = nil;
+ firstEvent = nil;
+ dragEvent = nil;
+ mouseUp = nil;
+ dragIt = NO;
+
+ while ((nextEvent = [[self window] nextEventMatchingMask:(NSLeftMouseUpMask | NSLeftMouseDraggedMask)
+ untilDate:expiration
+ inMode:NSEventTrackingRunLoopMode
+ dequeue:YES]) != nil) {
+ if (firstEvent == nil) {
+ firstEvent = nextEvent;
+ }
+
+ if ([nextEvent type] == NSLeftMouseDragged) {
+ float deltax = ABS([nextEvent locationInWindow].x - [mouseDownEvent locationInWindow].x);
+ float deltay = ABS([nextEvent locationInWindow].y - [mouseDownEvent locationInWindow].y);
+ dragEvent = nextEvent;
+
+ if (deltax >= xHysteresis) {
+ dragIt = YES;
+ break;
+ }
+
+ if (deltay >= yHysteresis) {
+ dragIt = YES;
+ break;
+ }
+ } else if ([nextEvent type] == NSLeftMouseUp) {
+ mouseUp = nextEvent;
+ break;
+ }
+ }
+
+ // Since we've been dequeuing the events (If we don't, we'll never see the mouse up...),
+ // we need to push some of the events back on. It makes sense to put the first and last
+ // drag events and the mouse up if there was one.
+ if (mouseUp != nil) {
+ [NSApp postEvent:mouseUp atStart:YES];
+ }
+ if (dragEvent != nil) {
+ [NSApp postEvent:dragEvent atStart:YES];
+ }
+ if (firstEvent != mouseUp && firstEvent != dragEvent) {
+ [NSApp postEvent:firstEvent atStart:YES];
+ }
+
+ return dragIt;
+}
+
+- (BOOL)_web_dragShouldBeginFromMouseDown:(NSEvent *)mouseDownEvent
+ withExpiration:(NSDate *)expiration
+{
+ return [self _web_dragShouldBeginFromMouseDown:mouseDownEvent
+ withExpiration:expiration
+ xHysteresis:WebDragStartHysteresisX
+ yHysteresis:WebDragStartHysteresisY];
+}
+
+
+- (NSDragOperation)_web_dragOperationForDraggingInfo:(id <NSDraggingInfo>)sender
+{
+ if (![NSApp modalWindow] &&
+ ![[self window] attachedSheet] &&
+ [sender draggingSource] != self &&
+ [[sender draggingPasteboard] _web_bestURL]) {
+
+ return NSDragOperationCopy;
+ }
+
+ return NSDragOperationNone;
+}
+
+- (void)_web_DragImageForElement:(DOMElement *)element
+ rect:(NSRect)rect
+ event:(NSEvent *)event
+ pasteboard:(NSPasteboard *)pasteboard
+ source:(id)source
+ offset:(NSPoint *)dragImageOffset
+{
+ NSPoint mouseDownPoint = [self convertPoint:[event locationInWindow] fromView:nil];
+ NSImage *dragImage;
+ NSPoint origin;
+
+ NSImage *image = [element image];
+ if (image != nil && [image size].height * [image size].width <= WebMaxOriginalImageArea) {
+ NSSize originalSize = rect.size;
+ origin = rect.origin;
+
+ dragImage = [[image copy] autorelease];
+ [dragImage setScalesWhenResized:YES];
+ [dragImage setSize:originalSize];
+
+ [dragImage _web_scaleToMaxSize:WebMaxDragImageSize];
+ NSSize newSize = [dragImage size];
+
+ [dragImage _web_dissolveToFraction:WebDragImageAlpha];
+
+ // Properly orient the drag image and orient it differently if it's smaller than the original
+ origin.x = mouseDownPoint.x - (((mouseDownPoint.x - origin.x) / originalSize.width) * newSize.width);
+ origin.y = origin.y + originalSize.height;
+ origin.y = mouseDownPoint.y - (((mouseDownPoint.y - origin.y) / originalSize.height) * newSize.height);
+ } else {
+ // FIXME: This has been broken for a while.
+ // There's no way to get the MIME type for the image from a DOM element.
+ // The old code used WKGetPreferredExtensionForMIMEType([image MIMEType]);
+ NSString *extension = @"";
+ dragImage = [[NSWorkspace sharedWorkspace] iconForFileType:extension];
+ NSSize offset = NSMakeSize([dragImage size].width - WebDragIconRightInset, -WebDragIconBottomInset);
+ origin = NSMakePoint(mouseDownPoint.x - offset.width, mouseDownPoint.y - offset.height);
+ }
+
+ // This is the offset from the lower left corner of the image to the mouse location. Because we
+ // are a flipped view the calculation of Y is inverted.
+ if (dragImageOffset) {
+ dragImageOffset->x = mouseDownPoint.x - origin.x;
+ dragImageOffset->y = origin.y - mouseDownPoint.y;
+ }
+
+ // Per kwebster, offset arg is ignored
+ [self dragImage:dragImage at:origin offset:NSZeroSize event:event pasteboard:pasteboard source:source slideBack:YES];
+}
+
+- (BOOL)_web_firstResponderIsSelfOrDescendantView
+{
+ NSResponder *responder = [[self window] firstResponder];
+ return (responder &&
+ (responder == self ||
+ ([responder isKindOfClass:[NSView class]] && [(NSView *)responder isDescendantOf:self])));
+}
+
+- (NSRect)_web_convertRect:(NSRect)aRect toView:(NSView *)aView
+{
+ // Converting to this view's window; let -convertRect:toView: handle it
+ if (aView == nil)
+ return [self convertRect:aRect toView:nil];
+
+ // This view must be in a window. Do whatever weird thing -convertRect:toView: does in this situation.
+ NSWindow *thisWindow = [self window];
+ if (!thisWindow)
+ return [self convertRect:aRect toView:aView];
+
+ // The other view must be in a window, too.
+ NSWindow *otherWindow = [aView window];
+ if (!otherWindow)
+ return [self convertRect:aRect toView:aView];
+
+ // Convert to this window's coordinates
+ NSRect convertedRect = [self convertRect:aRect toView:nil];
+
+ // Convert to screen coordinates
+ convertedRect.origin = [thisWindow convertBaseToScreen:convertedRect.origin];
+
+ // Convert to other window's coordinates
+ convertedRect.origin = [otherWindow convertScreenToBase:convertedRect.origin];
+
+ // Convert to other view's coordinates
+ convertedRect = [aView convertRect:convertedRect fromView:nil];
+
+ return convertedRect;
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebNSWindowExtras.h b/WebKit/mac/Misc/WebNSWindowExtras.h
new file mode 100644
index 0000000..0aebd4f
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSWindowExtras.h
@@ -0,0 +1,34 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@interface NSWindow (WebExtras)
+// centers "visually", putting 1/3 of the remaining space above, and 2/3 below
+- (void)centerOverMainWindow;
+@end
diff --git a/WebKit/mac/Misc/WebNSWindowExtras.m b/WebKit/mac/Misc/WebNSWindowExtras.m
new file mode 100644
index 0000000..ef27b13
--- /dev/null
+++ b/WebKit/mac/Misc/WebNSWindowExtras.m
@@ -0,0 +1,52 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNSWindowExtras.h"
+
+@implementation NSWindow (WebExtras)
+
+- (void)centerOverMainWindow
+{
+ NSRect frameToCenterOver;
+ if ([NSApp mainWindow]) {
+ frameToCenterOver = [[NSApp mainWindow] frame];
+ } else {
+ frameToCenterOver = [[NSScreen mainScreen] visibleFrame];
+ }
+
+ NSSize size = [self frame].size;
+ NSPoint origin;
+ origin.y = NSMaxY(frameToCenterOver)
+ - (frameToCenterOver.size.height - size.height) / 3
+ - size.height;
+ origin.x = frameToCenterOver.origin.x
+ + (frameToCenterOver.size.width - size.width) / 2;
+ [self setFrameOrigin:origin];
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebSearchableTextView.h b/WebKit/mac/Misc/WebSearchableTextView.h
new file mode 100644
index 0000000..fda38ee
--- /dev/null
+++ b/WebKit/mac/Misc/WebSearchableTextView.h
@@ -0,0 +1,32 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebDocumentPrivate.h>
+
+@interface WebSearchableTextView : NSTextView <WebDocumentSearching, WebDocumentSelection>
+@end
diff --git a/WebKit/mac/Misc/WebSearchableTextView.m b/WebKit/mac/Misc/WebSearchableTextView.m
new file mode 100644
index 0000000..f3106e5
--- /dev/null
+++ b/WebKit/mac/Misc/WebSearchableTextView.m
@@ -0,0 +1,254 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebSearchableTextView.h"
+#import "WebDocumentPrivate.h"
+#import "WebTypesInternal.h"
+
+@interface NSString (_Web_StringTextFinding)
+- (NSRange)findString:(NSString *)string selectedRange:(NSRange)selectedRange options:(unsigned)mask wrap:(BOOL)wrapFlag;
+@end
+
+@implementation WebSearchableTextView
+
+- (BOOL)searchFor: (NSString *)string direction: (BOOL)forward caseSensitive: (BOOL)caseFlag wrap: (BOOL)wrapFlag;
+{
+ if (![string length])
+ return NO;
+
+ BOOL lastFindWasSuccessful = NO;
+ NSString *textContents = [self string];
+ unsigned textLength;
+
+ if (textContents && (textLength = [textContents length])) {
+ NSRange range;
+ unsigned options = 0;
+
+ if (!forward)
+ options |= NSBackwardsSearch;
+
+ if (!caseFlag)
+ options |= NSCaseInsensitiveSearch;
+
+ range = [textContents findString:string selectedRange:[self selectedRange] options:options wrap:wrapFlag];
+ if (range.length) {
+ [self setSelectedRange:range];
+ [self scrollRangeToVisible:range];
+ lastFindWasSuccessful = YES;
+ }
+ }
+
+ return lastFindWasSuccessful;
+}
+
+- (void)copy:(id)sender
+{
+ if ([self isRichText]) {
+ [super copy:sender];
+ }else{
+ //Convert CRLF to LF to workaround: 3105538 - Carbon doesn't convert text with CRLF to LF
+ NSMutableString *string = [[[self string] substringWithRange:[self selectedRange]] mutableCopy];
+ [string replaceOccurrencesOfString:@"\r\n" withString:@"\n" options:0 range:NSMakeRange(0, [string length])];
+
+ NSPasteboard *pasteboard = [NSPasteboard generalPasteboard];
+ [pasteboard declareTypes:[NSArray arrayWithObject:NSStringPboardType] owner:self];
+ [pasteboard setString:string forType:NSStringPboardType];
+ }
+}
+
+- (NSRect)selectionRect
+{
+ // Note that this method would work for any NSTextView; some day we might want to use it
+ // for an NSTextView that isn't a WebTextView.
+ NSRect result = NSZeroRect;
+
+ // iterate over multiple selected ranges
+ NSEnumerator *rangeEnumerator = [[self selectedRanges] objectEnumerator];
+ NSValue *rangeAsValue;
+ while ((rangeAsValue = [rangeEnumerator nextObject]) != nil) {
+ NSRange range = [rangeAsValue rangeValue];
+ NSUInteger rectCount;
+ NSRectArray rectArray = [[self layoutManager] rectArrayForCharacterRange:range
+ withinSelectedCharacterRange:range
+ inTextContainer:[self textContainer]
+ rectCount:&rectCount];
+ unsigned i;
+ // iterate over multiple rects in each selected range
+ for (i = 0; i < rectCount; ++i) {
+ NSRect rect = rectArray[i];
+ if (NSEqualRects(result, NSZeroRect)) {
+ result = rect;
+ } else {
+ result = NSUnionRect(result, rect);
+ }
+ }
+ }
+
+ return result;
+}
+
+- (NSImage *)selectionImageForcingBlackText:(BOOL)forceBlackText
+{
+ // This is here to complete the <WebDocumentSelection> protocol, but it was introduced after this
+ // class was deprecated so there's no implementation.
+ return nil;
+}
+
+- (NSRect)selectionImageRect
+{
+ // This is here to complete the <WebDocumentSelection> protocol, but it was introduced after this
+ // class was deprecated so there's no implementation.
+ return NSZeroRect;
+}
+
+- (NSArray *)selectionTextRects
+{
+ // This is here to complete the <WebDocumentSelection> protocol, but it was introduced after this
+ // class was deprecated so there's no implementation.
+ return nil;
+}
+
+- (NSView *)selectionView
+{
+ return self;
+}
+
+- (NSArray *)pasteboardTypesForSelection
+{
+ return [self writablePasteboardTypes];
+}
+
+- (void)writeSelectionWithPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard
+{
+ [self writeSelectionToPasteboard:pasteboard types:types];
+}
+
+- (BOOL)supportsTextEncoding
+{
+ return YES;
+}
+
+- (NSString *)string
+{
+ return [super string];
+}
+
+- (NSAttributedString *)attributedString
+{
+ return [self attributedSubstringFromRange:NSMakeRange(0, [[self string] length])];
+}
+
+- (NSString *)selectedString
+{
+ return [[self string] substringWithRange:[self selectedRange]];
+}
+
+- (NSAttributedString *)selectedAttributedString
+{
+ return [self attributedSubstringFromRange:[self selectedRange]];
+}
+
+- (void)selectAll
+{
+ [self setSelectedRange:NSMakeRange(0, [[self string] length])];
+}
+
+- (void)deselectAll
+{
+ [self setSelectedRange:NSMakeRange(0,0)];
+}
+
+@end
+
+@implementation NSString (_Web_StringTextFinding)
+
+- (NSRange)findString:(NSString *)string selectedRange:(NSRange)selectedRange options:(unsigned)options wrap:(BOOL)wrap
+{
+ BOOL forwards = (options & NSBackwardsSearch) == 0;
+ unsigned length = [self length];
+ NSRange searchRange, range;
+
+ // Our search algorithm, used in WebCore also, is to search in the selection first. If the found text is the
+ // entire selection, then we search again from just past the selection.
+
+ if (forwards) {
+ // FIXME: If selectedRange has length of 0, we ignore it, which is appropriate for non-editable text (since
+ // a zero-length selection in non-editable is invisible). We might want to change this someday to only ignore the
+ // selection if its location is NSNotFound when the text is editable (and similarly for the backwards case).
+ searchRange.location = selectedRange.length > 0 ? selectedRange.location : 0;
+ searchRange.length = length - searchRange.location;
+ range = [self rangeOfString:string options:options range:searchRange];
+
+ // If found range matches (non-empty) selection, search again from just past selection
+ if (range.location != NSNotFound && NSEqualRanges(range, selectedRange)) {
+ searchRange.location = NSMaxRange(selectedRange);
+ searchRange.length = length - searchRange.location;
+ range = [self rangeOfString:string options:options range:searchRange];
+ }
+
+ // If not found, search again from the beginning. Make search range large enough that
+ // we'll find a match even if it partially overlapped the existing selection (including the
+ // case where it exactly matches the existing selection).
+ if ((range.length == 0) && wrap) {
+ searchRange.location = 0;
+ searchRange.length = selectedRange.location + selectedRange.length + [string length];
+ if (searchRange.length > length) {
+ searchRange.length = length;
+ }
+ range = [self rangeOfString:string options:options range:searchRange];
+ }
+ } else {
+ searchRange.location = 0;
+ searchRange.length = selectedRange.length > 0 ? NSMaxRange(selectedRange) : length;
+ range = [self rangeOfString:string options:options range:searchRange];
+
+ // If found range matches (non-empty) selection, search again from just before selection
+ if (range.location != NSNotFound && NSEqualRanges(range, selectedRange)) {
+ searchRange.location = 0;
+ searchRange.length = selectedRange.location;
+ range = [self rangeOfString:string options:options range:searchRange];
+ }
+
+ // If not found, search again from the end. Make search range large enough that
+ // we'll find a match even if it partially overlapped the existing selection (including the
+ // case where it exactly matches the existing selection).
+ if ((range.length == 0) && wrap) {
+ unsigned stringLength = [string length];
+ if (selectedRange.location > stringLength) {
+ searchRange.location = selectedRange.location - stringLength;
+ } else {
+ searchRange.location = 0;
+ }
+ searchRange.length = length - searchRange.location;
+ range = [self rangeOfString:string options:options range:searchRange];
+ }
+}
+return range;
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebStringTruncator.h b/WebKit/mac/Misc/WebStringTruncator.h
new file mode 100644
index 0000000..ed00d27
--- /dev/null
+++ b/WebKit/mac/Misc/WebStringTruncator.h
@@ -0,0 +1,44 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@class NSFont;
+
+@interface WebStringTruncator : NSObject
+
++ (NSString *)centerTruncateString:(NSString *)string toWidth:(float)maxWidth withFont:(NSFont *)font;
+
+// Default font is [NSFont menuFontOfSize:0].
++ (NSString *)centerTruncateString:(NSString *)string toWidth:(float)maxWidth;
+
++ (NSString *)rightTruncateString:(NSString *)string toWidth:(float)maxWidth withFont:(NSFont *)font;
+
++ (float)widthOfString:(NSString *)string font:(NSFont *)font;
+
+@end
diff --git a/WebKit/mac/Misc/WebStringTruncator.m b/WebKit/mac/Misc/WebStringTruncator.m
new file mode 100644
index 0000000..c395e7a
--- /dev/null
+++ b/WebKit/mac/Misc/WebStringTruncator.m
@@ -0,0 +1,92 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebStringTruncator.h"
+
+#import "WebSystemInterface.h"
+#import <WebCore/Font.h>
+#import <WebCore/FontPlatformData.h>
+#import <WebCore/PlatformString.h>
+#import <WebCore/StringTruncator.h>
+
+using namespace WebCore;
+
+static NSFont *defaultMenuFont()
+{
+ static NSFont *defaultMenuFont = nil;
+ if (!defaultMenuFont) {
+ defaultMenuFont = [NSFont menuFontOfSize:0];
+ CFRetain(defaultMenuFont);
+ }
+ return defaultMenuFont;
+}
+
+static Font& fontFromNSFont(NSFont *font)
+{
+ static NSFont *currentFont;
+ static Font currentRenderer;
+
+ if ([font isEqual:currentFont])
+ return currentRenderer;
+ if (currentFont)
+ CFRelease(currentFont);
+ currentFont = font;
+ CFRetain(currentFont);
+ FontPlatformData f(font);
+ currentRenderer = Font(f, ![[NSGraphicsContext currentContext] isDrawingToScreen]);
+ return currentRenderer;
+}
+
+@implementation WebStringTruncator
+
++ (void)initialize
+{
+ InitWebCoreSystemInterface();
+}
+
++ (NSString *)centerTruncateString:(NSString *)string toWidth:(float)maxWidth
+{
+ return StringTruncator::centerTruncate(string, maxWidth, fontFromNSFont(defaultMenuFont()));
+}
+
++ (NSString *)centerTruncateString:(NSString *)string toWidth:(float)maxWidth withFont:(NSFont *)font
+{
+ return StringTruncator::centerTruncate(string, maxWidth, fontFromNSFont(font));
+}
+
++ (NSString *)rightTruncateString:(NSString *)string toWidth:(float)maxWidth withFont:(NSFont *)font
+{
+ return StringTruncator::rightTruncate(string, maxWidth, fontFromNSFont(font));
+}
+
++ (float)widthOfString:(NSString *)string font:(NSFont *)font
+{
+ return StringTruncator::width(string, fontFromNSFont(font));
+}
+
+@end
diff --git a/WebKit/mac/Misc/WebTypesInternal.h b/WebKit/mac/Misc/WebTypesInternal.h
new file mode 100644
index 0000000..33bdf81
--- /dev/null
+++ b/WebKit/mac/Misc/WebTypesInternal.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifdef BUILDING_ON_TIGER
+typedef int NSInteger;
+typedef unsigned int NSUInteger;
+#endif
+
+#ifndef CGFLOAT_DEFINED
+#ifdef __LP64__
+typedef double CGFloat;
+#else
+typedef float CGFloat;
+#endif
+#define CGFLOAT_DEFINED 1
+#endif
diff --git a/WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/classes.nib b/WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/classes.nib
new file mode 100644
index 0000000..87a7210
--- /dev/null
+++ b/WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/classes.nib
@@ -0,0 +1,38 @@
+{
+ IBClasses = (
+ {CLASS = FirstResponder; LANGUAGE = ObjC; SUPERCLASS = NSObject; },
+ {
+ ACTIONS = {cancel = id; logIn = id; };
+ CLASS = IFAuthenticationPanel;
+ LANGUAGE = ObjC;
+ OUTLETS = {
+ imageView = id;
+ mainLabel = id;
+ panel = id;
+ password = id;
+ remember = id;
+ smallLabel = id;
+ username = id;
+ };
+ SUPERCLASS = NSObject;
+ },
+ {CLASS = NonBlockingPanel; LANGUAGE = ObjC; SUPERCLASS = NSPanel; },
+ {
+ ACTIONS = {cancel = id; logIn = id; };
+ CLASS = WebAuthenticationPanel;
+ LANGUAGE = ObjC;
+ OUTLETS = {
+ callback = id;
+ imageView = id;
+ mainLabel = id;
+ panel = id;
+ password = id;
+ remember = id;
+ smallLabel = id;
+ username = id;
+ };
+ SUPERCLASS = NSObject;
+ }
+ );
+ IBVersion = 1;
+} \ No newline at end of file
diff --git a/WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/info.nib b/WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/info.nib
new file mode 100644
index 0000000..eb229b0
--- /dev/null
+++ b/WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/info.nib
@@ -0,0 +1,16 @@
+<?xml version="1.0" encoding="UTF-8"?>
+<!DOCTYPE plist PUBLIC "-//Apple Computer//DTD PLIST 1.0//EN" "http://www.apple.com/DTDs/PropertyList-1.0.dtd">
+<plist version="1.0">
+<dict>
+ <key>IBDocumentLocation</key>
+ <string>773 144 356 240 0 0 1280 778 </string>
+ <key>IBFramework Version</key>
+ <string>446.1</string>
+ <key>IBOpenObjects</key>
+ <array>
+ <integer>5</integer>
+ </array>
+ <key>IBSystem Version</key>
+ <string>8N1106</string>
+</dict>
+</plist>
diff --git a/WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/objects.nib b/WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/objects.nib
new file mode 100644
index 0000000..59196ff
--- /dev/null
+++ b/WebKit/mac/Panels/English.lproj/WebAuthenticationPanel.nib/objects.nib
Binary files differ
diff --git a/WebKit/mac/Panels/WebAuthenticationPanel.h b/WebKit/mac/Panels/WebAuthenticationPanel.h
new file mode 100644
index 0000000..3e08857
--- /dev/null
+++ b/WebKit/mac/Panels/WebAuthenticationPanel.h
@@ -0,0 +1,68 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+#import <Foundation/NSURLCredentialStorage.h>
+
+@class NSURLAuthenticationChallenge;
+
+@interface WebAuthenticationPanel : NSObject
+{
+ IBOutlet id mainLabel;
+ IBOutlet id panel;
+ IBOutlet id password;
+ IBOutlet id smallLabel;
+ IBOutlet id username;
+ IBOutlet id imageView;
+ IBOutlet id remember;
+ BOOL nibLoaded;
+ BOOL usingSheet;
+ id callback;
+ SEL selector;
+ NSURLAuthenticationChallenge *challenge;
+}
+
+-(id)initWithCallback:(id)cb selector:(SEL)sel;
+
+// Interface-related methods
+- (IBAction)cancel:(id)sender;
+- (IBAction)logIn:(id)sender;
+
+- (BOOL)loadNib;
+
+- (void)runAsModalDialogWithChallenge:(NSURLAuthenticationChallenge *)chall;
+- (void)runAsSheetOnWindow:(NSWindow *)window withChallenge:(NSURLAuthenticationChallenge *)chall;
+
+- (void)sheetDidEnd:(NSWindow *)sheet returnCode:(int)returnCode contextInfo:(void *)contextInfo;
+
+@end
+
+// This is in the header so it can be used from the nib file
+@interface NonBlockingPanel : NSPanel
+@end
+
diff --git a/WebKit/mac/Panels/WebAuthenticationPanel.m b/WebKit/mac/Panels/WebAuthenticationPanel.m
new file mode 100644
index 0000000..b6904a1
--- /dev/null
+++ b/WebKit/mac/Panels/WebAuthenticationPanel.m
@@ -0,0 +1,244 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebAuthenticationPanel.h>
+
+#import <Foundation/NSURLAuthenticationChallenge.h>
+#import <Foundation/NSURLProtectionSpace.h>
+#import <Foundation/NSURLCredential.h>
+#import <JavaScriptCore/Assertions.h>
+#import <WebKit/WebLocalizableStrings.h>
+#import <WebKit/WebNSURLExtras.h>
+
+#import <WebKit/WebNSControlExtras.h>
+
+#define WebAuthenticationPanelNibName @"WebAuthenticationPanel"
+
+@implementation WebAuthenticationPanel
+
+-(id)initWithCallback:(id)cb selector:(SEL)sel
+{
+ self = [self init];
+ if (self != nil) {
+ callback = [cb retain];
+ selector = sel;
+ }
+ return self;
+}
+
+
+- (void)dealloc
+{
+ [panel release];
+
+ [callback release];
+
+ [super dealloc];
+}
+
+// IB actions
+
+- (IBAction)cancel:(id)sender
+{
+ // This is required because the body of this method is going to
+ // remove all of the panel's remaining refs, which can cause a
+ // crash later when finishing button hit tracking. So we make
+ // sure it lives on a bit longer.
+ [[panel retain] autorelease];
+
+ // This is required as a workaround for AppKit issue 4118422
+ [[self retain] autorelease];
+
+ [panel close];
+ if (usingSheet) {
+ [[NSApplication sharedApplication] endSheet:panel returnCode:1];
+ } else {
+ [[NSApplication sharedApplication] stopModalWithCode:1];
+ }
+}
+
+- (IBAction)logIn:(id)sender
+{
+ // This is required because the body of this method is going to
+ // remove all of the panel's remaining refs, which can cause a
+ // crash later when finishing button hit tracking. So we make
+ // sure it lives on a bit longer.
+ [[panel retain] autorelease];
+
+ [panel close];
+ if (usingSheet) {
+ [[NSApplication sharedApplication] endSheet:panel returnCode:0];
+ } else {
+ [[NSApplication sharedApplication] stopModalWithCode:0];
+ }
+}
+
+- (BOOL)loadNib
+{
+ if (!nibLoaded) {
+ if ([NSBundle loadNibNamed:WebAuthenticationPanelNibName owner:self]) {
+ nibLoaded = YES;
+ [imageView setImage:[NSImage imageNamed:@"NSApplicationIcon"]];
+ } else {
+ LOG_ERROR("couldn't load nib named '%@'", WebAuthenticationPanelNibName);
+ return FALSE;
+ }
+ }
+ return TRUE;
+}
+
+// Methods related to displaying the panel
+
+-(void)setUpForChallenge:(NSURLAuthenticationChallenge *)chall
+{
+ [self loadNib];
+
+ NSURLProtectionSpace *space = [chall protectionSpace];
+
+ NSString *host;
+ if ([space port] == 0) {
+ host = [space host];
+ } else {
+ host = [NSString stringWithFormat:@"%@:%u", [space host], [space port]];
+ }
+
+ NSString *realm = [space realm];
+ NSString *message;
+
+ if ([chall previousFailureCount] == 0) {
+ if ([space isProxy]) {
+ message = [NSString stringWithFormat:UI_STRING("To view this page, you need to log in to the %@ proxy server %@.",
+ "prompt string in authentication panel"),
+ [space proxyType], host];
+ } else {
+ message = [NSString stringWithFormat:UI_STRING("To view this page, you need to log in to area “%@” on %@.",
+ "prompt string in authentication panel"),
+ realm, host];
+ }
+ } else {
+ if ([space isProxy]) {
+ message = [NSString stringWithFormat:UI_STRING("The name or password entered for the %@ proxy server %@ was incorrect. Please try again.",
+ "prompt string in authentication panel"),
+ [space proxyType], host];
+ } else {
+ message = [NSString stringWithFormat:UI_STRING("The name or password entered for area “%@” on %@ was incorrect. Please try again.",
+ "prompt string in authentication panel"),
+ realm, host];
+ }
+ }
+
+ [mainLabel setStringValue:message];
+ [mainLabel sizeToFitAndAdjustWindowHeight];
+
+ if ([space receivesCredentialSecurely]) {
+ [smallLabel setStringValue:
+ UI_STRING("Your log-in information will be sent securely.",
+ "message in authentication panel")];
+ } else {
+ [smallLabel setStringValue:
+ UI_STRING("Your password will be sent in the clear.",
+ "message in authentication panel")];
+ }
+
+ if ([[chall proposedCredential] user] != nil) {
+ [username setStringValue:[[chall proposedCredential] user]];
+ [panel setInitialFirstResponder:password];
+ } else {
+ [username setStringValue:@""];
+ [password setStringValue:@""];
+ [panel setInitialFirstResponder:username];
+ }
+}
+
+- (void)runAsModalDialogWithChallenge:(NSURLAuthenticationChallenge *)chall
+{
+ [self setUpForChallenge:chall];
+ usingSheet = FALSE;
+ NSURLCredential *credential = nil;
+
+ if ([[NSApplication sharedApplication] runModalForWindow:panel] == 0) {
+ credential = [[NSURLCredential alloc] initWithUser:[username stringValue] password:[password stringValue] persistence:([remember state] == NSOnState) ? NSURLCredentialPersistencePermanent : NSURLCredentialPersistenceForSession];
+ }
+
+ [callback performSelector:selector withObject:chall withObject:credential];
+ [credential release];
+}
+
+- (void)runAsSheetOnWindow:(NSWindow *)window withChallenge:(NSURLAuthenticationChallenge *)chall
+{
+ ASSERT(!usingSheet);
+
+ [self setUpForChallenge:chall];
+
+ usingSheet = TRUE;
+ challenge = [chall retain];
+
+ [[NSApplication sharedApplication] beginSheet:panel modalForWindow:window modalDelegate:self didEndSelector:@selector(sheetDidEnd:returnCode:contextInfo:) contextInfo:NULL];
+}
+
+- (void)sheetDidEnd:(NSWindow *)sheet returnCode:(int)returnCode contextInfo:(void *)contextInfo
+{
+ NSURLCredential *credential = nil;
+ NSURLAuthenticationChallenge *chall;
+
+ ASSERT(usingSheet);
+ ASSERT(challenge != nil);
+
+ if (returnCode == 0) {
+ credential = [[NSURLCredential alloc] initWithUser:[username stringValue] password:[password stringValue] persistence:([remember state] == NSOnState) ? NSURLCredentialPersistencePermanent : NSURLCredentialPersistenceForSession];
+ }
+
+ // We take this tricky approach to nilling out and releasing the challenge
+ // because the callback below might remove our last ref.
+ chall = challenge;
+ challenge = nil;
+ [callback performSelector:selector withObject:chall withObject:credential];
+ [credential release];
+ [chall release];
+}
+
+@end
+
+@implementation NonBlockingPanel
+
+- (BOOL)_blocksActionWhenModal:(SEL)theAction
+{
+ // This override of a private AppKit method allows the user to quit when a login dialog
+ // is onscreen, which is nice in general but in particular prevents pathological cases
+ // like 3744583 from requiring a Force Quit.
+ //
+ // It would be nice to allow closing the individual window as well as quitting the app when
+ // a login sheet is up, but this _blocksActionWhenModal: mechanism doesn't support that.
+ // This override matches those in NSOpenPanel and NSToolbarConfigPanel.
+ if (theAction == @selector(terminate:)) {
+ return NO;
+ }
+ return YES;
+}
+
+@end
diff --git a/WebKit/mac/Panels/WebPanelAuthenticationHandler.h b/WebKit/mac/Panels/WebPanelAuthenticationHandler.h
new file mode 100644
index 0000000..ac5f449
--- /dev/null
+++ b/WebKit/mac/Panels/WebPanelAuthenticationHandler.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+#import <Foundation/NSURLCredentialStorage.h>
+
+@class NSURLAuthenticationChallenge;
+
+@interface WebPanelAuthenticationHandler : NSObject
+{
+ NSMutableDictionary *windowToPanel;
+ NSMutableDictionary *challengeToWindow;
+ NSMutableDictionary *windowToChallengeQueue;
+}
+
++ (id)sharedHandler;
+- (void)startAuthentication:(NSURLAuthenticationChallenge *)challenge window:(NSWindow *)w;
+- (void)cancelAuthentication:(NSURLAuthenticationChallenge *)challenge;
+
+@end
diff --git a/WebKit/mac/Panels/WebPanelAuthenticationHandler.m b/WebKit/mac/Panels/WebPanelAuthenticationHandler.m
new file mode 100644
index 0000000..f21b9c7
--- /dev/null
+++ b/WebKit/mac/Panels/WebPanelAuthenticationHandler.m
@@ -0,0 +1,164 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebPanelAuthenticationHandler.h>
+
+#import <Foundation/NSURLAuthenticationChallenge.h>
+#import <WebKit/WebAuthenticationPanel.h>
+#import <JavaScriptCore/Assertions.h>
+#import <WebKit/WebNSDictionaryExtras.h>
+
+static NSString *WebModalDialogPretendWindow = @"WebModalDialogPretendWindow";
+
+@implementation WebPanelAuthenticationHandler
+
+WebPanelAuthenticationHandler *sharedHandler;
+
++ (id)sharedHandler
+{
+ if (sharedHandler == nil)
+ sharedHandler = [[self alloc] init];
+ return sharedHandler;
+}
+
+-(id)init
+{
+ self = [super init];
+ if (self != nil) {
+ windowToPanel = [[NSMutableDictionary alloc] init];
+ challengeToWindow = [[NSMutableDictionary alloc] init];
+ windowToChallengeQueue = [[NSMutableDictionary alloc] init];
+ }
+ return self;
+}
+
+-(void)dealloc
+{
+ [windowToPanel release];
+ [challengeToWindow release];
+ [windowToChallengeQueue release];
+ [super dealloc];
+}
+
+-(void)enqueueChallenge:(NSURLAuthenticationChallenge *)challenge forWindow:(id)window
+{
+ NSMutableArray *queue = [windowToChallengeQueue objectForKey:window];
+ if (queue == nil) {
+ queue = [[NSMutableArray alloc] init];
+ [windowToChallengeQueue _webkit_setObject:queue forUncopiedKey:window];
+ [queue release];
+ }
+ [queue addObject:challenge];
+}
+
+-(void)tryNextChallengeForWindow:(id)window
+{
+ NSMutableArray *queue = [windowToChallengeQueue objectForKey:window];
+ if (queue == nil) {
+ return;
+ }
+
+ NSURLAuthenticationChallenge *challenge = [[queue objectAtIndex:0] retain];
+ [queue removeObjectAtIndex:0];
+ if ([queue count] == 0) {
+ [windowToChallengeQueue removeObjectForKey:window];
+ }
+
+ NSURLCredential *latestCredential = [[NSURLCredentialStorage sharedCredentialStorage] defaultCredentialForProtectionSpace:[challenge protectionSpace]];
+
+ if ([latestCredential hasPassword]) {
+ [[challenge sender] useCredential:latestCredential forAuthenticationChallenge:challenge];
+ [challenge release];
+ return;
+ }
+
+ [self startAuthentication:challenge window:(window == WebModalDialogPretendWindow ? nil : window)];
+ [challenge release];
+}
+
+
+-(void)startAuthentication:(NSURLAuthenticationChallenge *)challenge window:(NSWindow *)w
+{
+ id window = w ? (id)w : (id)WebModalDialogPretendWindow;
+
+ if ([windowToPanel objectForKey:window] != nil) {
+ [self enqueueChallenge:challenge forWindow:window];
+ return;
+ }
+
+ // In this case, we have an attached sheet that's not one of our
+ // authentication panels, so enqueing is not an option. Just
+ // cancel authentication instead, since this case is fairly
+ // unlikely (how would you be loading a page if you had an error
+ // sheet up?)
+ if ([w attachedSheet] != nil) {
+ [[challenge sender] cancelAuthenticationChallenge:challenge];
+ return;
+ }
+
+ WebAuthenticationPanel *panel = [[WebAuthenticationPanel alloc] initWithCallback:self selector:@selector(_authenticationDoneWithChallenge:result:)];
+ [challengeToWindow _webkit_setObject:window forUncopiedKey:challenge];
+ [windowToPanel _webkit_setObject:panel forUncopiedKey:window];
+ [panel release];
+
+ if (window == WebModalDialogPretendWindow) {
+ [panel runAsModalDialogWithChallenge:challenge];
+ } else {
+ [panel runAsSheetOnWindow:window withChallenge:challenge];
+ }
+}
+
+-(void)cancelAuthentication:(NSURLAuthenticationChallenge *)challenge
+{
+ id window = [challengeToWindow objectForKey:challenge];
+ if (window != nil) {
+ WebAuthenticationPanel *panel = [windowToPanel objectForKey:window];
+ [panel cancel:self];
+ }
+}
+
+-(void)_authenticationDoneWithChallenge:(NSURLAuthenticationChallenge *)challenge result:(NSURLCredential *)credential
+{
+ id window = [challengeToWindow objectForKey:challenge];
+ [window retain];
+ if (window != nil) {
+ [windowToPanel removeObjectForKey:window];
+ [challengeToWindow removeObjectForKey:challenge];
+ }
+
+ if (credential == nil) {
+ [[challenge sender] cancelAuthenticationChallenge:challenge];
+ } else {
+ [[challenge sender] useCredential:credential forAuthenticationChallenge:challenge];
+ }
+
+ [self tryNextChallengeForWindow:window];
+ [window release];
+}
+
+@end
diff --git a/WebKit/mac/Plugins/WebBaseNetscapePluginStream.h b/WebKit/mac/Plugins/WebBaseNetscapePluginStream.h
new file mode 100644
index 0000000..77cf609
--- /dev/null
+++ b/WebKit/mac/Plugins/WebBaseNetscapePluginStream.h
@@ -0,0 +1,93 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+#ifndef __LP64__
+#import <Foundation/Foundation.h>
+
+#import <WebKit/npfunctions.h>
+#import <WebKit/WebPlugInStreamLoaderDelegate.h>
+
+@class WebBaseNetscapePluginView;
+@class NSURLResponse;
+
+@interface WebBaseNetscapePluginStream : NSObject<WebPlugInStreamLoaderDelegate>
+{
+ NSMutableData *deliveryData;
+ NSURL *requestURL;
+ NSURL *responseURL;
+ NSString *MIMEType;
+
+ NPP plugin;
+ uint16 transferMode;
+ int32 offset;
+ NPStream stream;
+ NSString *path;
+ int fileDescriptor;
+ BOOL sendNotification;
+ void *notifyData;
+ char *headers;
+ WebBaseNetscapePluginView *pluginView;
+ NPReason reason;
+ BOOL isTerminated;
+
+ NPP_NewStreamProcPtr NPP_NewStream;
+ NPP_DestroyStreamProcPtr NPP_DestroyStream;
+ NPP_StreamAsFileProcPtr NPP_StreamAsFile;
+ NPP_WriteReadyProcPtr NPP_WriteReady;
+ NPP_WriteProcPtr NPP_Write;
+ NPP_URLNotifyProcPtr NPP_URLNotify;
+}
+
++ (NPP)ownerForStream:(NPStream *)stream;
++ (NPReason)reasonForError:(NSError *)error;
+
+- (NSError *)errorForReason:(NPReason)theReason;
+
+- (id)initWithRequestURL:(NSURL *)theRequestURL
+ plugin:(NPP)thePlugin
+ notifyData:(void *)theNotifyData
+ sendNotification:(BOOL)flag;
+
+- (void)setRequestURL:(NSURL *)theRequestURL;
+- (void)setResponseURL:(NSURL *)theResponseURL;
+- (void)setPlugin:(NPP)thePlugin;
+
+- (uint16)transferMode;
+- (NPP)plugin;
+
+- (void)startStreamResponseURL:(NSURL *)theResponseURL
+ expectedContentLength:(long long)expectedContentLength
+ lastModifiedDate:(NSDate *)lastModifiedDate
+ MIMEType:(NSString *)MIMEType
+ headers:(NSData *)theHeaders;
+
+// cancelLoadWithError cancels the NSURLConnection and informs WebKit of the load error.
+// This method is overriden by subclasses.
+- (void)cancelLoadWithError:(NSError *)error;
+
+@end
+#endif
diff --git a/WebKit/mac/Plugins/WebBaseNetscapePluginStream.mm b/WebKit/mac/Plugins/WebBaseNetscapePluginStream.mm
new file mode 100644
index 0000000..407c6d0
--- /dev/null
+++ b/WebKit/mac/Plugins/WebBaseNetscapePluginStream.mm
@@ -0,0 +1,613 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+#import "WebBaseNetscapePluginStream.h"
+
+#import "WebBaseNetscapePluginView.h"
+#import "WebKitErrorsPrivate.h"
+#import "WebKitLogging.h"
+#import "WebNSObjectExtras.h"
+#import "WebNSURLExtras.h"
+#import "WebNetscapePluginPackage.h"
+#import <Foundation/NSURLResponse.h>
+#import <WebCore/WebCoreObjCExtras.h>
+#import <WebKitSystemInterface.h>
+#import <wtf/HashMap.h>
+
+#define WEB_REASON_NONE -1
+
+static NSString *CarbonPathFromPOSIXPath(NSString *posixPath);
+
+typedef HashMap<NPStream*, NPP> StreamMap;
+static StreamMap& streams()
+{
+ static StreamMap staticStreams;
+ return staticStreams;
+}
+
+@implementation WebBaseNetscapePluginStream
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
++ (NPP)ownerForStream:(NPStream *)stream
+{
+ return streams().get(stream);
+}
+
++ (NPReason)reasonForError:(NSError *)error
+{
+ if (error == nil) {
+ return NPRES_DONE;
+ }
+ if ([[error domain] isEqualToString:NSURLErrorDomain] && [error code] == NSURLErrorCancelled) {
+ return NPRES_USER_BREAK;
+ }
+ return NPRES_NETWORK_ERR;
+}
+
+- (NSError *)_pluginCancelledConnectionError
+{
+ return [[[NSError alloc] _initWithPluginErrorCode:WebKitErrorPlugInCancelledConnection
+ contentURL:responseURL != nil ? responseURL : requestURL
+ pluginPageURL:nil
+ pluginName:[[pluginView pluginPackage] name]
+ MIMEType:MIMEType] autorelease];
+}
+
+- (NSError *)errorForReason:(NPReason)theReason
+{
+ if (theReason == NPRES_DONE) {
+ return nil;
+ }
+ if (theReason == NPRES_USER_BREAK) {
+ return [NSError _webKitErrorWithDomain:NSURLErrorDomain
+ code:NSURLErrorCancelled
+ URL:responseURL != nil ? responseURL : requestURL];
+ }
+ return [self _pluginCancelledConnectionError];
+}
+
+- (id)initWithRequestURL:(NSURL *)theRequestURL
+ plugin:(NPP)thePlugin
+ notifyData:(void *)theNotifyData
+ sendNotification:(BOOL)flag
+{
+ [super init];
+
+ // Temporarily set isTerminated to YES to avoid assertion failure in dealloc in case we are released in this method.
+ isTerminated = YES;
+
+ if (theRequestURL == nil || thePlugin == NULL) {
+ [self release];
+ return nil;
+ }
+
+ [self setRequestURL:theRequestURL];
+ [self setPlugin:thePlugin];
+ notifyData = theNotifyData;
+ sendNotification = flag;
+ fileDescriptor = -1;
+
+ streams().add(&stream, thePlugin);
+
+ isTerminated = NO;
+
+ return self;
+}
+
+- (void)dealloc
+{
+ ASSERT(!plugin);
+ ASSERT(isTerminated);
+ ASSERT(stream.ndata == nil);
+
+ // The stream file should have been deleted, and the path freed, in -_destroyStream
+ ASSERT(!path);
+ ASSERT(fileDescriptor == -1);
+
+ [requestURL release];
+ [responseURL release];
+ [MIMEType release];
+ [pluginView release];
+ [deliveryData release];
+
+ free((void *)stream.url);
+ free(path);
+ free(headers);
+
+ streams().remove(&stream);
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+ ASSERT(isTerminated);
+ ASSERT(stream.ndata == nil);
+
+ // The stream file should have been deleted, and the path freed, in -_destroyStream
+ ASSERT(!path);
+ ASSERT(fileDescriptor == -1);
+
+ free((void *)stream.url);
+ free(path);
+ free(headers);
+
+ streams().remove(&stream);
+
+ [super finalize];
+}
+
+- (uint16)transferMode
+{
+ return transferMode;
+}
+
+- (NPP)plugin
+{
+ return plugin;
+}
+
+- (void)setRequestURL:(NSURL *)theRequestURL
+{
+ [theRequestURL retain];
+ [requestURL release];
+ requestURL = theRequestURL;
+}
+
+- (void)setResponseURL:(NSURL *)theResponseURL
+{
+ [theResponseURL retain];
+ [responseURL release];
+ responseURL = theResponseURL;
+}
+
+- (void)setPlugin:(NPP)thePlugin
+{
+ if (thePlugin) {
+ plugin = thePlugin;
+ pluginView = [(WebBaseNetscapePluginView *)plugin->ndata retain];
+ WebNetscapePluginPackage *pluginPackage = [pluginView pluginPackage];
+ NPP_NewStream = [pluginPackage NPP_NewStream];
+ NPP_WriteReady = [pluginPackage NPP_WriteReady];
+ NPP_Write = [pluginPackage NPP_Write];
+ NPP_StreamAsFile = [pluginPackage NPP_StreamAsFile];
+ NPP_DestroyStream = [pluginPackage NPP_DestroyStream];
+ NPP_URLNotify = [pluginPackage NPP_URLNotify];
+ } else {
+ WebBaseNetscapePluginView *view = pluginView;
+
+ plugin = NULL;
+ NPP_NewStream = NULL;
+ NPP_WriteReady = NULL;
+ NPP_Write = NULL;
+ NPP_StreamAsFile = NULL;
+ NPP_DestroyStream = NULL;
+ NPP_URLNotify = NULL;
+ pluginView = nil;
+
+ [view disconnectStream:self];
+ [view release];
+ }
+}
+
+- (void)setMIMEType:(NSString *)theMIMEType
+{
+ [theMIMEType retain];
+ [MIMEType release];
+ MIMEType = theMIMEType;
+}
+
+- (void)startStreamResponseURL:(NSURL *)URL
+ expectedContentLength:(long long)expectedContentLength
+ lastModifiedDate:(NSDate *)lastModifiedDate
+ MIMEType:(NSString *)theMIMEType
+ headers:(NSData *)theHeaders
+{
+ ASSERT(!isTerminated);
+
+ [self setResponseURL:URL];
+ [self setMIMEType:theMIMEType];
+
+ free((void *)stream.url);
+ stream.url = strdup([responseURL _web_URLCString]);
+
+ stream.ndata = self;
+ stream.end = expectedContentLength > 0 ? (uint32)expectedContentLength : 0;
+ stream.lastmodified = (uint32)[lastModifiedDate timeIntervalSince1970];
+ stream.notifyData = notifyData;
+
+ if (theHeaders) {
+ unsigned len = [theHeaders length];
+ headers = (char*) malloc(len + 1);
+ [theHeaders getBytes:headers];
+ headers[len] = 0;
+ stream.headers = headers;
+ }
+
+ transferMode = NP_NORMAL;
+ offset = 0;
+ reason = WEB_REASON_NONE;
+ // FIXME: If WebNetscapePluginStream called our initializer we wouldn't have to do this here.
+ fileDescriptor = -1;
+
+ // FIXME: Need a way to check if stream is seekable
+
+ WebBaseNetscapePluginView *pv = pluginView;
+ [pv willCallPlugInFunction];
+ NPError npErr = NPP_NewStream(plugin, (char *)[MIMEType UTF8String], &stream, NO, &transferMode);
+ [pv didCallPlugInFunction];
+ LOG(Plugins, "NPP_NewStream URL=%@ MIME=%@ error=%d", responseURL, MIMEType, npErr);
+
+ if (npErr != NPERR_NO_ERROR) {
+ LOG_ERROR("NPP_NewStream failed with error: %d responseURL: %@", npErr, responseURL);
+ // Calling cancelLoadWithError: cancels the load, but doesn't call NPP_DestroyStream.
+ [self cancelLoadWithError:[self _pluginCancelledConnectionError]];
+ return;
+ }
+
+ switch (transferMode) {
+ case NP_NORMAL:
+ LOG(Plugins, "Stream type: NP_NORMAL");
+ break;
+ case NP_ASFILEONLY:
+ LOG(Plugins, "Stream type: NP_ASFILEONLY");
+ break;
+ case NP_ASFILE:
+ LOG(Plugins, "Stream type: NP_ASFILE");
+ break;
+ case NP_SEEK:
+ LOG_ERROR("Stream type: NP_SEEK not yet supported");
+ [self cancelLoadAndDestroyStreamWithError:[self _pluginCancelledConnectionError]];
+ break;
+ default:
+ LOG_ERROR("unknown stream type");
+ }
+}
+
+- (void)startStreamWithResponse:(NSURLResponse *)r
+{
+ NSMutableData *theHeaders = nil;
+ long long expectedContentLength = [r expectedContentLength];
+
+ if ([r isKindOfClass:[NSHTTPURLResponse class]]) {
+ NSHTTPURLResponse *httpResponse = (NSHTTPURLResponse *)r;
+ theHeaders = [NSMutableData dataWithCapacity:1024];
+
+ // FIXME: it would be nice to be able to get the raw HTTP header block.
+ // This includes the HTTP version, the real status text,
+ // all headers in their original order and including duplicates,
+ // and all original bytes verbatim, rather than sent through Unicode translation.
+ // Unfortunately NSHTTPURLResponse doesn't provide access at that low a level.
+
+ [theHeaders appendBytes:"HTTP " length:5];
+ char statusStr[10];
+ long statusCode = [httpResponse statusCode];
+ snprintf(statusStr, sizeof(statusStr), "%ld", statusCode);
+ [theHeaders appendBytes:statusStr length:strlen(statusStr)];
+ [theHeaders appendBytes:" OK\n" length:4];
+
+ // HACK: pass the headers through as UTF-8.
+ // This is not the intended behavior; we're supposed to pass original bytes verbatim.
+ // But we don't have the original bytes, we have NSStrings built by the URL loading system.
+ // It hopefully shouldn't matter, since RFC2616/RFC822 require ASCII-only headers,
+ // but surely someone out there is using non-ASCII characters, and hopefully UTF-8 is adequate here.
+ // It seems better than NSASCIIStringEncoding, which will lose information if non-ASCII is used.
+
+ NSDictionary *headerDict = [httpResponse allHeaderFields];
+ NSArray *keys = [[headerDict allKeys] sortedArrayUsingSelector:@selector(caseInsensitiveCompare:)];
+ NSEnumerator *i = [keys objectEnumerator];
+ NSString *k;
+ while ((k = [i nextObject]) != nil) {
+ NSString *v = [headerDict objectForKey:k];
+ [theHeaders appendData:[k dataUsingEncoding:NSUTF8StringEncoding]];
+ [theHeaders appendBytes:": " length:2];
+ [theHeaders appendData:[v dataUsingEncoding:NSUTF8StringEncoding]];
+ [theHeaders appendBytes:"\n" length:1];
+ }
+
+ // If the content is encoded (most likely compressed), then don't send its length to the plugin,
+ // which is only interested in the decoded length, not yet known at the moment.
+ // <rdar://problem/4470599> tracks a request for -[NSURLResponse expectedContentLength] to incorporate this logic.
+ NSString *contentEncoding = (NSString *)[[(NSHTTPURLResponse *)r allHeaderFields] objectForKey:@"Content-Encoding"];
+ if (contentEncoding && ![contentEncoding isEqualToString:@"identity"])
+ expectedContentLength = -1;
+
+ // startStreamResponseURL:... will null-terminate.
+ }
+
+ [self startStreamResponseURL:[r URL]
+ expectedContentLength:expectedContentLength
+ lastModifiedDate:WKGetNSURLResponseLastModifiedDate(r)
+ MIMEType:[r MIMEType]
+ headers:theHeaders];
+}
+
+- (void)_destroyStream
+{
+ if (isTerminated)
+ return;
+
+ [self retain];
+
+ ASSERT(reason != WEB_REASON_NONE);
+ ASSERT([deliveryData length] == 0);
+
+ [NSObject cancelPreviousPerformRequestsWithTarget:self selector:@selector(_deliverData) object:nil];
+
+ if (stream.ndata != nil) {
+ if (reason == NPRES_DONE && (transferMode == NP_ASFILE || transferMode == NP_ASFILEONLY)) {
+ ASSERT(fileDescriptor == -1);
+ ASSERT(path != NULL);
+ NSString *carbonPath = CarbonPathFromPOSIXPath(path);
+ ASSERT(carbonPath != NULL);
+ WebBaseNetscapePluginView *pv = pluginView;
+ [pv willCallPlugInFunction];
+ NPP_StreamAsFile(plugin, &stream, [carbonPath fileSystemRepresentation]);
+ [pv didCallPlugInFunction];
+ LOG(Plugins, "NPP_StreamAsFile responseURL=%@ path=%s", responseURL, carbonPath);
+ }
+
+ if (path) {
+ // Delete the file after calling NPP_StreamAsFile(), instead of in -dealloc/-finalize. It should be OK
+ // to delete the file here -- NPP_StreamAsFile() is always called immediately before NPP_DestroyStream()
+ // (the stream destruction function), so there can be no expectation that a plugin will read the stream
+ // file asynchronously after NPP_StreamAsFile() is called.
+ unlink([path fileSystemRepresentation]);
+ [path release];
+ path = nil;
+
+ if (isTerminated)
+ goto exit;
+ }
+
+ if (fileDescriptor != -1) {
+ // The file may still be open if we are destroying the stream before it completed loading.
+ close(fileDescriptor);
+ fileDescriptor = -1;
+ }
+
+ NPError npErr;
+ WebBaseNetscapePluginView *pv = pluginView;
+ [pv willCallPlugInFunction];
+ npErr = NPP_DestroyStream(plugin, &stream, reason);
+ [pv didCallPlugInFunction];
+ LOG(Plugins, "NPP_DestroyStream responseURL=%@ error=%d", responseURL, npErr);
+
+ free(headers);
+ headers = NULL;
+ stream.headers = NULL;
+
+ stream.ndata = nil;
+
+ if (isTerminated)
+ goto exit;
+ }
+
+ if (sendNotification) {
+ // NPP_URLNotify expects the request URL, not the response URL.
+ WebBaseNetscapePluginView *pv = pluginView;
+ [pv willCallPlugInFunction];
+ NPP_URLNotify(plugin, [requestURL _web_URLCString], reason, notifyData);
+ [pv didCallPlugInFunction];
+ LOG(Plugins, "NPP_URLNotify requestURL=%@ reason=%d", requestURL, reason);
+ }
+
+ isTerminated = YES;
+
+ [self setPlugin:NULL];
+
+exit:
+ [self release];
+}
+
+- (void)_destroyStreamWithReason:(NPReason)theReason
+{
+ reason = theReason;
+ if (reason != NPRES_DONE) {
+ // Stop any pending data from being streamed.
+ [deliveryData setLength:0];
+ } else if ([deliveryData length] > 0) {
+ // There is more data to be streamed, don't destroy the stream now.
+ return;
+ }
+ [self _destroyStream];
+ ASSERT(stream.ndata == nil);
+}
+
+- (void)cancelLoadWithError:(NSError *)error
+{
+ // Overridden by subclasses.
+ ASSERT_NOT_REACHED();
+}
+
+- (void)destroyStreamWithError:(NSError *)error
+{
+ [self _destroyStreamWithReason:[[self class] reasonForError:error]];
+}
+
+- (void)cancelLoadAndDestroyStreamWithError:(NSError *)error
+{
+ [self retain];
+ [self cancelLoadWithError:error];
+ [self destroyStreamWithError:error];
+ [self setPlugin:NULL];
+ [self release];
+}
+
+- (void)_deliverData
+{
+ if (!stream.ndata || [deliveryData length] == 0)
+ return;
+
+ [self retain];
+
+ int32 totalBytes = [deliveryData length];
+ int32 totalBytesDelivered = 0;
+
+ while (totalBytesDelivered < totalBytes) {
+ WebBaseNetscapePluginView *pv = pluginView;
+ [pv willCallPlugInFunction];
+ int32 deliveryBytes = NPP_WriteReady(plugin, &stream);
+ [pv didCallPlugInFunction];
+ LOG(Plugins, "NPP_WriteReady responseURL=%@ bytes=%d", responseURL, deliveryBytes);
+
+ if (isTerminated)
+ goto exit;
+
+ if (deliveryBytes <= 0) {
+ // Plug-in can't receive anymore data right now. Send it later.
+ [self performSelector:@selector(_deliverData) withObject:nil afterDelay:0];
+ break;
+ } else {
+ deliveryBytes = MIN(deliveryBytes, totalBytes - totalBytesDelivered);
+ NSData *subdata = [deliveryData subdataWithRange:NSMakeRange(totalBytesDelivered, deliveryBytes)];
+ pv = pluginView;
+ [pv willCallPlugInFunction];
+ deliveryBytes = NPP_Write(plugin, &stream, offset, [subdata length], (void *)[subdata bytes]);
+ [pv didCallPlugInFunction];
+ if (deliveryBytes < 0) {
+ // Netscape documentation says that a negative result from NPP_Write means cancel the load.
+ [self cancelLoadAndDestroyStreamWithError:[self _pluginCancelledConnectionError]];
+ return;
+ }
+ deliveryBytes = MIN((unsigned)deliveryBytes, [subdata length]);
+ offset += deliveryBytes;
+ totalBytesDelivered += deliveryBytes;
+ LOG(Plugins, "NPP_Write responseURL=%@ bytes=%d total-delivered=%d/%d", responseURL, deliveryBytes, offset, stream.end);
+ }
+ }
+
+ if (totalBytesDelivered > 0) {
+ if (totalBytesDelivered < totalBytes) {
+ NSMutableData *newDeliveryData = [[NSMutableData alloc] initWithCapacity:totalBytes - totalBytesDelivered];
+ [newDeliveryData appendBytes:(char *)[deliveryData bytes] + totalBytesDelivered length:totalBytes - totalBytesDelivered];
+ [deliveryData release];
+ deliveryData = newDeliveryData;
+ } else {
+ [deliveryData setLength:0];
+ if (reason != WEB_REASON_NONE) {
+ [self _destroyStream];
+ }
+ }
+ }
+
+exit:
+ [self release];
+}
+
+- (void)_deliverDataToFile:(NSData *)data
+{
+ if (fileDescriptor == -1 && !path) {
+ NSString *temporaryFileMask = [NSTemporaryDirectory() stringByAppendingPathComponent:@"WebKitPlugInStreamXXXXXX"];
+ char *temporaryFileName = strdup([temporaryFileMask fileSystemRepresentation]);
+ fileDescriptor = mkstemp(temporaryFileName);
+ if (fileDescriptor == -1) {
+ LOG_ERROR("Can't create a temporary file.");
+ // This is not a network error, but the only error codes are "network error" and "user break".
+ [self _destroyStreamWithReason:NPRES_NETWORK_ERR];
+ free(temporaryFileName);
+ return;
+ }
+
+ path = [[NSString stringWithUTF8String:temporaryFileName] retain];
+ free(temporaryFileName);
+ }
+
+ int dataLength = [data length];
+ if (!dataLength)
+ return;
+
+ int byteCount = write(fileDescriptor, [data bytes], dataLength);
+ if (byteCount != dataLength) {
+ // This happens only rarely, when we are out of disk space or have a disk I/O error.
+ LOG_ERROR("error writing to temporary file, errno %d", errno);
+ close(fileDescriptor);
+ fileDescriptor = -1;
+
+ // This is not a network error, but the only error codes are "network error" and "user break".
+ [self _destroyStreamWithReason:NPRES_NETWORK_ERR];
+ [path release];
+ path = nil;
+ }
+}
+
+- (void)finishedLoading
+{
+ if (!stream.ndata)
+ return;
+
+ if (transferMode == NP_ASFILE || transferMode == NP_ASFILEONLY) {
+ // Fake the delivery of an empty data to ensure that the file has been created
+ [self _deliverDataToFile:[NSData data]];
+ if (fileDescriptor != -1)
+ close(fileDescriptor);
+ fileDescriptor = -1;
+ }
+
+ [self _destroyStreamWithReason:NPRES_DONE];
+}
+
+- (void)receivedData:(NSData *)data
+{
+ ASSERT([data length] > 0);
+
+ if (transferMode != NP_ASFILEONLY) {
+ if (!deliveryData) {
+ deliveryData = [[NSMutableData alloc] initWithCapacity:[data length]];
+ }
+ [deliveryData appendData:data];
+ [self _deliverData];
+ }
+ if (transferMode == NP_ASFILE || transferMode == NP_ASFILEONLY)
+ [self _deliverDataToFile:data];
+
+}
+
+@end
+
+static NSString *CarbonPathFromPOSIXPath(NSString *posixPath)
+{
+ // Doesn't add a trailing colon for directories; this is a problem for paths to a volume,
+ // so this function would need to be revised if we ever wanted to call it with that.
+
+ CFURLRef url = (CFURLRef)[NSURL fileURLWithPath:posixPath];
+ if (!url)
+ return nil;
+
+ return WebCFAutorelease(CFURLCopyFileSystemPath(url, kCFURLHFSPathStyle));
+}
+
+#endif
diff --git a/WebKit/mac/Plugins/WebBaseNetscapePluginView.h b/WebKit/mac/Plugins/WebBaseNetscapePluginView.h
new file mode 100644
index 0000000..cf039ea
--- /dev/null
+++ b/WebKit/mac/Plugins/WebBaseNetscapePluginView.h
@@ -0,0 +1,182 @@
+/*
+ * Copyright (C) 2005, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+#import <Cocoa/Cocoa.h>
+
+#import <AGL/agl.h>
+#import <WebKit/npfunctions.h>
+#import <WebKit/npapi.h>
+#import <WebKit/WebBasePluginPackage.h>
+
+@class DOMElement;
+@class WebDataSource;
+@class WebFrame;
+@class WebNetscapePluginPackage;
+@class WebNetscapePluginNullEventSender;
+@class WebBaseNetscapePluginStream;
+@class WebNetscapePluginStream;
+@class WebView;
+
+typedef union PluginPort {
+#ifndef NP_NO_QUICKDRAW
+ NP_Port qdPort;
+#endif
+ NP_CGContext cgPort;
+ NP_GLContext aglPort;
+} PluginPort;
+
+@interface WebBaseNetscapePluginView : NSView <WebPluginManualLoader>
+{
+ WebNetscapePluginPackage *pluginPackage;
+
+ NSURL *sourceURL;
+ WebFrame *_webFrame;
+
+ BOOL _loadManually;
+ WebNetscapePluginStream *_manualStream;
+ unsigned _dataLengthReceived;
+ NSError *_error;
+
+ int mode;
+
+ unsigned argsCount;
+ char **cAttributes;
+ char **cValues;
+
+ NPP plugin;
+ NPWindow window;
+ NPWindow lastSetWindow;
+ PluginPort nPort;
+ PluginPort lastSetPort;
+ NPDrawingModel drawingModel;
+
+ // These are only valid when drawingModel is NPDrawingModelOpenGL
+ AGLContext aglContext;
+ NSWindow *aglWindow;
+
+#ifndef NP_NO_QUICKDRAW
+ // This is only valid when drawingModel is NPDrawingModelQuickDraw
+ GWorldPtr offscreenGWorld;
+#endif
+
+ BOOL isStarted;
+ BOOL inSetWindow;
+ BOOL suspendKeyUpEvents;
+ BOOL hasFocus;
+ BOOL currentEventIsUserGesture;
+ BOOL isTransparent;
+ BOOL isCompletelyObscured;
+ BOOL shouldStopSoon;
+
+ unsigned pluginFunctionCallDepth;
+
+ DOMElement *element;
+
+ int32 specifiedHeight;
+ int32 specifiedWidth;
+
+ NSString *MIMEType;
+ NSURL *baseURL;
+ NSTrackingRectTag trackingTag;
+ NSMutableArray *streams;
+ NSMutableDictionary *pendingFrameLoads;
+ NSTimer *nullEventTimer;
+
+ NPP_NewProcPtr NPP_New;
+ NPP_DestroyProcPtr NPP_Destroy;
+ NPP_SetWindowProcPtr NPP_SetWindow;
+ NPP_NewStreamProcPtr NPP_NewStream;
+ NPP_DestroyStreamProcPtr NPP_DestroyStream;
+ NPP_StreamAsFileProcPtr NPP_StreamAsFile;
+ NPP_WriteReadyProcPtr NPP_WriteReady;
+ NPP_WriteProcPtr NPP_Write;
+ NPP_PrintProcPtr NPP_Print;
+ NPP_HandleEventProcPtr NPP_HandleEvent;
+ NPP_URLNotifyProcPtr NPP_URLNotify;
+ NPP_GetValueProcPtr NPP_GetValue;
+ NPP_SetValueProcPtr NPP_SetValue;
+
+ EventHandlerRef keyEventHandler;
+}
+
++ (WebBaseNetscapePluginView *)currentPluginView;
+
+
+- (id)initWithFrame:(NSRect)r
+ pluginPackage:(WebNetscapePluginPackage *)thePluginPackage
+ URL:(NSURL *)URL
+ baseURL:(NSURL *)baseURL
+ MIMEType:(NSString *)MIME
+ attributeKeys:(NSArray *)keys
+ attributeValues:(NSArray *)values
+ loadManually:(BOOL)loadManually
+ DOMElement:(DOMElement *)anElement;
+
+
+- (BOOL)start;
+- (BOOL)isStarted;
+- (void)stop;
+
+- (WebFrame *)webFrame;
+- (WebDataSource *)dataSource;
+- (WebView *)webView;
+- (NSWindow *)currentWindow;
+
+- (NPP)plugin;
+
+- (WebNetscapePluginPackage *)pluginPackage;
+- (void)setPluginPackage:(WebNetscapePluginPackage *)thePluginPackage;
+- (void)setMIMEType:(NSString *)theMIMEType;
+- (void)setBaseURL:(NSURL *)theBaseURL;
+- (void)setAttributeKeys:(NSArray *)keys andValues:(NSArray *)values;
+- (void)setMode:(int)theMode;
+- (void)viewWillMoveToHostWindow:(NSWindow *)hostWindow;
+- (void)viewDidMoveToHostWindow;
+- (void)disconnectStream:(WebBaseNetscapePluginStream*)stream;
+
+// Returns the NPObject that represents the plugin interface.
+// The return value is expected to be retained.
+- (NPObject *)createPluginScriptableObject;
+
+// -willCallPlugInFunction must be called before calling any of the NPP_* functions for this view's plugin.
+// This is necessary to ensure that plug-ins are not destroyed while WebKit calls into them. Some plug-ins (Flash
+// at least) are written with the assumption that nothing they do in their plug-in functions can cause NPP_Destroy()
+// to be called. Unfortunately, this is not true, especially if the plug-in uses NPN_Invoke() to execute a
+// document.write(), which clears the document and destroys the plug-in.
+// See <rdar://problem/4480737>.
+- (void)willCallPlugInFunction;
+
+// -didCallPlugInFunction should be called after returning from a plug-in function. It should be called exactly
+// once for every call to -willCallPlugInFunction.
+// See <rdar://problem/4480737>.
+- (void)didCallPlugInFunction;
+
+@end
+#endif
+
diff --git a/WebKit/mac/Plugins/WebBaseNetscapePluginView.mm b/WebKit/mac/Plugins/WebBaseNetscapePluginView.mm
new file mode 100644
index 0000000..00a7b7d
--- /dev/null
+++ b/WebKit/mac/Plugins/WebBaseNetscapePluginView.mm
@@ -0,0 +1,3209 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+
+#import "WebBaseNetscapePluginView.h"
+
+#import "WebDataSourceInternal.h"
+#import "WebDefaultUIDelegate.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebFrameView.h"
+#import "WebGraphicsExtras.h"
+#import "WebKitLogging.h"
+#import "WebKitNSStringExtras.h"
+#import "WebKitSystemInterface.h"
+#import "WebNSDataExtras.h"
+#import "WebNSDictionaryExtras.h"
+#import "WebNSObjectExtras.h"
+#import "WebNSURLExtras.h"
+#import "WebNSURLRequestExtras.h"
+#import "WebNSViewExtras.h"
+#import "WebNetscapePluginPackage.h"
+#import "WebNetscapePluginStream.h"
+#import "WebNullPluginView.h"
+#import "WebPreferences.h"
+#import "WebViewInternal.h"
+#import "WebUIDelegatePrivate.h"
+#import <Carbon/Carbon.h>
+#import <JavaScriptCore/Assertions.h>
+#import <JavaScriptCore/JSLock.h>
+#import <JavaScriptCore/npruntime_impl.h>
+#import <WebCore/Document.h>
+#import <WebCore/Element.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/FrameTree.h>
+#import <WebCore/Page.h>
+#import <WebCore/SoftLinking.h>
+#import <WebCore/WebCoreObjCExtras.h>
+#import <WebKit/DOMPrivate.h>
+#import <WebKit/WebUIDelegate.h>
+#import <objc/objc-runtime.h>
+
+using namespace WebCore;
+
+// Send null events 50 times a second when active, so plug-ins like Flash get high frame rates.
+#define NullEventIntervalActive 0.02
+#define NullEventIntervalNotActive 0.25
+
+#define LoginWindowDidSwitchFromUserNotification @"WebLoginWindowDidSwitchFromUserNotification"
+#define LoginWindowDidSwitchToUserNotification @"WebLoginWindowDidSwitchToUserNotification"
+
+SOFT_LINK_FRAMEWORK(OpenGL)
+SOFT_LINK_FRAMEWORK(AGL)
+
+SOFT_LINK(OpenGL, CGLGetOffScreen, CGLError, (CGLContextObj ctx, GLsizei *width, GLsizei *height, GLint *rowbytes, void **baseaddr), (ctx, width, height, rowbytes, baseaddr))
+SOFT_LINK(OpenGL, CGLSetOffScreen, CGLError, (CGLContextObj ctx, GLsizei width, GLsizei height, GLint rowbytes, void *baseaddr), (ctx, width, height, rowbytes, baseaddr))
+SOFT_LINK(OpenGL, glViewport, void, (GLint x, GLint y, GLsizei width, GLsizei height), (x, y, width, height))
+SOFT_LINK(AGL, aglCreateContext, AGLContext, (AGLPixelFormat pix, AGLContext share), (pix, share))
+SOFT_LINK(AGL, aglSetWindowRef, GLboolean, (AGLContext ctx, WindowRef window), (ctx, window))
+SOFT_LINK(AGL, aglSetDrawable, GLboolean, (AGLContext ctx, AGLDrawable draw), (ctx, draw))
+#ifndef BUILDING_ON_TIGER
+SOFT_LINK(AGL, aglChoosePixelFormat, AGLPixelFormat, (const void *gdevs, GLint ndev, const GLint *attribs), (gdevs, ndev, attribs))
+#else
+SOFT_LINK(AGL, aglChoosePixelFormat, AGLPixelFormat, (const AGLDevice *gdevs, GLint ndev, const GLint *attribs), (gdevs, ndev, attribs))
+#endif
+SOFT_LINK(AGL, aglDestroyPixelFormat, void, (AGLPixelFormat pix), (pix))
+SOFT_LINK(AGL, aglDestroyContext, GLboolean, (AGLContext ctx), (ctx))
+SOFT_LINK(AGL, aglGetCGLContext, GLboolean, (AGLContext ctx, void **cgl_ctx), (ctx, cgl_ctx))
+SOFT_LINK(AGL, aglGetCurrentContext, AGLContext, (void), ())
+SOFT_LINK(AGL, aglSetCurrentContext, GLboolean, (AGLContext ctx), (ctx))
+SOFT_LINK(AGL, aglGetError, GLenum, (void), ())
+SOFT_LINK(AGL, aglUpdateContext, GLboolean, (AGLContext ctx), (ctx))
+SOFT_LINK(AGL, aglErrorString, const GLubyte *, (GLenum code), (code))
+
+@interface WebBaseNetscapePluginView (Internal)
+- (void)_viewHasMoved;
+- (NPError)_createPlugin;
+- (void)_destroyPlugin;
+- (NSBitmapImageRep *)_printedPluginBitmap;
+- (BOOL)_createAGLContextIfNeeded;
+- (BOOL)_createWindowedAGLContext;
+- (BOOL)_createWindowlessAGLContext;
+- (CGLContextObj)_cglContext;
+- (BOOL)_getAGLOffscreenBuffer:(GLvoid **)outBuffer width:(GLsizei *)outWidth height:(GLsizei *)outHeight;
+- (void)_destroyAGLContext;
+- (void)_reshapeAGLWindow;
+- (void)_hideAGLWindow;
+- (NSImage *)_aglOffscreenImageForDrawingInRect:(NSRect)drawingInRect;
+- (void)_redeliverStream;
+@end
+
+static WebBaseNetscapePluginView *currentPluginView = nil;
+
+typedef struct OpaquePortState* PortState;
+
+#ifndef NP_NO_QUICKDRAW
+
+// QuickDraw is not available in 64-bit
+
+typedef struct {
+ GrafPtr oldPort;
+ GDHandle oldDevice;
+ Point oldOrigin;
+ RgnHandle oldClipRegion;
+ RgnHandle oldVisibleRegion;
+ RgnHandle clipRegion;
+ BOOL forUpdate;
+} PortState_QD;
+
+#endif /* NP_NO_QUICKDRAW */
+
+typedef struct {
+ CGContextRef context;
+} PortState_CG;
+
+typedef struct {
+ AGLContext oldContext;
+} PortState_GL;
+
+@interface WebPluginRequest : NSObject
+{
+ NSURLRequest *_request;
+ NSString *_frameName;
+ void *_notifyData;
+ BOOL _didStartFromUserGesture;
+ BOOL _sendNotification;
+}
+
+- (id)initWithRequest:(NSURLRequest *)request frameName:(NSString *)frameName notifyData:(void *)notifyData sendNotification:(BOOL)sendNotification didStartFromUserGesture:(BOOL)currentEventIsUserGesture;
+
+- (NSURLRequest *)request;
+- (NSString *)frameName;
+- (void *)notifyData;
+- (BOOL)isCurrentEventUserGesture;
+- (BOOL)sendNotification;
+
+@end
+
+@interface NSData (WebPluginDataExtras)
+- (BOOL)_web_startsWithBlankLine;
+- (NSInteger)_web_locationAfterFirstBlankLine;
+@end
+
+static OSStatus TSMEventHandler(EventHandlerCallRef inHandlerRef, EventRef inEvent, void *pluginView);
+
+@interface WebBaseNetscapePluginView (ForwardDeclarations)
+- (void)setWindowIfNecessary;
+- (NPError)loadRequest:(NSMutableURLRequest *)request inTarget:(const char *)cTarget withNotifyData:(void *)notifyData sendNotification:(BOOL)sendNotification;
+@end
+
+@implementation WebBaseNetscapePluginView
+
++ (void)initialize
+{
+#ifndef BUILDING_ON_TIGER
+ WebCoreObjCFinalizeOnMainThread(self);
+#endif
+ WKSendUserChangeNotifications();
+}
+
+#pragma mark EVENTS
+
++ (void)getCarbonEvent:(EventRecord *)carbonEvent
+{
+ carbonEvent->what = nullEvent;
+ carbonEvent->message = 0;
+ carbonEvent->when = TickCount();
+
+ GetGlobalMouse(&carbonEvent->where);
+ carbonEvent->where.h = static_cast<short>(carbonEvent->where.h * HIGetScaleFactor());
+ carbonEvent->where.v = static_cast<short>(carbonEvent->where.v * HIGetScaleFactor());
+ carbonEvent->modifiers = GetCurrentKeyModifiers();
+ if (!Button())
+ carbonEvent->modifiers |= btnState;
+}
+
+- (void)getCarbonEvent:(EventRecord *)carbonEvent
+{
+ [[self class] getCarbonEvent:carbonEvent];
+}
+
+- (EventModifiers)modifiersForEvent:(NSEvent *)event
+{
+ EventModifiers modifiers;
+ unsigned int modifierFlags = [event modifierFlags];
+ NSEventType eventType = [event type];
+
+ modifiers = 0;
+
+ if (eventType != NSLeftMouseDown && eventType != NSRightMouseDown)
+ modifiers |= btnState;
+
+ if (modifierFlags & NSCommandKeyMask)
+ modifiers |= cmdKey;
+
+ if (modifierFlags & NSShiftKeyMask)
+ modifiers |= shiftKey;
+
+ if (modifierFlags & NSAlphaShiftKeyMask)
+ modifiers |= alphaLock;
+
+ if (modifierFlags & NSAlternateKeyMask)
+ modifiers |= optionKey;
+
+ if (modifierFlags & NSControlKeyMask || eventType == NSRightMouseDown)
+ modifiers |= controlKey;
+
+ return modifiers;
+}
+
+- (void)getCarbonEvent:(EventRecord *)carbonEvent withEvent:(NSEvent *)cocoaEvent
+{
+ if (WKConvertNSEventToCarbonEvent(carbonEvent, cocoaEvent)) {
+ carbonEvent->where.h = static_cast<short>(carbonEvent->where.h * HIGetScaleFactor());
+ carbonEvent->where.v = static_cast<short>(carbonEvent->where.v * HIGetScaleFactor());
+ return;
+ }
+
+ NSPoint where = [[cocoaEvent window] convertBaseToScreen:[cocoaEvent locationInWindow]];
+
+ carbonEvent->what = nullEvent;
+ carbonEvent->message = 0;
+ carbonEvent->when = (UInt32)([cocoaEvent timestamp] * 60); // seconds to ticks
+ carbonEvent->where.h = (short)where.x;
+ carbonEvent->where.v = (short)(NSMaxY([[[NSScreen screens] objectAtIndex:0] frame]) - where.y);
+ carbonEvent->modifiers = [self modifiersForEvent:cocoaEvent];
+}
+
+- (BOOL)superviewsHaveSuperviews
+{
+ NSView *contentView = [[self window] contentView];
+ NSView *view;
+ for (view = self; view != nil; view = [view superview]) {
+ if (view == contentView) {
+ return YES;
+ }
+ }
+ return NO;
+}
+
+#ifndef NP_NO_QUICKDRAW
+
+// The WindowRef created by -[NSWindow windowRef] has a QuickDraw GrafPort that covers
+// the entire window frame (or structure region to use the Carbon term) rather then just the window content.
+// We can remove this when <rdar://problem/4201099> is fixed.
+- (void)fixWindowPort
+{
+ ASSERT(drawingModel == NPDrawingModelQuickDraw);
+
+ NSWindow *currentWindow = [self currentWindow];
+ if ([currentWindow isKindOfClass:objc_getClass("NSCarbonWindow")])
+ return;
+
+ float windowHeight = [currentWindow frame].size.height;
+ NSView *contentView = [currentWindow contentView];
+ NSRect contentRect = [contentView convertRect:[contentView frame] toView:nil]; // convert to window-relative coordinates
+
+ CGrafPtr oldPort;
+ GetPort(&oldPort);
+ SetPort(GetWindowPort((WindowRef)[currentWindow windowRef]));
+
+ MovePortTo(static_cast<short>(contentRect.origin.x), /* Flip Y */ static_cast<short>(windowHeight - NSMaxY(contentRect)));
+ PortSize(static_cast<short>(contentRect.size.width), static_cast<short>(contentRect.size.height));
+
+ SetPort(oldPort);
+}
+
+static UInt32 getQDPixelFormatForBitmapContext(CGContextRef context)
+{
+ UInt32 byteOrder = CGBitmapContextGetBitmapInfo(context) & kCGBitmapByteOrderMask;
+ if (byteOrder == kCGBitmapByteOrderDefault)
+ switch (CGBitmapContextGetBitsPerPixel(context)) {
+ case 16:
+ byteOrder = kCGBitmapByteOrder16Host;
+ break;
+ case 32:
+ byteOrder = kCGBitmapByteOrder32Host;
+ break;
+ }
+ switch (byteOrder) {
+ case kCGBitmapByteOrder16Little:
+ return k16LE555PixelFormat;
+ case kCGBitmapByteOrder32Little:
+ return k32BGRAPixelFormat;
+ case kCGBitmapByteOrder16Big:
+ return k16BE555PixelFormat;
+ case kCGBitmapByteOrder32Big:
+ return k32ARGBPixelFormat;
+ }
+ ASSERT_NOT_REACHED();
+ return 0;
+}
+
+static inline void getNPRect(const CGRect& cgr, NPRect& npr)
+{
+ npr.top = static_cast<uint16>(cgr.origin.y);
+ npr.left = static_cast<uint16>(cgr.origin.x);
+ npr.bottom = static_cast<uint16>(CGRectGetMaxY(cgr));
+ npr.right = static_cast<uint16>(CGRectGetMaxX(cgr));
+}
+
+#endif
+
+static inline void getNPRect(const NSRect& nr, NPRect& npr)
+{
+ npr.top = static_cast<uint16>(nr.origin.y);
+ npr.left = static_cast<uint16>(nr.origin.x);
+ npr.bottom = static_cast<uint16>(NSMaxY(nr));
+ npr.right = static_cast<uint16>(NSMaxX(nr));
+}
+
+- (NSRect)visibleRect
+{
+ // WebCore may impose an additional clip (via CSS overflow or clip properties). Fetch
+ // that clip now.
+ return NSIntersectionRect([self convertRect:[element _windowClipRect] fromView:nil], [super visibleRect]);
+}
+
+- (PortState)saveAndSetNewPortStateForUpdate:(BOOL)forUpdate
+{
+ ASSERT([self currentWindow] != nil);
+
+#ifndef NP_NO_QUICKDRAW
+ // If drawing with QuickDraw, fix the window port so that it has the same bounds as the NSWindow's
+ // content view. This makes it easier to convert between AppKit view and QuickDraw port coordinates.
+ if (drawingModel == NPDrawingModelQuickDraw)
+ [self fixWindowPort];
+#endif
+
+ WindowRef windowRef = (WindowRef)[[self currentWindow] windowRef];
+ ASSERT(windowRef);
+
+ // Use AppKit to convert view coordinates to NSWindow coordinates.
+ NSRect boundsInWindow = [self convertRect:[self bounds] toView:nil];
+ NSRect visibleRectInWindow = [self convertRect:[self visibleRect] toView:nil];
+
+ // Flip Y to convert NSWindow coordinates to top-left-based window coordinates.
+ float borderViewHeight = [[self currentWindow] frame].size.height;
+ boundsInWindow.origin.y = borderViewHeight - NSMaxY(boundsInWindow);
+ visibleRectInWindow.origin.y = borderViewHeight - NSMaxY(visibleRectInWindow);
+
+#ifndef NP_NO_QUICKDRAW
+ // Look at the Carbon port to convert top-left-based window coordinates into top-left-based content coordinates.
+ if (drawingModel == NPDrawingModelQuickDraw) {
+ ::Rect portBounds;
+ CGrafPtr port = GetWindowPort(windowRef);
+ GetPortBounds(port, &portBounds);
+
+ PixMap *pix = *GetPortPixMap(port);
+ boundsInWindow.origin.x += pix->bounds.left - portBounds.left;
+ boundsInWindow.origin.y += pix->bounds.top - portBounds.top;
+ visibleRectInWindow.origin.x += pix->bounds.left - portBounds.left;
+ visibleRectInWindow.origin.y += pix->bounds.top - portBounds.top;
+ }
+#endif
+
+ window.x = (int32)boundsInWindow.origin.x;
+ window.y = (int32)boundsInWindow.origin.y;
+ window.width = static_cast<uint32>(NSWidth(boundsInWindow));
+ window.height = static_cast<uint32>(NSHeight(boundsInWindow));
+
+ // "Clip-out" the plug-in when:
+ // 1) it's not really in a window or off-screen or has no height or width.
+ // 2) window.x is a "big negative number" which is how WebCore expresses off-screen widgets.
+ // 3) the window is miniaturized or the app is hidden
+ // 4) we're inside of viewWillMoveToWindow: with a nil window. In this case, superviews may already have nil
+ // superviews and nil windows and results from convertRect:toView: are incorrect.
+ NSWindow *realWindow = [self window];
+ if (window.width <= 0 || window.height <= 0 || window.x < -100000
+ || realWindow == nil || [realWindow isMiniaturized]
+ || [NSApp isHidden]
+ || ![self superviewsHaveSuperviews]
+ || [self isHiddenOrHasHiddenAncestor]) {
+
+ // The following code tries to give plug-ins the same size they will eventually have.
+ // The specifiedWidth and specifiedHeight variables are used to predict the size that
+ // WebCore will eventually resize us to.
+
+ // The QuickTime plug-in has problems if you give it a width or height of 0.
+ // Since other plug-ins also might have the same sort of trouble, we make sure
+ // to always give plug-ins a size other than 0,0.
+
+ if (window.width <= 0)
+ window.width = specifiedWidth > 0 ? specifiedWidth : 100;
+ if (window.height <= 0)
+ window.height = specifiedHeight > 0 ? specifiedHeight : 100;
+
+ window.clipRect.bottom = window.clipRect.top;
+ window.clipRect.left = window.clipRect.right;
+ } else {
+ getNPRect(visibleRectInWindow, window.clipRect);
+ }
+
+ // Save the port state, set up the port for entry into the plugin
+ PortState portState;
+ switch (drawingModel) {
+#ifndef NP_NO_QUICKDRAW
+ case NPDrawingModelQuickDraw: {
+ // Set up NS_Port.
+ ::Rect portBounds;
+ CGrafPtr port = GetWindowPort(windowRef);
+ GetPortBounds(port, &portBounds);
+ nPort.qdPort.port = port;
+ nPort.qdPort.portx = (int32)-boundsInWindow.origin.x;
+ nPort.qdPort.porty = (int32)-boundsInWindow.origin.y;
+ window.window = &nPort;
+
+ PortState_QD *qdPortState = (PortState_QD*)malloc(sizeof(PortState_QD));
+ portState = (PortState)qdPortState;
+
+ GetGWorld(&qdPortState->oldPort, &qdPortState->oldDevice);
+
+ qdPortState->oldOrigin.h = portBounds.left;
+ qdPortState->oldOrigin.v = portBounds.top;
+
+ qdPortState->oldClipRegion = NewRgn();
+ GetPortClipRegion(port, qdPortState->oldClipRegion);
+
+ qdPortState->oldVisibleRegion = NewRgn();
+ GetPortVisibleRegion(port, qdPortState->oldVisibleRegion);
+
+ RgnHandle clipRegion = NewRgn();
+ qdPortState->clipRegion = clipRegion;
+
+ CGContextRef currentContext = (CGContextRef)[[NSGraphicsContext currentContext] graphicsPort];
+ if (currentContext && WKCGContextIsBitmapContext(currentContext)) {
+ // We use WKCGContextIsBitmapContext here, because if we just called CGBitmapContextGetData
+ // on any context, we'd log to the console every time. But even if WKCGContextIsBitmapContext
+ // returns true, it still might not be a context we need to create a GWorld for; for example
+ // transparency layers will return true, but return 0 for CGBitmapContextGetData.
+ void* offscreenData = CGBitmapContextGetData(currentContext);
+ if (offscreenData) {
+ // If the current context is an offscreen bitmap, then create a GWorld for it.
+ ::Rect offscreenBounds;
+ offscreenBounds.top = 0;
+ offscreenBounds.left = 0;
+ offscreenBounds.right = CGBitmapContextGetWidth(currentContext);
+ offscreenBounds.bottom = CGBitmapContextGetHeight(currentContext);
+ GWorldPtr newOffscreenGWorld;
+ QDErr err = NewGWorldFromPtr(&newOffscreenGWorld,
+ getQDPixelFormatForBitmapContext(currentContext), &offscreenBounds, 0, 0, 0,
+ static_cast<char*>(offscreenData), CGBitmapContextGetBytesPerRow(currentContext));
+ ASSERT(newOffscreenGWorld && !err);
+ if (!err) {
+ if (offscreenGWorld)
+ DisposeGWorld(offscreenGWorld);
+ offscreenGWorld = newOffscreenGWorld;
+
+ SetGWorld(offscreenGWorld, NULL);
+
+ port = offscreenGWorld;
+
+ nPort.qdPort.port = port;
+ boundsInWindow = [self bounds];
+
+ // Generate a QD origin based on the current affine transform for currentContext.
+ CGAffineTransform offscreenMatrix = CGContextGetCTM(currentContext);
+ CGPoint origin = {0,0};
+ CGPoint axisFlip = {1,1};
+ origin = CGPointApplyAffineTransform(origin, offscreenMatrix);
+ axisFlip = CGPointApplyAffineTransform(axisFlip, offscreenMatrix);
+
+ // Quartz bitmaps have origins at the bottom left, but the axes may be inverted, so handle that.
+ origin.x = offscreenBounds.left - origin.x * (axisFlip.x - origin.x);
+ origin.y = offscreenBounds.bottom + origin.y * (axisFlip.y - origin.y);
+
+ nPort.qdPort.portx = static_cast<int32>(-boundsInWindow.origin.x + origin.x);
+ nPort.qdPort.porty = static_cast<int32>(-boundsInWindow.origin.y - origin.y);
+ window.x = 0;
+ window.y = 0;
+ window.window = &nPort;
+
+ // Use the clip bounds from the context instead of the bounds we created
+ // from the window above.
+ getNPRect(CGRectOffset(CGContextGetClipBoundingBox(currentContext), -origin.x, origin.y), window.clipRect);
+ }
+ }
+ }
+
+ MacSetRectRgn(clipRegion,
+ window.clipRect.left + nPort.qdPort.portx, window.clipRect.top + nPort.qdPort.porty,
+ window.clipRect.right + nPort.qdPort.portx, window.clipRect.bottom + nPort.qdPort.porty);
+
+ // Clip to dirty region so plug-in does not draw over already-drawn regions of the window that are
+ // not going to be redrawn this update. This forces plug-ins to play nice with z-index ordering.
+ if (forUpdate) {
+ RgnHandle viewClipRegion = NewRgn();
+
+ // Get list of dirty rects from the opaque ancestor -- WebKit does some tricks with invalidation and
+ // display to enable z-ordering for NSViews; a side-effect of this is that only the WebHTMLView
+ // knows about the true set of dirty rects.
+ NSView *opaqueAncestor = [self opaqueAncestor];
+ const NSRect *dirtyRects;
+ NSInteger dirtyRectCount, dirtyRectIndex;
+ [opaqueAncestor getRectsBeingDrawn:&dirtyRects count:&dirtyRectCount];
+
+ for (dirtyRectIndex = 0; dirtyRectIndex < dirtyRectCount; dirtyRectIndex++) {
+ NSRect dirtyRect = [self convertRect:dirtyRects[dirtyRectIndex] fromView:opaqueAncestor];
+ if (!NSEqualSizes(dirtyRect.size, NSZeroSize)) {
+ // Create a region for this dirty rect
+ RgnHandle dirtyRectRegion = NewRgn();
+ SetRectRgn(dirtyRectRegion, static_cast<short>(NSMinX(dirtyRect)), static_cast<short>(NSMinY(dirtyRect)), static_cast<short>(NSMaxX(dirtyRect)), static_cast<short>(NSMaxY(dirtyRect)));
+
+ // Union this dirty rect with the rest of the dirty rects
+ UnionRgn(viewClipRegion, dirtyRectRegion, viewClipRegion);
+ DisposeRgn(dirtyRectRegion);
+ }
+ }
+
+ // Intersect the dirty region with the clip region, so that we only draw over dirty parts
+ SectRgn(clipRegion, viewClipRegion, clipRegion);
+ DisposeRgn(viewClipRegion);
+ }
+
+ // Switch to the port and set it up.
+ SetPort(port);
+ PenNormal();
+ ForeColor(blackColor);
+ BackColor(whiteColor);
+ SetOrigin(nPort.qdPort.portx, nPort.qdPort.porty);
+ SetPortClipRegion(nPort.qdPort.port, clipRegion);
+
+ if (forUpdate) {
+ // AppKit may have tried to help us by doing a BeginUpdate.
+ // But the invalid region at that level didn't include AppKit's notion of what was not valid.
+ // We reset the port's visible region to counteract what BeginUpdate did.
+ SetPortVisibleRegion(nPort.qdPort.port, clipRegion);
+ InvalWindowRgn(windowRef, clipRegion);
+ }
+
+ qdPortState->forUpdate = forUpdate;
+ break;
+ }
+#endif /* NP_NO_QUICKDRAW */
+
+ case NPDrawingModelCoreGraphics: {
+ ASSERT([NSView focusView] == self);
+
+ CGContextRef context = static_cast<CGContextRef>([[NSGraphicsContext currentContext] graphicsPort]);
+
+ PortState_CG *cgPortState = (PortState_CG *)malloc(sizeof(PortState_CG));
+ portState = (PortState)cgPortState;
+ cgPortState->context = context;
+
+ // Update the plugin's window/context
+ nPort.cgPort.window = windowRef;
+ nPort.cgPort.context = context;
+ window.window = &nPort.cgPort;
+
+ // Save current graphics context's state; will be restored by -restorePortState:
+ CGContextSaveGState(context);
+
+ // Get list of dirty rects from the opaque ancestor -- WebKit does some tricks with invalidation and
+ // display to enable z-ordering for NSViews; a side-effect of this is that only the WebHTMLView
+ // knows about the true set of dirty rects.
+ NSView *opaqueAncestor = [self opaqueAncestor];
+ const NSRect *dirtyRects;
+ NSInteger count;
+ [opaqueAncestor getRectsBeingDrawn:&dirtyRects count:&count];
+ Vector<CGRect, 16> convertedDirtyRects;
+ convertedDirtyRects.resize(count);
+ for (int i = 0; i < count; ++i)
+ reinterpret_cast<NSRect&>(convertedDirtyRects[i]) = [self convertRect:dirtyRects[i] fromView:opaqueAncestor];
+ CGContextClipToRects(context, convertedDirtyRects.data(), count);
+
+ break;
+ }
+
+ case NPDrawingModelOpenGL: {
+ ASSERT([NSView focusView] == self);
+
+ // Clear the "current" window and context -- they will be assigned below (if all goes well)
+ nPort.aglPort.window = NULL;
+ nPort.aglPort.context = NULL;
+
+ // Create AGL context if needed
+ if (![self _createAGLContextIfNeeded]) {
+ LOG_ERROR("Could not create AGL context");
+ return NULL;
+ }
+
+ // Update the plugin's window/context
+ nPort.aglPort.window = windowRef;
+ nPort.aglPort.context = [self _cglContext];
+ window.window = &nPort.aglPort;
+
+ // Save/set current AGL context
+ PortState_GL *glPortState = (PortState_GL *)malloc(sizeof(PortState_GL));
+ portState = (PortState)glPortState;
+ glPortState->oldContext = aglGetCurrentContext();
+ aglSetCurrentContext(aglContext);
+
+ // Adjust viewport according to clip
+ switch (window.type) {
+ case NPWindowTypeWindow:
+ glViewport(static_cast<GLint>(NSMinX(boundsInWindow) - NSMinX(visibleRectInWindow)),
+ static_cast<GLint>(NSMaxY(visibleRectInWindow) - NSMaxY(boundsInWindow)),
+ window.width, window.height);
+ break;
+
+ case NPWindowTypeDrawable: {
+ GLsizei width, height;
+ if ([self _getAGLOffscreenBuffer:NULL width:&width height:&height])
+ glViewport(0, 0, width, height);
+ break;
+ }
+
+ default:
+ ASSERT_NOT_REACHED();
+ break;
+ }
+ break;
+ }
+
+ default:
+ ASSERT_NOT_REACHED();
+ portState = NULL;
+ break;
+ }
+
+ return portState;
+}
+
+- (PortState)saveAndSetNewPortState
+{
+ return [self saveAndSetNewPortStateForUpdate:NO];
+}
+
+- (void)restorePortState:(PortState)portState
+{
+ ASSERT([self currentWindow]);
+ ASSERT(portState);
+
+ switch (drawingModel) {
+#ifndef NP_NO_QUICKDRAW
+ case NPDrawingModelQuickDraw: {
+ PortState_QD *qdPortState = (PortState_QD *)portState;
+ WindowRef windowRef = (WindowRef)[[self currentWindow] windowRef];
+ CGrafPtr port = GetWindowPort(windowRef);
+
+ SetPort(port);
+
+ if (qdPortState->forUpdate)
+ ValidWindowRgn(windowRef, qdPortState->clipRegion);
+
+ SetOrigin(qdPortState->oldOrigin.h, qdPortState->oldOrigin.v);
+
+ SetPortClipRegion(port, qdPortState->oldClipRegion);
+ if (qdPortState->forUpdate)
+ SetPortVisibleRegion(port, qdPortState->oldVisibleRegion);
+
+ DisposeRgn(qdPortState->oldClipRegion);
+ DisposeRgn(qdPortState->oldVisibleRegion);
+ DisposeRgn(qdPortState->clipRegion);
+
+ SetGWorld(qdPortState->oldPort, qdPortState->oldDevice);
+ break;
+ }
+#endif /* NP_NO_QUICKDRAW */
+
+ case NPDrawingModelCoreGraphics:
+ ASSERT([NSView focusView] == self);
+ ASSERT(((PortState_CG *)portState)->context == nPort.cgPort.context);
+ CGContextRestoreGState(nPort.cgPort.context);
+ break;
+
+ case NPDrawingModelOpenGL:
+ aglSetCurrentContext(((PortState_GL *)portState)->oldContext);
+ break;
+
+ default:
+ ASSERT_NOT_REACHED();
+ break;
+ }
+}
+
+- (BOOL)sendEvent:(EventRecord *)event
+{
+ if (![self window])
+ return NO;
+ ASSERT(event);
+
+ // If at any point the user clicks or presses a key from within a plugin, set the
+ // currentEventIsUserGesture flag to true. This is important to differentiate legitimate
+ // window.open() calls; we still want to allow those. See rdar://problem/4010765
+ if (event->what == mouseDown || event->what == keyDown || event->what == mouseUp || event->what == autoKey)
+ currentEventIsUserGesture = YES;
+
+ suspendKeyUpEvents = NO;
+
+ if (!isStarted)
+ return NO;
+
+ ASSERT(NPP_HandleEvent);
+
+ // Make sure we don't call NPP_HandleEvent while we're inside NPP_SetWindow.
+ // We probably don't want more general reentrancy protection; we are really
+ // protecting only against this one case, which actually comes up when
+ // you first install the SVG viewer plug-in.
+ if (inSetWindow)
+ return NO;
+
+ Frame* frame = core([self webFrame]);
+ if (!frame)
+ return NO;
+ Page* page = frame->page();
+ if (!page)
+ return NO;
+
+ bool wasDeferring = page->defersLoading();
+ if (!wasDeferring)
+ page->setDefersLoading(true);
+
+ // Can only send updateEvt to CoreGraphics and OpenGL plugins when actually drawing
+ ASSERT((drawingModel != NPDrawingModelCoreGraphics && drawingModel != NPDrawingModelOpenGL) || event->what != updateEvt || [NSView focusView] == self);
+
+ BOOL updating = event->what == updateEvt;
+ PortState portState;
+ if ((drawingModel != NPDrawingModelCoreGraphics && drawingModel != NPDrawingModelOpenGL) || event->what == updateEvt) {
+ // In CoreGraphics or OpenGL mode, the port state only needs to be saved/set when redrawing the plug-in view. The plug-in is not
+ // allowed to draw at any other time.
+ portState = [self saveAndSetNewPortStateForUpdate:updating];
+
+ // We may have changed the window, so inform the plug-in.
+ [self setWindowIfNecessary];
+ } else
+ portState = NULL;
+
+#if !defined(NDEBUG) && !defined(NP_NO_QUICKDRAW)
+ // Draw green to help debug.
+ // If we see any green we know something's wrong.
+ // Note that PaintRect() only works for QuickDraw plugins; otherwise the current QD port is undefined.
+ if (drawingModel == NPDrawingModelQuickDraw && !isTransparent && event->what == updateEvt) {
+ ForeColor(greenColor);
+ const ::Rect bigRect = { -10000, -10000, 10000, 10000 };
+ PaintRect(&bigRect);
+ ForeColor(blackColor);
+ }
+#endif
+
+ // Temporarily retain self in case the plug-in view is released while sending an event.
+ [[self retain] autorelease];
+
+ BOOL acceptedEvent;
+ [self willCallPlugInFunction];
+ {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ acceptedEvent = NPP_HandleEvent(plugin, event);
+ }
+ [self didCallPlugInFunction];
+
+ currentEventIsUserGesture = NO;
+
+ if (portState) {
+ if ([self currentWindow])
+ [self restorePortState:portState];
+ free(portState);
+ }
+
+ if (!wasDeferring)
+ page->setDefersLoading(false);
+
+ return acceptedEvent;
+}
+
+- (void)sendActivateEvent:(BOOL)activate
+{
+ EventRecord event;
+
+ [self getCarbonEvent:&event];
+ event.what = activateEvt;
+ WindowRef windowRef = (WindowRef)[[self window] windowRef];
+ event.message = (unsigned long)windowRef;
+ if (activate) {
+ event.modifiers |= activeFlag;
+ }
+
+ BOOL acceptedEvent;
+ acceptedEvent = [self sendEvent:&event];
+
+ LOG(PluginEvents, "NPP_HandleEvent(activateEvent): %d isActive: %d", acceptedEvent, activate);
+}
+
+- (BOOL)sendUpdateEvent
+{
+ EventRecord event;
+
+ [self getCarbonEvent:&event];
+ event.what = updateEvt;
+ WindowRef windowRef = (WindowRef)[[self window] windowRef];
+ event.message = (unsigned long)windowRef;
+
+ BOOL acceptedEvent = [self sendEvent:&event];
+
+ LOG(PluginEvents, "NPP_HandleEvent(updateEvt): %d", acceptedEvent);
+
+ return acceptedEvent;
+}
+
+-(void)sendNullEvent
+{
+ EventRecord event;
+
+ [self getCarbonEvent:&event];
+
+ // Plug-in should not react to cursor position when not active or when a menu is down.
+ MenuTrackingData trackingData;
+ OSStatus error = GetMenuTrackingData(NULL, &trackingData);
+
+ // Plug-in should not react to cursor position when the actual window is not key.
+ if (![[self window] isKeyWindow] || (error == noErr && trackingData.menu)) {
+ // FIXME: Does passing a v and h of -1 really prevent it from reacting to the cursor position?
+ event.where.v = -1;
+ event.where.h = -1;
+ }
+
+ [self sendEvent:&event];
+}
+
+- (void)stopNullEvents
+{
+ [nullEventTimer invalidate];
+ [nullEventTimer release];
+ nullEventTimer = nil;
+}
+
+- (void)restartNullEvents
+{
+ ASSERT([self window]);
+
+ if (nullEventTimer)
+ [self stopNullEvents];
+
+ if (!isStarted || [[self window] isMiniaturized])
+ return;
+
+ NSTimeInterval interval;
+
+ // If the plugin is completely obscured (scrolled out of view, for example), then we will
+ // send null events at a reduced rate.
+ interval = !isCompletelyObscured ? NullEventIntervalActive : NullEventIntervalNotActive;
+ nullEventTimer = [[NSTimer scheduledTimerWithTimeInterval:interval
+ target:self
+ selector:@selector(sendNullEvent)
+ userInfo:nil
+ repeats:YES] retain];
+}
+
+- (BOOL)acceptsFirstResponder
+{
+ return YES;
+}
+
+- (void)installKeyEventHandler
+{
+ static const EventTypeSpec sTSMEvents[] =
+ {
+ { kEventClassTextInput, kEventTextInputUnicodeForKeyEvent }
+ };
+
+ if (!keyEventHandler) {
+ InstallEventHandler(GetWindowEventTarget((WindowRef)[[self window] windowRef]),
+ NewEventHandlerUPP(TSMEventHandler),
+ GetEventTypeCount(sTSMEvents),
+ sTSMEvents,
+ self,
+ &keyEventHandler);
+ }
+}
+
+- (void)removeKeyEventHandler
+{
+ if (keyEventHandler) {
+ RemoveEventHandler(keyEventHandler);
+ keyEventHandler = NULL;
+ }
+}
+
+- (void)setHasFocus:(BOOL)flag
+{
+ if (hasFocus != flag) {
+ hasFocus = flag;
+ EventRecord event;
+ [self getCarbonEvent:&event];
+ BOOL acceptedEvent;
+ if (hasFocus) {
+ event.what = getFocusEvent;
+ acceptedEvent = [self sendEvent:&event];
+ LOG(PluginEvents, "NPP_HandleEvent(getFocusEvent): %d", acceptedEvent);
+ [self installKeyEventHandler];
+ } else {
+ event.what = loseFocusEvent;
+ acceptedEvent = [self sendEvent:&event];
+ LOG(PluginEvents, "NPP_HandleEvent(loseFocusEvent): %d", acceptedEvent);
+ [self removeKeyEventHandler];
+ }
+ }
+}
+
+- (BOOL)becomeFirstResponder
+{
+ [self setHasFocus:YES];
+ return YES;
+}
+
+- (BOOL)resignFirstResponder
+{
+ [self setHasFocus:NO];
+ return YES;
+}
+
+// AppKit doesn't call mouseDown or mouseUp on right-click. Simulate control-click
+// mouseDown and mouseUp so plug-ins get the right-click event as they do in Carbon (3125743).
+- (void)rightMouseDown:(NSEvent *)theEvent
+{
+ [self mouseDown:theEvent];
+}
+
+- (void)rightMouseUp:(NSEvent *)theEvent
+{
+ [self mouseUp:theEvent];
+}
+
+- (void)mouseDown:(NSEvent *)theEvent
+{
+ EventRecord event;
+
+ [self getCarbonEvent:&event withEvent:theEvent];
+ event.what = mouseDown;
+
+ BOOL acceptedEvent;
+ acceptedEvent = [self sendEvent:&event];
+
+ LOG(PluginEvents, "NPP_HandleEvent(mouseDown): %d pt.v=%d, pt.h=%d", acceptedEvent, event.where.v, event.where.h);
+}
+
+- (void)mouseUp:(NSEvent *)theEvent
+{
+ EventRecord event;
+
+ [self getCarbonEvent:&event withEvent:theEvent];
+ event.what = mouseUp;
+
+ BOOL acceptedEvent;
+ acceptedEvent = [self sendEvent:&event];
+
+ LOG(PluginEvents, "NPP_HandleEvent(mouseUp): %d pt.v=%d, pt.h=%d", acceptedEvent, event.where.v, event.where.h);
+}
+
+- (void)mouseEntered:(NSEvent *)theEvent
+{
+ EventRecord event;
+
+ [self getCarbonEvent:&event withEvent:theEvent];
+ event.what = adjustCursorEvent;
+
+ BOOL acceptedEvent;
+ acceptedEvent = [self sendEvent:&event];
+
+ LOG(PluginEvents, "NPP_HandleEvent(mouseEntered): %d", acceptedEvent);
+}
+
+- (void)mouseExited:(NSEvent *)theEvent
+{
+ EventRecord event;
+
+ [self getCarbonEvent:&event withEvent:theEvent];
+ event.what = adjustCursorEvent;
+
+ BOOL acceptedEvent;
+ acceptedEvent = [self sendEvent:&event];
+
+ // Set cursor back to arrow cursor. Because NSCursor doesn't know about changes that the plugin made, we could get confused about what we think the
+ // current cursor is otherwise. Therefore we have no choice but to unconditionally reset the cursor when the mouse exits the plugin.
+ [[NSCursor arrowCursor] set];
+
+ LOG(PluginEvents, "NPP_HandleEvent(mouseExited): %d", acceptedEvent);
+}
+
+- (void)mouseDragged:(NSEvent *)theEvent
+{
+ // Do nothing so that other responders don't respond to the drag that initiated in this view.
+}
+
+- (UInt32)keyMessageForEvent:(NSEvent *)event
+{
+ NSData *data = [[event characters] dataUsingEncoding:CFStringConvertEncodingToNSStringEncoding(CFStringGetSystemEncoding())];
+ if (!data) {
+ return 0;
+ }
+ UInt8 characterCode;
+ [data getBytes:&characterCode length:1];
+ UInt16 keyCode = [event keyCode];
+ return keyCode << 8 | characterCode;
+}
+
+- (void)keyUp:(NSEvent *)theEvent
+{
+ WKSendKeyEventToTSM(theEvent);
+
+ // TSM won't send keyUp events so we have to send them ourselves.
+ // Only send keyUp events after we receive the TSM callback because this is what plug-in expect from OS 9.
+ if (!suspendKeyUpEvents) {
+ EventRecord event;
+
+ [self getCarbonEvent:&event withEvent:theEvent];
+ event.what = keyUp;
+
+ if (event.message == 0) {
+ event.message = [self keyMessageForEvent:theEvent];
+ }
+
+ [self sendEvent:&event];
+ }
+}
+
+- (void)keyDown:(NSEvent *)theEvent
+{
+ suspendKeyUpEvents = YES;
+ WKSendKeyEventToTSM(theEvent);
+}
+
+static OSStatus TSMEventHandler(EventHandlerCallRef inHandlerRef, EventRef inEvent, void *pluginView)
+{
+ EventRef rawKeyEventRef;
+ OSStatus status = GetEventParameter(inEvent, kEventParamTextInputSendKeyboardEvent, typeEventRef, NULL, sizeof(EventRef), NULL, &rawKeyEventRef);
+ if (status != noErr) {
+ LOG_ERROR("GetEventParameter failed with error: %d", status);
+ return noErr;
+ }
+
+ // Two-pass read to allocate/extract Mac charCodes
+ ByteCount numBytes;
+ status = GetEventParameter(rawKeyEventRef, kEventParamKeyMacCharCodes, typeChar, NULL, 0, &numBytes, NULL);
+ if (status != noErr) {
+ LOG_ERROR("GetEventParameter failed with error: %d", status);
+ return noErr;
+ }
+ char *buffer = (char *)malloc(numBytes);
+ status = GetEventParameter(rawKeyEventRef, kEventParamKeyMacCharCodes, typeChar, NULL, numBytes, NULL, buffer);
+ if (status != noErr) {
+ LOG_ERROR("GetEventParameter failed with error: %d", status);
+ free(buffer);
+ return noErr;
+ }
+
+ EventRef cloneEvent = CopyEvent(rawKeyEventRef);
+ unsigned i;
+ for (i = 0; i < numBytes; i++) {
+ status = SetEventParameter(cloneEvent, kEventParamKeyMacCharCodes, typeChar, 1 /* one char code */, &buffer[i]);
+ if (status != noErr) {
+ LOG_ERROR("SetEventParameter failed with error: %d", status);
+ free(buffer);
+ return noErr;
+ }
+
+ EventRecord eventRec;
+ if (ConvertEventRefToEventRecord(cloneEvent, &eventRec)) {
+ BOOL acceptedEvent;
+ acceptedEvent = [(WebBaseNetscapePluginView *)pluginView sendEvent:&eventRec];
+
+ LOG(PluginEvents, "NPP_HandleEvent(keyDown): %d charCode:%c keyCode:%lu",
+ acceptedEvent, (char) (eventRec.message & charCodeMask), (eventRec.message & keyCodeMask));
+
+ // We originally thought that if the plug-in didn't accept this event,
+ // we should pass it along so that keyboard scrolling, for example, will work.
+ // In practice, this is not a good idea, because plug-ins tend to eat the event but return false.
+ // MacIE handles each key event twice because of this, but we will emulate the other browsers instead.
+ }
+ }
+ ReleaseEvent(cloneEvent);
+
+ free(buffer);
+
+ return noErr;
+}
+
+// Fake up command-modified events so cut, copy, paste and select all menus work.
+- (void)sendModifierEventWithKeyCode:(int)keyCode character:(char)character
+{
+ EventRecord event;
+ [self getCarbonEvent:&event];
+ event.what = keyDown;
+ event.modifiers |= cmdKey;
+ event.message = keyCode << 8 | character;
+ [self sendEvent:&event];
+}
+
+- (void)cut:(id)sender
+{
+ [self sendModifierEventWithKeyCode:7 character:'x'];
+}
+
+- (void)copy:(id)sender
+{
+ [self sendModifierEventWithKeyCode:8 character:'c'];
+}
+
+- (void)paste:(id)sender
+{
+ [self sendModifierEventWithKeyCode:9 character:'v'];
+}
+
+- (void)selectAll:(id)sender
+{
+ [self sendModifierEventWithKeyCode:0 character:'a'];
+}
+
+#pragma mark WEB_NETSCAPE_PLUGIN
+
+- (BOOL)isNewWindowEqualToOldWindow
+{
+ if (window.x != lastSetWindow.x)
+ return NO;
+ if (window.y != lastSetWindow.y)
+ return NO;
+ if (window.width != lastSetWindow.width)
+ return NO;
+ if (window.height != lastSetWindow.height)
+ return NO;
+ if (window.clipRect.top != lastSetWindow.clipRect.top)
+ return NO;
+ if (window.clipRect.left != lastSetWindow.clipRect.left)
+ return NO;
+ if (window.clipRect.bottom != lastSetWindow.clipRect.bottom)
+ return NO;
+ if (window.clipRect.right != lastSetWindow.clipRect.right)
+ return NO;
+ if (window.type != lastSetWindow.type)
+ return NO;
+
+ switch (drawingModel) {
+#ifndef NP_NO_QUICKDRAW
+ case NPDrawingModelQuickDraw:
+ if (nPort.qdPort.portx != lastSetPort.qdPort.portx)
+ return NO;
+ if (nPort.qdPort.porty != lastSetPort.qdPort.porty)
+ return NO;
+ if (nPort.qdPort.port != lastSetPort.qdPort.port)
+ return NO;
+ break;
+#endif /* NP_NO_QUICKDRAW */
+
+ case NPDrawingModelCoreGraphics:
+ if (nPort.cgPort.window != lastSetPort.cgPort.window)
+ return NO;
+ if (nPort.cgPort.context != lastSetPort.cgPort.context)
+ return NO;
+ break;
+
+ case NPDrawingModelOpenGL:
+ if (nPort.aglPort.window != lastSetPort.aglPort.window)
+ return NO;
+ if (nPort.aglPort.context != lastSetPort.aglPort.context)
+ return NO;
+ break;
+
+ default:
+ ASSERT_NOT_REACHED();
+ break;
+ }
+
+ return YES;
+}
+
+- (void)updateAndSetWindow
+{
+ // A plug-in can only update if it's (1) already been started (2) isn't stopped
+ // and (3) is able to draw on-screen. To meet condition (3) the plug-in must not
+ // be hidden and be attached to a window. QuickDraw plug-ins are an important
+ // excpetion to rule (3) because they manually must be told when to stop writing
+ // bits to the window backing store, thus to do so requires a new call to
+ // NPP_SetWindow() with an empty NPWindow struct.
+ if (!isStarted)
+ return;
+ if (drawingModel != NPDrawingModelQuickDraw && ![self canDraw])
+ return;
+
+ BOOL didLockFocus = [NSView focusView] != self && [self lockFocusIfCanDraw];
+ PortState portState = [self saveAndSetNewPortState];
+ if (portState) {
+ [self setWindowIfNecessary];
+ [self restorePortState:portState];
+ free(portState);
+ }
+ if (didLockFocus)
+ [self unlockFocus];
+}
+
+- (void)setWindowIfNecessary
+{
+ if (!isStarted) {
+ return;
+ }
+
+ if (![self isNewWindowEqualToOldWindow]) {
+ // Make sure we don't call NPP_HandleEvent while we're inside NPP_SetWindow.
+ // We probably don't want more general reentrancy protection; we are really
+ // protecting only against this one case, which actually comes up when
+ // you first install the SVG viewer plug-in.
+ NPError npErr;
+ ASSERT(!inSetWindow);
+
+ inSetWindow = YES;
+
+ // A CoreGraphics or OpenGL plugin's window may only be set while the plugin is being updated
+ ASSERT((drawingModel != NPDrawingModelCoreGraphics && drawingModel != NPDrawingModelOpenGL) || [NSView focusView] == self);
+
+ [self willCallPlugInFunction];
+ {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ npErr = NPP_SetWindow(plugin, &window);
+ }
+ [self didCallPlugInFunction];
+ inSetWindow = NO;
+
+#ifndef NDEBUG
+ switch (drawingModel) {
+#ifndef NP_NO_QUICKDRAW
+ case NPDrawingModelQuickDraw:
+ LOG(Plugins, "NPP_SetWindow (QuickDraw): %d, port=0x%08x, window.x:%d window.y:%d window.width:%d window.height:%d",
+ npErr, (int)nPort.qdPort.port, (int)window.x, (int)window.y, (int)window.width, (int)window.height);
+ break;
+#endif /* NP_NO_QUICKDRAW */
+
+ case NPDrawingModelCoreGraphics:
+ LOG(Plugins, "NPP_SetWindow (CoreGraphics): %d, window=%p, context=%p, window.x:%d window.y:%d window.width:%d window.height:%d",
+ npErr, nPort.cgPort.window, nPort.cgPort.context, (int)window.x, (int)window.y, (int)window.width, (int)window.height);
+ break;
+
+ case NPDrawingModelOpenGL:
+ LOG(Plugins, "NPP_SetWindow (CoreGraphics): %d, window=%p, context=%p, window.x:%d window.y:%d window.width:%d window.height:%d",
+ npErr, nPort.aglPort.window, nPort.aglPort.context, (int)window.x, (int)window.y, (int)window.width, (int)window.height);
+ break;
+
+ default:
+ ASSERT_NOT_REACHED();
+ break;
+ }
+#endif /* !defined(NDEBUG) */
+
+ lastSetWindow = window;
+ lastSetPort = nPort;
+ }
+}
+
+- (void)removeTrackingRect
+{
+ if (trackingTag) {
+ [self removeTrackingRect:trackingTag];
+ trackingTag = 0;
+
+ // Do the following after setting trackingTag to 0 so we don't re-enter.
+
+ // Balance the retain in resetTrackingRect. Use autorelease in case we hold
+ // the last reference to the window during tear-down, to avoid crashing AppKit.
+ [[self window] autorelease];
+ }
+}
+
+- (void)resetTrackingRect
+{
+ [self removeTrackingRect];
+ if (isStarted) {
+ // Retain the window so that removeTrackingRect can work after the window is closed.
+ [[self window] retain];
+ trackingTag = [self addTrackingRect:[self bounds] owner:self userData:nil assumeInside:NO];
+ }
+}
+
++ (void)setCurrentPluginView:(WebBaseNetscapePluginView *)view
+{
+ currentPluginView = view;
+}
+
++ (WebBaseNetscapePluginView *)currentPluginView
+{
+ return currentPluginView;
+}
+
+- (BOOL)canStart
+{
+ return YES;
+}
+
+- (void)didStart
+{
+ if (_loadManually) {
+ [self _redeliverStream];
+ return;
+ }
+
+ // If the OBJECT/EMBED tag has no SRC, the URL is passed to us as "".
+ // Check for this and don't start a load in this case.
+ if (sourceURL != nil && ![sourceURL _web_isEmpty]) {
+ NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:sourceURL];
+ [request _web_setHTTPReferrer:core([self webFrame])->loader()->outgoingReferrer()];
+ [self loadRequest:request inTarget:nil withNotifyData:nil sendNotification:NO];
+ }
+}
+
+- (void)addWindowObservers
+{
+ ASSERT([self window]);
+
+ NSWindow *theWindow = [self window];
+
+ NSNotificationCenter *notificationCenter = [NSNotificationCenter defaultCenter];
+ [notificationCenter addObserver:self selector:@selector(windowWillClose:)
+ name:NSWindowWillCloseNotification object:theWindow];
+ [notificationCenter addObserver:self selector:@selector(windowBecameKey:)
+ name:NSWindowDidBecomeKeyNotification object:theWindow];
+ [notificationCenter addObserver:self selector:@selector(windowResignedKey:)
+ name:NSWindowDidResignKeyNotification object:theWindow];
+ [notificationCenter addObserver:self selector:@selector(windowDidMiniaturize:)
+ name:NSWindowDidMiniaturizeNotification object:theWindow];
+ [notificationCenter addObserver:self selector:@selector(windowDidDeminiaturize:)
+ name:NSWindowDidDeminiaturizeNotification object:theWindow];
+
+ [notificationCenter addObserver:self selector:@selector(loginWindowDidSwitchFromUser:)
+ name:LoginWindowDidSwitchFromUserNotification object:nil];
+ [notificationCenter addObserver:self selector:@selector(loginWindowDidSwitchToUser:)
+ name:LoginWindowDidSwitchToUserNotification object:nil];
+}
+
+- (void)removeWindowObservers
+{
+ NSNotificationCenter *notificationCenter = [NSNotificationCenter defaultCenter];
+ [notificationCenter removeObserver:self name:NSWindowWillCloseNotification object:nil];
+ [notificationCenter removeObserver:self name:NSWindowDidBecomeKeyNotification object:nil];
+ [notificationCenter removeObserver:self name:NSWindowDidResignKeyNotification object:nil];
+ [notificationCenter removeObserver:self name:NSWindowDidMiniaturizeNotification object:nil];
+ [notificationCenter removeObserver:self name:NSWindowDidDeminiaturizeNotification object:nil];
+ [notificationCenter removeObserver:self name:LoginWindowDidSwitchFromUserNotification object:nil];
+ [notificationCenter removeObserver:self name:LoginWindowDidSwitchToUserNotification object:nil];
+}
+
+- (BOOL)start
+{
+ ASSERT([self currentWindow]);
+
+ if (isStarted)
+ return YES;
+
+ if (![self canStart])
+ return NO;
+
+ ASSERT([self webView]);
+
+ if (![[[self webView] preferences] arePlugInsEnabled])
+ return NO;
+
+ // Open the plug-in package so it remains loaded while our plugin uses it
+ [pluginPackage open];
+
+ // Initialize drawingModel to an invalid value so that we can detect when the plugin does not specify a drawingModel
+ drawingModel = (NPDrawingModel)-1;
+
+ // Plug-ins are "windowed" by default. On MacOS, windowed plug-ins share the same window and graphics port as the main
+ // browser window. Windowless plug-ins are rendered off-screen, then copied into the main browser window.
+ window.type = NPWindowTypeWindow;
+
+ NPError npErr = [self _createPlugin];
+ if (npErr != NPERR_NO_ERROR) {
+ LOG_ERROR("NPP_New failed with error: %d", npErr);
+ [self _destroyPlugin];
+ [pluginPackage close];
+ return NO;
+ }
+
+ if (drawingModel == (NPDrawingModel)-1) {
+#ifndef NP_NO_QUICKDRAW
+ // Default to QuickDraw if the plugin did not specify a drawing model.
+ drawingModel = NPDrawingModelQuickDraw;
+#else
+ // QuickDraw is not available, so we can't default to it. We could default to CoreGraphics instead, but
+ // if the plugin did not specify the CoreGraphics drawing model then it must be one of the old QuickDraw
+ // plugins. Thus, the plugin is unsupported and should not be started. Destroy it here and bail out.
+ LOG(Plugins, "Plugin only supports QuickDraw, but QuickDraw is unavailable: %@", pluginPackage);
+ [self _destroyPlugin];
+ [pluginPackage close];
+ return NO;
+#endif
+ }
+
+ isStarted = YES;
+
+ [self updateAndSetWindow];
+
+ if ([self window]) {
+ [self addWindowObservers];
+ if ([[self window] isKeyWindow]) {
+ [self sendActivateEvent:YES];
+ }
+ [self restartNullEvents];
+ }
+
+ [self resetTrackingRect];
+
+ [self didStart];
+
+ return YES;
+}
+
+- (void)stop
+{
+ // If we're already calling a plug-in function, do not call NPP_Destroy(). The plug-in function we are calling
+ // may assume that its instance->pdata, or other memory freed by NPP_Destroy(), is valid and unchanged until said
+ // plugin-function returns.
+ // See <rdar://problem/4480737>.
+ if (pluginFunctionCallDepth > 0) {
+ shouldStopSoon = YES;
+ return;
+ }
+
+ [self removeTrackingRect];
+
+ if (!isStarted)
+ return;
+
+ isStarted = NO;
+ // To stop active streams it's necessary to invoke makeObjectsPerformSelector on a copy
+ // of streams. This is because calling -[WebNetscapePluginStream stop] also has the side effect
+ // of removing a stream from this collection.
+ NSArray *streamsCopy = [streams copy];
+ [streamsCopy makeObjectsPerformSelector:@selector(stop)];
+ [streamsCopy release];
+
+ // Stop the null events
+ [self stopNullEvents];
+
+ // Stop notifications and callbacks.
+ [self removeWindowObservers];
+ [[pendingFrameLoads allKeys] makeObjectsPerformSelector:@selector(_setInternalLoadDelegate:) withObject:nil];
+ [NSObject cancelPreviousPerformRequestsWithTarget:self];
+
+ // Setting the window type to 0 ensures that NPP_SetWindow will be called if the plug-in is restarted.
+ lastSetWindow.type = (NPWindowType)0;
+
+ [self _destroyPlugin];
+ [pluginPackage close];
+
+ // We usually remove the key event handler in resignFirstResponder but it is possible that resignFirstResponder
+ // may never get called so we can't completely rely on it.
+ [self removeKeyEventHandler];
+
+ if (drawingModel == NPDrawingModelOpenGL)
+ [self _destroyAGLContext];
+}
+
+- (BOOL)isStarted
+{
+ return isStarted;
+}
+
+- (WebDataSource *)dataSource
+{
+ WebFrame *webFrame = kit(core(element)->document()->frame());
+ return [webFrame _dataSource];
+}
+
+- (WebFrame *)webFrame
+{
+ return [[self dataSource] webFrame];
+}
+
+- (WebView *)webView
+{
+ return [[self webFrame] webView];
+}
+
+- (NSWindow *)currentWindow
+{
+ return [self window] ? [self window] : [[self webView] hostWindow];
+}
+
+- (NPP)plugin
+{
+ return plugin;
+}
+
+- (WebNetscapePluginPackage *)pluginPackage
+{
+ return pluginPackage;
+}
+
+- (void)setPluginPackage:(WebNetscapePluginPackage *)thePluginPackage;
+{
+ [thePluginPackage retain];
+ [pluginPackage release];
+ pluginPackage = thePluginPackage;
+
+ NPP_New = [pluginPackage NPP_New];
+ NPP_Destroy = [pluginPackage NPP_Destroy];
+ NPP_SetWindow = [pluginPackage NPP_SetWindow];
+ NPP_NewStream = [pluginPackage NPP_NewStream];
+ NPP_WriteReady = [pluginPackage NPP_WriteReady];
+ NPP_Write = [pluginPackage NPP_Write];
+ NPP_StreamAsFile = [pluginPackage NPP_StreamAsFile];
+ NPP_DestroyStream = [pluginPackage NPP_DestroyStream];
+ NPP_HandleEvent = [pluginPackage NPP_HandleEvent];
+ NPP_URLNotify = [pluginPackage NPP_URLNotify];
+ NPP_GetValue = [pluginPackage NPP_GetValue];
+ NPP_SetValue = [pluginPackage NPP_SetValue];
+ NPP_Print = [pluginPackage NPP_Print];
+}
+
+- (void)setMIMEType:(NSString *)theMIMEType
+{
+ NSString *type = [theMIMEType copy];
+ [MIMEType release];
+ MIMEType = type;
+}
+
+- (void)setBaseURL:(NSURL *)theBaseURL
+{
+ [theBaseURL retain];
+ [baseURL release];
+ baseURL = theBaseURL;
+}
+
+- (void)setAttributeKeys:(NSArray *)keys andValues:(NSArray *)values;
+{
+ ASSERT([keys count] == [values count]);
+
+ // Convert the attributes to 2 C string arrays.
+ // These arrays are passed to NPP_New, but the strings need to be
+ // modifiable and live the entire life of the plugin.
+
+ // The Java plug-in requires the first argument to be the base URL
+ if ([MIMEType isEqualToString:@"application/x-java-applet"]) {
+ cAttributes = (char **)malloc(([keys count] + 1) * sizeof(char *));
+ cValues = (char **)malloc(([values count] + 1) * sizeof(char *));
+ cAttributes[0] = strdup("DOCBASE");
+ cValues[0] = strdup([baseURL _web_URLCString]);
+ argsCount++;
+ } else {
+ cAttributes = (char **)malloc([keys count] * sizeof(char *));
+ cValues = (char **)malloc([values count] * sizeof(char *));
+ }
+
+ BOOL isWMP = [[[pluginPackage bundle] bundleIdentifier] isEqualToString:@"com.microsoft.WMP.defaultplugin"];
+
+ unsigned i;
+ unsigned count = [keys count];
+ for (i = 0; i < count; i++) {
+ NSString *key = [keys objectAtIndex:i];
+ NSString *value = [values objectAtIndex:i];
+ if ([key _webkit_isCaseInsensitiveEqualToString:@"height"]) {
+ specifiedHeight = [value intValue];
+ } else if ([key _webkit_isCaseInsensitiveEqualToString:@"width"]) {
+ specifiedWidth = [value intValue];
+ }
+ // Avoid Window Media Player crash when these attributes are present.
+ if (isWMP && ([key _webkit_isCaseInsensitiveEqualToString:@"SAMIStyle"] || [key _webkit_isCaseInsensitiveEqualToString:@"SAMILang"])) {
+ continue;
+ }
+ cAttributes[argsCount] = strdup([key UTF8String]);
+ cValues[argsCount] = strdup([value UTF8String]);
+ LOG(Plugins, "%@ = %@", key, value);
+ argsCount++;
+ }
+}
+
+- (void)setMode:(int)theMode
+{
+ mode = theMode;
+}
+
+#pragma mark NSVIEW
+
+- (id)initWithFrame:(NSRect)frame
+ pluginPackage:(WebNetscapePluginPackage *)thePluginPackage
+ URL:(NSURL *)theURL
+ baseURL:(NSURL *)theBaseURL
+ MIMEType:(NSString *)MIME
+ attributeKeys:(NSArray *)keys
+ attributeValues:(NSArray *)values
+ loadManually:(BOOL)loadManually
+ DOMElement:(DOMElement *)anElement
+{
+ [super initWithFrame:frame];
+
+ streams = [[NSMutableArray alloc] init];
+ pendingFrameLoads = [[NSMutableDictionary alloc] init];
+
+ // load the plug-in if it is not already loaded
+ if (![thePluginPackage load]) {
+ [self release];
+ return nil;
+ }
+ [self setPluginPackage:thePluginPackage];
+
+ element = [anElement retain];
+ sourceURL = [theURL retain];
+
+ [self setMIMEType:MIME];
+ [self setBaseURL:theBaseURL];
+ [self setAttributeKeys:keys andValues:values];
+ if (loadManually)
+ [self setMode:NP_FULL];
+ else
+ [self setMode:NP_EMBED];
+
+ _loadManually = loadManually;
+
+ return self;
+}
+
+- (id)initWithFrame:(NSRect)frame
+{
+ ASSERT_NOT_REACHED();
+ return nil;
+}
+
+- (void)fini
+{
+#ifndef NP_NO_QUICKDRAW
+ if (offscreenGWorld)
+ DisposeGWorld(offscreenGWorld);
+#endif
+
+ unsigned i;
+ for (i = 0; i < argsCount; i++) {
+ free(cAttributes[i]);
+ free(cValues[i]);
+ }
+ free(cAttributes);
+ free(cValues);
+}
+
+- (void)disconnectStream:(WebBaseNetscapePluginStream*)stream
+{
+ [streams removeObjectIdenticalTo:stream];
+}
+
+- (void)dealloc
+{
+ ASSERT(!isStarted);
+
+ [sourceURL release];
+ [_manualStream release];
+ [_error release];
+
+ [pluginPackage release];
+ [streams release];
+ [MIMEType release];
+ [baseURL release];
+ [pendingFrameLoads release];
+ [element release];
+
+ ASSERT(!plugin);
+ ASSERT(!aglWindow);
+ ASSERT(!aglContext);
+
+ [self fini];
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+ ASSERT(!isStarted);
+
+ [self fini];
+
+ [super finalize];
+}
+
+- (void)drawRect:(NSRect)rect
+{
+ if (!isStarted) {
+ return;
+ }
+
+ if ([NSGraphicsContext currentContextDrawingToScreen])
+ [self sendUpdateEvent];
+ else {
+ NSBitmapImageRep *printedPluginBitmap = [self _printedPluginBitmap];
+ if (printedPluginBitmap) {
+ // Flip the bitmap before drawing because the QuickDraw port is flipped relative
+ // to this view.
+ CGContextRef cgContext = (CGContextRef)[[NSGraphicsContext currentContext] graphicsPort];
+ CGContextSaveGState(cgContext);
+ NSRect bounds = [self bounds];
+ CGContextTranslateCTM(cgContext, 0.0f, NSHeight(bounds));
+ CGContextScaleCTM(cgContext, 1.0f, -1.0f);
+ [printedPluginBitmap drawInRect:bounds];
+ CGContextRestoreGState(cgContext);
+ }
+ }
+
+ // If this is a windowless OpenGL plugin, blit its contents back into this view. The plug-in just drew into the offscreen context.
+ if (drawingModel == NPDrawingModelOpenGL && window.type == NPWindowTypeDrawable) {
+ NSImage *aglOffscreenImage = [self _aglOffscreenImageForDrawingInRect:rect];
+ if (aglOffscreenImage) {
+ // Flip the context before drawing because the CGL context is flipped relative to this view.
+ CGContextRef cgContext = (CGContextRef)[[NSGraphicsContext currentContext] graphicsPort];
+ CGContextSaveGState(cgContext);
+ NSRect bounds = [self bounds];
+ CGContextTranslateCTM(cgContext, 0.0f, NSHeight(bounds));
+ CGContextScaleCTM(cgContext, 1.0f, -1.0f);
+
+ // Copy 'rect' from the offscreen buffer to this view (the flip above makes this sort of tricky)
+ NSRect flippedRect = rect;
+ flippedRect.origin.y = NSMaxY(bounds) - NSMaxY(flippedRect);
+ [aglOffscreenImage drawInRect:flippedRect fromRect:flippedRect operation:NSCompositeSourceOver fraction:1.0f];
+ CGContextRestoreGState(cgContext);
+ }
+ }
+}
+
+- (BOOL)isFlipped
+{
+ return YES;
+}
+
+- (void)renewGState
+{
+ [super renewGState];
+
+ // -renewGState is called whenever the view's geometry changes. It's a little hacky to override this method, but
+ // much safer than walking up the view hierarchy and observing frame/bounds changed notifications, since you don't
+ // have to track subsequent changes to the view hierarchy and add/remove notification observers.
+ // NSOpenGLView uses the exact same technique to reshape its OpenGL surface.
+ [self _viewHasMoved];
+}
+
+#ifndef NP_NO_QUICKDRAW
+-(void)tellQuickTimeToChill
+{
+ ASSERT(drawingModel == NPDrawingModelQuickDraw);
+
+ // Make a call to the secret QuickDraw API that makes QuickTime calm down.
+ WindowRef windowRef = (WindowRef)[[self window] windowRef];
+ if (!windowRef) {
+ return;
+ }
+ CGrafPtr port = GetWindowPort(windowRef);
+ ::Rect bounds;
+ GetPortBounds(port, &bounds);
+ WKCallDrawingNotification(port, &bounds);
+}
+#endif /* NP_NO_QUICKDRAW */
+
+- (void)viewWillMoveToWindow:(NSWindow *)newWindow
+{
+#ifndef NP_NO_QUICKDRAW
+ if (drawingModel == NPDrawingModelQuickDraw)
+ [self tellQuickTimeToChill];
+#endif
+
+ // We must remove the tracking rect before we move to the new window.
+ // Once we move to the new window, it will be too late.
+ [self removeTrackingRect];
+ [self removeWindowObservers];
+
+ // Workaround for: <rdar://problem/3822871> resignFirstResponder is not sent to first responder view when it is removed from the window
+ [self setHasFocus:NO];
+
+ if (!newWindow) {
+ // Hide the AGL child window
+ if (drawingModel == NPDrawingModelOpenGL)
+ [self _hideAGLWindow];
+
+ if ([[self webView] hostWindow]) {
+ // View will be moved out of the actual window but it still has a host window.
+ [self stopNullEvents];
+ } else {
+ // View will have no associated windows.
+ [self stop];
+
+ // Stop observing WebPreferencesChangedNotification -- we only need to observe this when installed in the view hierarchy.
+ // When not in the view hierarchy, -viewWillMoveToWindow: and -viewDidMoveToWindow will start/stop the plugin as needed.
+ [[NSNotificationCenter defaultCenter] removeObserver:self name:WebPreferencesChangedNotification object:nil];
+ }
+ }
+}
+
+- (void)viewWillMoveToSuperview:(NSView *)newSuperview
+{
+ if (!newSuperview) {
+ // Stop the plug-in when it is removed from its superview. It is not sufficient to do this in -viewWillMoveToWindow:nil, because
+ // the WebView might still has a hostWindow at that point, which prevents the plug-in from being destroyed.
+ // There is no need to start the plug-in when moving into a superview. -viewDidMoveToWindow takes care of that.
+ [self stop];
+
+ // Stop observing WebPreferencesChangedNotification -- we only need to observe this when installed in the view hierarchy.
+ // When not in the view hierarchy, -viewWillMoveToWindow: and -viewDidMoveToWindow will start/stop the plugin as needed.
+ [[NSNotificationCenter defaultCenter] removeObserver:self name:WebPreferencesChangedNotification object:nil];
+ }
+}
+
+- (void)viewDidMoveToWindow
+{
+ [self resetTrackingRect];
+
+ if ([self window]) {
+ // While in the view hierarchy, observe WebPreferencesChangedNotification so that we can start/stop depending
+ // on whether plugins are enabled.
+ [[NSNotificationCenter defaultCenter] addObserver:self
+ selector:@selector(preferencesHaveChanged:)
+ name:WebPreferencesChangedNotification
+ object:nil];
+
+ // View moved to an actual window. Start it if not already started.
+ [self start];
+ [self restartNullEvents];
+ [self addWindowObservers];
+ } else if ([[self webView] hostWindow]) {
+ // View moved out of an actual window, but still has a host window.
+ // Call setWindow to explicitly "clip out" the plug-in from sight.
+ // FIXME: It would be nice to do this where we call stopNullEvents in viewWillMoveToWindow.
+ [self updateAndSetWindow];
+ }
+}
+
+- (void)viewWillMoveToHostWindow:(NSWindow *)hostWindow
+{
+ if (!hostWindow && ![self window]) {
+ // View will have no associated windows.
+ [self stop];
+
+ // Remove WebPreferencesChangedNotification observer -- we will observe once again when we move back into the window
+ [[NSNotificationCenter defaultCenter] removeObserver:self name:WebPreferencesChangedNotification object:nil];
+ }
+}
+
+- (void)viewDidMoveToHostWindow
+{
+ if ([[self webView] hostWindow]) {
+ // View now has an associated window. Start it if not already started.
+ [self start];
+ }
+}
+
+#pragma mark NOTIFICATIONS
+
+- (void)windowWillClose:(NSNotification *)notification
+{
+ [self stop];
+}
+
+- (void)windowBecameKey:(NSNotification *)notification
+{
+ [self sendActivateEvent:YES];
+ [self setNeedsDisplay:YES];
+ [self restartNullEvents];
+ SetUserFocusWindow((WindowRef)[[self window] windowRef]);
+}
+
+- (void)windowResignedKey:(NSNotification *)notification
+{
+ [self sendActivateEvent:NO];
+ [self setNeedsDisplay:YES];
+ [self restartNullEvents];
+}
+
+- (void)windowDidMiniaturize:(NSNotification *)notification
+{
+ [self stopNullEvents];
+}
+
+- (void)windowDidDeminiaturize:(NSNotification *)notification
+{
+ [self restartNullEvents];
+}
+
+- (void)loginWindowDidSwitchFromUser:(NSNotification *)notification
+{
+ [self stopNullEvents];
+}
+
+-(void)loginWindowDidSwitchToUser:(NSNotification *)notification
+{
+ [self restartNullEvents];
+}
+
+- (void)preferencesHaveChanged:(NSNotification *)notification
+{
+ WebPreferences *preferences = [[self webView] preferences];
+ BOOL arePlugInsEnabled = [preferences arePlugInsEnabled];
+
+ if ([notification object] == preferences && isStarted != arePlugInsEnabled) {
+ if (arePlugInsEnabled) {
+ if ([self currentWindow]) {
+ [self start];
+ }
+ } else {
+ [self stop];
+ [self setNeedsDisplay:YES];
+ }
+ }
+}
+
+- (NPObject *)createPluginScriptableObject
+{
+ if (!NPP_GetValue || ![self isStarted])
+ return NULL;
+
+ NPObject *value = NULL;
+ NPError error;
+ [self willCallPlugInFunction];
+ {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ error = NPP_GetValue(plugin, NPPVpluginScriptableNPObject, &value);
+ }
+ [self didCallPlugInFunction];
+ if (error != NPERR_NO_ERROR)
+ return NULL;
+
+ return value;
+}
+
+- (void)willCallPlugInFunction
+{
+ ASSERT(plugin);
+
+ // Could try to prevent infinite recursion here, but it's probably not worth the effort.
+ pluginFunctionCallDepth++;
+}
+
+- (void)didCallPlugInFunction
+{
+ ASSERT(pluginFunctionCallDepth > 0);
+ pluginFunctionCallDepth--;
+
+ // If -stop was called while we were calling into a plug-in function, and we're no longer
+ // inside a plug-in function, stop now.
+ if (pluginFunctionCallDepth == 0 && shouldStopSoon) {
+ shouldStopSoon = NO;
+ [self stop];
+ }
+}
+
+-(void)pluginView:(NSView *)pluginView receivedResponse:(NSURLResponse *)response
+{
+ ASSERT(_loadManually);
+ ASSERT(!_manualStream);
+
+ _manualStream = [[WebNetscapePluginStream alloc] initWithFrameLoader:core([self webFrame])->loader()];
+}
+
+- (void)pluginView:(NSView *)pluginView receivedData:(NSData *)data
+{
+ ASSERT(_loadManually);
+ ASSERT(_manualStream);
+
+ _dataLengthReceived += [data length];
+
+ if (![self isStarted])
+ return;
+
+ if ([_manualStream plugin] == NULL) {
+ [_manualStream setRequestURL:[[[self dataSource] request] URL]];
+ [_manualStream setPlugin:[self plugin]];
+ ASSERT([_manualStream plugin]);
+ [_manualStream startStreamWithResponse:[[self dataSource] response]];
+ }
+
+ if ([_manualStream plugin])
+ [_manualStream receivedData:data];
+}
+
+- (void)pluginView:(NSView *)pluginView receivedError:(NSError *)error
+{
+ ASSERT(_loadManually);
+
+ [error retain];
+ [_error release];
+ _error = error;
+
+ if (![self isStarted]) {
+ return;
+ }
+
+ [_manualStream destroyStreamWithError:error];
+}
+
+- (void)pluginViewFinishedLoading:(NSView *)pluginView
+{
+ ASSERT(_loadManually);
+ ASSERT(_manualStream);
+
+ if ([self isStarted])
+ [_manualStream finishedLoading];
+}
+
+@end
+
+@implementation WebBaseNetscapePluginView (WebNPPCallbacks)
+
+- (NSMutableURLRequest *)requestWithURLCString:(const char *)URLCString
+{
+ if (!URLCString)
+ return nil;
+
+ CFStringRef string = CFStringCreateWithCString(kCFAllocatorDefault, URLCString, kCFStringEncodingISOLatin1);
+ ASSERT(string); // All strings should be representable in ISO Latin 1
+
+ NSString *URLString = [(NSString *)string _web_stringByStrippingReturnCharacters];
+ NSURL *URL = [NSURL _web_URLWithDataAsString:URLString relativeToURL:baseURL];
+ CFRelease(string);
+ if (!URL)
+ return nil;
+
+ NSMutableURLRequest *request = [NSMutableURLRequest requestWithURL:URL];
+ Frame* frame = core([self webFrame]);
+ if (!frame)
+ return nil;
+ [request _web_setHTTPReferrer:frame->loader()->outgoingReferrer()];
+ return request;
+}
+
+- (void)evaluateJavaScriptPluginRequest:(WebPluginRequest *)JSPluginRequest
+{
+ // FIXME: Is this isStarted check needed here? evaluateJavaScriptPluginRequest should not be called
+ // if we are stopped since this method is called after a delay and we call
+ // cancelPreviousPerformRequestsWithTarget inside of stop.
+ if (!isStarted) {
+ return;
+ }
+
+ NSURL *URL = [[JSPluginRequest request] URL];
+ NSString *JSString = [URL _webkit_scriptIfJavaScriptURL];
+ ASSERT(JSString);
+
+ NSString *result = [[[self webFrame] _bridge] stringByEvaluatingJavaScriptFromString:JSString forceUserGesture:[JSPluginRequest isCurrentEventUserGesture]];
+
+ // Don't continue if stringByEvaluatingJavaScriptFromString caused the plug-in to stop.
+ if (!isStarted) {
+ return;
+ }
+
+ if ([JSPluginRequest frameName] != nil) {
+ // FIXME: If the result is a string, we probably want to put that string into the frame.
+ if ([JSPluginRequest sendNotification]) {
+ [self willCallPlugInFunction];
+ {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ NPP_URLNotify(plugin, [URL _web_URLCString], NPRES_DONE, [JSPluginRequest notifyData]);
+ }
+ [self didCallPlugInFunction];
+ }
+ } else if ([result length] > 0) {
+ // Don't call NPP_NewStream and other stream methods if there is no JS result to deliver. This is what Mozilla does.
+ NSData *JSData = [result dataUsingEncoding:NSUTF8StringEncoding];
+ WebBaseNetscapePluginStream *stream = [[WebBaseNetscapePluginStream alloc] initWithRequestURL:URL
+ plugin:plugin
+ notifyData:[JSPluginRequest notifyData]
+ sendNotification:[JSPluginRequest sendNotification]];
+ [stream startStreamResponseURL:URL
+ expectedContentLength:[JSData length]
+ lastModifiedDate:nil
+ MIMEType:@"text/plain"
+ headers:nil];
+ [stream receivedData:JSData];
+ [stream finishedLoading];
+ [stream release];
+ }
+}
+
+- (void)webFrame:(WebFrame *)webFrame didFinishLoadWithReason:(NPReason)reason
+{
+ ASSERT(isStarted);
+
+ WebPluginRequest *pluginRequest = [pendingFrameLoads objectForKey:webFrame];
+ ASSERT(pluginRequest != nil);
+ ASSERT([pluginRequest sendNotification]);
+
+ [self willCallPlugInFunction];
+ {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ NPP_URLNotify(plugin, [[[pluginRequest request] URL] _web_URLCString], reason, [pluginRequest notifyData]);
+ }
+ [self didCallPlugInFunction];
+
+ [pendingFrameLoads removeObjectForKey:webFrame];
+ [webFrame _setInternalLoadDelegate:nil];
+}
+
+- (void)webFrame:(WebFrame *)webFrame didFinishLoadWithError:(NSError *)error
+{
+ NPReason reason = NPRES_DONE;
+ if (error != nil) {
+ reason = [WebBaseNetscapePluginStream reasonForError:error];
+ }
+ [self webFrame:webFrame didFinishLoadWithReason:reason];
+}
+
+- (void)loadPluginRequest:(WebPluginRequest *)pluginRequest
+{
+ NSURLRequest *request = [pluginRequest request];
+ NSString *frameName = [pluginRequest frameName];
+ WebFrame *frame = nil;
+
+ NSURL *URL = [request URL];
+ NSString *JSString = [URL _webkit_scriptIfJavaScriptURL];
+
+ ASSERT(frameName || JSString);
+
+ if (frameName) {
+ // FIXME - need to get rid of this window creation which
+ // bypasses normal targeted link handling
+ frame = kit([[self webFrame] _frameLoader]->findFrameForNavigation(frameName));
+ if (frame == nil) {
+ WebView *currentWebView = [self webView];
+ NSDictionary *features = [[NSDictionary alloc] init];
+ WebView *newWebView = [[currentWebView _UIDelegateForwarder] webView:currentWebView
+ createWebViewWithRequest:nil
+ windowFeatures:features];
+ [features release];
+
+ if (!newWebView) {
+ if ([pluginRequest sendNotification]) {
+ [self willCallPlugInFunction];
+ {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ NPP_URLNotify(plugin, [[[pluginRequest request] URL] _web_URLCString], NPERR_GENERIC_ERROR, [pluginRequest notifyData]);
+ }
+ [self didCallPlugInFunction];
+ }
+ return;
+ }
+
+ frame = [newWebView mainFrame];
+ core(frame)->tree()->setName(frameName);
+ [[newWebView _UIDelegateForwarder] webViewShow:newWebView];
+ }
+ }
+
+ if (JSString) {
+ ASSERT(frame == nil || [self webFrame] == frame);
+ [self evaluateJavaScriptPluginRequest:pluginRequest];
+ } else {
+ [frame loadRequest:request];
+ if ([pluginRequest sendNotification]) {
+ // Check if another plug-in view or even this view is waiting for the frame to load.
+ // If it is, tell it that the load was cancelled because it will be anyway.
+ WebBaseNetscapePluginView *view = [frame _internalLoadDelegate];
+ if (view != nil) {
+ ASSERT([view isKindOfClass:[WebBaseNetscapePluginView class]]);
+ [view webFrame:frame didFinishLoadWithReason:NPRES_USER_BREAK];
+ }
+ [pendingFrameLoads _webkit_setObject:pluginRequest forUncopiedKey:frame];
+ [frame _setInternalLoadDelegate:self];
+ }
+ }
+}
+
+- (NPError)loadRequest:(NSMutableURLRequest *)request inTarget:(const char *)cTarget withNotifyData:(void *)notifyData sendNotification:(BOOL)sendNotification
+{
+ NSURL *URL = [request URL];
+
+ if (!URL)
+ return NPERR_INVALID_URL;
+
+ NSString *target = nil;
+ if (cTarget) {
+ // Find the frame given the target string.
+ target = (NSString *)CFStringCreateWithCString(kCFAllocatorDefault, cTarget, kCFStringEncodingWindowsLatin1);
+ }
+ WebFrame *frame = [self webFrame];
+
+ // don't let a plugin start any loads if it is no longer part of a document that is being
+ // displayed unless the loads are in the same frame as the plugin.
+ if ([[self dataSource] _documentLoader] != [[self webFrame] _frameLoader]->activeDocumentLoader() &&
+ (!cTarget || [frame findFrameNamed:target] != frame)) {
+ if (target)
+ CFRelease(target);
+ return NPERR_GENERIC_ERROR;
+ }
+
+ NSString *JSString = [URL _webkit_scriptIfJavaScriptURL];
+ if (JSString != nil) {
+ if (![[[self webView] preferences] isJavaScriptEnabled]) {
+ // Return NPERR_GENERIC_ERROR if JS is disabled. This is what Mozilla does.
+ return NPERR_GENERIC_ERROR;
+ } else if (cTarget == NULL && mode == NP_FULL) {
+ // Don't allow a JavaScript request from a standalone plug-in that is self-targetted
+ // because this can cause the user to be redirected to a blank page (3424039).
+ return NPERR_INVALID_PARAM;
+ }
+ }
+
+ if (cTarget || JSString) {
+ // Make when targetting a frame or evaluating a JS string, perform the request after a delay because we don't
+ // want to potentially kill the plug-in inside of its URL request.
+
+ if (JSString != nil && target != nil && [frame findFrameNamed:target] != frame) {
+ // For security reasons, only allow JS requests to be made on the frame that contains the plug-in.
+ CFRelease(target);
+ return NPERR_INVALID_PARAM;
+ }
+
+ WebPluginRequest *pluginRequest = [[WebPluginRequest alloc] initWithRequest:request frameName:target notifyData:notifyData sendNotification:sendNotification didStartFromUserGesture:currentEventIsUserGesture];
+ [self performSelector:@selector(loadPluginRequest:) withObject:pluginRequest afterDelay:0];
+ [pluginRequest release];
+ if (target)
+ CFRelease(target);
+ } else {
+ WebNetscapePluginStream *stream = [[WebNetscapePluginStream alloc] initWithRequest:request
+ plugin:plugin
+ notifyData:notifyData
+ sendNotification:sendNotification];
+ if (!stream)
+ return NPERR_INVALID_URL;
+
+ [streams addObject:stream];
+ [stream start];
+ [stream release];
+ }
+
+ return NPERR_NO_ERROR;
+}
+
+-(NPError)getURLNotify:(const char *)URLCString target:(const char *)cTarget notifyData:(void *)notifyData
+{
+ LOG(Plugins, "NPN_GetURLNotify: %s target: %s", URLCString, cTarget);
+
+ NSMutableURLRequest *request = [self requestWithURLCString:URLCString];
+ return [self loadRequest:request inTarget:cTarget withNotifyData:notifyData sendNotification:YES];
+}
+
+-(NPError)getURL:(const char *)URLCString target:(const char *)cTarget
+{
+ LOG(Plugins, "NPN_GetURL: %s target: %s", URLCString, cTarget);
+
+ NSMutableURLRequest *request = [self requestWithURLCString:URLCString];
+ return [self loadRequest:request inTarget:cTarget withNotifyData:NULL sendNotification:NO];
+}
+
+- (NPError)_postURL:(const char *)URLCString
+ target:(const char *)target
+ len:(UInt32)len
+ buf:(const char *)buf
+ file:(NPBool)file
+ notifyData:(void *)notifyData
+ sendNotification:(BOOL)sendNotification
+ allowHeaders:(BOOL)allowHeaders
+{
+ if (!URLCString || !len || !buf) {
+ return NPERR_INVALID_PARAM;
+ }
+
+ NSData *postData = nil;
+
+ if (file) {
+ // If we're posting a file, buf is either a file URL or a path to the file.
+ NSString *bufString = (NSString *)CFStringCreateWithCString(kCFAllocatorDefault, buf, kCFStringEncodingWindowsLatin1);
+ if (!bufString) {
+ return NPERR_INVALID_PARAM;
+ }
+ NSURL *fileURL = [NSURL _web_URLWithDataAsString:bufString];
+ NSString *path;
+ if ([fileURL isFileURL]) {
+ path = [fileURL path];
+ } else {
+ path = bufString;
+ }
+ postData = [NSData dataWithContentsOfFile:[path _webkit_fixedCarbonPOSIXPath]];
+ CFRelease(bufString);
+ if (!postData) {
+ return NPERR_FILE_NOT_FOUND;
+ }
+ } else {
+ postData = [NSData dataWithBytes:buf length:len];
+ }
+
+ if ([postData length] == 0) {
+ return NPERR_INVALID_PARAM;
+ }
+
+ NSMutableURLRequest *request = [self requestWithURLCString:URLCString];
+ [request setHTTPMethod:@"POST"];
+
+ if (allowHeaders) {
+ if ([postData _web_startsWithBlankLine]) {
+ postData = [postData subdataWithRange:NSMakeRange(1, [postData length] - 1)];
+ } else {
+ NSInteger location = [postData _web_locationAfterFirstBlankLine];
+ if (location != NSNotFound) {
+ // If the blank line is somewhere in the middle of postData, everything before is the header.
+ NSData *headerData = [postData subdataWithRange:NSMakeRange(0, location)];
+ NSMutableDictionary *header = [headerData _webkit_parseRFC822HeaderFields];
+ unsigned dataLength = [postData length] - location;
+
+ // Sometimes plugins like to set Content-Length themselves when they post,
+ // but WebFoundation does not like that. So we will remove the header
+ // and instead truncate the data to the requested length.
+ NSString *contentLength = [header objectForKey:@"Content-Length"];
+
+ if (contentLength != nil)
+ dataLength = MIN((unsigned)[contentLength intValue], dataLength);
+ [header removeObjectForKey:@"Content-Length"];
+
+ if ([header count] > 0) {
+ [request setAllHTTPHeaderFields:header];
+ }
+ // Everything after the blank line is the actual content of the POST.
+ postData = [postData subdataWithRange:NSMakeRange(location, dataLength)];
+
+ }
+ }
+ if ([postData length] == 0) {
+ return NPERR_INVALID_PARAM;
+ }
+ }
+
+ // Plug-ins expect to receive uncached data when doing a POST (3347134).
+ [request setCachePolicy:NSURLRequestReloadIgnoringCacheData];
+ [request setHTTPBody:postData];
+
+ return [self loadRequest:request inTarget:target withNotifyData:notifyData sendNotification:sendNotification];
+}
+
+- (NPError)postURLNotify:(const char *)URLCString
+ target:(const char *)target
+ len:(UInt32)len
+ buf:(const char *)buf
+ file:(NPBool)file
+ notifyData:(void *)notifyData
+{
+ LOG(Plugins, "NPN_PostURLNotify: %s", URLCString);
+ return [self _postURL:URLCString target:target len:len buf:buf file:file notifyData:notifyData sendNotification:YES allowHeaders:YES];
+}
+
+-(NPError)postURL:(const char *)URLCString
+ target:(const char *)target
+ len:(UInt32)len
+ buf:(const char *)buf
+ file:(NPBool)file
+{
+ LOG(Plugins, "NPN_PostURL: %s", URLCString);
+ // As documented, only allow headers to be specified via NPP_PostURL when using a file.
+ return [self _postURL:URLCString target:target len:len buf:buf file:file notifyData:NULL sendNotification:NO allowHeaders:file];
+}
+
+-(NPError)newStream:(NPMIMEType)type target:(const char *)target stream:(NPStream**)stream
+{
+ LOG(Plugins, "NPN_NewStream");
+ return NPERR_GENERIC_ERROR;
+}
+
+-(NPError)write:(NPStream*)stream len:(SInt32)len buffer:(void *)buffer
+{
+ LOG(Plugins, "NPN_Write");
+ return NPERR_GENERIC_ERROR;
+}
+
+-(NPError)destroyStream:(NPStream*)stream reason:(NPReason)reason
+{
+ LOG(Plugins, "NPN_DestroyStream");
+ // This function does a sanity check to ensure that the NPStream provided actually
+ // belongs to the plug-in that provided it, which fixes a crash in the DivX
+ // plug-in: <rdar://problem/5093862> | http://bugs.webkit.org/show_bug.cgi?id=13203
+ if (!stream || [WebBaseNetscapePluginStream ownerForStream:stream] != plugin) {
+ LOG(Plugins, "Invalid NPStream passed to NPN_DestroyStream: %p", stream);
+ return NPERR_INVALID_INSTANCE_ERROR;
+ }
+
+ WebBaseNetscapePluginStream *browserStream = static_cast<WebBaseNetscapePluginStream *>(stream->ndata);
+ [browserStream cancelLoadAndDestroyStreamWithError:[browserStream errorForReason:reason]];
+
+ return NPERR_NO_ERROR;
+}
+
+- (const char *)userAgent
+{
+ return [[[self webView] userAgentForURL:baseURL] UTF8String];
+}
+
+-(void)status:(const char *)message
+{
+ if (!message) {
+ LOG_ERROR("NPN_Status passed a NULL status message");
+ return;
+ }
+
+ CFStringRef status = CFStringCreateWithCString(NULL, message, kCFStringEncodingUTF8);
+ if (!status) {
+ LOG_ERROR("NPN_Status: the message was not valid UTF-8");
+ return;
+ }
+
+ LOG(Plugins, "NPN_Status: %@", status);
+ WebView *wv = [self webView];
+ [[wv _UIDelegateForwarder] webView:wv setStatusText:(NSString *)status];
+ CFRelease(status);
+}
+
+-(void)invalidateRect:(NPRect *)invalidRect
+{
+ LOG(Plugins, "NPN_InvalidateRect");
+ [self setNeedsDisplayInRect:NSMakeRect(invalidRect->left, invalidRect->top,
+ (float)invalidRect->right - invalidRect->left, (float)invalidRect->bottom - invalidRect->top)];
+}
+
+-(bool)isOpaque
+{
+ return YES;
+}
+
+- (void)invalidateRegion:(NPRegion)invalidRegion
+{
+ LOG(Plugins, "NPN_InvalidateRegion");
+ NSRect invalidRect = NSZeroRect;
+ switch (drawingModel) {
+#ifndef NP_NO_QUICKDRAW
+ case NPDrawingModelQuickDraw:
+ {
+ ::Rect qdRect;
+ GetRegionBounds((NPQDRegion)invalidRegion, &qdRect);
+ invalidRect = NSMakeRect(qdRect.left, qdRect.top, qdRect.right - qdRect.left, qdRect.bottom - qdRect.top);
+ }
+ break;
+#endif /* NP_NO_QUICKDRAW */
+
+ case NPDrawingModelCoreGraphics:
+ case NPDrawingModelOpenGL:
+ {
+ CGRect cgRect = CGPathGetBoundingBox((NPCGRegion)invalidRegion);
+ invalidRect = *(NSRect *)&cgRect;
+ }
+ break;
+
+ default:
+ ASSERT_NOT_REACHED();
+ break;
+ }
+
+ [self setNeedsDisplayInRect:invalidRect];
+}
+
+-(void)forceRedraw
+{
+ LOG(Plugins, "forceRedraw");
+ [self setNeedsDisplay:YES];
+ [[self window] displayIfNeeded];
+}
+
+- (NPError)getVariable:(NPNVariable)variable value:(void *)value
+{
+ switch (variable) {
+ case NPNVWindowNPObject:
+ {
+ Frame* frame = core([self webFrame]);
+ NPObject* windowScriptObject = frame ? frame->windowScriptNPObject() : 0;
+
+ // Return value is expected to be retained, as described here: <http://www.mozilla.org/projects/plugins/npruntime.html#browseraccess>
+ if (windowScriptObject)
+ _NPN_RetainObject(windowScriptObject);
+
+ void **v = (void **)value;
+ *v = windowScriptObject;
+
+ return NPERR_NO_ERROR;
+ }
+
+ case NPNVPluginElementNPObject:
+ {
+ if (!element)
+ return NPERR_GENERIC_ERROR;
+
+ NPObject *plugInScriptObject = (NPObject *)[element _NPObject];
+
+ // Return value is expected to be retained, as described here: <http://www.mozilla.org/projects/plugins/npruntime.html#browseraccess>
+ if (plugInScriptObject)
+ _NPN_RetainObject(plugInScriptObject);
+
+ void **v = (void **)value;
+ *v = plugInScriptObject;
+
+ return NPERR_NO_ERROR;
+ }
+
+ case NPNVpluginDrawingModel:
+ {
+ *(NPDrawingModel *)value = drawingModel;
+ return NPERR_NO_ERROR;
+ }
+
+#ifndef NP_NO_QUICKDRAW
+ case NPNVsupportsQuickDrawBool:
+ {
+ *(NPBool *)value = TRUE;
+ return NPERR_NO_ERROR;
+ }
+#endif /* NP_NO_QUICKDRAW */
+
+ case NPNVsupportsCoreGraphicsBool:
+ {
+ *(NPBool *)value = TRUE;
+ return NPERR_NO_ERROR;
+ }
+
+ case NPNVsupportsOpenGLBool:
+ {
+ *(NPBool *)value = TRUE;
+ return NPERR_NO_ERROR;
+ }
+
+ default:
+ break;
+ }
+
+ return NPERR_GENERIC_ERROR;
+}
+
+- (NPError)setVariable:(NPPVariable)variable value:(void *)value
+{
+ switch (variable) {
+ case NPPVpluginWindowBool:
+ {
+ NPWindowType newWindowType = (value ? NPWindowTypeWindow : NPWindowTypeDrawable);
+
+ // Redisplay if window type is changing (some drawing models can only have their windows set while updating).
+ if (newWindowType != window.type)
+ [self setNeedsDisplay:YES];
+
+ window.type = newWindowType;
+ }
+
+ case NPPVpluginTransparentBool:
+ {
+ BOOL newTransparent = (value != 0);
+
+ // Redisplay if transparency is changing
+ if (isTransparent != newTransparent)
+ [self setNeedsDisplay:YES];
+
+ isTransparent = newTransparent;
+
+ return NPERR_NO_ERROR;
+ }
+
+ case NPPVpluginDrawingModel:
+ {
+ // Can only set drawing model inside NPP_New()
+ if (self != [[self class] currentPluginView])
+ return NPERR_GENERIC_ERROR;
+
+ // Check for valid, supported drawing model
+ NPDrawingModel newDrawingModel = (NPDrawingModel)(uintptr_t)value;
+ switch (newDrawingModel) {
+ // Supported drawing models:
+#ifndef NP_NO_QUICKDRAW
+ case NPDrawingModelQuickDraw:
+#endif
+ case NPDrawingModelCoreGraphics:
+ case NPDrawingModelOpenGL:
+ drawingModel = newDrawingModel;
+ return NPERR_NO_ERROR;
+
+ // Unsupported (or unknown) drawing models:
+ default:
+ LOG(Plugins, "Plugin %@ uses unsupported drawing model: %d", pluginPackage, drawingModel);
+ return NPERR_GENERIC_ERROR;
+ }
+ }
+
+ default:
+ return NPERR_GENERIC_ERROR;
+ }
+}
+
+@end
+
+@implementation WebPluginRequest
+
+- (id)initWithRequest:(NSURLRequest *)request frameName:(NSString *)frameName notifyData:(void *)notifyData sendNotification:(BOOL)sendNotification didStartFromUserGesture:(BOOL)currentEventIsUserGesture
+{
+ [super init];
+ _didStartFromUserGesture = currentEventIsUserGesture;
+ _request = [request retain];
+ _frameName = [frameName retain];
+ _notifyData = notifyData;
+ _sendNotification = sendNotification;
+ return self;
+}
+
+- (void)dealloc
+{
+ [_request release];
+ [_frameName release];
+ [super dealloc];
+}
+
+- (NSURLRequest *)request
+{
+ return _request;
+}
+
+- (NSString *)frameName
+{
+ return _frameName;
+}
+
+- (BOOL)isCurrentEventUserGesture
+{
+ return _didStartFromUserGesture;
+}
+
+- (BOOL)sendNotification
+{
+ return _sendNotification;
+}
+
+- (void *)notifyData
+{
+ return _notifyData;
+}
+
+@end
+
+@implementation WebBaseNetscapePluginView (Internal)
+
+- (NPError)_createPlugin
+{
+ plugin = (NPP)calloc(1, sizeof(NPP_t));
+ plugin->ndata = self;
+
+ ASSERT(NPP_New);
+
+ // NPN_New(), which creates the plug-in instance, should never be called while calling a plug-in function for that instance.
+ ASSERT(pluginFunctionCallDepth == 0);
+
+ [[self class] setCurrentPluginView:self];
+ NPError npErr = NPP_New((char *)[MIMEType cString], plugin, mode, argsCount, cAttributes, cValues, NULL);
+ [[self class] setCurrentPluginView:nil];
+
+ LOG(Plugins, "NPP_New: %d", npErr);
+ return npErr;
+}
+
+- (void)_destroyPlugin
+{
+ NPError npErr;
+ npErr = NPP_Destroy(plugin, NULL);
+ LOG(Plugins, "NPP_Destroy: %d", npErr);
+
+ if (Frame* frame = core([self webFrame]))
+ frame->cleanupScriptObjectsForPlugin(self);
+
+ free(plugin);
+ plugin = NULL;
+}
+
+- (void)_viewHasMoved
+{
+ // All of the work this method does may safely be skipped if the view is not in a window. When the view
+ // is moved back into a window, everything should be set up correctly.
+ if (![self window])
+ return;
+
+ if (drawingModel == NPDrawingModelOpenGL)
+ [self _reshapeAGLWindow];
+
+#ifndef NP_NO_QUICKDRAW
+ if (drawingModel == NPDrawingModelQuickDraw)
+ [self tellQuickTimeToChill];
+#endif
+ [self updateAndSetWindow];
+ [self resetTrackingRect];
+
+ // Check to see if the plugin view is completely obscured (scrolled out of view, for example).
+ // For performance reasons, we send null events at a lower rate to plugins which are obscured.
+ BOOL oldIsObscured = isCompletelyObscured;
+ isCompletelyObscured = NSIsEmptyRect([self visibleRect]);
+ if (isCompletelyObscured != oldIsObscured)
+ [self restartNullEvents];
+}
+
+- (NSBitmapImageRep *)_printedPluginBitmap
+{
+#ifdef NP_NO_QUICKDRAW
+ return nil;
+#else
+ // Cannot print plugins that do not implement NPP_Print
+ if (!NPP_Print)
+ return nil;
+
+ // This NSBitmapImageRep will share its bitmap buffer with a GWorld that the plugin will draw into.
+ // The bitmap is created in 32-bits-per-pixel ARGB format, which is the default GWorld pixel format.
+ NSBitmapImageRep *bitmap = [[[NSBitmapImageRep alloc] initWithBitmapDataPlanes:NULL
+ pixelsWide:window.width
+ pixelsHigh:window.height
+ bitsPerSample:8
+ samplesPerPixel:4
+ hasAlpha:YES
+ isPlanar:NO
+ colorSpaceName:NSDeviceRGBColorSpace
+ bitmapFormat:NSAlphaFirstBitmapFormat
+ bytesPerRow:0
+ bitsPerPixel:0] autorelease];
+ ASSERT(bitmap);
+
+ // Create a GWorld with the same underlying buffer into which the plugin can draw
+ ::Rect printGWorldBounds;
+ SetRect(&printGWorldBounds, 0, 0, window.width, window.height);
+ GWorldPtr printGWorld;
+ if (NewGWorldFromPtr(&printGWorld,
+ k32ARGBPixelFormat,
+ &printGWorldBounds,
+ NULL,
+ NULL,
+ 0,
+ (Ptr)[bitmap bitmapData],
+ [bitmap bytesPerRow]) != noErr) {
+ LOG_ERROR("Could not create GWorld for printing");
+ return nil;
+ }
+
+ /// Create NPWindow for the GWorld
+ NPWindow printNPWindow;
+ printNPWindow.window = &printGWorld; // Normally this is an NP_Port, but when printing it is the actual CGrafPtr
+ printNPWindow.x = 0;
+ printNPWindow.y = 0;
+ printNPWindow.width = window.width;
+ printNPWindow.height = window.height;
+ printNPWindow.clipRect.top = 0;
+ printNPWindow.clipRect.left = 0;
+ printNPWindow.clipRect.right = window.width;
+ printNPWindow.clipRect.bottom = window.height;
+ printNPWindow.type = NPWindowTypeDrawable; // Offscreen graphics port as opposed to a proper window
+
+ // Create embed-mode NPPrint
+ NPPrint npPrint;
+ npPrint.mode = NP_EMBED;
+ npPrint.print.embedPrint.window = printNPWindow;
+ npPrint.print.embedPrint.platformPrint = printGWorld;
+
+ // Tell the plugin to print into the GWorld
+ [self willCallPlugInFunction];
+ {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ NPP_Print(plugin, &npPrint);
+ }
+ [self didCallPlugInFunction];
+
+ // Don't need the GWorld anymore
+ DisposeGWorld(printGWorld);
+
+ return bitmap;
+#endif
+}
+
+- (BOOL)_createAGLContextIfNeeded
+{
+ ASSERT(drawingModel == NPDrawingModelOpenGL);
+
+ // Do nothing (but indicate success) if the AGL context already exists
+ if (aglContext)
+ return YES;
+
+ switch (window.type) {
+ case NPWindowTypeWindow:
+ return [self _createWindowedAGLContext];
+
+ case NPWindowTypeDrawable:
+ return [self _createWindowlessAGLContext];
+
+ default:
+ ASSERT_NOT_REACHED();
+ return NO;
+ }
+}
+
+- (BOOL)_createWindowedAGLContext
+{
+ ASSERT(drawingModel == NPDrawingModelOpenGL);
+ ASSERT(!aglContext);
+ ASSERT(!aglWindow);
+ ASSERT([self window]);
+
+ GLint pixelFormatAttributes[] = {
+ AGL_RGBA,
+ AGL_RED_SIZE, 8,
+ AGL_GREEN_SIZE, 8,
+ AGL_BLUE_SIZE, 8,
+ AGL_ALPHA_SIZE, 8,
+ AGL_DEPTH_SIZE, 32,
+ AGL_WINDOW,
+ AGL_ACCELERATED,
+ 0
+ };
+
+ // Choose AGL pixel format
+ AGLPixelFormat pixelFormat = aglChoosePixelFormat(NULL, 0, pixelFormatAttributes);
+ if (!pixelFormat) {
+ LOG_ERROR("Could not find suitable AGL pixel format: %s", aglErrorString(aglGetError()));
+ return NO;
+ }
+
+ // Create AGL context
+ aglContext = aglCreateContext(pixelFormat, NULL);
+ aglDestroyPixelFormat(pixelFormat);
+ if (!aglContext) {
+ LOG_ERROR("Could not create AGL context: %s", aglErrorString(aglGetError()));
+ return NO;
+ }
+
+ // Create AGL window
+ aglWindow = [[NSWindow alloc] initWithContentRect:NSZeroRect styleMask:NSBorderlessWindowMask backing:NSBackingStoreBuffered defer:NO];
+ if (!aglWindow) {
+ LOG_ERROR("Could not create window for AGL drawable.");
+ return NO;
+ }
+
+ // AGL window should allow clicks to go through -- mouse events are tracked by WebCore
+ [aglWindow setIgnoresMouseEvents:YES];
+
+ // Make sure the window is not opaque -- windowed plug-ins cannot layer with other page elements
+ [aglWindow setOpaque:YES];
+
+ // Position and order in the AGL window
+ [self _reshapeAGLWindow];
+
+ // Attach the AGL context to its window
+ GLboolean success;
+#ifdef AGL_VERSION_3_0
+ success = aglSetWindowRef(aglContext, (WindowRef)[aglWindow windowRef]);
+#else
+ success = aglSetDrawable(aglContext, (AGLDrawable)GetWindowPort((WindowRef)[aglWindow windowRef]));
+#endif
+ if (!success) {
+ LOG_ERROR("Could not set AGL drawable: %s", aglErrorString(aglGetError()));
+ aglDestroyContext(aglContext);
+ aglContext = NULL;
+ return NO;
+ }
+
+ return YES;
+}
+
+- (BOOL)_createWindowlessAGLContext
+{
+ ASSERT(drawingModel == NPDrawingModelOpenGL);
+ ASSERT(!aglContext);
+ ASSERT(!aglWindow);
+
+ GLint pixelFormatAttributes[] = {
+ AGL_RGBA,
+ AGL_RED_SIZE, 8,
+ AGL_GREEN_SIZE, 8,
+ AGL_BLUE_SIZE, 8,
+ AGL_ALPHA_SIZE, 8,
+ AGL_DEPTH_SIZE, 32,
+ AGL_OFFSCREEN,
+ 0
+ };
+
+ // Choose AGL pixel format
+ AGLPixelFormat pixelFormat = aglChoosePixelFormat(NULL, 0, pixelFormatAttributes);
+ if (!pixelFormat) {
+ LOG_ERROR("Could not find suitable AGL pixel format: %s", aglErrorString(aglGetError()));
+ return NO;
+ }
+
+ // Create AGL context
+ aglContext = aglCreateContext(pixelFormat, NULL);
+ aglDestroyPixelFormat(pixelFormat);
+ if (!aglContext) {
+ LOG_ERROR("Could not create AGL context: %s", aglErrorString(aglGetError()));
+ return NO;
+ }
+
+ // Create offscreen buffer for AGL context
+ NSSize boundsSize = [self bounds].size;
+ GLvoid *offscreenBuffer = (GLvoid *)malloc(static_cast<size_t>(boundsSize.width * boundsSize.height * 4));
+ if (!offscreenBuffer) {
+ LOG_ERROR("Could not allocate offscreen buffer for AGL context");
+ aglDestroyContext(aglContext);
+ aglContext = NULL;
+ return NO;
+ }
+
+ // Attach AGL context to offscreen buffer
+ CGLContextObj cglContext = [self _cglContext];
+ CGLError error = CGLSetOffScreen(cglContext, static_cast<long>(boundsSize.width), static_cast<long>(boundsSize.height), static_cast<long>(boundsSize.width * 4), offscreenBuffer);
+ if (error) {
+ LOG_ERROR("Could not set offscreen buffer for AGL context: %d", error);
+ aglDestroyContext(aglContext);
+ aglContext = NULL;
+ return NO;
+ }
+
+ return YES;
+}
+
+- (CGLContextObj)_cglContext
+{
+ ASSERT(drawingModel == NPDrawingModelOpenGL);
+
+ CGLContextObj cglContext = NULL;
+ if (!aglGetCGLContext(aglContext, (void **)&cglContext) || !cglContext)
+ LOG_ERROR("Could not get CGL context for AGL context: %s", aglErrorString(aglGetError()));
+
+ return cglContext;
+}
+
+- (BOOL)_getAGLOffscreenBuffer:(GLvoid **)outBuffer width:(GLsizei *)outWidth height:(GLsizei *)outHeight
+{
+ ASSERT(drawingModel == NPDrawingModelOpenGL);
+
+ if (outBuffer)
+ *outBuffer = NULL;
+ if (outWidth)
+ *outWidth = 0;
+ if (outHeight)
+ *outHeight = 0;
+
+ // Only windowless plug-ins have offscreen buffers
+ if (window.type != NPWindowTypeDrawable)
+ return NO;
+
+ CGLContextObj cglContext = [self _cglContext];
+ if (!cglContext)
+ return NO;
+
+ GLsizei width, height;
+ GLint rowBytes;
+ void *offscreenBuffer = NULL;
+ CGLError error = CGLGetOffScreen(cglContext, &width, &height, &rowBytes, &offscreenBuffer);
+ if (error || !offscreenBuffer) {
+ LOG_ERROR("Could not get offscreen buffer for AGL context: %d", error);
+ return NO;
+ }
+
+ if (outBuffer)
+ *outBuffer = offscreenBuffer;
+ if (outWidth)
+ *outWidth = width;
+ if (outHeight)
+ *outHeight = height;
+
+ return YES;
+}
+
+- (void)_destroyAGLContext
+{
+ ASSERT(drawingModel == NPDrawingModelOpenGL);
+
+ if (!aglContext)
+ return;
+
+ if (aglContext) {
+ // If this is a windowless plug-in, free its offscreen buffer
+ GLvoid *offscreenBuffer;
+ if ([self _getAGLOffscreenBuffer:&offscreenBuffer width:NULL height:NULL])
+ free(offscreenBuffer);
+
+ // Detach context from the AGL window
+#ifdef AGL_VERSION_3_0
+ aglSetWindowRef(aglContext, NULL);
+#else
+ aglSetDrawable(aglContext, NULL);
+#endif
+
+ // Destroy the context
+ aglDestroyContext(aglContext);
+ aglContext = NULL;
+ }
+
+ // Destroy the AGL window
+ if (aglWindow) {
+ [self _hideAGLWindow];
+ aglWindow = nil;
+ }
+}
+
+- (void)_reshapeAGLWindow
+{
+ ASSERT(drawingModel == NPDrawingModelOpenGL);
+
+ if (!aglContext)
+ return;
+
+ switch (window.type) {
+ case NPWindowTypeWindow:
+ {
+ if (!aglWindow)
+ break;
+
+ // The AGL window is being reshaped because the plugin view has moved. Since the view has moved, it will soon redraw.
+ // We want the AGL window to update at the same time as its underlying view. So, we disable screen updates until the
+ // plugin view's window flushes.
+ NSWindow *browserWindow = [self window];
+ ASSERT(browserWindow);
+ [browserWindow disableScreenUpdatesUntilFlush];
+
+ // Add the AGL window as a child of the main window if necessary
+ if ([aglWindow parentWindow] != browserWindow)
+ [browserWindow addChildWindow:aglWindow ordered:NSWindowAbove];
+
+ // Update the AGL window frame
+ NSRect aglWindowFrame = [self convertRect:[self visibleRect] toView:nil];
+ aglWindowFrame.origin = [browserWindow convertBaseToScreen:aglWindowFrame.origin];
+ [aglWindow setFrame:aglWindowFrame display:NO];
+
+ // Update the AGL context
+ aglUpdateContext(aglContext);
+ }
+ break;
+
+ case NPWindowTypeDrawable:
+ {
+ // Get offscreen buffer; we can skip this step if we don't have one yet
+ GLvoid *offscreenBuffer;
+ GLsizei width, height;
+ if (![self _getAGLOffscreenBuffer:&offscreenBuffer width:&width height:&height] || !offscreenBuffer)
+ break;
+
+ // Don't resize the offscreen buffer if it's already the same size as the view bounds
+ NSSize boundsSize = [self bounds].size;
+ if (boundsSize.width == width && boundsSize.height == height)
+ break;
+
+ // Resize the offscreen buffer
+ offscreenBuffer = realloc(offscreenBuffer, static_cast<size_t>(boundsSize.width * boundsSize.height * 4));
+ if (!offscreenBuffer) {
+ LOG_ERROR("Could not allocate offscreen buffer for AGL context");
+ break;
+ }
+
+ // Update the offscreen
+ CGLContextObj cglContext = [self _cglContext];
+ CGLError error = CGLSetOffScreen(cglContext, static_cast<long>(boundsSize.width), static_cast<long>(boundsSize.height), static_cast<long>(boundsSize.width * 4), offscreenBuffer);
+ if (error) {
+ LOG_ERROR("Could not set offscreen buffer for AGL context: %d", error);
+ break;
+ }
+
+ // Update the AGL context
+ aglUpdateContext(aglContext);
+ }
+ break;
+
+ default:
+ ASSERT_NOT_REACHED();
+ break;
+ }
+}
+
+- (void)_hideAGLWindow
+{
+ ASSERT(drawingModel == NPDrawingModelOpenGL);
+
+ if (!aglWindow)
+ return;
+
+ // aglWindow should only be set for a windowed OpenGL plug-in
+ ASSERT(window.type == NPWindowTypeWindow);
+
+ NSWindow *parentWindow = [aglWindow parentWindow];
+ if (parentWindow) {
+ // Disable screen updates so that this AGL window orders out atomically with other plugins' AGL windows
+ [parentWindow disableScreenUpdatesUntilFlush];
+ ASSERT(parentWindow == [self window]);
+ [parentWindow removeChildWindow:aglWindow];
+ }
+ [aglWindow orderOut:nil];
+}
+
+- (NSImage *)_aglOffscreenImageForDrawingInRect:(NSRect)drawingInRect
+{
+ ASSERT(drawingModel == NPDrawingModelOpenGL);
+
+ CGLContextObj cglContext = [self _cglContext];
+ if (!cglContext)
+ return nil;
+
+ // Get the offscreen buffer
+ GLvoid *offscreenBuffer;
+ GLsizei width, height;
+ if (![self _getAGLOffscreenBuffer:&offscreenBuffer width:&width height:&height])
+ return nil;
+
+ unsigned char *plane = (unsigned char *)offscreenBuffer;
+
+#if defined(__i386__) || defined(__x86_64__)
+ // Make rect inside the offscreen buffer because we're about to directly modify the bits inside drawingInRect
+ NSRect rect = NSIntegralRect(NSIntersectionRect(drawingInRect, NSMakeRect(0, 0, width, height)));
+
+ // The offscreen buffer, being an OpenGL framebuffer, is in BGRA format on x86. We need to swap the blue and red channels before
+ // wrapping the buffer in an NSBitmapImageRep, which only supports RGBA and ARGB.
+ // On PowerPC, the OpenGL framebuffer is in ARGB format. Since that is a format that NSBitmapImageRep supports, all that is
+ // needed on PowerPC is to pass the NSAlphaFirstBitmapFormat flag when creating the NSBitmapImageRep. On x86, we need to swap the
+ // framebuffer color components such that they are in ARGB order, as they are on PowerPC.
+ // If only a small region of the plug-in is being redrawn, then it would be a waste to convert the entire image from BGRA to ARGB.
+ // Since we know what region of the image will ultimately be drawn to screen (drawingInRect), we restrict the channel swapping to
+ // just that region within the offscreen buffer.
+ if (!WebConvertBGRAToARGB(plane, width * 4, (int)rect.origin.x, (int)rect.origin.y, (int)rect.size.width, (int)rect.size.height))
+ return nil;
+#endif /* defined(__i386__) || defined(__x86_64__) */
+
+ NSBitmapImageRep *aglBitmap = [[NSBitmapImageRep alloc]
+ initWithBitmapDataPlanes:&plane
+ pixelsWide:width
+ pixelsHigh:height
+ bitsPerSample:8
+ samplesPerPixel:4
+ hasAlpha:YES
+ isPlanar:NO
+ colorSpaceName:NSDeviceRGBColorSpace
+ bitmapFormat:NSAlphaFirstBitmapFormat
+ bytesPerRow:width * 4
+ bitsPerPixel:32];
+ if (!aglBitmap) {
+ LOG_ERROR("Could not create bitmap for AGL offscreen buffer");
+ return nil;
+ }
+
+ // Wrap the bitmap in an NSImage. This allocation isn't very expensive -- the actual image data is already in the bitmap rep
+ NSImage *aglImage = [[[NSImage alloc] initWithSize:[aglBitmap size]] autorelease];
+ [aglImage addRepresentation:aglBitmap];
+ [aglBitmap release];
+
+ return aglImage;
+}
+
+- (void)_redeliverStream
+{
+ if ([self dataSource] && [self isStarted]) {
+ // Deliver what has not been passed to the plug-in up to this point.
+ if (_dataLengthReceived > 0) {
+ NSData *data = [[[self dataSource] data] subdataWithRange:NSMakeRange(0, _dataLengthReceived)];
+ _dataLengthReceived = 0;
+ [self pluginView:self receivedData:data];
+ if (![[self dataSource] isLoading]) {
+ if (_error)
+ [self pluginView:self receivedError:_error];
+ else
+ [self pluginViewFinishedLoading:self];
+ }
+ }
+ }
+}
+
+@end
+
+@implementation NSData (PluginExtras)
+
+- (BOOL)_web_startsWithBlankLine
+{
+ return [self length] > 0 && ((const char *)[self bytes])[0] == '\n';
+}
+
+
+- (NSInteger)_web_locationAfterFirstBlankLine
+{
+ const char *bytes = (const char *)[self bytes];
+ unsigned length = [self length];
+
+ unsigned i;
+ for (i = 0; i < length - 4; i++) {
+
+ // Support for Acrobat. It sends "\n\n".
+ if (bytes[i] == '\n' && bytes[i+1] == '\n') {
+ return i+2;
+ }
+
+ // Returns the position after 2 CRLF's or 1 CRLF if it is the first line.
+ if (bytes[i] == '\r' && bytes[i+1] == '\n') {
+ i += 2;
+ if (i == 2) {
+ return i;
+ } else if (bytes[i] == '\n') {
+ // Support for Director. It sends "\r\n\n" (3880387).
+ return i+1;
+ } else if (bytes[i] == '\r' && bytes[i+1] == '\n') {
+ // Support for Flash. It sends "\r\n\r\n" (3758113).
+ return i+2;
+ }
+ }
+ }
+ return NSNotFound;
+}
+
+@end
+#endif
diff --git a/WebKit/mac/Plugins/WebBaseNetscapePluginViewInternal.h b/WebKit/mac/Plugins/WebBaseNetscapePluginViewInternal.h
new file mode 100644
index 0000000..1285052
--- /dev/null
+++ b/WebKit/mac/Plugins/WebBaseNetscapePluginViewInternal.h
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+#import <WebKit/WebBaseNetscapePluginView.h>
+
+@interface WebBaseNetscapePluginView (WebInternal)
+- (void)restartNullEvents;
+- (void)stopNullEvents;
+@end
+#endif
+
diff --git a/WebKit/mac/Plugins/WebBaseNetscapePluginViewPrivate.h b/WebKit/mac/Plugins/WebBaseNetscapePluginViewPrivate.h
new file mode 100644
index 0000000..7be24b0
--- /dev/null
+++ b/WebKit/mac/Plugins/WebBaseNetscapePluginViewPrivate.h
@@ -0,0 +1,53 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+#import <WebBaseNetscapePluginView.h>
+
+@class NSURLRequest;
+
+@interface WebBaseNetscapePluginView (WebNPPCallbacks)
+
+- (NPError)loadRequest:(NSURLRequest *)request inTarget:(NSString *)target withNotifyData:(void *)notifyData sendNotification:(BOOL)sendNotification;
+- (NPError)getURLNotify:(const char *)URL target:(const char *)target notifyData:(void *)notifyData;
+- (NPError)getURL:(const char *)URL target:(const char *)target;
+- (NPError)postURLNotify:(const char *)URL target:(const char *)target len:(UInt32)len buf:(const char *)buf file:(NPBool)file notifyData:(void *)notifyData;
+- (NPError)postURL:(const char *)URL target:(const char *)target len:(UInt32)len buf:(const char *)buf file:(NPBool)file;
+- (NPError)newStream:(NPMIMEType)type target:(const char *)target stream:(NPStream**)stream;
+- (NPError)write:(NPStream*)stream len:(SInt32)len buffer:(void *)buffer;
+- (NPError)destroyStream:(NPStream*)stream reason:(NPReason)reason;
+- (void)status:(const char *)message;
+- (const char *)userAgent;
+- (void)invalidateRect:(NPRect *)invalidRect;
+- (void)invalidateRegion:(NPRegion)invalidateRegion;
+- (void)forceRedraw;
+- (NPError)getVariable:(NPNVariable)variable value:(void *)value;
+- (NPError)setVariable:(NPPVariable)variable value:(void *)value;
+
+@end
+#endif
diff --git a/WebKit/mac/Plugins/WebBasePluginPackage.h b/WebKit/mac/Plugins/WebBasePluginPackage.h
new file mode 100644
index 0000000..7a884b8
--- /dev/null
+++ b/WebKit/mac/Plugins/WebBasePluginPackage.h
@@ -0,0 +1,106 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/WebCoreViewFactory.h>
+
+#if USE(NPOBJECT)
+#import <WebKit/npfunctions.h>
+#else
+typedef void (*BP_CreatePluginMIMETypesPreferencesFuncPtr)(void);
+#endif
+
+@class WebPluginDatabase;
+
+@protocol WebPluginManualLoader
+- (void)pluginView:(NSView *)pluginView receivedResponse:(NSURLResponse *)response;
+- (void)pluginView:(NSView *)pluginView receivedData:(NSData *)data;
+- (void)pluginView:(NSView *)pluginView receivedError:(NSError *)error;
+- (void)pluginViewFinishedLoading:(NSView *)pluginView;
+@end
+
+#define WebPluginExtensionsKey @"WebPluginExtensions"
+#define WebPluginDescriptionKey @"WebPluginDescription"
+#define WebPluginLocalizationNameKey @"WebPluginLocalizationName"
+#define WebPluginMIMETypesFilenameKey @"WebPluginMIMETypesFilename"
+#define WebPluginMIMETypesKey @"WebPluginMIMETypes"
+#define WebPluginNameKey @"WebPluginName"
+#define WebPluginTypeDescriptionKey @"WebPluginTypeDescription"
+#define WebPluginTypeEnabledKey @"WebPluginTypeEnabled"
+
+@interface WebBasePluginPackage : NSObject <WebCorePluginInfo>
+{
+ NSMutableSet *pluginDatabases;
+
+ NSString *name;
+ NSString *path;
+ NSString *pluginDescription;
+
+ NSBundle *bundle;
+ CFBundleRef cfBundle;
+
+ NSDictionary *MIMEToDescription;
+ NSDictionary *MIMEToExtensions;
+ NSMutableDictionary *extensionToMIME;
+
+ BP_CreatePluginMIMETypesPreferencesFuncPtr BP_CreatePluginMIMETypesPreferences;
+}
+
++ (WebBasePluginPackage *)pluginWithPath:(NSString *)pluginPath;
+- (id)initWithPath:(NSString *)pluginPath;
+
+- (BOOL)getPluginInfoFromPLists;
+
+- (BOOL)load;
+
+- (NSString *)name;
+- (NSString *)path;
+- (NSString *)filename;
+- (NSString *)pluginDescription;
+- (NSBundle *)bundle;
+
+- (NSEnumerator *)extensionEnumerator;
+- (NSEnumerator *)MIMETypeEnumerator;
+- (NSString *)descriptionForMIMEType:(NSString *)MIMEType;
+- (NSString *)MIMETypeForExtension:(NSString *)extension;
+- (NSArray *)extensionsForMIMEType:(NSString *)MIMEType;
+
+- (void)setName:(NSString *)theName;
+- (void)setPath:(NSString *)thePath;
+- (void)setPluginDescription:(NSString *)description;
+- (void)setMIMEToDescriptionDictionary:(NSDictionary *)MIMEToDescriptionDictionary;
+- (void)setMIMEToExtensionsDictionary:(NSDictionary *)MIMEToExtensionsDictionary;
+
+- (BOOL)isQuickTimePlugIn;
+- (BOOL)isJavaPlugIn;
+
+- (BOOL)isNativeLibraryData:(NSData *)data;
+- (UInt32)versionNumber;
+- (void)wasAddedToPluginDatabase:(WebPluginDatabase *)database;
+- (void)wasRemovedFromPluginDatabase:(WebPluginDatabase *)database;
+
+@end
diff --git a/WebKit/mac/Plugins/WebBasePluginPackage.m b/WebKit/mac/Plugins/WebBasePluginPackage.m
new file mode 100644
index 0000000..99d4e74
--- /dev/null
+++ b/WebKit/mac/Plugins/WebBasePluginPackage.m
@@ -0,0 +1,453 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebBasePluginPackage.h>
+
+#import <JavaScriptCore/Assertions.h>
+#import <WebKit/WebKitNSStringExtras.h>
+#import <WebKit/WebNetscapePluginPackage.h>
+#import <WebKit/WebNSObjectExtras.h>
+#import <WebKit/WebPluginPackage.h>
+#import <WebCore/WebCoreObjCExtras.h>
+
+#import <WebKitSystemInterface.h>
+
+#import "WebKitLogging.h"
+#import "WebTypesInternal.h"
+
+#import <mach-o/arch.h>
+#import <mach-o/loader.h>
+
+#define JavaCocoaPluginIdentifier @"com.apple.JavaPluginCocoa"
+#define JavaCarbonPluginIdentifier @"com.apple.JavaAppletPlugin"
+#define JavaCFMPluginFilename @"Java Applet Plugin Enabler"
+
+#define QuickTimeCarbonPluginIdentifier @"com.apple.QuickTime Plugin.plugin"
+#define QuickTimeCocoaPluginIdentifier @"com.apple.quicktime.webplugin"
+
+@interface NSArray (WebPluginExtensions)
+- (NSArray *)_web_lowercaseStrings;
+@end;
+
+@implementation WebBasePluginPackage
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
++ (WebBasePluginPackage *)pluginWithPath:(NSString *)pluginPath
+{
+
+ WebBasePluginPackage *pluginPackage = [[WebPluginPackage alloc] initWithPath:pluginPath];
+
+ if (!pluginPackage) {
+#ifdef __LP64__
+ return nil;
+#else
+ pluginPackage = [[WebNetscapePluginPackage alloc] initWithPath:pluginPath];
+#endif
+ }
+
+ return [pluginPackage autorelease];
+}
+
++ (NSString *)preferredLocalizationName
+{
+ return WebCFAutorelease(WKCopyCFLocalizationPreferredName(NULL));
+}
+
+- (NSString *)pathByResolvingSymlinksAndAliasesInPath:(NSString *)thePath
+{
+ NSString *newPath = [thePath stringByResolvingSymlinksInPath];
+
+ FSRef fref;
+ OSStatus err;
+
+ err = FSPathMakeRef((const UInt8 *)[thePath fileSystemRepresentation], &fref, NULL);
+ if (err != noErr)
+ return newPath;
+
+ Boolean targetIsFolder;
+ Boolean wasAliased;
+ err = FSResolveAliasFileWithMountFlags(&fref, TRUE, &targetIsFolder, &wasAliased, kResolveAliasFileNoUI);
+ if (err != noErr)
+ return newPath;
+
+ if (wasAliased) {
+ CFURLRef URL = CFURLCreateFromFSRef(kCFAllocatorDefault, &fref);
+ newPath = [(NSURL *)URL path];
+ CFRelease(URL);
+ }
+
+ return newPath;
+}
+
+- (id)initWithPath:(NSString *)pluginPath
+{
+ if (!(self = [super init]))
+ return nil;
+
+ path = [[self pathByResolvingSymlinksAndAliasesInPath:pluginPath] retain];
+ bundle = [[NSBundle alloc] initWithPath:path];
+#ifndef __ppc__
+ // 32-bit PowerPC is the only platform where non-bundled CFM plugins are supported
+ if (!bundle) {
+ [self release];
+ return nil;
+ }
+#endif
+ cfBundle = CFBundleCreate(NULL, (CFURLRef)[NSURL fileURLWithPath:path]);
+ extensionToMIME = [[NSMutableDictionary alloc] init];
+
+ return self;
+}
+
+- (BOOL)getPluginInfoFromBundleAndMIMEDictionary:(NSDictionary *)MIMETypes
+{
+ if (!bundle)
+ return NO;
+
+ if (!MIMETypes) {
+ MIMETypes = [bundle objectForInfoDictionaryKey:WebPluginMIMETypesKey];
+ if (!MIMETypes)
+ return NO;
+ }
+
+ NSMutableDictionary *MIMEToExtensionsDictionary = [NSMutableDictionary dictionary];
+ NSMutableDictionary *MIMEToDescriptionDictionary = [NSMutableDictionary dictionary];
+ NSEnumerator *keyEnumerator = [MIMETypes keyEnumerator];
+ NSDictionary *MIMEDictionary;
+ NSString *MIME, *description;
+ NSArray *extensions;
+
+ while ((MIME = [keyEnumerator nextObject]) != nil) {
+ MIMEDictionary = [MIMETypes objectForKey:MIME];
+
+ // FIXME: Consider storing disabled MIME types.
+ NSNumber *isEnabled = [MIMEDictionary objectForKey:WebPluginTypeEnabledKey];
+ if (isEnabled && [isEnabled boolValue] == NO)
+ continue;
+
+ extensions = [[MIMEDictionary objectForKey:WebPluginExtensionsKey] _web_lowercaseStrings];
+ if ([extensions count] == 0)
+ extensions = [NSArray arrayWithObject:@""];
+
+ MIME = [MIME lowercaseString];
+
+ [MIMEToExtensionsDictionary setObject:extensions forKey:MIME];
+
+ description = [MIMEDictionary objectForKey:WebPluginTypeDescriptionKey];
+ if (!description)
+ description = @"";
+
+ [MIMEToDescriptionDictionary setObject:description forKey:MIME];
+ }
+
+ [self setMIMEToExtensionsDictionary:MIMEToExtensionsDictionary];
+ [self setMIMEToDescriptionDictionary:MIMEToDescriptionDictionary];
+
+ NSString *filename = [self filename];
+
+ NSString *theName = [bundle objectForInfoDictionaryKey:WebPluginNameKey];
+ if (!theName)
+ theName = filename;
+ [self setName:theName];
+
+ description = [bundle objectForInfoDictionaryKey:WebPluginDescriptionKey];
+ if (!description)
+ description = filename;
+ [self setPluginDescription:description];
+
+ return YES;
+}
+
+- (NSDictionary *)pListForPath:(NSString *)pListPath createFile:(BOOL)createFile
+{
+ if (createFile && [self load] && BP_CreatePluginMIMETypesPreferences)
+ BP_CreatePluginMIMETypesPreferences();
+
+ NSDictionary *pList = nil;
+ NSData *data = [NSData dataWithContentsOfFile:pListPath];
+ if (data) {
+ pList = [NSPropertyListSerialization propertyListFromData:data
+ mutabilityOption:NSPropertyListImmutable
+ format:nil
+ errorDescription:nil];
+ }
+
+ return pList;
+}
+
+- (BOOL)getPluginInfoFromPLists
+{
+ if (!bundle)
+ return NO;
+
+ NSDictionary *MIMETypes = nil;
+ NSString *pListFilename = [bundle objectForInfoDictionaryKey:WebPluginMIMETypesFilenameKey];
+
+ // Check if the MIME types are claimed in a plist in the user's preferences directory.
+ if (pListFilename) {
+ NSString *pListPath = [NSString stringWithFormat:@"%@/Library/Preferences/%@", NSHomeDirectory(), pListFilename];
+ NSDictionary *pList = [self pListForPath:pListPath createFile:NO];
+ if (pList) {
+ // If the plist isn't localized, have the plug-in recreate it in the preferred language.
+ NSString *localizationName = [pList objectForKey:WebPluginLocalizationNameKey];
+ if (![localizationName isEqualToString:[[self class] preferredLocalizationName]])
+ pList = [self pListForPath:pListPath createFile:YES];
+ MIMETypes = [pList objectForKey:WebPluginMIMETypesKey];
+ } else
+ // Plist doesn't exist, ask the plug-in to create it.
+ MIMETypes = [[self pListForPath:pListPath createFile:YES] objectForKey:WebPluginMIMETypesKey];
+ }
+
+ // Pass the MIME dictionary to the superclass to parse it.
+ return [self getPluginInfoFromBundleAndMIMEDictionary:MIMETypes];
+}
+
+- (BOOL)load
+{
+ if (bundle && !BP_CreatePluginMIMETypesPreferences)
+ BP_CreatePluginMIMETypesPreferences = (BP_CreatePluginMIMETypesPreferencesFuncPtr)CFBundleGetFunctionPointerForName(cfBundle, CFSTR("BP_CreatePluginMIMETypesPreferences"));
+
+ return YES;
+}
+
+- (void)dealloc
+{
+ ASSERT(!pluginDatabases || [pluginDatabases count] == 0);
+ [pluginDatabases release];
+
+ [name release];
+ [path release];
+ [pluginDescription release];
+
+ [MIMEToDescription release];
+ [MIMEToExtensions release];
+ [extensionToMIME release];
+
+ [bundle release];
+ if (cfBundle)
+ CFRelease(cfBundle);
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+ ASSERT(!pluginDatabases || [pluginDatabases count] == 0);
+ [pluginDatabases release];
+
+ if (cfBundle)
+ CFRelease(cfBundle);
+
+ [super finalize];
+}
+
+- (NSString *)name
+{
+ return name;
+}
+
+- (NSString *)path
+{
+ return path;
+}
+
+- (NSString *)filename
+{
+ return [path lastPathComponent];
+}
+
+- (NSString *)pluginDescription
+{
+ return pluginDescription;
+}
+
+- (NSEnumerator *)extensionEnumerator
+{
+ return [extensionToMIME keyEnumerator];
+}
+
+- (NSEnumerator *)MIMETypeEnumerator
+{
+ return [MIMEToExtensions keyEnumerator];
+}
+
+- (NSString *)descriptionForMIMEType:(NSString *)MIMEType
+{
+ return [MIMEToDescription objectForKey:MIMEType];
+}
+
+- (NSString *)MIMETypeForExtension:(NSString *)extension
+{
+ return [extensionToMIME objectForKey:extension];
+}
+
+- (NSArray *)extensionsForMIMEType:(NSString *)MIMEType
+{
+ return [MIMEToExtensions objectForKey:MIMEType];
+}
+
+- (NSBundle *)bundle
+{
+ return bundle;
+}
+
+- (void)setName:(NSString *)theName
+{
+ [name release];
+ name = [theName retain];
+}
+
+- (void)setPath:(NSString *)thePath
+{
+ [path release];
+ path = [thePath retain];
+}
+
+- (void)setPluginDescription:(NSString *)description
+{
+ [pluginDescription release];
+ pluginDescription = [description retain];
+}
+
+- (void)setMIMEToDescriptionDictionary:(NSDictionary *)MIMEToDescriptionDictionary
+{
+ [MIMEToDescription release];
+ MIMEToDescription = [MIMEToDescriptionDictionary retain];
+}
+
+- (void)setMIMEToExtensionsDictionary:(NSDictionary *)MIMEToExtensionsDictionary
+{
+ [MIMEToExtensions release];
+ MIMEToExtensions = [MIMEToExtensionsDictionary retain];
+
+ // Reverse the mapping
+ [extensionToMIME removeAllObjects];
+
+ NSEnumerator *MIMEEnumerator = [MIMEToExtensions keyEnumerator], *extensionEnumerator;
+ NSString *MIME, *extension;
+ NSArray *extensions;
+
+ while ((MIME = [MIMEEnumerator nextObject]) != nil) {
+ extensions = [MIMEToExtensions objectForKey:MIME];
+ extensionEnumerator = [extensions objectEnumerator];
+
+ while ((extension = [extensionEnumerator nextObject]) != nil) {
+ if (![extension isEqualToString:@""])
+ [extensionToMIME setObject:MIME forKey:extension];
+ }
+ }
+}
+
+- (NSString *)description
+{
+ return [NSString stringWithFormat:@"name: %@\npath: %@\nmimeTypes:\n%@\npluginDescription:%@",
+ name, path, [MIMEToExtensions description], [MIMEToDescription description], pluginDescription];
+}
+
+- (BOOL)isQuickTimePlugIn
+{
+ NSString *bundleIdentifier = [[self bundle] bundleIdentifier];
+ return [bundleIdentifier _webkit_isCaseInsensitiveEqualToString:QuickTimeCarbonPluginIdentifier] ||
+ [bundleIdentifier _webkit_isCaseInsensitiveEqualToString:QuickTimeCocoaPluginIdentifier];
+}
+
+- (BOOL)isJavaPlugIn
+{
+ NSString *bundleIdentifier = [[self bundle] bundleIdentifier];
+ return [bundleIdentifier _webkit_isCaseInsensitiveEqualToString:JavaCocoaPluginIdentifier] ||
+ [bundleIdentifier _webkit_isCaseInsensitiveEqualToString:JavaCarbonPluginIdentifier] ||
+ [[path lastPathComponent] _webkit_isCaseInsensitiveEqualToString:JavaCFMPluginFilename];
+}
+
+- (BOOL)isNativeLibraryData:(NSData *)data
+{
+ // If we have a 32-bit thin Mach-O file, see if we have an i386 binary. If not, don't load it.
+ // This is designed to be the safest possible test for now. We'll only reject files that we
+ // can easily tell are wrong.
+ if ([data length] >= sizeof(struct mach_header)) {
+ const NXArchInfo *localArch = NXGetLocalArchInfo();
+ if (localArch != NULL) {
+ struct mach_header *header = (struct mach_header *)[data bytes];
+ if (header->magic == MH_MAGIC)
+ return (header->cputype == localArch->cputype);
+ if (header->magic == MH_CIGAM)
+ return ((cpu_type_t) OSSwapInt32(header->cputype) == localArch->cputype);
+ }
+ }
+ return YES;
+}
+
+- (UInt32)versionNumber
+{
+ // CFBundleGetVersionNumber doesn't work with all possible versioning schemes, but we think for now it's good enough for us.
+ return CFBundleGetVersionNumber(cfBundle);
+}
+
+- (void)wasAddedToPluginDatabase:(WebPluginDatabase *)database
+{
+ if (!pluginDatabases)
+ pluginDatabases = [[NSMutableSet alloc] init];
+
+ ASSERT(![pluginDatabases containsObject:database]);
+ [pluginDatabases addObject:database];
+}
+
+- (void)wasRemovedFromPluginDatabase:(WebPluginDatabase *)database
+{
+ ASSERT(pluginDatabases);
+ ASSERT([pluginDatabases containsObject:database]);
+
+ [pluginDatabases removeObject:database];
+}
+
+@end
+
+@implementation NSArray (WebPluginExtensions)
+
+- (NSArray *)_web_lowercaseStrings
+{
+ NSMutableArray *lowercaseStrings = [NSMutableArray arrayWithCapacity:[self count]];
+ NSEnumerator *strings = [self objectEnumerator];
+ NSString *string;
+
+ while ((string = [strings nextObject]) != nil) {
+ if ([string isKindOfClass:[NSString class]])
+ [lowercaseStrings addObject:[string lowercaseString]];
+ }
+
+ return lowercaseStrings;
+}
+
+@end
diff --git a/WebKit/mac/Plugins/WebJavaPlugIn.h b/WebKit/mac/Plugins/WebJavaPlugIn.h
new file mode 100644
index 0000000..5a1be6d
--- /dev/null
+++ b/WebKit/mac/Plugins/WebJavaPlugIn.h
@@ -0,0 +1,85 @@
+/*
+ * Copyright (C) 2004 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <JavaVM/jni.h>
+
+/*!
+ The Java plug-in adds the following additional methods to facilitate JNI
+ access to Java VM via the plug-in.
+*/
+
+typedef enum {
+ WebJNIReturnTypeInvalid = 0,
+ WebJNIReturnTypeVoid,
+ WebJNIReturnTypeObject,
+ WebJNIReturnTypeBoolean,
+ WebJNIReturnTypeByte,
+ WebJNIReturnTypeChar,
+ WebJNIReturnTypeShort,
+ WebJNIReturnTypeInt,
+ WebJNIReturnTypeLong,
+ WebJNIReturnTypeFloat,
+ WebJNIReturnTypeDouble
+} WebJNIReturnType;
+
+@interface NSObject (WebJavaPlugIn)
+
+/*!
+ @method webPlugInGetApplet
+ @discusssion This returns the jobject representing the java applet to the
+ WebPlugInContainer. It should always be called from the AppKit Main Thread.
+ This method is only implemented by the Java plug-in.
+*/
+- (jobject)webPlugInGetApplet;
+
+/*!
+ @method webPlugInCallJava:isStatic:returnType:method:arguments:callingURL:exceptionDescription:
+ @param object The Java instance that will receive the method call.
+ @param isStatic A flag that indicated whether the method is a class method.
+ @param returnType The return type of the Java method.
+ @param method The ID of the Java method to call.
+ @param args The arguments to use with the method invocation.
+ @param callingURL The URL of the page that contains the JavaScript that is calling Java.
+ @param exceptionDescription Pass in nil or the address of pointer to a string object. If any exception
+ is thrown by Java the return value will be a description of the exception, otherwise nil.
+ @discussion Calls to Java from native code should not make direct
+ use of JNI. Instead they should use this method to dispatch calls to the
+ Java VM. This is required to guarantee that the correct thread will receive
+ the call. webPlugInCallJava:isStatic:returnType:method:arguments:callingURL:exceptionDescription: must
+ always be called from the AppKit main thread. This method is only implemented by the Java plug-in.
+ @result The result of the method invocation.
+*/
+- (jvalue)webPlugInCallJava:(jobject)object
+ isStatic:(BOOL)isStatic
+ returnType:(WebJNIReturnType)returnType
+ method:(jmethodID)method
+ arguments:(jvalue*)args
+ callingURL:(NSURL *)url
+ exceptionDescription:(NSString **)exceptionString;
+
+@end
diff --git a/WebKit/mac/Plugins/WebKitPluginContainerView.h b/WebKit/mac/Plugins/WebKitPluginContainerView.h
new file mode 100644
index 0000000..c1b93c7
--- /dev/null
+++ b/WebKit/mac/Plugins/WebKitPluginContainerView.h
@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@class DOMElement;
+
+@interface WebKitPluginContainerView : NSView
+{
+ DOMElement *_element;
+}
+
+- (id)initWithFrame:(NSRect)r
+ DOMElement:(DOMElement *)anElement;
+
+- (id)objectForWebScript;
+
+@end
diff --git a/WebKit/mac/Plugins/WebKitPluginContainerView.mm b/WebKit/mac/Plugins/WebKitPluginContainerView.mm
new file mode 100644
index 0000000..fb61644
--- /dev/null
+++ b/WebKit/mac/Plugins/WebKitPluginContainerView.mm
@@ -0,0 +1,74 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebKitPluginContainerView.h"
+#import <WebKit/DOMPrivate.h>
+
+@implementation WebKitPluginContainerView
+
+- (id)initWithFrame:(NSRect)frame
+ DOMElement:(DOMElement *)anElement
+{
+ [super initWithFrame:frame];
+
+ _element = [anElement retain];
+
+ return self;
+}
+
+- (void)dealloc
+{
+ [_element release];
+
+ [super dealloc];
+}
+
+- (NSRect)visibleRect
+{
+ if (![self window])
+ return [super visibleRect];
+
+ // WebCore may impose an additional clip (via CSS overflow or clip properties). Fetch
+ // that clip now.
+ return NSIntersectionRect([self convertRect:[_element _windowClipRect] fromView:nil], [super visibleRect]);
+}
+
+- (BOOL)respondsToSelector:(SEL)selector
+{
+ if (selector == @selector(objectForWebScript))
+ return [[[self subviews] objectAtIndex: 0] respondsToSelector:selector];
+ return [super respondsToSelector:selector];
+}
+
+- (id)objectForWebScript
+{
+ return [[[self subviews] objectAtIndex: 0] objectForWebScript];
+}
+
+@end
+
diff --git a/WebKit/mac/Plugins/WebNetscapeDeprecatedFunctions.c b/WebKit/mac/Plugins/WebNetscapeDeprecatedFunctions.c
new file mode 100644
index 0000000..c9ade7b
--- /dev/null
+++ b/WebKit/mac/Plugins/WebNetscapeDeprecatedFunctions.c
@@ -0,0 +1,50 @@
+/*
+ * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "WebNetscapeDeprecatedFunctions.h"
+
+#ifndef __LP64__
+
+OSErr WebGetDiskFragment(const FSSpec *fileSpec, UInt32 offset, UInt32 length, ConstStr63Param fragName, CFragLoadOptions options, CFragConnectionID *connID, Ptr *mainAddr, Str255 errMessage)
+{
+ return GetDiskFragment(fileSpec, offset, length, fragName, options, connID, mainAddr, errMessage);
+}
+
+OSErr WebCloseConnection(CFragConnectionID *connID)
+{
+ return CloseConnection(connID);
+}
+
+SInt16 WebLMGetCurApRefNum(void)
+{
+ return LMGetCurApRefNum();
+}
+
+extern void WebLMSetCurApRefNum(SInt16 value)
+{
+ LMSetCurApRefNum(value);
+}
+
+#endif /* !__LP64__ */
diff --git a/WebKit/mac/Plugins/WebNetscapeDeprecatedFunctions.h b/WebKit/mac/Plugins/WebNetscapeDeprecatedFunctions.h
new file mode 100644
index 0000000..3c90847
--- /dev/null
+++ b/WebKit/mac/Plugins/WebNetscapeDeprecatedFunctions.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+
+#import <CoreServices/CoreServices.h>
+
+extern OSErr WebGetDiskFragment(const FSSpec *fileSpec, UInt32 offset, UInt32 length, ConstStr63Param fragName, CFragLoadOptions options, CFragConnectionID *connID, Ptr *mainAddr, Str255 errMessage);
+extern OSErr WebCloseConnection(CFragConnectionID *connID);
+extern SInt16 WebLMGetCurApRefNum(void);
+extern void WebLMSetCurApRefNum(SInt16 value);
+
+#endif /* !__LP64__ */
diff --git a/WebKit/mac/Plugins/WebNetscapePluginEmbeddedView.h b/WebKit/mac/Plugins/WebNetscapePluginEmbeddedView.h
new file mode 100644
index 0000000..9dca60d
--- /dev/null
+++ b/WebKit/mac/Plugins/WebNetscapePluginEmbeddedView.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+#ifndef __LP64__
+#import <AppKit/AppKit.h>
+
+#import <WebKit/WebBaseNetscapePluginView.h>
+
+@class WebFrame;
+@class WebNetscapePluginStream;
+
+// Because the Adobe 7.x Acrobat plug-in has a hard coded check for a view named
+// "WebNetscapePluginDocumentView", this class must retain the old name in order
+// for the plug-in to function correctly. (rdar://problem/4699455)
+#define WebNetscapePluginEmbeddedView WebNetscapePluginDocumentView
+
+@interface WebNetscapePluginEmbeddedView : WebBaseNetscapePluginView
+{
+}
+@end
+#endif
diff --git a/WebKit/mac/Plugins/WebNetscapePluginEmbeddedView.mm b/WebKit/mac/Plugins/WebNetscapePluginEmbeddedView.mm
new file mode 100644
index 0000000..e9f9d94
--- /dev/null
+++ b/WebKit/mac/Plugins/WebNetscapePluginEmbeddedView.mm
@@ -0,0 +1,50 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+#ifndef __LP64__
+#import "WebNetscapePluginEmbeddedView.h"
+
+#import "WebBaseNetscapePluginViewPrivate.h"
+#import "WebDataSource.h"
+#import "WebFrame.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebFrameView.h"
+#import "WebNSURLExtras.h"
+#import "WebNSURLRequestExtras.h"
+#import "WebNSViewExtras.h"
+#import "WebNetscapePluginPackage.h"
+#import "WebNetscapePluginStream.h"
+#import "WebView.h"
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoader.h>
+
+@implementation WebNetscapePluginEmbeddedView
+
+@end
+#endif
diff --git a/WebKit/mac/Plugins/WebNetscapePluginPackage.h b/WebKit/mac/Plugins/WebNetscapePluginPackage.h
new file mode 100644
index 0000000..75404d8
--- /dev/null
+++ b/WebKit/mac/Plugins/WebNetscapePluginPackage.h
@@ -0,0 +1,104 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+#import "WebBasePluginPackage.h"
+
+#ifdef BUILDING_ON_TIGER
+typedef short ResFileRefNum;
+#endif
+
+#if defined(__ppc__) && !defined(__LP64__)
+#define SUPPORT_CFM
+#endif
+
+typedef enum {
+ WebCFMExecutableType,
+ WebMachOExecutableType
+} WebExecutableType;
+
+@interface WebNetscapePluginPackage : WebBasePluginPackage
+{
+ NPPluginFuncs pluginFuncs;
+ NPNetscapeFuncs browserFuncs;
+
+ uint16 pluginSize;
+ uint16 pluginVersion;
+
+ ResFileRefNum resourceRef;
+
+ NPP_NewProcPtr NPP_New;
+ NPP_DestroyProcPtr NPP_Destroy;
+ NPP_SetWindowProcPtr NPP_SetWindow;
+ NPP_NewStreamProcPtr NPP_NewStream;
+ NPP_DestroyStreamProcPtr NPP_DestroyStream;
+ NPP_StreamAsFileProcPtr NPP_StreamAsFile;
+ NPP_WriteReadyProcPtr NPP_WriteReady;
+ NPP_WriteProcPtr NPP_Write;
+ NPP_PrintProcPtr NPP_Print;
+ NPP_HandleEventProcPtr NPP_HandleEvent;
+ NPP_URLNotifyProcPtr NPP_URLNotify;
+ NPP_GetValueProcPtr NPP_GetValue;
+ NPP_SetValueProcPtr NPP_SetValue;
+ NPP_ShutdownProcPtr NPP_Shutdown;
+ NPP_GetJavaClassProcPtr NPP_GetJavaClass;
+
+ BOOL isLoaded;
+ BOOL needsUnload;
+ unsigned int instanceCount;
+
+#ifdef SUPPORT_CFM
+ BOOL isBundle;
+ BOOL isCFM;
+ CFragConnectionID connID;
+#endif
+}
+
+// Netscape plug-in packages must be explicitly opened and closed by each plug-in instance.
+// This is to protect Netscape plug-ins from being unloaded while they are in use.
+- (void)open;
+- (void)close;
+
+- (WebExecutableType)executableType;
+
+- (NPP_NewProcPtr)NPP_New;
+- (NPP_DestroyProcPtr)NPP_Destroy;
+- (NPP_SetWindowProcPtr)NPP_SetWindow;
+- (NPP_NewStreamProcPtr)NPP_NewStream;
+- (NPP_WriteReadyProcPtr)NPP_WriteReady;
+- (NPP_WriteProcPtr)NPP_Write;
+- (NPP_StreamAsFileProcPtr)NPP_StreamAsFile;
+- (NPP_DestroyStreamProcPtr)NPP_DestroyStream;
+- (NPP_HandleEventProcPtr)NPP_HandleEvent;
+- (NPP_URLNotifyProcPtr)NPP_URLNotify;
+- (NPP_GetValueProcPtr)NPP_GetValue;
+- (NPP_SetValueProcPtr)NPP_SetValue;
+- (NPP_PrintProcPtr)NPP_Print;
+
+@end
+#endif
diff --git a/WebKit/mac/Plugins/WebNetscapePluginPackage.m b/WebKit/mac/Plugins/WebNetscapePluginPackage.m
new file mode 100644
index 0000000..297ff11
--- /dev/null
+++ b/WebKit/mac/Plugins/WebNetscapePluginPackage.m
@@ -0,0 +1,773 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef __LP64__
+#import "WebNetscapePluginPackage.h"
+
+#import "WebKitLogging.h"
+#import "WebKitNSStringExtras.h"
+#import "WebNSObjectExtras.h"
+#import "WebNetscapeDeprecatedFunctions.h"
+#import <JavaScriptCore/npruntime_impl.h>
+
+#ifdef SUPPORT_CFM
+typedef void (* FunctionPointer)(void);
+typedef void (* TransitionVector)(void);
+static FunctionPointer functionPointerForTVector(TransitionVector);
+static TransitionVector tVectorForFunctionPointer(FunctionPointer);
+#endif
+
+#define PluginNameOrDescriptionStringNumber 126
+#define MIMEDescriptionStringNumber 127
+#define MIMEListStringStringNumber 128
+
+#define RealPlayerAppIndentifier @"com.RealNetworks.RealOne Player"
+#define RealPlayerPluginFilename @"RealPlayer Plugin"
+
+@interface WebNetscapePluginPackage (Internal)
+- (void)_unloadWithShutdown:(BOOL)shutdown;
+@end
+
+@implementation WebNetscapePluginPackage
+
+#ifndef __LP64__
++ (void)initialize
+{
+ // The Shockwave plugin requires a valid file in CurApRefNum.
+ // But it doesn't seem to matter what file it is.
+ // If we're called inside a Cocoa application which won't have a
+ // CurApRefNum, we set it to point to the system resource file.
+
+ // Call CurResFile before testing the result of WebLMGetCurApRefNum.
+ // If we are called before the bundle resource map has been opened
+ // for a Carbon application (or a Cocoa app with Resource Manager
+ // resources) we *do not* want to set CurApRefNum to point at the
+ // system resource file. CurResFile triggers Resource Manager lazy
+ // initialization, and will open the bundle resource map as necessary.
+
+ CurResFile();
+
+ if (WebLMGetCurApRefNum() == -1) {
+ // To get the refNum for the system resource file, we have to do
+ // UseResFile(kSystemResFile) and then look at CurResFile().
+ short savedCurResFile = CurResFile();
+ UseResFile(kSystemResFile);
+ WebLMSetCurApRefNum(CurResFile());
+ UseResFile(savedCurResFile);
+ }
+}
+#endif
+
+- (ResFileRefNum)openResourceFile
+{
+#ifdef SUPPORT_CFM
+ if (!isBundle) {
+ FSRef fref;
+ OSErr err = FSPathMakeRef((const UInt8 *)[path fileSystemRepresentation], &fref, NULL);
+ if (err != noErr)
+ return -1;
+
+ return FSOpenResFile(&fref, fsRdPerm);
+ }
+#endif
+
+ return CFBundleOpenBundleResourceMap(cfBundle);
+}
+
+- (void)closeResourceFile:(ResFileRefNum)resRef
+{
+#ifdef SUPPORT_CFM
+ if (!isBundle) {
+ CloseResFile(resRef);
+ return;
+ }
+#endif
+
+ CFBundleCloseBundleResourceMap(cfBundle, resRef);
+}
+
+- (NSString *)stringForStringListID:(SInt16)stringListID andIndex:(SInt16)index
+{
+ // Get resource, and dereference the handle.
+ Handle stringHandle = Get1Resource('STR#', stringListID);
+ if (stringHandle == NULL) {
+ return nil;
+ }
+ unsigned char *p = (unsigned char *)*stringHandle;
+ if (!p)
+ return nil;
+
+ // Check the index against the length of the string list, then skip the length.
+ if (index < 1 || index > *(SInt16 *)p)
+ return nil;
+ p += sizeof(SInt16);
+
+ // Skip any strings that come before the one we are looking for.
+ while (--index)
+ p += 1 + *p;
+
+ // Convert the one we found into an NSString.
+ return [[[NSString alloc] initWithBytes:(p + 1) length:*p encoding:[NSString _web_encodingForResource:stringHandle]] autorelease];
+}
+
+- (BOOL)getPluginInfoFromResources
+{
+ SInt16 resRef = [self openResourceFile];
+ if (resRef == -1)
+ return NO;
+
+ UseResFile(resRef);
+ if (ResError() != noErr)
+ return NO;
+
+ NSString *MIME, *extensionsList, *description;
+ NSArray *extensions;
+ unsigned i;
+
+ NSMutableDictionary *MIMEToExtensionsDictionary = [NSMutableDictionary dictionary];
+ NSMutableDictionary *MIMEToDescriptionDictionary = [NSMutableDictionary dictionary];
+
+ for (i=1; 1; i+=2) {
+ MIME = [[self stringForStringListID:MIMEListStringStringNumber
+ andIndex:i] lowercaseString];
+ if (!MIME)
+ break;
+
+ extensionsList = [[self stringForStringListID:MIMEListStringStringNumber andIndex:i+1] lowercaseString];
+ if (extensionsList) {
+ extensions = [extensionsList componentsSeparatedByString:@","];
+ [MIMEToExtensionsDictionary setObject:extensions forKey:MIME];
+ } else
+ // DRM and WMP claim MIMEs without extensions. Use a @"" extension in this case.
+ [MIMEToExtensionsDictionary setObject:[NSArray arrayWithObject:@""] forKey:MIME];
+
+ description = [self stringForStringListID:MIMEDescriptionStringNumber
+ andIndex:[MIMEToExtensionsDictionary count]];
+ if (description)
+ [MIMEToDescriptionDictionary setObject:description forKey:MIME];
+ else
+ [MIMEToDescriptionDictionary setObject:@"" forKey:MIME];
+ }
+
+ [self setMIMEToDescriptionDictionary:MIMEToDescriptionDictionary];
+ [self setMIMEToExtensionsDictionary:MIMEToExtensionsDictionary];
+
+ NSString *filename = [self filename];
+
+ description = [self stringForStringListID:PluginNameOrDescriptionStringNumber andIndex:1];
+ if (!description)
+ description = filename;
+ [self setPluginDescription:description];
+
+
+ NSString *theName = [self stringForStringListID:PluginNameOrDescriptionStringNumber andIndex:2];
+ if (!theName)
+ theName = filename;
+ [self setName:theName];
+
+ [self closeResourceFile:resRef];
+
+ return YES;
+}
+
+- (BOOL)_initWithPath:(NSString *)pluginPath
+{
+ resourceRef = -1;
+
+ OSType type = 0;
+
+ if (bundle) {
+ // Bundle
+ CFBundleGetPackageInfo(cfBundle, &type, NULL);
+#ifdef SUPPORT_CFM
+ isBundle = YES;
+#endif
+ } else {
+#ifdef SUPPORT_CFM
+ // Single-file plug-in with resource fork
+ type = [[[NSFileManager defaultManager] fileAttributesAtPath:path traverseLink:YES] fileHFSTypeCode];
+ isBundle = NO;
+ isCFM = YES;
+#else
+ return NO;
+#endif
+ }
+
+ if (type != FOUR_CHAR_CODE('BRPL'))
+ return NO;
+
+ // Check if the executable is Mach-O or CFM.
+ if (bundle) {
+ NSFileHandle *executableFile = [NSFileHandle fileHandleForReadingAtPath:[bundle executablePath]];
+ NSData *data = [executableFile readDataOfLength:512];
+ [executableFile closeFile];
+ // Check the length of the data before calling memcmp. We think this fixes 3782543.
+ if (data == nil || [data length] < 8)
+ return NO;
+ BOOL hasCFMHeader = memcmp([data bytes], "Joy!peff", 8) == 0;
+#ifdef SUPPORT_CFM
+ isCFM = hasCFMHeader;
+#else
+ if (hasCFMHeader)
+ return NO;
+#endif
+ if (![self isNativeLibraryData:data])
+ return NO;
+ }
+
+ if (![self getPluginInfoFromPLists] && ![self getPluginInfoFromResources])
+ return NO;
+
+ return YES;
+}
+
+- (id)initWithPath:(NSString *)pluginPath
+{
+ if (!(self = [super initWithPath:pluginPath]))
+ return nil;
+
+ // Initializing a plugin package can cause it to be loaded. If there was an error initializing the plugin package,
+ // ensure that it is unloaded before deallocating it (WebBasePluginPackage requires & asserts this).
+ if (![self _initWithPath:pluginPath]) {
+ [self _unloadWithShutdown:YES];
+ [self release];
+ return nil;
+ }
+
+ return self;
+}
+
+- (WebExecutableType)executableType
+{
+#ifdef SUPPORT_CFM
+ if (isCFM)
+ return WebCFMExecutableType;
+#endif
+ return WebMachOExecutableType;
+}
+
+- (void)launchRealPlayer
+{
+ CFURLRef appURL = NULL;
+ OSStatus error = LSFindApplicationForInfo(kLSUnknownCreator, (CFStringRef)RealPlayerAppIndentifier, NULL, NULL, &appURL);
+ if (!error) {
+ LSLaunchURLSpec URLSpec;
+ bzero(&URLSpec, sizeof(URLSpec));
+ URLSpec.launchFlags = kLSLaunchDefaults | kLSLaunchDontSwitch;
+ URLSpec.appURL = appURL;
+ LSOpenFromURLSpec(&URLSpec, NULL);
+ CFRelease(appURL);
+ }
+}
+
+- (void)_applyDjVuWorkaround
+{
+ if (!cfBundle)
+ return;
+
+ if ([(NSString *)CFBundleGetIdentifier(cfBundle) isEqualToString:@"com.lizardtech.NPDjVu"]) {
+ // The DjVu plug-in will crash copying the vtable if it's too big so we cap it to
+ // what the plug-in expects here.
+ // size + version + 40 function pointers.
+ browserFuncs.size = 2 + 2 + sizeof(void *) * 40;
+ }
+
+}
+
+- (BOOL)load
+{
+ NP_GetEntryPointsFuncPtr NP_GetEntryPoints = NULL;
+ NP_InitializeFuncPtr NP_Initialize = NULL;
+ NPError npErr;
+
+#ifdef SUPPORT_CFM
+ MainFuncPtr pluginMainFunc = NULL;
+#endif
+
+#if !LOG_DISABLED
+ CFAbsoluteTime start = CFAbsoluteTimeGetCurrent();
+ CFAbsoluteTime currentTime;
+ CFAbsoluteTime duration;
+#endif
+ LOG(Plugins, "%f Load timing started for: %@", start, [self name]);
+
+ if (isLoaded)
+ return YES;
+
+#ifdef SUPPORT_CFM
+ if (isBundle) {
+#endif
+ if (!CFBundleLoadExecutable(cfBundle))
+ goto abort;
+#if !LOG_DISABLED
+ currentTime = CFAbsoluteTimeGetCurrent();
+ duration = currentTime - start;
+#endif
+ LOG(Plugins, "%f CFBundleLoadExecutable took %f seconds", currentTime, duration);
+ isLoaded = YES;
+
+#ifdef SUPPORT_CFM
+ if (isCFM) {
+ pluginMainFunc = (MainFuncPtr)CFBundleGetFunctionPointerForName(cfBundle, CFSTR("main") );
+ if (!pluginMainFunc)
+ goto abort;
+ } else {
+#endif
+ NP_Initialize = (NP_InitializeFuncPtr)CFBundleGetFunctionPointerForName(cfBundle, CFSTR("NP_Initialize"));
+ NP_GetEntryPoints = (NP_GetEntryPointsFuncPtr)CFBundleGetFunctionPointerForName(cfBundle, CFSTR("NP_GetEntryPoints"));
+ NPP_Shutdown = (NPP_ShutdownProcPtr)CFBundleGetFunctionPointerForName(cfBundle, CFSTR("NP_Shutdown"));
+ if (!NP_Initialize || !NP_GetEntryPoints || !NPP_Shutdown)
+ goto abort;
+#ifdef SUPPORT_CFM
+ }
+ } else {
+ // single CFM file
+ FSSpec spec;
+ FSRef fref;
+ OSErr err;
+
+ err = FSPathMakeRef((UInt8 *)[path fileSystemRepresentation], &fref, NULL);
+ if (err != noErr) {
+ LOG_ERROR("FSPathMakeRef failed. Error=%d", err);
+ goto abort;
+ }
+ err = FSGetCatalogInfo(&fref, kFSCatInfoNone, NULL, NULL, &spec, NULL);
+ if (err != noErr) {
+ LOG_ERROR("FSGetCatalogInfo failed. Error=%d", err);
+ goto abort;
+ }
+ err = WebGetDiskFragment(&spec, 0, kCFragGoesToEOF, nil, kPrivateCFragCopy, &connID, (Ptr *)&pluginMainFunc, nil);
+ if (err != noErr) {
+ LOG_ERROR("WebGetDiskFragment failed. Error=%d", err);
+ goto abort;
+ }
+#if !LOG_DISABLED
+ currentTime = CFAbsoluteTimeGetCurrent();
+ duration = currentTime - start;
+#endif
+ LOG(Plugins, "%f WebGetDiskFragment took %f seconds", currentTime, duration);
+ isLoaded = YES;
+
+ pluginMainFunc = (MainFuncPtr)functionPointerForTVector((TransitionVector)pluginMainFunc);
+ if (!pluginMainFunc) {
+ goto abort;
+ }
+
+ // NOTE: pluginMainFunc is freed after it is called. Be sure not to return before that.
+
+ isCFM = YES;
+ }
+#endif /* SUPPORT_CFM */
+
+ // Plugins (at least QT) require that you call UseResFile on the resource file before loading it.
+ resourceRef = [self openResourceFile];
+ if (resourceRef != -1) {
+ UseResFile(resourceRef);
+ }
+
+ // swap function tables
+#ifdef SUPPORT_CFM
+ if (isCFM) {
+ browserFuncs.version = NP_VERSION_MINOR;
+ browserFuncs.size = sizeof(NPNetscapeFuncs);
+ browserFuncs.geturl = (NPN_GetURLProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_GetURL);
+ browserFuncs.posturl = (NPN_PostURLProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_PostURL);
+ browserFuncs.requestread = (NPN_RequestReadProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_RequestRead);
+ browserFuncs.newstream = (NPN_NewStreamProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_NewStream);
+ browserFuncs.write = (NPN_WriteProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_Write);
+ browserFuncs.destroystream = (NPN_DestroyStreamProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_DestroyStream);
+ browserFuncs.status = (NPN_StatusProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_Status);
+ browserFuncs.uagent = (NPN_UserAgentProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_UserAgent);
+ browserFuncs.memalloc = (NPN_MemAllocProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_MemAlloc);
+ browserFuncs.memfree = (NPN_MemFreeProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_MemFree);
+ browserFuncs.memflush = (NPN_MemFlushProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_MemFlush);
+ browserFuncs.reloadplugins = (NPN_ReloadPluginsProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_ReloadPlugins);
+ browserFuncs.geturlnotify = (NPN_GetURLNotifyProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_GetURLNotify);
+ browserFuncs.posturlnotify = (NPN_PostURLNotifyProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_PostURLNotify);
+ browserFuncs.getvalue = (NPN_GetValueProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_GetValue);
+ browserFuncs.setvalue = (NPN_SetValueProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_SetValue);
+ browserFuncs.invalidaterect = (NPN_InvalidateRectProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_InvalidateRect);
+ browserFuncs.invalidateregion = (NPN_InvalidateRegionProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_InvalidateRegion);
+ browserFuncs.forceredraw = (NPN_ForceRedrawProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_ForceRedraw);
+ browserFuncs.getJavaEnv = (NPN_GetJavaEnvProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_GetJavaEnv);
+ browserFuncs.getJavaPeer = (NPN_GetJavaPeerProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_GetJavaPeer);
+ browserFuncs.pushpopupsenabledstate = (NPN_PushPopupsEnabledStateProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_PushPopupsEnabledState);
+ browserFuncs.poppopupsenabledstate = (NPN_PopPopupsEnabledStateProcPtr)tVectorForFunctionPointer((FunctionPointer)NPN_PopPopupsEnabledState);
+
+ browserFuncs.releasevariantvalue = (NPN_ReleaseVariantValueProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_ReleaseVariantValue);
+ browserFuncs.getstringidentifier = (NPN_GetStringIdentifierProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_GetStringIdentifier);
+ browserFuncs.getstringidentifiers = (NPN_GetStringIdentifiersProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_GetStringIdentifiers);
+ browserFuncs.getintidentifier = (NPN_GetIntIdentifierProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_GetIntIdentifier);
+ browserFuncs.identifierisstring = (NPN_IdentifierIsStringProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_IdentifierIsString);
+ browserFuncs.utf8fromidentifier = (NPN_UTF8FromIdentifierProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_UTF8FromIdentifier);
+ browserFuncs.createobject = (NPN_CreateObjectProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_CreateObject);
+ browserFuncs.retainobject = (NPN_RetainObjectProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_RetainObject);
+ browserFuncs.releaseobject = (NPN_ReleaseObjectProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_ReleaseObject);
+ browserFuncs.invoke = (NPN_InvokeProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_Invoke);
+ browserFuncs.invokeDefault = (NPN_InvokeDefaultProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_InvokeDefault);
+ browserFuncs.evaluate = (NPN_EvaluateProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_Evaluate);
+ browserFuncs.getproperty = (NPN_GetPropertyProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_GetProperty);
+ browserFuncs.setproperty = (NPN_SetPropertyProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_SetProperty);
+ browserFuncs.removeproperty = (NPN_RemovePropertyProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_RemoveProperty);
+ browserFuncs.setexception = (NPN_SetExceptionProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_SetException);
+ browserFuncs.enumerate = (NPN_EnumerateProcPtr)tVectorForFunctionPointer((FunctionPointer)_NPN_Enumerate);
+
+ [self _applyDjVuWorkaround];
+
+#if !LOG_DISABLED
+ CFAbsoluteTime mainStart = CFAbsoluteTimeGetCurrent();
+#endif
+ LOG(Plugins, "%f main timing started", mainStart);
+ NPP_ShutdownProcPtr shutdownFunction;
+ npErr = pluginMainFunc(&browserFuncs, &pluginFuncs, &shutdownFunction);
+ NPP_Shutdown = (NPP_ShutdownProcPtr)functionPointerForTVector((TransitionVector)shutdownFunction);
+ if (!isBundle)
+ // Don't free pluginMainFunc if we got it from a bundle because it is owned by CFBundle in that case.
+ free(pluginMainFunc);
+
+ // Workaround for 3270576. The RealPlayer plug-in fails to load if its preference file is out of date.
+ // Launch the RealPlayer application to refresh the file.
+ if (npErr != NPERR_NO_ERROR) {
+ if (npErr == NPERR_MODULE_LOAD_FAILED_ERROR && [[self filename] isEqualToString:RealPlayerPluginFilename])
+ [self launchRealPlayer];
+ goto abort;
+ }
+#if !LOG_DISABLED
+ currentTime = CFAbsoluteTimeGetCurrent();
+ duration = currentTime - mainStart;
+#endif
+ LOG(Plugins, "%f main took %f seconds", currentTime, duration);
+
+ pluginSize = pluginFuncs.size;
+ pluginVersion = pluginFuncs.version;
+ LOG(Plugins, "pluginMainFunc: %d, size=%d, version=%d", npErr, pluginSize, pluginVersion);
+
+ NPP_New = (NPP_NewProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.newp);
+ NPP_Destroy = (NPP_DestroyProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.destroy);
+ NPP_SetWindow = (NPP_SetWindowProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.setwindow);
+ NPP_NewStream = (NPP_NewStreamProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.newstream);
+ NPP_DestroyStream = (NPP_DestroyStreamProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.destroystream);
+ NPP_StreamAsFile = (NPP_StreamAsFileProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.asfile);
+ NPP_WriteReady = (NPP_WriteReadyProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.writeready);
+ NPP_Write = (NPP_WriteProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.write);
+ NPP_Print = (NPP_PrintProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.print);
+ NPP_HandleEvent = (NPP_HandleEventProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.event);
+ NPP_URLNotify = (NPP_URLNotifyProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.urlnotify);
+ NPP_GetValue = (NPP_GetValueProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.getvalue);
+ NPP_SetValue = (NPP_SetValueProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.setvalue);
+
+ // LiveConnect support
+ NPP_GetJavaClass = (NPP_GetJavaClassProcPtr)functionPointerForTVector((TransitionVector)pluginFuncs.javaClass);
+ if (NPP_GetJavaClass) {
+ LOG(LiveConnect, "%@: CFM entry point for NPP_GetJavaClass = %p", [self name], NPP_GetJavaClass);
+ } else {
+ LOG(LiveConnect, "%@: no entry point for NPP_GetJavaClass", [self name]);
+ }
+
+ } else {
+
+#endif
+
+ // no function pointer conversion necessary for Mach-O
+ browserFuncs.version = NP_VERSION_MINOR;
+ browserFuncs.size = sizeof(NPNetscapeFuncs);
+ browserFuncs.geturl = NPN_GetURL;
+ browserFuncs.posturl = NPN_PostURL;
+ browserFuncs.requestread = NPN_RequestRead;
+ browserFuncs.newstream = NPN_NewStream;
+ browserFuncs.write = NPN_Write;
+ browserFuncs.destroystream = NPN_DestroyStream;
+ browserFuncs.status = NPN_Status;
+ browserFuncs.uagent = NPN_UserAgent;
+ browserFuncs.memalloc = NPN_MemAlloc;
+ browserFuncs.memfree = NPN_MemFree;
+ browserFuncs.memflush = NPN_MemFlush;
+ browserFuncs.reloadplugins = NPN_ReloadPlugins;
+ browserFuncs.geturlnotify = NPN_GetURLNotify;
+ browserFuncs.posturlnotify = NPN_PostURLNotify;
+ browserFuncs.getvalue = NPN_GetValue;
+ browserFuncs.setvalue = NPN_SetValue;
+ browserFuncs.invalidaterect = NPN_InvalidateRect;
+ browserFuncs.invalidateregion = NPN_InvalidateRegion;
+ browserFuncs.forceredraw = NPN_ForceRedraw;
+ browserFuncs.getJavaEnv = NPN_GetJavaEnv;
+ browserFuncs.getJavaPeer = NPN_GetJavaPeer;
+ browserFuncs.pushpopupsenabledstate = NPN_PushPopupsEnabledState;
+ browserFuncs.poppopupsenabledstate = NPN_PopPopupsEnabledState;
+
+ browserFuncs.releasevariantvalue = _NPN_ReleaseVariantValue;
+ browserFuncs.getstringidentifier = _NPN_GetStringIdentifier;
+ browserFuncs.getstringidentifiers = _NPN_GetStringIdentifiers;
+ browserFuncs.getintidentifier = _NPN_GetIntIdentifier;
+ browserFuncs.identifierisstring = _NPN_IdentifierIsString;
+ browserFuncs.utf8fromidentifier = _NPN_UTF8FromIdentifier;
+ browserFuncs.createobject = _NPN_CreateObject;
+ browserFuncs.retainobject = _NPN_RetainObject;
+ browserFuncs.releaseobject = _NPN_ReleaseObject;
+ browserFuncs.invoke = _NPN_Invoke;
+ browserFuncs.invokeDefault = _NPN_InvokeDefault;
+ browserFuncs.evaluate = _NPN_Evaluate;
+ browserFuncs.getproperty = _NPN_GetProperty;
+ browserFuncs.setproperty = _NPN_SetProperty;
+ browserFuncs.removeproperty = _NPN_RemoveProperty;
+ browserFuncs.setexception = _NPN_SetException;
+ browserFuncs.enumerate = _NPN_Enumerate;
+
+ [self _applyDjVuWorkaround];
+
+#if !LOG_DISABLED
+ CFAbsoluteTime initializeStart = CFAbsoluteTimeGetCurrent();
+#endif
+ LOG(Plugins, "%f NP_Initialize timing started", initializeStart);
+ npErr = NP_Initialize(&browserFuncs);
+ if (npErr != NPERR_NO_ERROR)
+ goto abort;
+#if !LOG_DISABLED
+ currentTime = CFAbsoluteTimeGetCurrent();
+ duration = currentTime - initializeStart;
+#endif
+ LOG(Plugins, "%f NP_Initialize took %f seconds", currentTime, duration);
+
+ npErr = NP_GetEntryPoints(&pluginFuncs);
+ if (npErr != NPERR_NO_ERROR)
+ goto abort;
+
+ pluginSize = pluginFuncs.size;
+ pluginVersion = pluginFuncs.version;
+
+ NPP_New = pluginFuncs.newp;
+ NPP_Destroy = pluginFuncs.destroy;
+ NPP_SetWindow = pluginFuncs.setwindow;
+ NPP_NewStream = pluginFuncs.newstream;
+ NPP_DestroyStream = pluginFuncs.destroystream;
+ NPP_StreamAsFile = pluginFuncs.asfile;
+ NPP_WriteReady = pluginFuncs.writeready;
+ NPP_Write = pluginFuncs.write;
+ NPP_Print = pluginFuncs.print;
+ NPP_HandleEvent = pluginFuncs.event;
+ NPP_URLNotify = pluginFuncs.urlnotify;
+ NPP_GetValue = pluginFuncs.getvalue;
+ NPP_SetValue = pluginFuncs.setvalue;
+
+ // LiveConnect support
+ NPP_GetJavaClass = pluginFuncs.javaClass;
+ if (NPP_GetJavaClass){
+ LOG(LiveConnect, "%@: mach-o entry point for NPP_GetJavaClass = %p", [self name], NPP_GetJavaClass);
+ } else {
+ LOG(LiveConnect, "%@: no entry point for NPP_GetJavaClass", [self name]);
+ }
+
+#ifdef SUPPORT_CFM
+ }
+#endif
+
+#if !LOG_DISABLED
+ currentTime = CFAbsoluteTimeGetCurrent();
+ duration = currentTime - start;
+#endif
+ LOG(Plugins, "%f Total load time: %f seconds", currentTime, duration);
+
+ return [super load];
+
+abort:
+ [self _unloadWithShutdown:NO];
+ return NO;
+}
+
+- (NPP_SetWindowProcPtr)NPP_SetWindow
+{
+ return NPP_SetWindow;
+}
+
+- (NPP_NewProcPtr)NPP_New
+{
+ return NPP_New;
+}
+
+- (NPP_DestroyProcPtr)NPP_Destroy
+{
+ return NPP_Destroy;
+}
+
+- (NPP_NewStreamProcPtr)NPP_NewStream
+{
+ return NPP_NewStream;
+}
+
+- (NPP_StreamAsFileProcPtr)NPP_StreamAsFile
+{
+ return NPP_StreamAsFile;
+}
+- (NPP_DestroyStreamProcPtr)NPP_DestroyStream
+{
+ return NPP_DestroyStream;
+}
+
+- (NPP_WriteReadyProcPtr)NPP_WriteReady
+{
+ return NPP_WriteReady;
+}
+- (NPP_WriteProcPtr)NPP_Write
+{
+ return NPP_Write;
+}
+
+- (NPP_HandleEventProcPtr)NPP_HandleEvent
+{
+ return NPP_HandleEvent;
+}
+
+-(NPP_URLNotifyProcPtr)NPP_URLNotify
+{
+ return NPP_URLNotify;
+}
+
+-(NPP_GetValueProcPtr)NPP_GetValue
+{
+ return NPP_GetValue;
+}
+
+-(NPP_SetValueProcPtr)NPP_SetValue
+{
+ return NPP_SetValue;
+}
+
+-(NPP_PrintProcPtr)NPP_Print
+{
+ return NPP_Print;
+}
+
+- (void)wasRemovedFromPluginDatabase:(WebPluginDatabase *)database
+{
+ [super wasRemovedFromPluginDatabase:database];
+
+ // Unload when removed from final plug-in database
+ if ([pluginDatabases count] == 0)
+ [self _unloadWithShutdown:YES];
+}
+
+- (void)open
+{
+ instanceCount++;
+
+ // Handle the case where all instances close a plug-in package, but another
+ // instance opens the package before it is unloaded (which only happens when
+ // the plug-in database is refreshed)
+ needsUnload = NO;
+
+ if (!isLoaded) {
+ // Should load when the first instance opens the plug-in package
+ ASSERT(instanceCount == 1);
+ [self load];
+ }
+}
+
+- (void)close
+{
+ ASSERT(instanceCount > 0);
+ instanceCount--;
+ if (instanceCount == 0 && needsUnload)
+ [self _unloadWithShutdown:YES];
+}
+
+@end
+
+#ifdef SUPPORT_CFM
+
+// function pointer converters
+
+FunctionPointer functionPointerForTVector(TransitionVector tvp)
+{
+ const uint32 temp[6] = {0x3D800000, 0x618C0000, 0x800C0000, 0x804C0004, 0x7C0903A6, 0x4E800420};
+ uint32 *newGlue = NULL;
+
+ if (tvp != NULL) {
+ newGlue = (uint32 *)malloc(sizeof(temp));
+ if (newGlue != NULL) {
+ unsigned i;
+ for (i = 0; i < 6; i++) newGlue[i] = temp[i];
+ newGlue[0] |= ((uintptr_t)tvp >> 16);
+ newGlue[1] |= ((uintptr_t)tvp & 0xFFFF);
+ MakeDataExecutable(newGlue, sizeof(temp));
+ }
+ }
+
+ return (FunctionPointer)newGlue;
+}
+
+TransitionVector tVectorForFunctionPointer(FunctionPointer fp)
+{
+ FunctionPointer *newGlue = NULL;
+ if (fp != NULL) {
+ newGlue = (FunctionPointer *)malloc(2 * sizeof(FunctionPointer));
+ if (newGlue != NULL) {
+ newGlue[0] = fp;
+ newGlue[1] = NULL;
+ }
+ }
+ return (TransitionVector)newGlue;
+}
+
+#endif
+
+@implementation WebNetscapePluginPackage (Internal)
+
+- (void)_unloadWithShutdown:(BOOL)shutdown
+{
+ if (!isLoaded)
+ return;
+
+ LOG(Plugins, "Unloading %@...", name);
+
+ // Cannot unload a plug-in package while an instance is still using it
+ if (instanceCount > 0) {
+ needsUnload = YES;
+ return;
+ }
+
+ if (shutdown && NPP_Shutdown)
+ NPP_Shutdown();
+
+ if (resourceRef != -1)
+ [self closeResourceFile:resourceRef];
+
+#ifdef SUPPORT_CFM
+ if (isBundle)
+#endif
+ CFBundleUnloadExecutable(cfBundle);
+#ifdef SUPPORT_CFM
+ else
+ WebCloseConnection(&connID);
+#endif
+
+ LOG(Plugins, "Plugin Unloaded");
+ isLoaded = NO;
+}
+
+@end
+#endif
diff --git a/WebKit/mac/Plugins/WebNetscapePluginStream.h b/WebKit/mac/Plugins/WebNetscapePluginStream.h
new file mode 100644
index 0000000..e9e48f0
--- /dev/null
+++ b/WebKit/mac/Plugins/WebNetscapePluginStream.h
@@ -0,0 +1,57 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+#ifndef __LP64__
+#import <WebKit/WebBaseNetscapePluginStream.h>
+#import <WebKit/npapi.h>
+
+namespace WebCore {
+ class FrameLoader;
+ class NetscapePlugInStreamLoader;
+}
+@class NSURLRequest;
+
+class WebNetscapePlugInStreamLoaderClient;
+
+@interface WebNetscapePluginStream : WebBaseNetscapePluginStream
+{
+ WebCore::FrameLoader* _frameLoader;
+ WebCore::NetscapePlugInStreamLoader* _loader;
+ WebNetscapePlugInStreamLoaderClient* _client;
+ NSURLRequest *request;
+}
+
+- (id)initWithFrameLoader:(WebCore::FrameLoader *)frameLoader;
+- (id)initWithRequest:(NSURLRequest *)theRequest
+ plugin:(NPP)thePlugin
+ notifyData:(void *)theNotifyData
+ sendNotification:(BOOL)sendNotification;
+- (void)start;
+- (void)stop;
+
+@end
+#endif
diff --git a/WebKit/mac/Plugins/WebNetscapePluginStream.mm b/WebKit/mac/Plugins/WebNetscapePluginStream.mm
new file mode 100644
index 0000000..8b03e01
--- /dev/null
+++ b/WebKit/mac/Plugins/WebNetscapePluginStream.mm
@@ -0,0 +1,154 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+#ifndef __LP64__
+#import <WebKit/WebNetscapePluginStream.h>
+
+#import <Foundation/NSURLConnection.h>
+#import <WebCore/DocumentLoader.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/NetscapePlugInStreamLoader.h>
+#import <WebKit/WebDataSourceInternal.h>
+#import <WebKit/WebFrameBridge.h>
+#import <WebKit/WebFrameInternal.h>
+#import <WebKit/WebKitErrorsPrivate.h>
+#import <WebKit/WebKitLogging.h>
+#import <WebKit/WebNSURLRequestExtras.h>
+#import <WebKit/WebNetscapePluginEmbeddedView.h>
+#import <WebKit/WebNetscapePluginPackage.h>
+#import <WebKit/WebNetscapePlugInStreamLoaderClient.h>
+#import <WebKit/WebViewInternal.h>
+#import <WebCore/ResourceError.h>
+#import <WebCore/WebCoreObjCExtras.h>
+#import <wtf/PassRefPtr.h>
+
+using namespace WebCore;
+
+@implementation WebNetscapePluginStream
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
+- (id)initWithFrameLoader:(FrameLoader *)frameLoader
+{
+ _frameLoader = frameLoader;
+
+ return self;
+}
+
+- (id)initWithRequest:(NSURLRequest *)theRequest
+ plugin:(NPP)thePlugin
+ notifyData:(void *)theNotifyData
+ sendNotification:(BOOL)flag
+{
+ WebBaseNetscapePluginView *view = (WebBaseNetscapePluginView *)thePlugin->ndata;
+
+ if (!core([view webFrame])->loader()->canLoad([theRequest URL], core([view webFrame])->document()))
+ return nil;
+
+ if ([self initWithRequestURL:[theRequest URL]
+ plugin:thePlugin
+ notifyData:theNotifyData
+ sendNotification:flag] == nil) {
+ return nil;
+ }
+
+ // Temporarily set isTerminated to YES to avoid assertion failure in dealloc in case we are released in this method.
+ isTerminated = YES;
+
+ request = [theRequest mutableCopy];
+ if (core([view webFrame])->loader()->shouldHideReferrer([theRequest URL], core([view webFrame])->loader()->outgoingReferrer()))
+ [(NSMutableURLRequest *)request _web_setHTTPReferrer:nil];
+
+ _client = new WebNetscapePlugInStreamLoaderClient(self);
+ _loader = NetscapePlugInStreamLoader::create(core([view webFrame]), _client).releaseRef();
+ _loader->setShouldBufferData(false);
+
+ isTerminated = NO;
+
+ return self;
+}
+
+- (void)dealloc
+{
+ if (_loader)
+ _loader->deref();
+ delete _client;
+ [request release];
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+ if (_loader)
+ _loader->deref();
+ delete _client;
+ [super finalize];
+}
+
+- (void)start
+{
+ ASSERT(request);
+ ASSERT(!_frameLoader);
+
+ _loader->documentLoader()->addPlugInStreamLoader(_loader);
+ _loader->load(request);
+}
+
+- (void)cancelLoadWithError:(NSError *)error
+{
+ if (_frameLoader) {
+ ASSERT(!_loader);
+
+ DocumentLoader* documentLoader = _frameLoader->activeDocumentLoader();
+ ASSERT(documentLoader);
+
+ if (documentLoader->isLoadingMainResource())
+ documentLoader->cancelMainResourceLoad(error);
+ return;
+ }
+
+ if (!_loader->isDone())
+ _loader->cancel(error);
+}
+
+- (void)stop
+{
+ ASSERT(!_frameLoader);
+
+ if (!_loader->isDone())
+ [self cancelLoadAndDestroyStreamWithError:_loader->cancelledError()];
+}
+
+@end
+#endif
diff --git a/WebKit/mac/Plugins/WebNullPluginView.h b/WebKit/mac/Plugins/WebNullPluginView.h
new file mode 100644
index 0000000..3ca1532
--- /dev/null
+++ b/WebKit/mac/Plugins/WebNullPluginView.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2005, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <AppKit/AppKit.h>
+
+@class DOMElement;
+
+@interface WebNullPluginView : NSImageView
+{
+ NSError *error;
+ DOMElement *element;
+}
+
+- (id)initWithFrame:(NSRect)frame error:(NSError *)error DOMElement:(DOMElement *)element;
+
+@end
diff --git a/WebKit/mac/Plugins/WebNullPluginView.mm b/WebKit/mac/Plugins/WebNullPluginView.mm
new file mode 100644
index 0000000..48e0e9d
--- /dev/null
+++ b/WebKit/mac/Plugins/WebNullPluginView.mm
@@ -0,0 +1,97 @@
+/*
+ * Copyright (C) 2005, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNullPluginView.h"
+
+#import "WebFrameInternal.h"
+#import "WebViewInternal.h"
+#import <WebCore/Document.h>
+
+@implementation WebNullPluginView
+
+- initWithFrame:(NSRect)frame error:(NSError *)err DOMElement:(DOMElement *)elem
+{
+ static NSImage *nullPlugInImage;
+ if (!nullPlugInImage) {
+ NSBundle *bundle = [NSBundle bundleForClass:[WebNullPluginView class]];
+ NSString *imagePath = [bundle pathForResource:@"nullplugin" ofType:@"tiff"];
+ nullPlugInImage = [[NSImage alloc] initWithContentsOfFile:imagePath];
+ }
+
+ self = [super initWithFrame:frame];
+ if (!self)
+ return nil;
+
+ error = [err retain];
+ if (err)
+ element = [elem retain];
+
+ [self setImage:nullPlugInImage];
+
+ return self;
+}
+
+- (void)dealloc
+
+{
+ [error release];
+ [element release];
+ [super dealloc];
+}
+
+- (void)reportFailure
+{
+ NSError *localError = error;
+ DOMElement *localElement = element;
+
+ error = nil;
+ element = nil;
+
+ WebFrame *webFrame = kit(core(localElement)->document()->frame());
+ if (webFrame) {
+ WebView *webView = [webFrame webView];
+ WebResourceDelegateImplementationCache* implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+ if (implementations->plugInFailedWithErrorFunc)
+ CallResourceLoadDelegate(implementations->plugInFailedWithErrorFunc, webView,
+ @selector(webView:plugInFailedWithError:dataSource:), localError, [webFrame _dataSource]);
+ }
+
+ [localError release];
+ [localElement release];
+}
+
+- (void)viewDidMoveToWindow
+{
+ if (!error)
+ return;
+
+ if ([self window])
+ [self reportFailure];
+}
+
+@end
diff --git a/WebKit/mac/Plugins/WebPlugInStreamLoaderDelegate.h b/WebKit/mac/Plugins/WebPlugInStreamLoaderDelegate.h
new file mode 100644
index 0000000..b4d6ed8
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPlugInStreamLoaderDelegate.h
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+@class NSURLResponse;
+@class NSError;
+@class NSData;
+
+@protocol WebPlugInStreamLoaderDelegate
+
+- (void)startStreamWithResponse:(NSURLResponse *)r;
+
+// destroyStreamWithError tells the plug-in that the load is completed (error == nil) or ended in error.
+- (void)destroyStreamWithError:(NSError *)error;
+
+// cancelLoadAndDestoryStreamWithError calls cancelLoadWithError: then destroyStreamWithError:.
+- (void)cancelLoadAndDestroyStreamWithError:(NSError *)error;
+
+- (void)receivedData:(NSData *)data;
+- (void)finishedLoading;
+
+@end
diff --git a/WebKit/mac/Plugins/WebPlugin.h b/WebKit/mac/Plugins/WebPlugin.h
new file mode 100644
index 0000000..3163c06
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPlugin.h
@@ -0,0 +1,95 @@
+/*
+ * Copyright (C) 2004 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+/*!
+ WebPlugIn is an informal protocol that enables interaction between an application
+ and web related plug-ins it may contain.
+*/
+
+@interface NSObject (WebPlugIn)
+
+/*!
+ @method webPlugInInitialize
+ @abstract Tell the plug-in to perform one-time initialization.
+ @discussion This method must be only called once per instance of the plug-in
+ object and must be called before any other methods in this protocol.
+*/
+- (void)webPlugInInitialize;
+
+/*!
+ @method webPlugInStart
+ @abstract Tell the plug-in to start normal operation.
+ @discussion The plug-in usually begins drawing, playing sounds and/or
+ animation in this method. This method must be called before calling webPlugInStop.
+ This method may called more than once, provided that the application has
+ already called webPlugInInitialize and that each call to webPlugInStart is followed
+ by a call to webPlugInStop.
+*/
+- (void)webPlugInStart;
+
+/*!
+ @method webPlugInStop
+ @abstract Tell the plug-in to stop normal operation.
+ @discussion webPlugInStop must be called before this method. This method may be
+ called more than once, provided that the application has already called
+ webPlugInInitialize and that each call to webPlugInStop is preceded by a call to
+ webPlugInStart.
+*/
+- (void)webPlugInStop;
+
+/*!
+ @method webPlugInDestroy
+ @abstract Tell the plug-in perform cleanup and prepare to be deallocated.
+ @discussion The plug-in typically releases memory and other resources in this
+ method. If the plug-in has retained the WebPlugInContainer, it must release
+ it in this mehthod. This method must be only called once per instance of the
+ plug-in object. No other methods in this interface may be called after the
+ application has called webPlugInDestroy.
+*/
+- (void)webPlugInDestroy;
+
+/*!
+ @method webPlugInSetIsSelected:
+ @discusssion Informs the plug-in whether or not it is selected. This is typically
+ used to allow the plug-in to alter it's appearance when selected.
+*/
+- (void)webPlugInSetIsSelected:(BOOL)isSelected;
+
+/*!
+ @method objectForWebScript
+ @discussion objectForWebScript is used to expose a plug-in's scripting interface. The
+ methods of the object are exposed to the script environment. See the WebScripting
+ informal protocol for more details.
+ @result Returns the object that exposes the plug-in's interface. The class of this
+ object can implement methods from the WebScripting informal protocol.
+*/
+- (id)objectForWebScript;
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginContainer.h b/WebKit/mac/Plugins/WebPluginContainer.h
new file mode 100644
index 0000000..112b677
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginContainer.h
@@ -0,0 +1,72 @@
+/*
+ * Copyright (C) 2004 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+/*!
+ This informal protocol enables a plug-in to request that its containing application
+ perform certain operations.
+*/
+
+@interface NSObject (WebPlugInContainer)
+
+/*!
+ @method webPlugInContainerLoadRequest:inFrame:
+ @abstract Tell the application to show a URL in a target frame
+ @param request The request to be loaded.
+ @param target The target frame. If the frame with the specified target is not
+ found, a new window is opened and the main frame of the new window is named
+ with the specified target. If nil is specified, the frame that contains
+ the applet is targeted.
+*/
+- (void)webPlugInContainerLoadRequest:(NSURLRequest *)request inFrame:(NSString *)target;
+
+/*!
+ @method webPlugInContainerShowStatus:
+ @abstract Tell the application to show the specified status message.
+ @param message The string to be shown.
+*/
+- (void)webPlugInContainerShowStatus:(NSString *)message;
+
+/*!
+ @method webPlugInContainerSelectionColor
+ @result Returns the color that should be used for any special drawing when
+ plug-in is selected.
+*/
+- (NSColor *)webPlugInContainerSelectionColor;
+
+/*!
+ @method webFrame
+ @discussion The webFrame method allows the plug-in to access the WebFrame that
+ contains the plug-in. This method will not be implemented by containers that
+ are not WebKit based.
+ @result Return the WebFrame that contains the plug-in.
+*/
+- (WebFrame *)webFrame;
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginContainerCheck.h b/WebKit/mac/Plugins/WebPluginContainerCheck.h
new file mode 100644
index 0000000..1b7bbda
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginContainerCheck.h
@@ -0,0 +1,55 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@class NSURLRequest;
+@class NSString;
+@class WebPluginController;
+@class WebPolicyDecisionListener;
+
+@interface WebPluginContainerCheck : NSObject
+{
+ NSURLRequest *_request;
+ NSString *_target;
+ WebPluginController *_controller;
+ id _resultObject;
+ SEL _resultSelector;
+ BOOL _done;
+ WebPolicyDecisionListener *_listener;
+}
+
++ (id)checkWithRequest:(NSURLRequest *)request target:(NSString *)target resultObject:(id)obj selector:(SEL)selector controller:(WebPluginController *)controller;
+
+- (id)initWithRequest:(NSURLRequest *)request target:(NSString *)target resultObject:(id)obj selector:(SEL)selector controller:(WebPluginController *)controller;
+
+- (void)start;
+
+- (void)cancel;
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginContainerCheck.mm b/WebKit/mac/Plugins/WebPluginContainerCheck.mm
new file mode 100644
index 0000000..e784224
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginContainerCheck.mm
@@ -0,0 +1,183 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebPluginContainerCheck.h"
+
+#import "WebFrame.h"
+#import "WebFrameBridge.h"
+#import "WebPluginContainer.h"
+#import "WebPluginContainerPrivate.h"
+#import "WebPluginController.h"
+#import "WebPolicyDelegate.h"
+#import "WebPolicyDelegatePrivate.h"
+#import "WebView.h"
+#import "WebViewInternal.h"
+#import <Foundation/NSDictionary.h>
+#import <Foundation/NSURL.h>
+#import <Foundation/NSURLRequest.h>
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/FrameLoaderTypes.h>
+#import <objc/objc-runtime.h>
+
+using namespace WebCore;
+
+@implementation WebPluginContainerCheck
+
++ (id)checkWithRequest:(NSURLRequest *)request target:(NSString *)target resultObject:(id)obj selector:(SEL)selector controller:(WebPluginController *)controller
+{
+ return [[[self alloc] initWithRequest:request target:target resultObject:obj selector:selector controller:controller] autorelease];
+}
+
+- (id)initWithRequest:(NSURLRequest *)request target:(NSString *)target resultObject:(id)obj selector:(SEL)selector controller:(WebPluginController *)controller
+{
+ if (!(self = [super init]))
+ return nil;
+
+ _request = [request copy];
+ _target = [target copy];
+ _resultObject = [obj retain];
+ _resultSelector = selector;
+
+ // controller owns us so don't retain, to avoid cycle
+ _controller = controller;
+
+ return self;
+}
+
+- (void)finalize
+{
+ // mandatory to complete or cancel before releasing this object
+ ASSERT(_done);
+ [super finalize];
+}
+
+- (void)dealloc
+{
+ // mandatory to complete or cancel before releasing this object
+ ASSERT(_done);
+ [super dealloc];
+}
+
+- (void)_continueWithPolicy:(PolicyAction)policy
+{
+ ((void (*)(id, SEL, BOOL))objc_msgSend)(_resultObject, _resultSelector, (policy == PolicyUse));
+
+ // this will call indirectly call cancel
+ [_controller _webPluginContainerCancelCheckIfAllowedToLoadRequest:self];
+}
+
+- (BOOL)_isForbiddenFileLoad
+{
+ WebFrameBridge *bridge = [_controller bridge];
+ ASSERT(bridge);
+ if (![bridge _frame]->loader()->canLoad([_request URL], [bridge _frame]->document())) {
+ [self _continueWithPolicy:PolicyIgnore];
+ return YES;
+ }
+
+ return NO;
+}
+
+- (NSDictionary *)_actionInformationWithURL:(NSURL *)URL
+{
+ return [NSDictionary dictionaryWithObjectsAndKeys:
+ [NSNumber numberWithInt:WebNavigationTypePlugInRequest], WebActionNavigationTypeKey,
+ [NSNumber numberWithInt:0], WebActionModifierFlagsKey,
+ URL, WebActionOriginalURLKey,
+ nil];
+}
+
+- (void)_askPolicyDelegate
+{
+ WebView *webView = [_controller webView];
+
+ WebFrame *targetFrame;
+ if ([_target length] > 0) {
+ targetFrame = [[_controller webFrame] findFrameNamed:_target];
+ } else {
+ targetFrame = [_controller webFrame];
+ }
+
+ NSDictionary *action = [self _actionInformationWithURL:[_request URL]];
+
+ _listener = [[WebPolicyDecisionListener alloc] _initWithTarget:self action:@selector(_continueWithPolicy:)];
+
+ if (targetFrame == nil) {
+ // would open new window
+ [[webView _policyDelegateForwarder] webView:webView
+ decidePolicyForNewWindowAction:action
+ request:_request
+ newFrameName:_target
+ decisionListener:_listener];
+ } else {
+ // would target existing frame
+ [[webView _policyDelegateForwarder] webView:webView
+ decidePolicyForNavigationAction:action
+ request:_request
+ frame:targetFrame
+ decisionListener:_listener];
+ }
+}
+
+- (void)start
+{
+ ASSERT(!_listener);
+ ASSERT(!_done);
+
+ if ([self _isForbiddenFileLoad])
+ return;
+
+ [self _askPolicyDelegate];
+}
+
+- (void)cancel
+{
+ if (_done)
+ return;
+
+ [_request release];
+ _request = nil;
+
+ [_target release];
+ _target = nil;
+
+ [_listener _invalidate];
+ [_listener release];
+ _listener = nil;
+
+ [_resultObject autorelease];
+ _resultObject = nil;
+
+ _controller = nil;
+
+ _done = YES;
+}
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginContainerPrivate.h b/WebKit/mac/Plugins/WebPluginContainerPrivate.h
new file mode 100644
index 0000000..c9d64d5
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginContainerPrivate.h
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@interface NSObject (WebPlugInContainerPrivate)
+
+- (id)_webPluginContainerCheckIfAllowedToLoadRequest:(NSURLRequest *)Request inFrame:(NSString *)target resultObject:(id)obj selector:(SEL)selector;
+
+- (void)_webPluginContainerCancelCheckIfAllowedToLoadRequest:(id)checkIdentifier;
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginController.h b/WebKit/mac/Plugins/WebPluginController.h
new file mode 100644
index 0000000..4f25326
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginController.h
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+#import <WebKit/WebBasePluginPackage.h>
+
+@class WebHTMLView;
+@class WebPluginPackage;
+@class WebFrameBridge;
+@class WebView;
+@class WebDataSource;
+
+@interface WebPluginController : NSObject <WebPluginManualLoader>
+{
+ NSView *_documentView;
+ WebDataSource *_dataSource;
+ NSMutableArray *_views;
+ BOOL _started;
+ NSMutableSet *_checksInProgress;
+}
+
++ (NSView *)plugInViewWithArguments:(NSDictionary *)arguments fromPluginPackage:(WebPluginPackage *)plugin;
++ (BOOL)isPlugInView:(NSView *)view;
+
+- (id)initWithDocumentView:(NSView *)view;
+
+- (void)setDataSource:(WebDataSource *)dataSource;
+
+- (void)addPlugin:(NSView *)view;
+- (void)destroyPlugin:(NSView *)view;
+
+- (void)startAllPlugins;
+- (void)stopAllPlugins;
+- (void)destroyAllPlugins;
+
+- (WebFrameBridge *)bridge;
+- (WebView *)webView;
+
+- (NSString *)URLPolicyCheckReferrer;
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginController.mm b/WebKit/mac/Plugins/WebPluginController.mm
new file mode 100644
index 0000000..9e9ec19
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginController.mm
@@ -0,0 +1,435 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+
+#import <WebKit/WebPluginController.h>
+
+#import <Foundation/NSURLRequest.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/ResourceRequest.h>
+#import <WebCore/PlatformString.h>
+#import <WebCore/WebCoreFrameBridge.h>
+#import <WebCore/DocumentLoader.h>
+#import <WebKit/WebDataSourceInternal.h>
+#import <WebKit/WebFrameBridge.h>
+#import <WebKit/WebFrameInternal.h>
+#import <WebKit/WebFrameView.h>
+#import <WebKit/WebHTMLViewPrivate.h>
+#import <WebKit/WebKitErrorsPrivate.h>
+#import <WebKit/WebKitLogging.h>
+#import <WebKit/WebNSURLExtras.h>
+#import <WebKit/WebNSViewExtras.h>
+#import <WebKit/WebPlugin.h>
+#import <WebKit/WebPluginContainer.h>
+#import <WebKit/WebPluginContainerCheck.h>
+#import <WebKit/WebPluginPackage.h>
+#import <WebKit/WebPluginPrivate.h>
+#import <WebKit/WebPluginViewFactory.h>
+#import <WebKit/WebUIDelegate.h>
+#import <WebKit/WebViewInternal.h>
+
+using namespace WebCore;
+
+@interface NSView (PluginSecrets)
+- (void)setContainingWindow:(NSWindow *)w;
+@end
+
+// For compatibility only.
+@interface NSObject (OldPluginAPI)
++ (NSView *)pluginViewWithArguments:(NSDictionary *)arguments;
+@end
+
+@interface NSView (OldPluginAPI)
+- (void)pluginInitialize;
+- (void)pluginStart;
+- (void)pluginStop;
+- (void)pluginDestroy;
+@end
+
+static NSMutableSet *pluginViews = nil;
+
+@implementation WebPluginController
+
++ (NSView *)plugInViewWithArguments:(NSDictionary *)arguments fromPluginPackage:(WebPluginPackage *)pluginPackage
+{
+ [pluginPackage load];
+ Class viewFactory = [pluginPackage viewFactory];
+
+ NSView *view = nil;
+
+ if ([viewFactory respondsToSelector:@selector(plugInViewWithArguments:)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ view = [viewFactory plugInViewWithArguments:arguments];
+ } else if ([viewFactory respondsToSelector:@selector(pluginViewWithArguments:)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ view = [viewFactory pluginViewWithArguments:arguments];
+ }
+
+ if (view == nil) {
+ return nil;
+ }
+
+ if (pluginViews == nil) {
+ pluginViews = [[NSMutableSet alloc] init];
+ }
+ [pluginViews addObject:view];
+
+ return view;
+}
+
++ (BOOL)isPlugInView:(NSView *)view
+{
+ return [pluginViews containsObject:view];
+}
+
+- (id)initWithDocumentView:(NSView *)view
+{
+ [super init];
+ _documentView = view;
+ _views = [[NSMutableArray alloc] init];
+ _checksInProgress = (NSMutableSet *)CFMakeCollectable(CFSetCreateMutable(NULL, 0, NULL));
+ return self;
+}
+
+- (void)setDataSource:(WebDataSource *)dataSource
+{
+ _dataSource = dataSource;
+}
+
+- (void)dealloc
+{
+ [_views release];
+ [_checksInProgress release];
+ [super dealloc];
+}
+
+- (void)startAllPlugins
+{
+ if (_started)
+ return;
+
+ if ([_views count] > 0)
+ LOG(Plugins, "starting WebKit plugins : %@", [_views description]);
+
+ int i, count = [_views count];
+ for (i = 0; i < count; i++) {
+ id aView = [_views objectAtIndex:i];
+ if ([aView respondsToSelector:@selector(webPlugInStart)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [aView webPlugInStart];
+ } else if ([aView respondsToSelector:@selector(pluginStart)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [aView pluginStart];
+ }
+ }
+ _started = YES;
+}
+
+- (void)stopAllPlugins
+{
+ if (!_started)
+ return;
+
+ if ([_views count] > 0) {
+ LOG(Plugins, "stopping WebKit plugins: %@", [_views description]);
+ }
+
+ int i, count = [_views count];
+ for (i = 0; i < count; i++) {
+ id aView = [_views objectAtIndex:i];
+ if ([aView respondsToSelector:@selector(webPlugInStop)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [aView webPlugInStop];
+ } else if ([aView respondsToSelector:@selector(pluginStop)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [aView pluginStop];
+ }
+ }
+ _started = NO;
+}
+
+- (void)addPlugin:(NSView *)view
+{
+ if (!_documentView) {
+ LOG_ERROR("can't add a plug-in to a defunct WebPluginController");
+ return;
+ }
+
+ if (![_views containsObject:view]) {
+ [_views addObject:view];
+
+ LOG(Plugins, "initializing plug-in %@", view);
+ if ([view respondsToSelector:@selector(webPlugInInitialize)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [view webPlugInInitialize];
+ } else if ([view respondsToSelector:@selector(pluginInitialize)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [view pluginInitialize];
+ }
+
+ if (_started) {
+ LOG(Plugins, "starting plug-in %@", view);
+ if ([view respondsToSelector:@selector(webPlugInStart)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [view webPlugInStart];
+ } else if ([view respondsToSelector:@selector(pluginStart)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [view pluginStart];
+ }
+
+ if ([view respondsToSelector:@selector(setContainingWindow:)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [view setContainingWindow:[_documentView window]];
+ }
+ }
+ }
+}
+
+- (void)destroyPlugin:(NSView *)view
+{
+ if ([_views containsObject:view]) {
+ if (_started) {
+ if ([view respondsToSelector:@selector(webPlugInStop)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [view webPlugInStop];
+ } else if ([view respondsToSelector:@selector(pluginStop)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [view pluginStop];
+ }
+ }
+
+ if ([view respondsToSelector:@selector(webPlugInDestroy)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [view webPlugInDestroy];
+ } else if ([view respondsToSelector:@selector(pluginDestroy)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [view pluginDestroy];
+ }
+
+ if (Frame* frame = core([self webFrame]))
+ frame->cleanupScriptObjectsForPlugin(self);
+
+ [pluginViews removeObject:view];
+ [_views removeObject:view];
+ }
+}
+
+- (void)_webPluginContainerCancelCheckIfAllowedToLoadRequest:(id)checkIdentifier
+{
+ [checkIdentifier cancel];
+ [_checksInProgress removeObject:checkIdentifier];
+}
+
+static void cancelOutstandingCheck(const void *item, void *context)
+{
+ [(id)item cancel];
+}
+
+- (void)_cancelOutstandingChecks
+{
+ if (_checksInProgress) {
+ CFSetApplyFunction((CFSetRef)_checksInProgress, cancelOutstandingCheck, NULL);
+ [_checksInProgress release];
+ _checksInProgress = nil;
+ }
+}
+
+- (void)destroyAllPlugins
+{
+ [self stopAllPlugins];
+
+ if ([_views count] > 0) {
+ LOG(Plugins, "destroying WebKit plugins: %@", [_views description]);
+ }
+
+ [self _cancelOutstandingChecks];
+
+ int i, count = [_views count];
+ for (i = 0; i < count; i++) {
+ id aView = [_views objectAtIndex:i];
+ if ([aView respondsToSelector:@selector(webPlugInDestroy)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [aView webPlugInDestroy];
+ } else if ([aView respondsToSelector:@selector(pluginDestroy)]) {
+ KJS::JSLock::DropAllLocks dropAllLocks;
+ [aView pluginDestroy];
+ }
+
+ if (Frame* frame = core([self webFrame]))
+ frame->cleanupScriptObjectsForPlugin(self);
+
+ [pluginViews removeObject:aView];
+ }
+ [_views makeObjectsPerformSelector:@selector(removeFromSuperviewWithoutNeedingDisplay)];
+ [_views release];
+ _views = nil;
+
+ _documentView = nil;
+}
+
+- (id)_webPluginContainerCheckIfAllowedToLoadRequest:(NSURLRequest *)request inFrame:(NSString *)target resultObject:(id)obj selector:(SEL)selector
+{
+ WebPluginContainerCheck *check = [WebPluginContainerCheck checkWithRequest:request target:target resultObject:obj selector:selector controller:self];
+ [_checksInProgress addObject:check];
+ [check start];
+
+ return check;
+}
+
+- (void)webPlugInContainerLoadRequest:(NSURLRequest *)request inFrame:(NSString *)target
+{
+ if (!request) {
+ LOG_ERROR("nil URL passed");
+ return;
+ }
+ if (!_documentView) {
+ LOG_ERROR("could not load URL %@ because plug-in has already been destroyed", request);
+ return;
+ }
+ WebFrame *frame = [_dataSource webFrame];
+ if (!frame) {
+ LOG_ERROR("could not load URL %@ because plug-in has already been stopped", request);
+ return;
+ }
+ if (!target) {
+ target = @"_top";
+ }
+ NSString *JSString = [[request URL] _webkit_scriptIfJavaScriptURL];
+ if (JSString) {
+ if ([frame findFrameNamed:target] != frame) {
+ LOG_ERROR("JavaScript requests can only be made on the frame that contains the plug-in");
+ return;
+ }
+ [[frame _bridge] stringByEvaluatingJavaScriptFromString:JSString];
+ } else {
+ if (!request) {
+ LOG_ERROR("could not load URL %@", [request URL]);
+ return;
+ }
+ [frame _frameLoader]->load(request, target);
+ }
+}
+
+// For compatibility only.
+- (void)showURL:(NSURL *)URL inFrame:(NSString *)target
+{
+ [self webPlugInContainerLoadRequest:[NSURLRequest requestWithURL:URL] inFrame:target];
+}
+
+- (void)webPlugInContainerShowStatus:(NSString *)message
+{
+ if (!message) {
+ message = @"";
+ }
+ if (!_documentView) {
+ LOG_ERROR("could not show status message (%@) because plug-in has already been destroyed", message);
+ return;
+ }
+ WebView *v = [_dataSource _webView];
+ [[v _UIDelegateForwarder] webView:v setStatusText:message];
+}
+
+// For compatibility only.
+- (void)showStatus:(NSString *)message
+{
+ [self webPlugInContainerShowStatus:message];
+}
+
+- (NSColor *)webPlugInContainerSelectionColor
+{
+ bool primary = true;
+ if (Frame* frame = core([self webFrame]))
+ primary = frame->selectionController()->isFocusedAndActive();
+ return primary ? [NSColor selectedTextBackgroundColor] : [NSColor secondarySelectedControlColor];
+}
+
+// For compatibility only.
+- (NSColor *)selectionColor
+{
+ return [self webPlugInContainerSelectionColor];
+}
+
+- (WebFrame *)webFrame
+{
+ return [_dataSource webFrame];
+}
+
+- (WebFrameBridge *)bridge
+{
+ return [[self webFrame] _bridge];
+}
+
+- (WebView *)webView
+{
+ return [[self webFrame] webView];
+}
+
+- (NSString *)URLPolicyCheckReferrer
+{
+ NSURL *responseURL = [[[[self webFrame] _dataSource] response] URL];
+ ASSERT(responseURL);
+ return [responseURL _web_originalDataAsString];
+}
+
+- (void)pluginView:(NSView *)pluginView receivedResponse:(NSURLResponse *)response
+{
+ if ([pluginView respondsToSelector:@selector(webPlugInMainResourceDidReceiveResponse:)])
+ [pluginView webPlugInMainResourceDidReceiveResponse:response];
+ else {
+ // Cancel the load since this plug-in does its own loading.
+ // FIXME: See <rdar://problem/4258008> for a problem with this.
+ NSError *error = [[NSError alloc] _initWithPluginErrorCode:WebKitErrorPlugInWillHandleLoad
+ contentURL:[response URL]
+ pluginPageURL:nil
+ pluginName:nil // FIXME: Get this from somewhere
+ MIMEType:[response MIMEType]];
+ [_dataSource _documentLoader]->cancelMainResourceLoad(error);
+ [error release];
+ }
+}
+
+- (void)pluginView:(NSView *)pluginView receivedData:(NSData *)data
+{
+ if ([pluginView respondsToSelector:@selector(webPlugInMainResourceDidReceiveData:)])
+ [pluginView webPlugInMainResourceDidReceiveData:data];
+}
+
+- (void)pluginView:(NSView *)pluginView receivedError:(NSError *)error
+{
+ if ([pluginView respondsToSelector:@selector(webPlugInMainResourceDidFailWithError:)])
+ [pluginView webPlugInMainResourceDidFailWithError:error];
+}
+
+- (void)pluginViewFinishedLoading:(NSView *)pluginView
+{
+ if ([pluginView respondsToSelector:@selector(webPlugInMainResourceDidFinishLoading)])
+ [pluginView webPlugInMainResourceDidFinishLoading];
+}
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginDatabase.h b/WebKit/mac/Plugins/WebPluginDatabase.h
new file mode 100644
index 0000000..edc6a46
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginDatabase.h
@@ -0,0 +1,63 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@class WebBasePluginPackage;
+
+@interface WebPluginDatabase : NSObject
+{
+ NSMutableDictionary *plugins;
+ NSMutableSet *registeredMIMETypes;
+ NSArray *plugInPaths;
+}
+
++ (WebPluginDatabase *)sharedDatabase;
++ (void)closeSharedDatabase; // avoids creating the database just to close it
+
+// Plug-ins are returned in this order: New plug-in (WBPL), Mach-O Netscape, CFM Netscape
+- (WebBasePluginPackage *)pluginForMIMEType:(NSString *)mimeType;
+- (WebBasePluginPackage *)pluginForExtension:(NSString *)extension;
+
+- (BOOL)isMIMETypeRegistered:(NSString *)MIMEType;
+
+- (NSArray *)plugins;
+
+- (void)refresh;
+
+- (void)setPlugInPaths:(NSArray *)newPaths;
+
+- (void)close;
+
+@end
+
+@interface NSObject (WebPlugInDatabase)
+
++ (void)setAdditionalWebPlugInPaths:(NSArray *)path;
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginDatabase.m b/WebKit/mac/Plugins/WebPluginDatabase.m
new file mode 100644
index 0000000..e799443
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginDatabase.m
@@ -0,0 +1,398 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebPluginDatabase.h>
+
+#import <JavaScriptCore/Assertions.h>
+#import <WebKit/WebBasePluginPackage.h>
+#import <WebKit/WebDataSourcePrivate.h>
+#import <WebKit/WebFrame.h>
+#import <WebKit/WebFrameViewInternal.h>
+#import <WebKit/WebHTMLRepresentation.h>
+#import <WebKit/WebHTMLView.h>
+#import <WebKit/WebKitLogging.h>
+#import <WebKit/WebNetscapePluginPackage.h>
+#import <WebKit/WebPluginPackage.h>
+#import <WebKit/WebViewPrivate.h>
+#import <WebKitSystemInterface.h>
+
+static void checkCandidate(WebBasePluginPackage **currentPlugin, WebBasePluginPackage **candidatePlugin);
+
+@interface WebPluginDatabase (Internal)
++ (NSArray *)_defaultPlugInPaths;
+- (NSArray *)_plugInPaths;
+- (void)_addPlugin:(WebBasePluginPackage *)plugin;
+- (void)_removePlugin:(WebBasePluginPackage *)plugin;
+- (NSMutableSet *)_scanForNewPlugins;
+@end
+
+@implementation WebPluginDatabase
+
+static WebPluginDatabase *sharedDatabase = nil;
+
++ (WebPluginDatabase *)sharedDatabase
+{
+ if (!sharedDatabase) {
+ sharedDatabase = [[WebPluginDatabase alloc] init];
+ [sharedDatabase setPlugInPaths:[self _defaultPlugInPaths]];
+ [sharedDatabase refresh];
+ }
+
+ return sharedDatabase;
+}
+
++ (void)closeSharedDatabase
+{
+ [sharedDatabase close];
+}
+
+static void checkCandidate(WebBasePluginPackage **currentPlugin, WebBasePluginPackage **candidatePlugin)
+{
+ if (!*currentPlugin) {
+ *currentPlugin = *candidatePlugin;
+ return;
+ }
+
+ if ([[[*currentPlugin bundle] bundleIdentifier] isEqualToString:[[*candidatePlugin bundle] bundleIdentifier]] && [*candidatePlugin versionNumber] > [*currentPlugin versionNumber])
+ *currentPlugin = *candidatePlugin;
+}
+
+- (WebBasePluginPackage *)pluginForKey:(NSString *)key withEnumeratorSelector:(SEL)enumeratorSelector
+{
+ WebBasePluginPackage *plugin = nil;
+ WebBasePluginPackage *webPlugin = nil;
+#ifndef __LP64__
+ WebBasePluginPackage *CFMPlugin = nil;
+ WebBasePluginPackage *machoPlugin = nil;
+#endif
+
+ NSEnumerator *pluginEnumerator = [plugins objectEnumerator];
+ key = [key lowercaseString];
+
+ while ((plugin = [pluginEnumerator nextObject]) != nil) {
+ if ([[[plugin performSelector:enumeratorSelector] allObjects] containsObject:key]) {
+ if ([plugin isKindOfClass:[WebPluginPackage class]])
+ checkCandidate(&webPlugin, &plugin);
+#ifndef __LP64__
+ else if([plugin isKindOfClass:[WebNetscapePluginPackage class]]) {
+ WebExecutableType executableType = [(WebNetscapePluginPackage *)plugin executableType];
+ if (executableType == WebCFMExecutableType) {
+ checkCandidate(&CFMPlugin, &plugin);
+ } else if (executableType == WebMachOExecutableType) {
+ checkCandidate(&machoPlugin, &plugin);
+ } else {
+ ASSERT_NOT_REACHED();
+ }
+ } else {
+ ASSERT_NOT_REACHED();
+ }
+#endif
+ }
+ }
+
+ // Allow other plug-ins to win over QT because if the user has installed a plug-in that can handle a type
+ // that the QT plug-in can handle, they probably intended to override QT.
+ if (webPlugin && ![webPlugin isQuickTimePlugIn])
+ return webPlugin;
+
+#ifndef __LP64__
+ else if (machoPlugin && ![machoPlugin isQuickTimePlugIn])
+ return machoPlugin;
+ else if (CFMPlugin && ![CFMPlugin isQuickTimePlugIn])
+ return CFMPlugin;
+#endif
+ else if (webPlugin)
+ return webPlugin;
+#ifndef __LP64__
+ else if (machoPlugin)
+ return machoPlugin;
+ else if (CFMPlugin)
+ return CFMPlugin;
+#endif
+ return nil;
+}
+
+- (WebBasePluginPackage *)pluginForMIMEType:(NSString *)MIMEType
+{
+ return [self pluginForKey:[MIMEType lowercaseString]
+ withEnumeratorSelector:@selector(MIMETypeEnumerator)];
+}
+
+- (WebBasePluginPackage *)pluginForExtension:(NSString *)extension
+{
+ WebBasePluginPackage *plugin = [self pluginForKey:[extension lowercaseString]
+ withEnumeratorSelector:@selector(extensionEnumerator)];
+ if (!plugin) {
+ // If no plug-in was found from the extension, attempt to map from the extension to a MIME type
+ // and find the a plug-in from the MIME type. This is done in case the plug-in has not fully specified
+ // an extension <-> MIME type mapping.
+ NSString *MIMEType = WKGetMIMETypeForExtension(extension);
+ if ([MIMEType length] > 0)
+ plugin = [self pluginForMIMEType:MIMEType];
+ }
+ return plugin;
+}
+
+- (NSArray *)plugins
+{
+ return [plugins allValues];
+}
+
+static NSArray *additionalWebPlugInPaths;
+
++ (void)setAdditionalWebPlugInPaths:(NSArray *)additionalPaths
+{
+ if (additionalPaths == additionalWebPlugInPaths)
+ return;
+
+ [additionalWebPlugInPaths release];
+ additionalWebPlugInPaths = [additionalPaths copy];
+
+ // One might be tempted to add additionalWebPlugInPaths to the global WebPluginDatabase here.
+ // For backward compatibility with earlier versions of the +setAdditionalWebPlugInPaths: SPI,
+ // we need to save a copy of the additional paths and not cause a refresh of the plugin DB
+ // at this time.
+ // See Radars 4608487 and 4609047.
+}
+
+- (void)setPlugInPaths:(NSArray *)newPaths
+{
+ if (plugInPaths == newPaths)
+ return;
+
+ [plugInPaths release];
+ plugInPaths = [newPaths copy];
+}
+
+- (void)close
+{
+ NSEnumerator *pluginEnumerator = [[self plugins] objectEnumerator];
+ WebBasePluginPackage *plugin;
+ while ((plugin = [pluginEnumerator nextObject]) != nil)
+ [self _removePlugin:plugin];
+ [plugins release];
+ plugins = nil;
+}
+
+- (id)init
+{
+ if (!(self = [super init]))
+ return nil;
+
+ registeredMIMETypes = [[NSMutableSet alloc] init];
+
+ return self;
+}
+
+- (void)dealloc
+{
+ [plugInPaths release];
+ [plugins release];
+ [registeredMIMETypes release];
+
+ [super dealloc];
+}
+
+- (void)refresh
+{
+ // This method does a bit of autoreleasing, so create an autorelease pool to ensure that calling
+ // -refresh multiple times does not bloat the default pool.
+ NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
+
+ // Create map from plug-in path to WebBasePluginPackage
+ if (!plugins)
+ plugins = [[NSMutableDictionary alloc] initWithCapacity:12];
+
+ // Find all plug-ins on disk
+ NSMutableSet *newPlugins = [self _scanForNewPlugins];
+
+ // Find plug-ins to remove from database (i.e., plug-ins that no longer exist on disk)
+ NSMutableSet *pluginsToRemove = [NSMutableSet set];
+ NSEnumerator *pluginEnumerator = [plugins objectEnumerator];
+ WebBasePluginPackage *plugin;
+ while ((plugin = [pluginEnumerator nextObject]) != nil) {
+ // Any plug-ins that were removed from disk since the last refresh should be removed from
+ // the database.
+ if (![newPlugins containsObject:plugin])
+ [pluginsToRemove addObject:plugin];
+
+ // Remove every member of 'plugins' from 'newPlugins'. After this loop exits, 'newPlugins'
+ // will be the set of new plug-ins that should be added to the database.
+ [newPlugins removeObject:plugin];
+ }
+
+#if !LOG_DISABLED
+ if ([newPlugins count] > 0)
+ LOG(Plugins, "New plugins:\n%@", newPlugins);
+ if ([pluginsToRemove count] > 0)
+ LOG(Plugins, "Removed plugins:\n%@", pluginsToRemove);
+#endif
+
+ // Remove plugins from database
+ pluginEnumerator = [pluginsToRemove objectEnumerator];
+ while ((plugin = [pluginEnumerator nextObject]) != nil)
+ [self _removePlugin:plugin];
+
+ // Add new plugins to database
+ pluginEnumerator = [newPlugins objectEnumerator];
+ while ((plugin = [pluginEnumerator nextObject]) != nil)
+ [self _addPlugin:plugin];
+
+ // Build a list of MIME types.
+ NSMutableSet *MIMETypes = [[NSMutableSet alloc] init];
+ pluginEnumerator = [plugins objectEnumerator];
+ while ((plugin = [pluginEnumerator nextObject]) != nil)
+ [MIMETypes addObjectsFromArray:[[plugin MIMETypeEnumerator] allObjects]];
+
+ // Register plug-in views and representations.
+ NSEnumerator *MIMEEnumerator = [MIMETypes objectEnumerator];
+ NSString *MIMEType;
+ while ((MIMEType = [MIMEEnumerator nextObject]) != nil) {
+ [registeredMIMETypes addObject:MIMEType];
+
+ if ([WebView canShowMIMETypeAsHTML:MIMEType])
+ // Don't allow plug-ins to override our core HTML types.
+ continue;
+ plugin = [self pluginForMIMEType:MIMEType];
+ if ([plugin isJavaPlugIn])
+ // Don't register the Java plug-in for a document view since Java files should be downloaded when not embedded.
+ continue;
+ if ([plugin isQuickTimePlugIn] && [[WebFrameView _viewTypesAllowImageTypeOmission:NO] objectForKey:MIMEType])
+ // Don't allow the QT plug-in to override any types because it claims many that we can handle ourselves.
+ continue;
+
+ if (self == sharedDatabase)
+ [WebView registerViewClass:[WebHTMLView class] representationClass:[WebHTMLRepresentation class] forMIMEType:MIMEType];
+ }
+ [MIMETypes release];
+
+ [pool drain];
+}
+
+- (BOOL)isMIMETypeRegistered:(NSString *)MIMEType
+{
+ return [registeredMIMETypes containsObject:MIMEType];
+}
+
+@end
+
+@implementation WebPluginDatabase (Internal)
+
++ (NSArray *)_defaultPlugInPaths
+{
+ // Plug-ins are found in order of precedence.
+ // If there are duplicates, the first found plug-in is used.
+ // For example, if there is a QuickTime.plugin in the users's home directory
+ // that is used instead of the /Library/Internet Plug-ins version.
+ // The purpose is to allow non-admin users to update their plug-ins.
+ return [NSArray arrayWithObjects:
+ [NSHomeDirectory() stringByAppendingPathComponent:@"Library/Internet Plug-Ins"],
+ @"/Library/Internet Plug-Ins",
+ [[NSBundle mainBundle] builtInPlugInsPath],
+ nil];
+}
+
+- (NSArray *)_plugInPaths
+{
+ if (self == sharedDatabase && additionalWebPlugInPaths) {
+ // Add additionalWebPlugInPaths to the global WebPluginDatabase. We do this here for
+ // backward compatibility with earlier versions of the +setAdditionalWebPlugInPaths: SPI,
+ // which simply saved a copy of the additional paths and did not cause the plugin DB to
+ // refresh. See Radars 4608487 and 4609047.
+ NSMutableArray *modifiedPlugInPaths = [[plugInPaths mutableCopy] autorelease];
+ [modifiedPlugInPaths addObjectsFromArray:additionalWebPlugInPaths];
+ return modifiedPlugInPaths;
+ } else
+ return plugInPaths;
+}
+
+- (void)_addPlugin:(WebBasePluginPackage *)plugin
+{
+ ASSERT(plugin);
+ NSString *pluginPath = [plugin path];
+ ASSERT(pluginPath);
+ [plugins setObject:plugin forKey:pluginPath];
+ [plugin wasAddedToPluginDatabase:self];
+}
+
+- (void)_removePlugin:(WebBasePluginPackage *)plugin
+{
+ ASSERT(plugin);
+
+ // Unregister plug-in's MIME type registrations
+ NSEnumerator *MIMETypeEnumerator = [plugin MIMETypeEnumerator];
+ NSString *MIMEType;
+ while ((MIMEType = [MIMETypeEnumerator nextObject])) {
+ if ([registeredMIMETypes containsObject:MIMEType]) {
+ if (self == sharedDatabase)
+ [WebView _unregisterViewClassAndRepresentationClassForMIMEType:MIMEType];
+ [registeredMIMETypes removeObject:MIMEType];
+ }
+ }
+
+ // Remove plug-in from database
+ NSString *pluginPath = [plugin path];
+ ASSERT(pluginPath);
+ [plugin retain];
+ [plugins removeObjectForKey:pluginPath];
+ [plugin wasRemovedFromPluginDatabase:self];
+ [plugin release];
+}
+
+- (NSMutableSet *)_scanForNewPlugins
+{
+ NSMutableSet *newPlugins = [NSMutableSet set];
+ NSEnumerator *directoryEnumerator = [[self _plugInPaths] objectEnumerator];
+ NSMutableSet *uniqueFilenames = [[NSMutableSet alloc] init];
+ NSFileManager *fileManager = [NSFileManager defaultManager];
+ NSString *pluginDirectory;
+ while ((pluginDirectory = [directoryEnumerator nextObject]) != nil) {
+ // Get contents of each plug-in directory
+ NSEnumerator *filenameEnumerator = [[fileManager directoryContentsAtPath:pluginDirectory] objectEnumerator];
+ NSString *filename;
+ while ((filename = [filenameEnumerator nextObject]) != nil) {
+ // Unique plug-ins by filename
+ if ([uniqueFilenames containsObject:filename])
+ continue;
+ [uniqueFilenames addObject:filename];
+
+ // Create a plug-in package for this path
+ NSString *pluginPath = [pluginDirectory stringByAppendingPathComponent:filename];
+ WebBasePluginPackage *pluginPackage = [plugins objectForKey:pluginPath];
+ if (!pluginPackage)
+ pluginPackage = [WebBasePluginPackage pluginWithPath:pluginPath];
+ if (pluginPackage)
+ [newPlugins addObject:pluginPackage];
+ }
+ }
+ [uniqueFilenames release];
+
+ return newPlugins;
+}
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginJava.h b/WebKit/mac/Plugins/WebPluginJava.h
new file mode 100644
index 0000000..8015dba
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginJava.h
@@ -0,0 +1,48 @@
+/*
+ * Copyright (C) 2004 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <JavaVM/JavaVM.h>
+
+// The WebPluginContainer will call these methods for LiveConnect support. The
+// WebPluginContainer should see if the WebPlugin supports these methods before
+// calling them.
+
+@protocol WebPluginJava <NSObject>
+
+// This returns the jobject representing the java applet to the WebPluginContainer.
+// It should always be called from the AppKit Main Thread.
+- (jobject) getApplet;
+
+// This will call the given method on the given jobject with the given arguments
+// from the proper thread for this WebPlugin. This way, no java applet code will
+// be run on the AppKit Main Thread, it will be called on a thread belonging to the
+// java applet.
+// It should always be called from the AppKit Main Thread.
+- (jvalue) callJavaOn:(jobject)object withMethod:(jmethodID) withArgs:(jvalue*)args;
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginPackage.h b/WebKit/mac/Plugins/WebPluginPackage.h
new file mode 100644
index 0000000..290bb1b
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginPackage.h
@@ -0,0 +1,39 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+#import <WebKit/WebBasePluginPackage.h>
+
+@protocol WebPluginViewFactory;
+
+@interface WebPluginPackage : WebBasePluginPackage
+
+- (Class)viewFactory;
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginPackage.m b/WebKit/mac/Plugins/WebPluginPackage.m
new file mode 100644
index 0000000..d7f144e
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginPackage.m
@@ -0,0 +1,116 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebPluginPackage.h>
+
+#import <WebKit/WebKitLogging.h>
+#import <WebKit/WebKitNSStringExtras.h>
+
+NSString *WebPlugInBaseURLKey = @"WebPlugInBaseURLKey";
+NSString *WebPlugInAttributesKey = @"WebPlugInAttributesKey";
+NSString *WebPlugInContainerKey = @"WebPlugInContainerKey";
+NSString *WebPlugInModeKey = @"WebPlugInModeKey";
+NSString *WebPlugInShouldLoadMainResourceKey = @"WebPlugInShouldLoadMainResourceKey";
+NSString *WebPlugInContainingElementKey = @"WebPlugInContainingElementKey";
+
+@implementation WebPluginPackage
+
+- initWithPath:(NSString *)pluginPath
+{
+ if (!(self = [super initWithPath:pluginPath]))
+ return nil;
+
+ if (bundle == nil) {
+ [self release];
+ return nil;
+ }
+
+ if (![[pluginPath pathExtension] _webkit_isCaseInsensitiveEqualToString:@"webplugin"]) {
+ UInt32 type = 0;
+ CFBundleGetPackageInfo(cfBundle, &type, NULL);
+ if (type != FOUR_CHAR_CODE('WBPL')) {
+ [self release];
+ return nil;
+ }
+ }
+
+ NSFileHandle *executableFile = [NSFileHandle fileHandleForReadingAtPath:[bundle executablePath]];
+ NSData *data = [executableFile readDataOfLength:512];
+ [executableFile closeFile];
+ if (![self isNativeLibraryData:data]) {
+ [self release];
+ return nil;
+ }
+
+ if (![self getPluginInfoFromPLists]) {
+ [self release];
+ return nil;
+ }
+
+ return self;
+}
+
+- (Class)viewFactory
+{
+ return [bundle principalClass];
+}
+
+- (BOOL)load
+{
+#if !LOG_DISABLED
+ CFAbsoluteTime start = CFAbsoluteTimeGetCurrent();
+#endif
+
+ // Load the bundle
+ if (![bundle isLoaded]) {
+ if (![bundle load])
+ return NO;
+ }
+
+#if !LOG_DISABLED
+ CFAbsoluteTime duration = CFAbsoluteTimeGetCurrent() - start;
+ LOG(Plugins, "principalClass took %f seconds for: %@", duration, [self name]);
+#endif
+ return [super load];
+}
+
+@end
+
+@implementation NSObject (WebScripting)
+
++ (BOOL)isSelectorExcludedFromWebScript:(SEL)aSelector
+{
+ return YES;
+}
+
++ (BOOL)isKeyExcludedFromWebScript:(const char *)name
+{
+ return YES;
+}
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginPrivate.h b/WebKit/mac/Plugins/WebPluginPrivate.h
new file mode 100644
index 0000000..e79efc2
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginPrivate.h
@@ -0,0 +1,75 @@
+/*
+ * Copyright (C) 2004 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+/*
+ Private extensions to the WebPlugin interface. A plugin may implement these methods
+ to receive loading callbacks for its main resource. Plug-ins that implement this SPI
+ show better loading progress in the browser, can be saved to disk, and are
+ more efficient by avoiding making duplicate GET or POST requests for the plug-in's main
+ resource.
+*/
+
+@interface NSObject (WebPlugInPrivate)
+
+/*!
+ @method webPlugInMainResourceDidReceiveResponse:
+ @abstract Called on the plug-in when WebKit receives -connection:didReceiveResponse:
+ for the plug-in's main resource.
+ @discussion This method is only sent to the plug-in if the
+ WebPlugInShouldLoadMainResourceKey argument passed to the plug-in was NO.
+*/
+- (void)webPlugInMainResourceDidReceiveResponse:(NSURLResponse *)response;
+
+/*!
+ @method webPlugInMainResourceDidReceiveData:
+ @abstract Called on the plug-in when WebKit recieves -connection:didReceiveData:
+ for the plug-in's main resource.
+ @discussion This method is only sent to the plug-in if the
+ WebPlugInShouldLoadMainResourceKey argument passed to the plug-in was NO.
+*/
+- (void)webPlugInMainResourceDidReceiveData:(NSData *)data;
+
+/*!
+ @method webPlugInMainResourceDidFailWithError:
+ @abstract Called on the plug-in when WebKit receives -connection:didFailWithError:
+ for the plug-in's main resource.
+ @discussion This method is only sent to the plug-in if the
+ WebPlugInShouldLoadMainResourceKey argument passed to the plug-in was NO.
+*/
+- (void)webPlugInMainResourceDidFailWithError:(NSError *)error;
+
+/*!
+ @method webPlugInMainResourceDidFinishLoading
+ @abstract Called on the plug-in when WebKit receives -connectionDidFinishLoading:
+ for the plug-in's main resource.
+ @discussion This method is only sent to the plug-in if the
+ WebPlugInShouldLoadMainResourceKey argument passed to the plug-in was NO.
+*/
+- (void)webPlugInMainResourceDidFinishLoading;
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginViewFactory.h b/WebKit/mac/Plugins/WebPluginViewFactory.h
new file mode 100644
index 0000000..565168c
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginViewFactory.h
@@ -0,0 +1,76 @@
+/*
+ * Copyright (C) 2004 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+/*!
+ @constant WebPlugInBaseURLKey REQUIRED. The base URL of the document containing
+ the plug-in's view.
+*/
+extern NSString *WebPlugInBaseURLKey;
+
+/*!
+ @constant WebPlugInAttributesKey REQUIRED. The dictionary containing the names
+ and values of all attributes of the HTML element associated with the plug-in AND
+ the names and values of all parameters to be passed to the plug-in (e.g. PARAM
+ elements within an APPLET element). In the case of a conflict between names,
+ the attributes of an element take precedence over any PARAMs. All of the keys
+ and values in this NSDictionary must be NSStrings.
+*/
+extern NSString *WebPlugInAttributesKey;
+
+/*!
+ @constant WebPlugInContainer OPTIONAL. An object that conforms to the
+ WebPlugInContainer informal protocol. This object is used for
+ callbacks from the plug-in to the app. if this argument is nil, no callbacks will
+ occur.
+*/
+extern NSString *WebPlugInContainerKey;
+
+/*!
+ @constant WebPlugInContainingElementKey The DOMElement that was used to specify
+ the plug-in. May be nil.
+*/
+extern NSString *WebPlugInContainingElementKey;
+
+/*!
+ @protocol WebPlugInViewFactory
+ @discussion WebPlugInViewFactory are used to create the NSView for a plug-in.
+ The principal class of the plug-in bundle must implement this protocol.
+*/
+
+@protocol WebPlugInViewFactory <NSObject>
+
+/*!
+ @method plugInViewWithArguments:
+ @param arguments The arguments dictionary with the mentioned keys and objects. This method is required to implement.
+ @result Returns an NSView object that conforms to the WebPlugIn informal protocol.
+*/
++ (NSView *)plugInViewWithArguments:(NSDictionary *)arguments;
+
+@end
diff --git a/WebKit/mac/Plugins/WebPluginViewFactoryPrivate.h b/WebKit/mac/Plugins/WebPluginViewFactoryPrivate.h
new file mode 100644
index 0000000..b7b7302
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginViewFactoryPrivate.h
@@ -0,0 +1,48 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebPluginViewFactory.h>
+
+typedef enum {
+ WebPlugInModeEmbed = 0,
+ WebPlugInModeFull = 1
+} WebPlugInMode;
+
+/*!
+ @constant WebPlugInModeKey REQUIRED. Number with one of the values from the WebPlugInMode enum.
+*/
+extern NSString *WebPlugInModeKey;
+
+/*!
+ @constant WebPlugInShouldLoadMainResourceKey REQUIRED. NSNumber (BOOL) indicating whether the plug-in should load its
+ own main resource (the "src" URL, in most cases). If YES, the plug-in should load its own main resource. If NO, the
+ plug-in should use the data provided by WebKit. See -webPlugInMainResourceReceivedData: in WebPluginPrivate.h.
+ For compatibility with older versions of WebKit, the plug-in should assume that the value for
+ WebPlugInShouldLoadMainResourceKey is NO if it is absent from the arguments dictionary.
+*/
+extern NSString *WebPlugInShouldLoadMainResourceKey;
diff --git a/WebKit/mac/Plugins/WebPluginsPrivate.h b/WebKit/mac/Plugins/WebPluginsPrivate.h
new file mode 100644
index 0000000..fc0067d
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginsPrivate.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// WebPluginWillPresentNativeUserInterfaceNotification is sent by plugins to notify the WebKit client
+// application that the plugin will present a dialog or some other "native" user interface to the user.
+// This is currently only needed by Dashboard, which must hide itself when a plugin presents a dialog
+// box (4318632).
+extern NSString *WebPluginWillPresentNativeUserInterfaceNotification;
diff --git a/WebKit/mac/Plugins/WebPluginsPrivate.m b/WebKit/mac/Plugins/WebPluginsPrivate.m
new file mode 100644
index 0000000..79896b6
--- /dev/null
+++ b/WebKit/mac/Plugins/WebPluginsPrivate.m
@@ -0,0 +1,31 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "WebPluginsPrivate.h"
+
+NSString *WebPluginWillPresentNativeUserInterfaceNotification = @"WebPluginWillPresentNativeUserInterface";
diff --git a/WebKit/mac/Plugins/npapi.m b/WebKit/mac/Plugins/npapi.m
new file mode 100644
index 0000000..0a630a6
--- /dev/null
+++ b/WebKit/mac/Plugins/npapi.m
@@ -0,0 +1,171 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+#ifndef __LP64__
+#import <WebKit/npapi.h>
+
+#import <WebKit/WebBaseNetscapePluginViewPrivate.h>
+#import <WebKit/WebKitLogging.h>
+
+WebBaseNetscapePluginView *pluginViewForInstance(NPP instance);
+
+// general plug-in to browser functions
+
+void* NPN_MemAlloc(uint32 size)
+{
+ return malloc(size);
+}
+
+void NPN_MemFree(void* ptr)
+{
+ free(ptr);
+}
+
+uint32 NPN_MemFlush(uint32 size)
+{
+ LOG(Plugins, "NPN_MemFlush");
+ return size;
+}
+
+void NPN_ReloadPlugins(NPBool reloadPages)
+{
+ LOG(Plugins, "NPN_ReloadPlugins");
+}
+
+NPError NPN_RequestRead(NPStream* stream, NPByteRange* rangeList)
+{
+ LOG(Plugins, "NPN_RequestRead");
+ return NPERR_GENERIC_ERROR;
+}
+
+// instance-specific functions
+// The plugin view is always the ndata of the instance. Sometimes, plug-ins will call an instance-specific function
+// with a NULL instance. To workaround this, call the last plug-in view that made a call to a plug-in.
+// Currently, the current plug-in view is only set before NPP_New in [WebBaseNetscapePluginView start].
+// This specifically works around Flash and Shockwave. When we call NPP_New, they call NPN_UserAgent with a NULL instance.
+WebBaseNetscapePluginView *pluginViewForInstance(NPP instance)
+{
+ if (instance && instance->ndata)
+ return (WebBaseNetscapePluginView *)instance->ndata;
+ else
+ return [WebBaseNetscapePluginView currentPluginView];
+}
+
+NPError NPN_GetURLNotify(NPP instance, const char* URL, const char* target, void* notifyData)
+{
+ return [pluginViewForInstance(instance) getURLNotify:URL target:target notifyData:notifyData];
+}
+
+NPError NPN_GetURL(NPP instance, const char* URL, const char* target)
+{
+ return [pluginViewForInstance(instance) getURL:URL target:target];
+}
+
+NPError NPN_PostURLNotify(NPP instance, const char* URL, const char* target, uint32 len, const char* buf, NPBool file, void* notifyData)
+{
+ return [pluginViewForInstance(instance) postURLNotify:URL target:target len:len buf:buf file:file notifyData:notifyData];
+}
+
+NPError NPN_PostURL(NPP instance, const char* URL, const char* target, uint32 len, const char* buf, NPBool file)
+{
+ return [pluginViewForInstance(instance) postURL:URL target:target len:len buf:buf file:file];
+}
+
+NPError NPN_NewStream(NPP instance, NPMIMEType type, const char* target, NPStream** stream)
+{
+ return [pluginViewForInstance(instance) newStream:type target:target stream:stream];
+}
+
+int32 NPN_Write(NPP instance, NPStream* stream, int32 len, void* buffer)
+{
+ return [pluginViewForInstance(instance) write:stream len:len buffer:buffer];
+}
+
+NPError NPN_DestroyStream(NPP instance, NPStream* stream, NPReason reason)
+{
+ return [pluginViewForInstance(instance) destroyStream:stream reason:reason];
+}
+
+const char* NPN_UserAgent(NPP instance)
+{
+ return [pluginViewForInstance(instance) userAgent];
+}
+
+void NPN_Status(NPP instance, const char* message)
+{
+ [pluginViewForInstance(instance) status:message];
+}
+
+void NPN_InvalidateRect(NPP instance, NPRect *invalidRect)
+{
+ [pluginViewForInstance(instance) invalidateRect:invalidRect];
+}
+
+void NPN_InvalidateRegion(NPP instance, NPRegion invalidRegion)
+{
+ [pluginViewForInstance(instance) invalidateRegion:invalidRegion];
+}
+
+void NPN_ForceRedraw(NPP instance)
+{
+ [pluginViewForInstance(instance) forceRedraw];
+}
+
+NPError NPN_GetValue(NPP instance, NPNVariable variable, void *value)
+{
+ return [pluginViewForInstance(instance) getVariable:variable value:value];
+}
+
+NPError NPN_SetValue(NPP instance, NPPVariable variable, void *value)
+{
+ return [pluginViewForInstance(instance) setVariable:variable value:value];
+}
+
+// Unsupported functions
+
+void* NPN_GetJavaEnv(void)
+{
+ LOG(Plugins, "NPN_GetJavaEnv");
+ return NULL;
+}
+
+void* NPN_GetJavaPeer(NPP instance)
+{
+ LOG(Plugins, "NPN_GetJavaPeer");
+ return NULL;
+}
+
+void
+NPN_PushPopupsEnabledState(NPP instance, NPBool enabled)
+{
+}
+
+void
+NPN_PopPopupsEnabledState(NPP instance)
+{
+}
+#endif
diff --git a/WebKit/mac/Plugins/npfunctions.h b/WebKit/mac/Plugins/npfunctions.h
new file mode 100644
index 0000000..60d6cad
--- /dev/null
+++ b/WebKit/mac/Plugins/npfunctions.h
@@ -0,0 +1,161 @@
+#ifndef NPFUNCTIONS_H
+#define NPFUNCTIONS_H
+
+#include <WebKit/npruntime.h>
+#include <WebKit/npapi.h>
+
+#if defined(XP_MACOSX) && defined(__LP64__)
+#error 64-bit Netscape plug-ins are not supported on Mac OS X
+#endif
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+typedef NPError (*NPN_GetURLNotifyProcPtr)(NPP instance, const char* URL, const char* window, void* notifyData);
+typedef NPError (*NPN_PostURLNotifyProcPtr)(NPP instance, const char* URL, const char* window, uint32 len, const char* buf, NPBool file, void* notifyData);
+typedef NPError (*NPN_RequestReadProcPtr)(NPStream* stream, NPByteRange* rangeList);
+typedef NPError (*NPN_NewStreamProcPtr)(NPP instance, NPMIMEType type, const char* window, NPStream** stream);
+typedef int32 (*NPN_WriteProcPtr)(NPP instance, NPStream* stream, int32 len, void* buffer);
+typedef NPError (*NPN_DestroyStreamProcPtr)(NPP instance, NPStream* stream, NPReason reason);
+typedef void (*NPN_StatusProcPtr)(NPP instance, const char* message);
+typedef const char*(*NPN_UserAgentProcPtr)(NPP instance);
+typedef void* (*NPN_MemAllocProcPtr)(uint32 size);
+typedef void (*NPN_MemFreeProcPtr)(void* ptr);
+typedef uint32 (*NPN_MemFlushProcPtr)(uint32 size);
+typedef void (*NPN_ReloadPluginsProcPtr)(NPBool reloadPages);
+typedef NPError (*NPN_GetValueProcPtr)(NPP instance, NPNVariable variable, void *ret_value);
+typedef NPError (*NPN_SetValueProcPtr)(NPP instance, NPPVariable variable, void *value);
+typedef void (*NPN_InvalidateRectProcPtr)(NPP instance, NPRect *rect);
+typedef void (*NPN_InvalidateRegionProcPtr)(NPP instance, NPRegion region);
+typedef void (*NPN_ForceRedrawProcPtr)(NPP instance);
+typedef NPError (*NPN_GetURLProcPtr)(NPP instance, const char* URL, const char* window);
+typedef NPError (*NPN_PostURLProcPtr)(NPP instance, const char* URL, const char* window, uint32 len, const char* buf, NPBool file);
+typedef void* (*NPN_GetJavaEnvProcPtr)(void);
+typedef void* (*NPN_GetJavaPeerProcPtr)(NPP instance);
+typedef void (*NPN_PushPopupsEnabledStateProcPtr)(NPP instance, NPBool enabled);
+typedef void (*NPN_PopPopupsEnabledStateProcPtr)(NPP instance);
+
+
+typedef void (*NPN_ReleaseVariantValueProcPtr) (NPVariant *variant);
+
+typedef NPIdentifier (*NPN_GetStringIdentifierProcPtr) (const NPUTF8 *name);
+typedef void (*NPN_GetStringIdentifiersProcPtr) (const NPUTF8 **names, int32_t nameCount, NPIdentifier *identifiers);
+typedef NPIdentifier (*NPN_GetIntIdentifierProcPtr) (int32_t intid);
+typedef int32_t (*NPN_IntFromIdentifierProcPtr) (NPIdentifier identifier);
+typedef bool (*NPN_IdentifierIsStringProcPtr) (NPIdentifier identifier);
+typedef NPUTF8 *(*NPN_UTF8FromIdentifierProcPtr) (NPIdentifier identifier);
+
+typedef NPObject* (*NPN_CreateObjectProcPtr) (NPP, NPClass *aClass);
+typedef NPObject* (*NPN_RetainObjectProcPtr) (NPObject *obj);
+typedef void (*NPN_ReleaseObjectProcPtr) (NPObject *obj);
+typedef bool (*NPN_InvokeProcPtr) (NPP npp, NPObject *obj, NPIdentifier methodName, const NPVariant *args, unsigned argCount, NPVariant *result);
+typedef bool (*NPN_InvokeDefaultProcPtr) (NPP npp, NPObject *obj, const NPVariant *args, unsigned argCount, NPVariant *result);
+typedef bool (*NPN_EvaluateProcPtr) (NPP npp, NPObject *obj, NPString *script, NPVariant *result);
+typedef bool (*NPN_GetPropertyProcPtr) (NPP npp, NPObject *obj, NPIdentifier propertyName, NPVariant *result);
+typedef bool (*NPN_SetPropertyProcPtr) (NPP npp, NPObject *obj, NPIdentifier propertyName, const NPVariant *value);
+typedef bool (*NPN_HasPropertyProcPtr) (NPP, NPObject *npobj, NPIdentifier propertyName);
+typedef bool (*NPN_HasMethodProcPtr) (NPP npp, NPObject *npobj, NPIdentifier methodName);
+typedef bool (*NPN_RemovePropertyProcPtr) (NPP npp, NPObject *obj, NPIdentifier propertyName);
+typedef void (*NPN_SetExceptionProcPtr) (NPObject *obj, const NPUTF8 *message);
+typedef bool (*NPN_EnumerateProcPtr) (NPP npp, NPObject *npobj, NPIdentifier **identifier, uint32_t *count);
+
+typedef NPError (*NPP_NewProcPtr)(NPMIMEType pluginType, NPP instance, uint16 mode, int16 argc, char* argn[], char* argv[], NPSavedData* saved);
+typedef NPError (*NPP_DestroyProcPtr)(NPP instance, NPSavedData** save);
+typedef NPError (*NPP_SetWindowProcPtr)(NPP instance, NPWindow* window);
+typedef NPError (*NPP_NewStreamProcPtr)(NPP instance, NPMIMEType type, NPStream* stream, NPBool seekable, uint16* stype);
+typedef NPError (*NPP_DestroyStreamProcPtr)(NPP instance, NPStream* stream, NPReason reason);
+typedef void (*NPP_StreamAsFileProcPtr)(NPP instance, NPStream* stream, const char* fname);
+typedef int32 (*NPP_WriteReadyProcPtr)(NPP instance, NPStream* stream);
+typedef int32 (*NPP_WriteProcPtr)(NPP instance, NPStream* stream, int32_t offset, int32_t len, void* buffer);
+typedef void (*NPP_PrintProcPtr)(NPP instance, NPPrint* platformPrint);
+typedef int16 (*NPP_HandleEventProcPtr)(NPP instance, void* event);
+typedef void (*NPP_URLNotifyProcPtr)(NPP instance, const char* URL, NPReason reason, void* notifyData);
+typedef NPError (*NPP_GetValueProcPtr)(NPP instance, NPPVariable variable, void *ret_value);
+typedef NPError (*NPP_SetValueProcPtr)(NPP instance, NPNVariable variable, void *value);
+typedef void (*NPP_ShutdownProcPtr)(void);
+
+typedef void *(*NPP_GetJavaClassProcPtr)(void);
+typedef void* JRIGlobalRef; //not using this right now
+
+typedef struct _NPNetscapeFuncs {
+ uint16 size;
+ uint16 version;
+
+ NPN_GetURLProcPtr geturl;
+ NPN_PostURLProcPtr posturl;
+ NPN_RequestReadProcPtr requestread;
+ NPN_NewStreamProcPtr newstream;
+ NPN_WriteProcPtr write;
+ NPN_DestroyStreamProcPtr destroystream;
+ NPN_StatusProcPtr status;
+ NPN_UserAgentProcPtr uagent;
+ NPN_MemAllocProcPtr memalloc;
+ NPN_MemFreeProcPtr memfree;
+ NPN_MemFlushProcPtr memflush;
+ NPN_ReloadPluginsProcPtr reloadplugins;
+ NPN_GetJavaEnvProcPtr getJavaEnv;
+ NPN_GetJavaPeerProcPtr getJavaPeer;
+ NPN_GetURLNotifyProcPtr geturlnotify;
+ NPN_PostURLNotifyProcPtr posturlnotify;
+ NPN_GetValueProcPtr getvalue;
+ NPN_SetValueProcPtr setvalue;
+ NPN_InvalidateRectProcPtr invalidaterect;
+ NPN_InvalidateRegionProcPtr invalidateregion;
+ NPN_ForceRedrawProcPtr forceredraw;
+
+ NPN_GetStringIdentifierProcPtr getstringidentifier;
+ NPN_GetStringIdentifiersProcPtr getstringidentifiers;
+ NPN_GetIntIdentifierProcPtr getintidentifier;
+ NPN_IdentifierIsStringProcPtr identifierisstring;
+ NPN_UTF8FromIdentifierProcPtr utf8fromidentifier;
+ NPN_IntFromIdentifierProcPtr intfromidentifier;
+ NPN_CreateObjectProcPtr createobject;
+ NPN_RetainObjectProcPtr retainobject;
+ NPN_ReleaseObjectProcPtr releaseobject;
+ NPN_InvokeProcPtr invoke;
+ NPN_InvokeDefaultProcPtr invokeDefault;
+ NPN_EvaluateProcPtr evaluate;
+ NPN_GetPropertyProcPtr getproperty;
+ NPN_SetPropertyProcPtr setproperty;
+ NPN_RemovePropertyProcPtr removeproperty;
+ NPN_HasPropertyProcPtr hasproperty;
+ NPN_HasMethodProcPtr hasmethod;
+ NPN_ReleaseVariantValueProcPtr releasevariantvalue;
+ NPN_SetExceptionProcPtr setexception;
+ NPN_PushPopupsEnabledStateProcPtr pushpopupsenabledstate;
+ NPN_PopPopupsEnabledStateProcPtr poppopupsenabledstate;
+ NPN_EnumerateProcPtr enumerate;
+} NPNetscapeFuncs;
+
+typedef struct _NPPluginFuncs {
+ uint16 size;
+ uint16 version;
+ NPP_NewProcPtr newp;
+ NPP_DestroyProcPtr destroy;
+ NPP_SetWindowProcPtr setwindow;
+ NPP_NewStreamProcPtr newstream;
+ NPP_DestroyStreamProcPtr destroystream;
+ NPP_StreamAsFileProcPtr asfile;
+ NPP_WriteReadyProcPtr writeready;
+ NPP_WriteProcPtr write;
+ NPP_PrintProcPtr print;
+ NPP_HandleEventProcPtr event;
+ NPP_URLNotifyProcPtr urlnotify;
+ JRIGlobalRef javaClass;
+ NPP_GetValueProcPtr getvalue;
+ NPP_SetValueProcPtr setvalue;
+} NPPluginFuncs;
+
+#if defined(XP_MACOSX)
+typedef NPError (*NP_InitializeFuncPtr)(NPNetscapeFuncs*);
+typedef NPError (*NP_GetEntryPointsFuncPtr)(NPPluginFuncs*);
+typedef void (*BP_CreatePluginMIMETypesPreferencesFuncPtr)(void);
+typedef NPError (*MainFuncPtr)(NPNetscapeFuncs*, NPPluginFuncs*, NPP_ShutdownProcPtr*);
+#endif
+
+#ifdef __cplusplus
+}
+#endif
+
+#endif
diff --git a/WebKit/mac/PublicHeaderChangesFromTiger.txt b/WebKit/mac/PublicHeaderChangesFromTiger.txt
new file mode 100644
index 0000000..f8cb96a
--- /dev/null
+++ b/WebKit/mac/PublicHeaderChangesFromTiger.txt
@@ -0,0 +1,32 @@
+This file lists changes to WebKit public header files that have been made since WebKit-412, which shipped with Mac OS X 10.4. All of these changes will have to be approved by the Apple API approval process, or rolled out, before Apple ships a new version of WebKit.
+
+When you make changes to public header files, please update this file, in the same general style as the ChangeLog file (new entries at top).
+===============================================
+
+2005-08-01 John Sullivan <sullivan@apple.com>
+
+Removed -[DOMHTMLInputElement isTextField] from DOMExtensions.h. I changed it to _isTextField and put it in
+DOMPrivate.h instead, until we decide what we want to do about the public API.
+
+2005-07-22 John Sullivan <sullivan@apple.com>
+
+Added -[DOMHTMLInputElement isTextField] to DOMExtensions.h (in WebCore, copied by build steps to WebKit).
+This is used by autocomplete code in Safari and could be moved there, but is a better fit in WebKit and
+is useful for developers.
+
+2005-06-22 John Sullivan <sullivan@apple.com>
+
+Added the following values to the enum of WebMenuItem tags in WebUIDelegate.h:
+
+ WebMenuItemTagOpenWithDefaultApplication,
+ WebMenuItemPDFActualSize,
+ WebMenuItemPDFZoomIn,
+ WebMenuItemPDFZoomOut,
+ WebMenuItemPDFAutoSize,
+ WebMenuItemPDFSinglePage,
+ WebMenuItemPDFFacingPages,
+ WebMenuItemPDFContinuous,
+ WebMenuItemPDFNextPage,
+ WebMenuItemPDFPreviousPage,
+
+These are all used by the context menu for PDF documents.
diff --git a/WebKit/mac/Resources/IDNScriptWhiteList.txt b/WebKit/mac/Resources/IDNScriptWhiteList.txt
new file mode 100644
index 0000000..d635a34
--- /dev/null
+++ b/WebKit/mac/Resources/IDNScriptWhiteList.txt
@@ -0,0 +1,23 @@
+# Default Web Kit International Domain Name Script White List.
+
+Common
+Inherited
+
+Arabic
+Armenian
+Bopomofo
+Canadian_Aboriginal
+Devanagari
+Deseret
+Gujarati
+Gurmukhi
+Hangul
+Han
+Hebrew
+Hiragana
+Katakana_Or_Hiragana
+Katakana
+Latin
+Tamil
+Thai
+Yi
diff --git a/WebKit/mac/Resources/nullplugin.tiff b/WebKit/mac/Resources/nullplugin.tiff
new file mode 100644
index 0000000..8a2d9df
--- /dev/null
+++ b/WebKit/mac/Resources/nullplugin.tiff
Binary files differ
diff --git a/WebKit/mac/Resources/url_icon.tiff b/WebKit/mac/Resources/url_icon.tiff
new file mode 100644
index 0000000..2b1b153
--- /dev/null
+++ b/WebKit/mac/Resources/url_icon.tiff
Binary files differ
diff --git a/WebKit/mac/Storage/WebDatabaseManager.mm b/WebKit/mac/Storage/WebDatabaseManager.mm
new file mode 100644
index 0000000..c975007
--- /dev/null
+++ b/WebKit/mac/Storage/WebDatabaseManager.mm
@@ -0,0 +1,140 @@
+/*
+ * Copyright (C) 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebDatabaseManagerPrivate.h"
+#import "WebDatabaseManagerInternal.h"
+
+#import "WebDatabaseTrackerClient.h"
+#import "WebSecurityOriginPrivate.h"
+#import "WebSecurityOriginInternal.h"
+
+#import <WebCore/DatabaseTracker.h>
+#import <WebCore/SecurityOrigin.h>
+
+using namespace WebCore;
+
+NSString *WebDatabaseDirectoryDefaultsKey = @"WebDatabaseDirectory";
+
+NSString *WebDatabaseDisplayNameKey = @"WebDatabaseDisplayNameKey";
+NSString *WebDatabaseExpectedSizeKey = @"WebDatabaseExpectedSizeKey";
+NSString *WebDatabaseUsageKey = @"WebDatabaseUsageKey";
+
+NSString *WebDatabaseDidModifyOriginNotification = @"WebDatabaseDidModifyOriginNotification";
+NSString *WebDatabaseDidModifyDatabaseNotification = @"WebDatabaseDidModifyDatabaseNotification";
+NSString *WebDatabaseIdentifierKey = @"WebDatabaseIdentifierKey";
+
+@implementation WebDatabaseManager
+
++ (WebDatabaseManager *) sharedWebDatabaseManager
+{
+ static WebDatabaseManager *sharedManager = [[WebDatabaseManager alloc] init];
+ return sharedManager;
+}
+
+- (NSArray *)origins
+{
+ Vector<RefPtr<SecurityOrigin> > coreOrigins;
+ DatabaseTracker::tracker().origins(coreOrigins);
+ NSMutableArray *webOrigins = [[NSMutableArray alloc] initWithCapacity:coreOrigins.size()];
+
+ for (unsigned i = 0; i < coreOrigins.size(); ++i) {
+ WebSecurityOrigin *webOrigin = [[WebSecurityOrigin alloc] _initWithWebCoreSecurityOrigin:coreOrigins[i].get()];
+ [webOrigins addObject:webOrigin];
+ [webOrigin release];
+ }
+
+ return [webOrigins autorelease];
+}
+
+- (NSArray *)databasesWithOrigin:(WebSecurityOrigin *)origin
+{
+ Vector<String> nameVector;
+ if (!DatabaseTracker::tracker().databaseNamesForOrigin([origin _core], nameVector))
+ return nil;
+
+ NSMutableArray *names = [[NSMutableArray alloc] initWithCapacity:nameVector.size()];
+
+ for (unsigned i = 0; i < nameVector.size(); ++i)
+ [names addObject:(NSString *)nameVector[i]];
+
+ return [names autorelease];
+}
+
+- (NSDictionary *)detailsForDatabase:(NSString *)databaseIdentifier withOrigin:(WebSecurityOrigin *)origin
+{
+ static id keys[3] = {WebDatabaseDisplayNameKey, WebDatabaseExpectedSizeKey, WebDatabaseUsageKey};
+
+ DatabaseDetails details = DatabaseTracker::tracker().detailsForNameAndOrigin(databaseIdentifier, [origin _core]);
+ if (details.name().isNull())
+ return nil;
+
+ id objects[3];
+ objects[0] = details.displayName().isEmpty() ? databaseIdentifier : (NSString *)details.displayName();
+ objects[1] = [NSNumber numberWithUnsignedLongLong:details.expectedUsage()];
+ objects[2] = [NSNumber numberWithUnsignedLongLong:details.currentUsage()];
+
+ return [[[NSDictionary alloc] initWithObjects:objects forKeys:keys count:3] autorelease];
+}
+
+- (void)deleteAllDatabases
+{
+ DatabaseTracker::tracker().deleteAllDatabases();
+}
+
+- (void)deleteOrigin:(WebSecurityOrigin *)origin
+{
+ DatabaseTracker::tracker().deleteOrigin([origin _core]);
+}
+
+- (void)deleteDatabase:(NSString *)databaseIdentifier withOrigin:(WebSecurityOrigin *)origin
+{
+ DatabaseTracker::tracker().deleteDatabase([origin _core], databaseIdentifier);
+}
+
+@end
+
+void WebKitInitializeDatabasesIfNecessary()
+{
+ static BOOL initialized = NO;
+ if (initialized)
+ return;
+
+ // Set the database root path in WebCore
+ NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
+
+ NSString *databasesDirectory = [defaults objectForKey:WebDatabaseDirectoryDefaultsKey];
+ if (!databasesDirectory || ![databasesDirectory isKindOfClass:[NSString class]])
+ databasesDirectory = @"~/Library/WebKit/Databases";
+
+ DatabaseTracker::tracker().setDatabaseDirectoryPath([databasesDirectory stringByStandardizingPath]);
+
+ // Set the DatabaseTrackerClient
+ DatabaseTracker::tracker().setClient(WebDatabaseTrackerClient::sharedWebDatabaseTrackerClient());
+
+ initialized = YES;
+}
diff --git a/WebKit/mac/Storage/WebDatabaseManagerInternal.h b/WebKit/mac/Storage/WebDatabaseManagerInternal.h
new file mode 100644
index 0000000..2065a4e
--- /dev/null
+++ b/WebKit/mac/Storage/WebDatabaseManagerInternal.h
@@ -0,0 +1,29 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+void WebKitInitializeDatabasesIfNecessary();
diff --git a/WebKit/mac/Storage/WebDatabaseManagerPrivate.h b/WebKit/mac/Storage/WebDatabaseManagerPrivate.h
new file mode 100644
index 0000000..faa4e5d
--- /dev/null
+++ b/WebKit/mac/Storage/WebDatabaseManagerPrivate.h
@@ -0,0 +1,64 @@
+/*
+ * Copyright (C) 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+extern NSString *WebDatabaseDirectoryDefaultsKey;
+
+extern NSString *WebDatabaseDisplayNameKey;
+extern NSString *WebDatabaseExpectedSizeKey;
+extern NSString *WebDatabaseUsageKey;
+
+// Posted with an origin is created from scratch, gets a new database, has a database deleted, has a quota change, etc
+// The notification object will be a WebSecurityOrigin object corresponding to the origin.
+extern NSString *WebDatabaseDidModifyOriginNotification;
+
+// Posted when a database is created, its size increases, its display name changes, or its estimated size changes, or the database is removed
+// The notification object will be a WebSecurityOrigin object corresponding to the origin.
+// The notification userInfo will have a WebDatabaseNameKey whose value is the database name.
+extern NSString *WebDatabaseDidModifyDatabaseNotification;
+extern NSString *WebDatabaseIdentifierKey;
+
+@class WebSecurityOrigin;
+
+@interface WebDatabaseManager : NSObject
+
++ (WebDatabaseManager *)sharedWebDatabaseManager;
+
+// Will return an array of WebSecurityOrigin objects.
+- (NSArray *)origins;
+
+// Will return an array of strings, the identifiers of each database in the given origin.
+- (NSArray *)databasesWithOrigin:(WebSecurityOrigin *)origin;
+
+// Will return the dictionary describing everything about the database for the passed identifier and origin.
+- (NSDictionary *)detailsForDatabase:(NSString *)databaseIdentifier withOrigin:(WebSecurityOrigin *)origin;
+
+- (void)deleteAllDatabases; // Deletes all databases and all origins.
+- (void)deleteOrigin:(WebSecurityOrigin *)origin;
+- (void)deleteDatabase:(NSString *)databaseIdentifier withOrigin:(WebSecurityOrigin *)origin;
+
+@end
diff --git a/WebKit/mac/Storage/WebDatabaseTrackerClient.h b/WebKit/mac/Storage/WebDatabaseTrackerClient.h
new file mode 100644
index 0000000..5db444c
--- /dev/null
+++ b/WebKit/mac/Storage/WebDatabaseTrackerClient.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/DatabaseTrackerClient.h>
+
+class WebDatabaseTrackerClient : public WebCore::DatabaseTrackerClient {
+public:
+ static WebDatabaseTrackerClient* sharedWebDatabaseTrackerClient();
+
+ virtual ~WebDatabaseTrackerClient();
+ virtual void dispatchDidModifyOrigin(WebCore::SecurityOrigin*);
+ virtual void dispatchDidModifyDatabase(WebCore::SecurityOrigin*, const WebCore::String& databaseIdentifier);
+private:
+ WebDatabaseTrackerClient();
+};
diff --git a/WebKit/mac/Storage/WebDatabaseTrackerClient.mm b/WebKit/mac/Storage/WebDatabaseTrackerClient.mm
new file mode 100644
index 0000000..7a2c809
--- /dev/null
+++ b/WebKit/mac/Storage/WebDatabaseTrackerClient.mm
@@ -0,0 +1,70 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebDatabaseTrackerClient.h"
+
+#import "WebDatabaseManagerPrivate.h"
+#import "WebSecurityOriginPrivate.h"
+#import "WebSecurityOriginInternal.h"
+#import <wtf/RetainPtr.h>
+#import <WebCore/SecurityOrigin.h>
+
+using namespace WebCore;
+
+WebDatabaseTrackerClient* WebDatabaseTrackerClient::sharedWebDatabaseTrackerClient()
+{
+ static WebDatabaseTrackerClient* sharedClient = new WebDatabaseTrackerClient();
+ return sharedClient;
+}
+
+WebDatabaseTrackerClient::WebDatabaseTrackerClient()
+{
+}
+
+WebDatabaseTrackerClient::~WebDatabaseTrackerClient()
+{
+}
+
+void WebDatabaseTrackerClient::dispatchDidModifyOrigin(SecurityOrigin* origin)
+{
+ RetainPtr<WebSecurityOrigin> webSecurityOrigin(AdoptNS, [[WebSecurityOrigin alloc] _initWithWebCoreSecurityOrigin:origin]);
+
+ [[NSNotificationCenter defaultCenter] postNotificationName:WebDatabaseDidModifyOriginNotification
+ object:webSecurityOrigin.get()];
+}
+
+void WebDatabaseTrackerClient::dispatchDidModifyDatabase(SecurityOrigin* origin, const String& databaseIdentifier)
+{
+ RetainPtr<WebSecurityOrigin> webSecurityOrigin(AdoptNS, [[WebSecurityOrigin alloc] _initWithWebCoreSecurityOrigin:origin]);
+ RetainPtr<NSDictionary> userInfo(AdoptNS, [[NSDictionary alloc]
+ initWithObjectsAndKeys:(NSString *)databaseIdentifier, WebDatabaseIdentifierKey, nil]);
+
+ [[NSNotificationCenter defaultCenter] postNotificationName:WebDatabaseDidModifyDatabaseNotification
+ object:webSecurityOrigin.get()
+ userInfo:userInfo.get()];
+}
diff --git a/WebKit/mac/Storage/WebSecurityOrigin.mm b/WebKit/mac/Storage/WebSecurityOrigin.mm
new file mode 100644
index 0000000..c980744
--- /dev/null
+++ b/WebKit/mac/Storage/WebSecurityOrigin.mm
@@ -0,0 +1,135 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+#import "WebSecurityOriginPrivate.h"
+
+#import "WebSecurityOriginInternal.h"
+
+#import <WebCore/DatabaseTracker.h>
+#import <WebCore/SecurityOrigin.h>
+
+using namespace WebCore;
+
+@implementation WebSecurityOrigin
+
+- (id)initWithProtocol:(NSString *)protocol domain:(NSString *)domain
+{
+ return [self initWithProtocol:protocol domain:domain port:0];
+}
+
+- (id)initWithProtocol:(NSString *)protocol domain:(NSString *)domain port:(unsigned short)port
+{
+ self = [super init];
+ if (!self)
+ return nil;
+
+ RefPtr<SecurityOrigin> origin = SecurityOrigin::create(protocol, domain, port, 0);
+ origin->ref();
+ _private = reinterpret_cast<WebSecurityOriginPrivate*>(origin.get());
+
+ return self;
+}
+
+- (NSString*)protocol
+{
+ return reinterpret_cast<SecurityOrigin*>(_private)->protocol();
+}
+
+- (NSString*)domain
+{
+ return reinterpret_cast<SecurityOrigin*>(_private)->host();
+}
+
+- (unsigned short)port
+{
+ return reinterpret_cast<SecurityOrigin*>(_private)->port();
+}
+
+- (unsigned long long)usage
+{
+ return DatabaseTracker::tracker().usageForOrigin(reinterpret_cast<SecurityOrigin*>(_private));
+}
+
+- (unsigned long long)quota
+{
+ return DatabaseTracker::tracker().quotaForOrigin(reinterpret_cast<SecurityOrigin*>(_private));
+}
+
+// Sets the storage quota (in bytes)
+// If the quota is set to a value lower than the current usage, that quota will "stick" but no data will be purged to meet the new quota.
+// This will simply prevent new data from being added to databases in that origin
+- (void)setQuota:(unsigned long long)quota
+{
+ DatabaseTracker::tracker().setQuota(reinterpret_cast<SecurityOrigin*>(_private), quota);
+}
+
+- (BOOL)isEqual:(id)anObject
+{
+ if (![anObject isMemberOfClass:[WebSecurityOrigin class]]) {
+ return NO;
+ }
+
+ return [self _core]->equal([anObject _core]);
+}
+
+- (void)dealloc
+{
+ if (_private)
+ reinterpret_cast<SecurityOrigin*>(_private)->deref();
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ if (_private)
+ reinterpret_cast<SecurityOrigin*>(_private)->deref();
+ [super finalize];
+}
+
+@end
+
+@implementation WebSecurityOrigin (WebInternal)
+
+- (id)_initWithWebCoreSecurityOrigin:(SecurityOrigin*)origin
+{
+ ASSERT(origin);
+ self = [super init];
+ if (!self)
+ return nil;
+
+ origin->ref();
+ _private = reinterpret_cast<WebSecurityOriginPrivate*>(origin);
+
+ return self;
+}
+
+- (SecurityOrigin *)_core
+{
+ return reinterpret_cast<SecurityOrigin*>(_private);
+}
+
+@end
diff --git a/WebKit/mac/Storage/WebSecurityOriginInternal.h b/WebKit/mac/Storage/WebSecurityOriginInternal.h
new file mode 100644
index 0000000..d60f52b
--- /dev/null
+++ b/WebKit/mac/Storage/WebSecurityOriginInternal.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+namespace WebCore {
+ class SecurityOrigin;
+}
+
+typedef WebCore::SecurityOrigin WebCoreSecurityOrigin;
+
+@interface WebSecurityOrigin (WebInternal)
+
+- (id)_initWithWebCoreSecurityOrigin:(WebCoreSecurityOrigin *)origin;
+- (WebCoreSecurityOrigin *)_core;
+
+@end
diff --git a/WebKit/mac/Storage/WebSecurityOriginPrivate.h b/WebKit/mac/Storage/WebSecurityOriginPrivate.h
new file mode 100644
index 0000000..1e66f42
--- /dev/null
+++ b/WebKit/mac/Storage/WebSecurityOriginPrivate.h
@@ -0,0 +1,53 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+@class WebSecurityOriginPrivate;
+
+@interface WebSecurityOrigin : NSObject {
+ WebSecurityOriginPrivate *_private;
+}
+
+- (id)initWithProtocol:(NSString *)protocol domain:(NSString *)domain;
+- (id)initWithProtocol:(NSString *)protocol domain:(NSString *)domain port:(unsigned short)port;
+
+- (NSString*)protocol;
+- (NSString*)domain;
+
+// Returns zero if the port is the default port for the protocol, non-zero otherwise
+- (unsigned short)port;
+
+// Returns the current total usage of all databases in this security origin in bytes
+- (unsigned long long)usage;
+
+- (unsigned long long)quota;
+// Sets the storage quota (in bytes)
+// If the quota is set to a value lower than the current usage, that quota will "stick" but no data will be purged to meet the new quota.
+// This will simply prevent new data from being added to databases in that origin
+- (void)setQuota:(unsigned long long)quota;
+
+@end
diff --git a/WebKit/mac/WebCoreSupport/WebCachedPagePlatformData.h b/WebKit/mac/WebCoreSupport/WebCachedPagePlatformData.h
new file mode 100644
index 0000000..3b0ab32
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebCachedPagePlatformData.h
@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <objc/objc-runtime.h>
+#import <WebCore/CachedPagePlatformData.h>
+#import <wtf/RetainPtr.h>
+
+class WebCachedPagePlatformData : public WebCore::CachedPagePlatformData {
+public:
+ WebCachedPagePlatformData(id webDocumentView) : m_webDocumentView(webDocumentView) { }
+
+ virtual void clear() { objc_msgSend(m_webDocumentView.get(), @selector(closeIfNotCurrentView)); }
+
+ id webDocumentView() { return m_webDocumentView.get(); }
+private:
+ RetainPtr<id> m_webDocumentView;
+};
+
diff --git a/WebKit/mac/WebCoreSupport/WebChromeClient.h b/WebKit/mac/WebCoreSupport/WebChromeClient.h
new file mode 100644
index 0000000..603ef96
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebChromeClient.h
@@ -0,0 +1,107 @@
+/*
+ * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved.
+ * Copyright (C) 2007 Trolltech ASA
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/ChromeClient.h>
+#import <WebCore/FocusDirection.h>
+#import <wtf/Forward.h>
+
+@class WebView;
+
+class WebChromeClient : public WebCore::ChromeClient {
+public:
+ WebChromeClient(WebView *webView);
+ WebView *webView() { return m_webView; }
+
+ virtual void chromeDestroyed();
+
+ virtual void setWindowRect(const WebCore::FloatRect&);
+ virtual WebCore::FloatRect windowRect();
+
+ virtual WebCore::FloatRect pageRect();
+
+ virtual float scaleFactor();
+
+ virtual void focus();
+ virtual void unfocus();
+
+ virtual bool canTakeFocus(WebCore::FocusDirection);
+ virtual void takeFocus(WebCore::FocusDirection);
+
+ virtual WebCore::Page* createWindow(WebCore::Frame*, const WebCore::FrameLoadRequest&, const WebCore::WindowFeatures&);
+ virtual void show();
+
+ virtual bool canRunModal();
+ virtual void runModal();
+
+ virtual void setToolbarsVisible(bool);
+ virtual bool toolbarsVisible();
+
+ virtual void setStatusbarVisible(bool);
+ virtual bool statusbarVisible();
+
+ virtual void setScrollbarsVisible(bool);
+ virtual bool scrollbarsVisible();
+
+ virtual void setMenubarVisible(bool);
+ virtual bool menubarVisible();
+
+ virtual void setResizable(bool);
+
+ virtual void addMessageToConsole(const WebCore::String& message, unsigned int lineNumber, const WebCore::String& sourceID);
+
+ virtual bool canRunBeforeUnloadConfirmPanel();
+ virtual bool runBeforeUnloadConfirmPanel(const WebCore::String& message, WebCore::Frame* frame);
+
+ virtual void closeWindowSoon();
+
+ virtual void runJavaScriptAlert(WebCore::Frame*, const WebCore::String&);
+ virtual bool runJavaScriptConfirm(WebCore::Frame*, const WebCore::String&);
+ virtual bool runJavaScriptPrompt(WebCore::Frame*, const WebCore::String& message, const WebCore::String& defaultValue, WebCore::String& result);
+ virtual bool shouldInterruptJavaScript();
+
+ virtual bool tabsToLinks() const;
+
+ virtual WebCore::IntRect windowResizerRect() const;
+ virtual void addToDirtyRegion(const WebCore::IntRect&);
+ virtual void scrollBackingStore(int dx, int dy, const WebCore::IntRect& scrollViewRect, const WebCore::IntRect& clipRect);
+ virtual void updateBackingStore();
+
+ virtual void setStatusbarText(const WebCore::String&);
+
+ virtual void mouseDidMoveOverElement(const WebCore::HitTestResult&, unsigned modifierFlags);
+
+ virtual void setToolTip(const WebCore::String&);
+
+ virtual void print(WebCore::Frame*);
+
+ virtual void exceededDatabaseQuota(WebCore::Frame*, const WebCore::String& databaseName);
+
+private:
+ WebView *m_webView;
+};
diff --git a/WebKit/mac/WebCoreSupport/WebChromeClient.mm b/WebKit/mac/WebCoreSupport/WebChromeClient.mm
new file mode 100644
index 0000000..fcbecf4
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebChromeClient.mm
@@ -0,0 +1,428 @@
+/*
+ * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved.
+ * Copyright (C) 2007 Trolltech ASA
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebChromeClient.h"
+
+#import "WebDefaultUIDelegate.h"
+#import "WebElementDictionary.h"
+#import "WebFrameInternal.h"
+#import "WebFrameView.h"
+#import "WebHTMLView.h"
+#import "WebHTMLViewPrivate.h"
+#import "WebKitSystemInterface.h"
+#import "WebNSURLRequestExtras.h"
+#import "WebSecurityOriginPrivate.h"
+#import "WebSecurityOriginInternal.h"
+#import "WebUIDelegate.h"
+#import "WebUIDelegatePrivate.h"
+#import "WebView.h"
+#import "WebViewInternal.h"
+#import <WebCore/BlockExceptions.h>
+#import <WebCore/FloatRect.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoadRequest.h>
+#import <WebCore/HitTestResult.h>
+#import <WebCore/IntRect.h>
+#import <WebCore/PlatformScreen.h>
+#import <WebCore/PlatformString.h>
+#import <WebCore/ResourceRequest.h>
+#import <WebCore/WindowFeatures.h>
+#import <wtf/PassRefPtr.h>
+
+@interface NSView (AppKitSecretsWebBridgeKnowsAbout)
+- (NSView *)_findLastViewInKeyViewLoop;
+@end
+
+using namespace WebCore;
+
+WebChromeClient::WebChromeClient(WebView *webView)
+ : m_webView(webView)
+{
+}
+
+void WebChromeClient::chromeDestroyed()
+{
+ delete this;
+}
+
+// These functions scale between window and WebView coordinates because JavaScript/DOM operations
+// assume that the WebView and the window share the same coordinate system.
+
+void WebChromeClient::setWindowRect(const FloatRect& rect)
+{
+ NSRect windowRect = toDeviceSpace(rect, [m_webView window]);
+ [[m_webView _UIDelegateForwarder] webView:m_webView setFrame:windowRect];
+}
+
+FloatRect WebChromeClient::windowRect()
+{
+ NSRect windowRect = [[m_webView _UIDelegateForwarder] webViewFrame:m_webView];
+ return toUserSpace(windowRect, [m_webView window]);
+}
+
+// FIXME: We need to add API for setting and getting this.
+FloatRect WebChromeClient::pageRect()
+{
+ return [m_webView frame];
+}
+
+float WebChromeClient::scaleFactor()
+{
+ if (NSWindow *window = [m_webView window])
+ return [window userSpaceScaleFactor];
+ return [[NSScreen mainScreen] userSpaceScaleFactor];
+}
+
+void WebChromeClient::focus()
+{
+ [[m_webView _UIDelegateForwarder] webViewFocus:m_webView];
+}
+
+void WebChromeClient::unfocus()
+{
+ [[m_webView _UIDelegateForwarder] webViewUnfocus:m_webView];
+}
+
+bool WebChromeClient::canTakeFocus(FocusDirection)
+{
+ // There's unfortunately no way to determine if we will become first responder again
+ // once we give it up, so we just have to guess that we won't.
+ return true;
+}
+
+void WebChromeClient::takeFocus(FocusDirection direction)
+{
+ if (direction == FocusDirectionForward) {
+ // Since we're trying to move focus out of m_webView, and because
+ // m_webView may contain subviews within it, we ask it for the next key
+ // view of the last view in its key view loop. This makes m_webView
+ // behave as if it had no subviews, which is the behavior we want.
+ NSView *lastView = [m_webView _findLastViewInKeyViewLoop];
+ // avoid triggering assertions if the WebView is the only thing in the key loop
+ if ([m_webView _becomingFirstResponderFromOutside] && m_webView == [lastView nextValidKeyView])
+ return;
+ [[m_webView window] selectKeyViewFollowingView:lastView];
+ } else {
+ // avoid triggering assertions if the WebView is the only thing in the key loop
+ if ([m_webView _becomingFirstResponderFromOutside] && m_webView == [m_webView previousValidKeyView])
+ return;
+ [[m_webView window] selectKeyViewPrecedingView:m_webView];
+ }
+}
+
+Page* WebChromeClient::createWindow(Frame* frame, const FrameLoadRequest& request, const WindowFeatures& features)
+{
+ NSURLRequest *URLRequest = nil;
+ if (!request.isEmpty())
+ URLRequest = request.resourceRequest().nsURLRequest();
+
+ id delegate = [m_webView UIDelegate];
+ WebView *newWebView;
+
+ if ([delegate respondsToSelector:@selector(webView:createWebViewWithRequest:windowFeatures:)]) {
+ NSNumber *x = features.xSet ? [[NSNumber alloc] initWithFloat:features.x] : nil;
+ NSNumber *y = features.ySet ? [[NSNumber alloc] initWithFloat:features.y] : nil;
+ NSNumber *width = features.widthSet ? [[NSNumber alloc] initWithFloat:features.width] : nil;
+ NSNumber *height = features.heightSet ? [[NSNumber alloc] initWithFloat:features.height] : nil;
+ NSNumber *menuBarVisible = [[NSNumber alloc] initWithBool:features.menuBarVisible];
+ NSNumber *statusBarVisible = [[NSNumber alloc] initWithBool:features.statusBarVisible];
+ NSNumber *toolBarVisible = [[NSNumber alloc] initWithBool:features.toolBarVisible];
+ NSNumber *scrollbarsVisible = [[NSNumber alloc] initWithBool:features.scrollbarsVisible];
+ NSNumber *resizable = [[NSNumber alloc] initWithBool:features.resizable];
+ NSNumber *fullscreen = [[NSNumber alloc] initWithBool:features.fullscreen];
+ NSNumber *dialog = [[NSNumber alloc] initWithBool:features.dialog];
+
+ NSMutableDictionary *dictFeatures = [[NSMutableDictionary alloc] initWithObjectsAndKeys:
+ menuBarVisible, @"menuBarVisible",
+ statusBarVisible, @"statusBarVisible",
+ toolBarVisible, @"toolBarVisible",
+ scrollbarsVisible, @"scrollbarsVisible",
+ resizable, @"resizable",
+ fullscreen, @"fullscreen",
+ dialog, @"dialog",
+ nil];
+
+ if (x)
+ [dictFeatures setObject:x forKey:@"x"];
+ if (y)
+ [dictFeatures setObject:y forKey:@"y"];
+ if (width)
+ [dictFeatures setObject:width forKey:@"width"];
+ if (height)
+ [dictFeatures setObject:height forKey:@"height"];
+
+ newWebView = CallUIDelegate(m_webView, @selector(webView:createWebViewWithRequest:windowFeatures:), URLRequest, dictFeatures);
+
+ [dictFeatures release];
+ [x release];
+ [y release];
+ [width release];
+ [height release];
+ [menuBarVisible release];
+ [statusBarVisible release];
+ [toolBarVisible release];
+ [scrollbarsVisible release];
+ [resizable release];
+ [fullscreen release];
+ [dialog release];
+ } else if (features.dialog && [delegate respondsToSelector:@selector(webView:createWebViewModalDialogWithRequest:)]) {
+ newWebView = CallUIDelegate(m_webView, @selector(webView:createWebViewModalDialogWithRequest:), URLRequest);
+ } else {
+ newWebView = CallUIDelegate(m_webView, @selector(webView:createWebViewWithRequest:), URLRequest);
+ }
+
+ return core(newWebView);
+}
+
+void WebChromeClient::show()
+{
+ [[m_webView _UIDelegateForwarder] webViewShow:m_webView];
+}
+
+bool WebChromeClient::canRunModal()
+{
+ return [[m_webView UIDelegate] respondsToSelector:@selector(webViewRunModal:)];
+}
+
+void WebChromeClient::runModal()
+{
+ CallUIDelegate(m_webView, @selector(webViewRunModal:));
+}
+
+void WebChromeClient::setToolbarsVisible(bool b)
+{
+ [[m_webView _UIDelegateForwarder] webView:m_webView setToolbarsVisible:b];
+}
+
+bool WebChromeClient::toolbarsVisible()
+{
+ return CallUIDelegateReturningBoolean(NO, m_webView, @selector(webViewAreToolbarsVisible:));
+}
+
+void WebChromeClient::setStatusbarVisible(bool b)
+{
+ [[m_webView _UIDelegateForwarder] webView:m_webView setStatusBarVisible:b];
+}
+
+bool WebChromeClient::statusbarVisible()
+{
+ return CallUIDelegateReturningBoolean(NO, m_webView, @selector(webViewIsStatusBarVisible:));
+}
+
+void WebChromeClient::setScrollbarsVisible(bool b)
+{
+ [[[m_webView mainFrame] frameView] setAllowsScrolling:b];
+}
+
+bool WebChromeClient::scrollbarsVisible()
+{
+ return [[[m_webView mainFrame] frameView] allowsScrolling];
+}
+
+void WebChromeClient::setMenubarVisible(bool)
+{
+ // The menubar is always visible in Mac OS X.
+ return;
+}
+
+bool WebChromeClient::menubarVisible()
+{
+ // The menubar is always visible in Mac OS X.
+ return true;
+}
+
+void WebChromeClient::setResizable(bool b)
+{
+ [[m_webView _UIDelegateForwarder] webView:m_webView setResizable:b];
+}
+
+void WebChromeClient::addMessageToConsole(const String& message, unsigned int lineNumber, const String& sourceURL)
+{
+ id delegate = [m_webView UIDelegate];
+ SEL selector = @selector(webView:addMessageToConsole:);
+ if (![delegate respondsToSelector:selector])
+ return;
+
+ NSDictionary *dictionary = [[NSDictionary alloc] initWithObjectsAndKeys:
+ (NSString *)message, @"message", [NSNumber numberWithUnsignedInt:lineNumber], @"lineNumber",
+ (NSString *)sourceURL, @"sourceURL", NULL];
+
+ CallUIDelegate(m_webView, selector, dictionary);
+
+ [dictionary release];
+}
+
+bool WebChromeClient::canRunBeforeUnloadConfirmPanel()
+{
+ return [[m_webView UIDelegate] respondsToSelector:@selector(webView:runBeforeUnloadConfirmPanelWithMessage:initiatedByFrame:)];
+}
+
+bool WebChromeClient::runBeforeUnloadConfirmPanel(const String& message, Frame* frame)
+{
+ return CallUIDelegateReturningBoolean(true, m_webView, @selector(webView:runBeforeUnloadConfirmPanelWithMessage:initiatedByFrame:), message, kit(frame));
+}
+
+void WebChromeClient::closeWindowSoon()
+{
+ // We need to remove the parent WebView from WebViewSets here, before it actually
+ // closes, to make sure that JavaScript code that executes before it closes
+ // can't find it. Otherwise, window.open will select a closed WebView instead of
+ // opening a new one <rdar://problem/3572585>.
+
+ // We also need to stop the load to prevent further parsing or JavaScript execution
+ // after the window has torn down <rdar://problem/4161660>.
+
+ // FIXME: This code assumes that the UI delegate will respond to a webViewClose
+ // message by actually closing the WebView. Safari guarantees this behavior, but other apps might not.
+ // This approach is an inherent limitation of not making a close execute immediately
+ // after a call to window.close.
+
+ [m_webView setGroupName:nil];
+ [m_webView stopLoading:nil];
+ [m_webView performSelector:@selector(_closeWindow) withObject:nil afterDelay:0.0];
+}
+
+void WebChromeClient::runJavaScriptAlert(Frame* frame, const String& message)
+{
+ id delegate = [m_webView UIDelegate];
+ SEL selector = @selector(webView:runJavaScriptAlertPanelWithMessage:initiatedByFrame:);
+ if ([delegate respondsToSelector:selector]) {
+ CallUIDelegate(m_webView, selector, message, kit(frame));
+ return;
+ }
+
+ // Call the old version of the delegate method if it is implemented.
+ selector = @selector(webView:runJavaScriptAlertPanelWithMessage:);
+ if ([delegate respondsToSelector:selector]) {
+ CallUIDelegate(m_webView, selector, message);
+ return;
+ }
+}
+
+bool WebChromeClient::runJavaScriptConfirm(Frame* frame, const String& message)
+{
+ id delegate = [m_webView UIDelegate];
+ SEL selector = @selector(webView:runJavaScriptConfirmPanelWithMessage:initiatedByFrame:);
+ if ([delegate respondsToSelector:selector])
+ return CallUIDelegateReturningBoolean(NO, m_webView, selector, message, kit(frame));
+
+ // Call the old version of the delegate method if it is implemented.
+ selector = @selector(webView:runJavaScriptConfirmPanelWithMessage:);
+ if ([delegate respondsToSelector:selector])
+ return CallUIDelegateReturningBoolean(NO, m_webView, selector, message);
+
+ return NO;
+}
+
+bool WebChromeClient::runJavaScriptPrompt(Frame* frame, const String& prompt, const String& defaultText, String& result)
+{
+ id delegate = [m_webView UIDelegate];
+ SEL selector = @selector(webView:runJavaScriptTextInputPanelWithPrompt:defaultText:initiatedByFrame:);
+ if ([delegate respondsToSelector:selector]) {
+ result = (NSString *)CallUIDelegate(m_webView, selector, prompt, defaultText, kit(frame));
+ return !result.isNull();
+ }
+
+ // Call the old version of the delegate method if it is implemented.
+ selector = @selector(webView:runJavaScriptTextInputPanelWithPrompt:defaultText:);
+ if ([delegate respondsToSelector:selector]) {
+ result = (NSString *)CallUIDelegate(m_webView, selector, prompt, defaultText);
+ return !result.isNull();
+ }
+
+ result = [[WebDefaultUIDelegate sharedUIDelegate] webView:m_webView runJavaScriptTextInputPanelWithPrompt:prompt defaultText:defaultText initiatedByFrame:kit(frame)];
+ return !result.isNull();
+}
+
+bool WebChromeClient::shouldInterruptJavaScript()
+{
+ return CallUIDelegate(m_webView, @selector(webViewShouldInterruptJavaScript:));
+}
+
+void WebChromeClient::setStatusbarText(const String& status)
+{
+ // We want the temporaries allocated here to be released even before returning to the
+ // event loop; see <http://bugs.webkit.org/show_bug.cgi?id=9880>.
+ NSAutoreleasePool* localPool = [[NSAutoreleasePool alloc] init];
+ CallUIDelegate(m_webView, @selector(webView:setStatusText:), (NSString *)status);
+ [localPool drain];
+}
+
+bool WebChromeClient::tabsToLinks() const
+{
+ return [[m_webView preferences] tabsToLinks];
+}
+
+IntRect WebChromeClient::windowResizerRect() const
+{
+ return IntRect();
+}
+
+void WebChromeClient::addToDirtyRegion(const IntRect&)
+{
+}
+
+void WebChromeClient::scrollBackingStore(int, int, const IntRect&, const IntRect&)
+{
+}
+
+void WebChromeClient::updateBackingStore()
+{
+}
+
+void WebChromeClient::mouseDidMoveOverElement(const HitTestResult& result, unsigned modifierFlags)
+{
+ WebElementDictionary *element = [[WebElementDictionary alloc] initWithHitTestResult:result];
+ [m_webView _mouseDidMoveOverElement:element modifierFlags:modifierFlags];
+ [element release];
+}
+
+void WebChromeClient::setToolTip(const String& toolTip)
+{
+ [(WebHTMLView *)[[[m_webView mainFrame] frameView] documentView] _setToolTip:toolTip];
+}
+
+void WebChromeClient::print(Frame* frame)
+{
+ WebFrameView* frameView = [kit(frame) frameView];
+ CallUIDelegate(m_webView, @selector(webView:printFrameView:), frameView);
+}
+
+void WebChromeClient::exceededDatabaseQuota(Frame* frame, const String& databaseName)
+{
+ WebSecurityOrigin *webOrigin = [[WebSecurityOrigin alloc] _initWithWebCoreSecurityOrigin:frame->document()->securityOrigin()];
+ // FIXME: remove this workaround once shipping Safari has the necessary delegate implemented.
+ if (WKAppVersionCheckLessThan(@"com.apple.Safari", -1, 3.1)) {
+ const unsigned long long defaultQuota = 5 * 1024 * 1024; // 5 megabytes should hopefully be enough to test storage support.
+ [webOrigin setQuota:defaultQuota];
+ } else
+ CallUIDelegate(m_webView, @selector(webView:frame:exceededDatabaseQuotaForSecurityOrigin:database:), kit(frame), webOrigin, (NSString *)databaseName);
+ [webOrigin release];
+}
+
diff --git a/WebKit/mac/WebCoreSupport/WebContextMenuClient.h b/WebKit/mac/WebCoreSupport/WebContextMenuClient.h
new file mode 100644
index 0000000..7ab68a2
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebContextMenuClient.h
@@ -0,0 +1,53 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/ContextMenuClient.h>
+
+@class WebView;
+
+class WebContextMenuClient : public WebCore::ContextMenuClient {
+public:
+ WebContextMenuClient(WebView *webView);
+
+ virtual void contextMenuDestroyed();
+
+ virtual NSMutableArray* getCustomMenuFromDefaultItems(WebCore::ContextMenu*);
+ virtual void contextMenuItemSelected(WebCore::ContextMenuItem*, const WebCore::ContextMenu*);
+
+ virtual void downloadURL(const WebCore::KURL&);
+ virtual void searchWithGoogle(const WebCore::Frame*);
+ virtual void lookUpInDictionary(WebCore::Frame*);
+ virtual void speak(const WebCore::String&);
+ virtual void stopSpeaking();
+ virtual void searchWithSpotlight();
+
+ WebView *webView() { return m_webView; }
+
+private:
+ WebView *m_webView;
+};
diff --git a/WebKit/mac/WebCoreSupport/WebContextMenuClient.mm b/WebKit/mac/WebCoreSupport/WebContextMenuClient.mm
new file mode 100644
index 0000000..6b5ad14
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebContextMenuClient.mm
@@ -0,0 +1,327 @@
+/*
+ * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebContextMenuClient.h"
+
+#import "WebElementDictionary.h"
+#import "WebFrame.h"
+#import "WebFrameInternal.h"
+#import "WebHTMLView.h"
+#import "WebHTMLViewInternal.h"
+#import "WebKitVersionChecks.h"
+#import "WebNSPasteboardExtras.h"
+#import "WebUIDelegate.h"
+#import "WebUIDelegatePrivate.h"
+#import "WebView.h"
+#import "WebViewFactory.h"
+#import "WebViewInternal.h"
+#import <WebCore/ContextMenu.h>
+#import <WebCore/KURL.h>
+#import <WebKit/DOMPrivate.h>
+
+using namespace WebCore;
+
+@interface NSApplication (AppKitSecretsIKnowAbout)
+- (void)speakString:(NSString *)string;
+@end
+
+WebContextMenuClient::WebContextMenuClient(WebView *webView)
+ : m_webView(webView)
+{
+}
+
+void WebContextMenuClient::contextMenuDestroyed()
+{
+ delete this;
+}
+
+static BOOL isAppleMail(void)
+{
+ return [[[NSBundle mainBundle] bundleIdentifier] isEqualToString:@"com.apple.mail"];
+}
+
+static BOOL isPreVersion3Client(void)
+{
+ static BOOL preVersion3Client = !WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITH_3_0_CONTEXT_MENU_TAGS);
+ return preVersion3Client;
+}
+
+static BOOL isPreInspectElementTagClient(void)
+{
+ static BOOL preInspectElementTagClient = !WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITH_INSPECT_ELEMENT_MENU_TAG);
+ return preInspectElementTagClient;
+}
+
+static NSMutableArray *fixMenusToSendToOldClients(NSMutableArray *defaultMenuItems)
+{
+ NSMutableArray *savedItems = nil;
+
+ unsigned defaultItemsCount = [defaultMenuItems count];
+
+ if (isPreInspectElementTagClient() && defaultItemsCount >= 2) {
+ NSMenuItem *secondToLastItem = [defaultMenuItems objectAtIndex:defaultItemsCount - 2];
+ NSMenuItem *lastItem = [defaultMenuItems objectAtIndex:defaultItemsCount - 1];
+
+ if ([secondToLastItem isSeparatorItem] && [lastItem tag] == WebMenuItemTagInspectElement) {
+ savedItems = [NSMutableArray arrayWithCapacity:2];
+ [savedItems addObject:secondToLastItem];
+ [savedItems addObject:lastItem];
+
+ [defaultMenuItems removeObject:secondToLastItem];
+ [defaultMenuItems removeObject:lastItem];
+ defaultItemsCount -= 2;
+ }
+ }
+
+ BOOL preVersion3Client = isPreVersion3Client();
+ if (!preVersion3Client)
+ return savedItems;
+
+ BOOL isMail = isAppleMail();
+ for (unsigned i = 0; i < defaultItemsCount; ++i) {
+ NSMenuItem *item = [defaultMenuItems objectAtIndex:i];
+ int tag = [item tag];
+ int oldStyleTag = tag;
+
+ if (preVersion3Client && isMail && tag == WebMenuItemTagOpenLink) {
+ // Tiger Mail changes our "Open Link in New Window" item to "Open Link"
+ // and doesn't expect us to include an "Open Link" item at all. (5011905)
+ [defaultMenuItems removeObjectAtIndex:i];
+ i--;
+ defaultItemsCount--;
+ continue;
+ }
+
+ if (tag >= WEBMENUITEMTAG_WEBKIT_3_0_SPI_START) {
+ // Change all editing-related SPI tags listed in WebUIDelegatePrivate.h to WebMenuItemTagOther
+ // to match our old WebKit context menu behavior.
+ oldStyleTag = WebMenuItemTagOther;
+ } else {
+ // All items are expected to have useful tags coming into this method.
+ ASSERT(tag != WebMenuItemTagOther);
+
+ // Use the pre-3.0 tags for the few items that changed tags as they moved from SPI to API. We
+ // do this only for old clients; new Mail already expects the new symbols in this case.
+ if (preVersion3Client) {
+ switch (tag) {
+ case WebMenuItemTagSearchInSpotlight:
+ oldStyleTag = OldWebMenuItemTagSearchInSpotlight;
+ break;
+ case WebMenuItemTagSearchWeb:
+ oldStyleTag = OldWebMenuItemTagSearchWeb;
+ break;
+ case WebMenuItemTagLookUpInDictionary:
+ oldStyleTag = OldWebMenuItemTagLookUpInDictionary;
+ break;
+ default:
+ break;
+ }
+ }
+ }
+
+ if (oldStyleTag != tag)
+ [item setTag:oldStyleTag];
+ }
+
+ return savedItems;
+}
+
+static void fixMenusReceivedFromOldClients(NSMutableArray *newMenuItems, NSMutableArray *savedItems)
+{
+ if (savedItems)
+ [newMenuItems addObjectsFromArray:savedItems];
+
+ BOOL preVersion3Client = isPreVersion3Client();
+ if (!preVersion3Client)
+ return;
+
+ // Restore the modern tags to the menu items whose tags we altered in fixMenusToSendToOldClients.
+ unsigned newItemsCount = [newMenuItems count];
+ for (unsigned i = 0; i < newItemsCount; ++i) {
+ NSMenuItem *item = [newMenuItems objectAtIndex:i];
+
+ int tag = [item tag];
+ int modernTag = tag;
+
+ if (tag == WebMenuItemTagOther) {
+ // Restore the specific tag for items on which we temporarily set WebMenuItemTagOther to match old behavior.
+ NSString *title = [item title];
+ if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagOpenLink]])
+ modernTag = WebMenuItemTagOpenLink;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagIgnoreGrammar]])
+ modernTag = WebMenuItemTagIgnoreGrammar;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagSpellingMenu]])
+ modernTag = WebMenuItemTagSpellingMenu;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagShowSpellingPanel:true]]
+ || [title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagShowSpellingPanel:false]])
+ modernTag = WebMenuItemTagShowSpellingPanel;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagCheckSpelling]])
+ modernTag = WebMenuItemTagCheckSpelling;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagCheckSpellingWhileTyping]])
+ modernTag = WebMenuItemTagCheckSpellingWhileTyping;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagCheckGrammarWithSpelling]])
+ modernTag = WebMenuItemTagCheckGrammarWithSpelling;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagFontMenu]])
+ modernTag = WebMenuItemTagFontMenu;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagShowFonts]])
+ modernTag = WebMenuItemTagShowFonts;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagBold]])
+ modernTag = WebMenuItemTagBold;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagItalic]])
+ modernTag = WebMenuItemTagItalic;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagUnderline]])
+ modernTag = WebMenuItemTagUnderline;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagOutline]])
+ modernTag = WebMenuItemTagOutline;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagStyles]])
+ modernTag = WebMenuItemTagStyles;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagShowColors]])
+ modernTag = WebMenuItemTagShowColors;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagSpeechMenu]])
+ modernTag = WebMenuItemTagSpeechMenu;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagStartSpeaking]])
+ modernTag = WebMenuItemTagStartSpeaking;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagStopSpeaking]])
+ modernTag = WebMenuItemTagStopSpeaking;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagWritingDirectionMenu]])
+ modernTag = WebMenuItemTagWritingDirectionMenu;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagDefaultDirection]])
+ modernTag = WebMenuItemTagDefaultDirection;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagLeftToRight]])
+ modernTag = WebMenuItemTagLeftToRight;
+ else if ([title isEqualToString:[[WebViewFactory sharedFactory] contextMenuItemTagRightToLeft]])
+ modernTag = WebMenuItemTagRightToLeft;
+ else {
+ // We don't expect WebMenuItemTagOther for any items other than the ones we explicitly handle.
+ // There's nothing to prevent an app from applying this tag, but they are supposed to only
+ // use tags in the range starting with WebMenuItemBaseApplicationTag=10000
+ ASSERT_NOT_REACHED();
+ }
+ } else if (preVersion3Client) {
+ // Restore the new API tag for items on which we temporarily set the old SPI tag. The old SPI tag was
+ // needed to avoid confusing clients linked against earlier WebKits; the new API tag is needed for
+ // WebCore to handle the menu items appropriately (without needing to know about the old SPI tags).
+ switch (tag) {
+ case OldWebMenuItemTagSearchInSpotlight:
+ modernTag = WebMenuItemTagSearchInSpotlight;
+ break;
+ case OldWebMenuItemTagSearchWeb:
+ modernTag = WebMenuItemTagSearchWeb;
+ break;
+ case OldWebMenuItemTagLookUpInDictionary:
+ modernTag = WebMenuItemTagLookUpInDictionary;
+ break;
+ default:
+ break;
+ }
+ }
+
+ if (modernTag != tag)
+ [item setTag:modernTag];
+ }
+}
+
+NSMutableArray* WebContextMenuClient::getCustomMenuFromDefaultItems(ContextMenu* defaultMenu)
+{
+ id delegate = [m_webView UIDelegate];
+ SEL selector = @selector(webView:contextMenuItemsForElement:defaultMenuItems:);
+ if (![delegate respondsToSelector:selector])
+ return defaultMenu->platformDescription();
+
+ NSDictionary *element = [[[WebElementDictionary alloc] initWithHitTestResult:defaultMenu->hitTestResult()] autorelease];
+
+ BOOL preVersion3Client = isPreVersion3Client();
+ if (preVersion3Client) {
+ DOMNode *node = [element objectForKey:WebElementDOMNodeKey];
+ if ([node isKindOfClass:[DOMHTMLInputElement class]] && [(DOMHTMLInputElement *)node _isTextField])
+ return defaultMenu->platformDescription();
+ if ([node isKindOfClass:[DOMHTMLTextAreaElement class]])
+ return defaultMenu->platformDescription();
+ }
+
+ NSMutableArray *defaultMenuItems = defaultMenu->platformDescription();
+
+ unsigned defaultItemsCount = [defaultMenuItems count];
+ for (unsigned i = 0; i < defaultItemsCount; ++i)
+ [[defaultMenuItems objectAtIndex:i] setRepresentedObject:element];
+
+ NSMutableArray *savedItems = [fixMenusToSendToOldClients(defaultMenuItems) retain];
+ NSArray *delegateSuppliedItems = CallUIDelegate(m_webView, selector, element, defaultMenuItems);
+ NSMutableArray *newMenuItems = [delegateSuppliedItems mutableCopy];
+ fixMenusReceivedFromOldClients(newMenuItems, savedItems);
+ [savedItems release];
+ return [newMenuItems autorelease];
+}
+
+void WebContextMenuClient::contextMenuItemSelected(ContextMenuItem* item, const ContextMenu* parentMenu)
+{
+ id delegate = [m_webView UIDelegate];
+ SEL selector = @selector(webView:contextMenuItemSelected:forElement:);
+ if ([delegate respondsToSelector:selector]) {
+ NSDictionary *element = [[WebElementDictionary alloc] initWithHitTestResult:parentMenu->hitTestResult()];
+ NSMenuItem *platformItem = item->releasePlatformDescription();
+
+ CallUIDelegate(m_webView, selector, platformItem, element);
+
+ [element release];
+ [platformItem release];
+ }
+}
+
+void WebContextMenuClient::downloadURL(const KURL& url)
+{
+ [m_webView _downloadURL:url];
+}
+
+void WebContextMenuClient::searchWithSpotlight()
+{
+ [m_webView _searchWithSpotlightFromMenu:nil];
+}
+
+void WebContextMenuClient::searchWithGoogle(const Frame*)
+{
+ [m_webView _searchWithGoogleFromMenu:nil];
+}
+
+void WebContextMenuClient::lookUpInDictionary(Frame* frame)
+{
+ WebHTMLView* htmlView = (WebHTMLView*)[[kit(frame) frameView] documentView];
+ if(![htmlView isKindOfClass:[WebHTMLView class]])
+ return;
+ [htmlView _lookUpInDictionaryFromMenu:nil];
+}
+
+void WebContextMenuClient::speak(const String& string)
+{
+ [NSApp speakString:[[(NSString*)string copy] autorelease]];
+}
+
+void WebContextMenuClient::stopSpeaking()
+{
+ [NSApp stopSpeaking];
+}
diff --git a/WebKit/mac/WebCoreSupport/WebDragClient.h b/WebKit/mac/WebCoreSupport/WebDragClient.h
new file mode 100644
index 0000000..234090e
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebDragClient.h
@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/DragClient.h>
+
+@class WebView;
+
+class WebDragClient : public WebCore::DragClient {
+public:
+ WebDragClient(WebView*);
+ virtual void willPerformDragDestinationAction(WebCore::DragDestinationAction, WebCore::DragData*);
+ virtual void willPerformDragSourceAction(WebCore::DragSourceAction, const WebCore::IntPoint&, WebCore::Clipboard*);
+ virtual WebCore::DragDestinationAction actionMaskForDrag(WebCore::DragData*);
+ virtual void dragControllerDestroyed();
+ virtual WebCore::DragSourceAction dragSourceActionMaskForPoint(const WebCore::IntPoint& windowPoint);
+ virtual void startDrag(WebCore::DragImageRef dragImage, const WebCore::IntPoint& dragPos, const WebCore::IntPoint& eventPos, WebCore::Clipboard*, WebCore::Frame*, bool linkDrag);
+ virtual WebCore::DragImageRef createDragImageForLink(WebCore::KURL& url, const WebCore::String& label, WebCore::Frame*);
+ virtual void declareAndWriteDragImage(NSPasteboard*, DOMElement*, NSURL*, NSString*, WebCore::Frame*);
+private:
+ WebView* m_webView;
+};
diff --git a/WebKit/mac/WebCoreSupport/WebDragClient.mm b/WebKit/mac/WebCoreSupport/WebDragClient.mm
new file mode 100644
index 0000000..2cc7570
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebDragClient.mm
@@ -0,0 +1,146 @@
+/*
+ * Copyright (C) 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebDragClient.h"
+
+#import "WebArchive.h"
+#import "WebArchiver.h"
+#import "WebDOMOperations.h"
+#import "WebFrame.h"
+#import "WebFrameInternal.h"
+#import "WebHTMLViewInternal.h"
+#import "WebHTMLViewPrivate.h"
+#import "WebKitLogging.h"
+#import "WebNSPasteboardExtras.h"
+#import "WebNSURLExtras.h"
+#import "WebUIDelegate.h"
+#import "WebUIDelegatePrivate.h"
+#import "WebViewInternal.h"
+#import <WebCore/ClipboardMac.h>
+#import <WebCore/DragData.h>
+#import <WebCore/EventHandler.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameView.h>
+#import <WebCore/Image.h>
+#import <WebCore/Page.h>
+
+using namespace WebCore;
+
+WebDragClient::WebDragClient(WebView* webView)
+ : m_webView(webView)
+{
+}
+
+static WebHTMLView *getTopHTMLView(Frame* frame)
+{
+ ASSERT(frame);
+ ASSERT(frame->page());
+ return (WebHTMLView*)[[kit(frame->page()->mainFrame()) frameView] documentView];
+}
+
+WebCore::DragDestinationAction WebDragClient::actionMaskForDrag(WebCore::DragData* dragData)
+{
+ return (WebCore::DragDestinationAction)[[m_webView _UIDelegateForwarder] webView:m_webView dragDestinationActionMaskForDraggingInfo:dragData->platformData()];
+}
+
+void WebDragClient::willPerformDragDestinationAction(WebCore::DragDestinationAction action, WebCore::DragData* dragData)
+{
+ [[m_webView _UIDelegateForwarder] webView:m_webView willPerformDragDestinationAction:(WebDragDestinationAction)action forDraggingInfo:dragData->platformData()];
+}
+
+
+WebCore::DragSourceAction WebDragClient::dragSourceActionMaskForPoint(const IntPoint& windowPoint)
+{
+ NSPoint viewPoint = [m_webView convertPoint:windowPoint fromView:nil];
+ return (DragSourceAction)[[m_webView _UIDelegateForwarder] webView:m_webView dragSourceActionMaskForPoint:viewPoint];
+}
+
+void WebDragClient::willPerformDragSourceAction(WebCore::DragSourceAction action, const WebCore::IntPoint& mouseDownPoint, WebCore::Clipboard* clipboard)
+{
+ ASSERT(clipboard);
+ [[m_webView _UIDelegateForwarder] webView:m_webView willPerformDragSourceAction:(WebDragSourceAction)action fromPoint:mouseDownPoint withPasteboard:static_cast<WebCore::ClipboardMac*>(clipboard)->pasteboard()];
+}
+
+void WebDragClient::startDrag(DragImageRef dragImage, const IntPoint& at, const IntPoint& eventPos, Clipboard* clipboard, Frame* frame, bool linkDrag)
+{
+ if (!frame)
+ return;
+ ASSERT(clipboard);
+ RetainPtr<WebHTMLView> htmlView = (WebHTMLView*)[[kit(frame) frameView] documentView];
+ if (![htmlView.get() isKindOfClass:[WebHTMLView class]])
+ return;
+
+ NSEvent *event = linkDrag ? frame->eventHandler()->currentNSEvent() : [htmlView.get() _mouseDownEvent];
+ WebHTMLView* topHTMLView = getTopHTMLView(frame);
+ RetainPtr<WebHTMLView> topViewProtector = topHTMLView;
+
+ [topHTMLView _stopAutoscrollTimer];
+ NSPasteboard *pasteboard = static_cast<ClipboardMac*>(clipboard)->pasteboard();
+
+ NSImage *dragNSImage = dragImage.get();
+ WebHTMLView *sourceHTMLView = htmlView.get();
+
+ id delegate = [m_webView UIDelegate];
+ SEL selector = @selector(webView:dragImage:at:offset:event:pasteboard:source:slideBack:forView:);
+ if ([delegate respondsToSelector:selector]) {
+ if ([m_webView _catchesDelegateExceptions]) {
+ @try {
+ [delegate webView:m_webView dragImage:dragNSImage at:at offset:NSZeroSize event:event pasteboard:pasteboard source:sourceHTMLView slideBack:YES forView:topHTMLView];
+ } @catch (id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ } else
+ [delegate webView:m_webView dragImage:dragNSImage at:at offset:NSZeroSize event:event pasteboard:pasteboard source:sourceHTMLView slideBack:YES forView:topHTMLView];
+ } else
+ [topHTMLView dragImage:dragNSImage at:at offset:NSZeroSize event:event pasteboard:pasteboard source:sourceHTMLView slideBack:YES];
+}
+
+DragImageRef WebDragClient::createDragImageForLink(KURL& url, const String& title, Frame* frame)
+{
+ if (!frame)
+ return nil;
+ WebHTMLView *htmlView = (WebHTMLView *)[[kit(frame) frameView] documentView];
+ NSString *label = 0;
+ if (!title.isEmpty())
+ label = title;
+ NSURL *cocoaURL = url;
+ return [htmlView _dragImageForURL:[cocoaURL _web_userVisibleString] withLabel:label];
+}
+
+
+void WebDragClient::declareAndWriteDragImage(NSPasteboard* pasteboard, DOMElement* element, NSURL* URL, NSString* title, WebCore::Frame* frame)
+{
+ ASSERT(pasteboard);
+ ASSERT(element);
+ WebHTMLView *source = getTopHTMLView(frame);
+ WebArchive *archive = [element webArchive];
+
+ [pasteboard _web_declareAndWriteDragImageForElement:element URL:URL title:title archive:archive source:source];
+}
+
+void WebDragClient::dragControllerDestroyed()
+{
+ delete this;
+}
diff --git a/WebKit/mac/WebCoreSupport/WebEditorClient.h b/WebKit/mac/WebCoreSupport/WebEditorClient.h
new file mode 100644
index 0000000..ef54d2a
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebEditorClient.h
@@ -0,0 +1,118 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ * Copyright (C) 2007 Trolltech ASA
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/EditorClient.h>
+#import <wtf/RetainPtr.h>
+#import <wtf/Forward.h>
+#import <wtf/Vector.h>
+
+@class WebView;
+@class WebEditorUndoTarget;
+
+class WebEditorClient : public WebCore::EditorClient {
+public:
+ WebEditorClient(WebView *);
+
+ virtual void pageDestroyed();
+
+ virtual bool isGrammarCheckingEnabled();
+ virtual void toggleGrammarChecking();
+ virtual bool isContinuousSpellCheckingEnabled();
+ virtual void toggleContinuousSpellChecking();
+ virtual int spellCheckerDocumentTag();
+
+ virtual bool smartInsertDeleteEnabled();
+ virtual bool isEditable();
+
+ virtual bool shouldDeleteRange(WebCore::Range*);
+ virtual bool shouldShowDeleteInterface(WebCore::HTMLElement*);
+
+ virtual bool shouldBeginEditing(WebCore::Range*);
+ virtual bool shouldEndEditing(WebCore::Range*);
+ virtual bool shouldInsertNode(WebCore::Node*, WebCore::Range*, WebCore::EditorInsertAction);
+ virtual bool shouldInsertText(WebCore::String, WebCore::Range*, WebCore::EditorInsertAction);
+ virtual bool shouldChangeSelectedRange(WebCore::Range* fromRange, WebCore::Range* toRange, WebCore::EAffinity, bool stillSelecting);
+
+ virtual bool shouldApplyStyle(WebCore::CSSStyleDeclaration*, WebCore::Range*);
+
+ virtual bool shouldMoveRangeAfterDelete(WebCore::Range* range, WebCore::Range* rangeToBeReplaced);
+
+ virtual void didBeginEditing();
+ virtual void didEndEditing();
+ virtual void didWriteSelectionToPasteboard();
+ virtual void didSetSelectionTypesForPasteboard();
+
+ virtual NSData* dataForArchivedSelection(WebCore::Frame*);
+ virtual NSString* userVisibleString(NSURL*);
+#ifdef BUILDING_ON_TIGER
+ virtual NSArray* pasteboardTypesForSelection(WebCore::Frame*);
+#endif
+
+ virtual void respondToChangedContents();
+ virtual void respondToChangedSelection();
+
+ virtual void registerCommandForUndo(PassRefPtr<WebCore::EditCommand>);
+ virtual void registerCommandForRedo(PassRefPtr<WebCore::EditCommand>);
+ virtual void clearUndoRedoOperations();
+
+ virtual bool canUndo() const;
+ virtual bool canRedo() const;
+
+ virtual void undo();
+ virtual void redo();
+
+ virtual void handleKeyboardEvent(WebCore::KeyboardEvent*);
+ virtual void handleInputMethodKeydown(WebCore::KeyboardEvent*);
+
+ virtual void textFieldDidBeginEditing(WebCore::Element*);
+ virtual void textFieldDidEndEditing(WebCore::Element*);
+ virtual void textDidChangeInTextField(WebCore::Element*);
+ virtual bool doTextFieldCommandFromEvent(WebCore::Element*, WebCore::KeyboardEvent*);
+ virtual void textWillBeDeletedInTextField(WebCore::Element*);
+ virtual void textDidChangeInTextArea(WebCore::Element*);
+
+ virtual void ignoreWordInSpellDocument(const WebCore::String&);
+ virtual void learnWord(const WebCore::String&);
+ virtual void checkSpellingOfString(const UChar*, int length, int* misspellingLocation, int* misspellingLength);
+ virtual void checkGrammarOfString(const UChar*, int length, WTF::Vector<WebCore::GrammarDetail>&, int* badGrammarLocation, int* badGrammarLength);
+ virtual void updateSpellingUIWithGrammarString(const WebCore::String&, const WebCore::GrammarDetail&);
+ virtual void updateSpellingUIWithMisspelledWord(const WebCore::String&);
+ virtual void showSpellingUI(bool show);
+ virtual bool spellingUIIsShowing();
+ virtual void getGuessesForWord(const WebCore::String&, WTF::Vector<WebCore::String>& guesses);
+ virtual void setInputMethodState(bool enabled);
+private:
+ void registerCommandForUndoOrRedo(PassRefPtr<WebCore::EditCommand>, bool isRedo);
+ WebEditorClient();
+
+ WebView *m_webView;
+ RetainPtr<WebEditorUndoTarget> m_undoTarget;
+
+ bool m_haveUndoRedoOperations;
+};
diff --git a/WebKit/mac/WebCoreSupport/WebEditorClient.mm b/WebKit/mac/WebCoreSupport/WebEditorClient.mm
new file mode 100644
index 0000000..62a6675
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebEditorClient.mm
@@ -0,0 +1,627 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ * Copyright (C) 2007 Trolltech ASA
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebEditorClient.h"
+
+#import "DOMHTMLInputElementInternal.h"
+#import "DOMHTMLTextAreaElementInternal.h"
+#import "DOMRangeInternal.h"
+#import "WebArchive.h"
+#import "WebArchiver.h"
+#import "WebDataSourceInternal.h"
+#import "WebDocument.h"
+#import "WebEditingDelegatePrivate.h"
+#import "WebFormDelegate.h"
+#import "WebFrameInternal.h"
+#import "WebHTMLView.h"
+#import "WebHTMLViewInternal.h"
+#import "WebKitLogging.h"
+#import "WebKitVersionChecks.h"
+#import "WebLocalizableStrings.h"
+#import "WebNSURLExtras.h"
+#import "WebViewInternal.h"
+#import <WebCore/Document.h>
+#import <WebCore/EditAction.h>
+#import <WebCore/EditCommand.h>
+#import <WebCore/KeyboardEvent.h>
+#import <WebCore/PlatformKeyboardEvent.h>
+#import <WebCore/PlatformString.h>
+#import <WebCore/WebCoreObjCExtras.h>
+#import <wtf/PassRefPtr.h>
+
+using namespace WebCore;
+using namespace WTF;
+
+EditorInsertAction core(WebViewInsertAction);
+WebViewInsertAction kit(EditorInsertAction);
+
+EditorInsertAction core(WebViewInsertAction kitAction)
+{
+ return static_cast<EditorInsertAction>(kitAction);
+}
+
+WebViewInsertAction kit(EditorInsertAction coreAction)
+{
+ return static_cast<WebViewInsertAction>(coreAction);
+}
+
+#ifdef BUILDING_ON_TIGER
+@interface NSSpellChecker (NotYetPublicMethods)
+- (void)learnWord:(NSString *)word;
+@end
+#endif
+
+@interface WebEditCommand : NSObject
+{
+ EditCommand *m_command;
+}
+
++ (WebEditCommand *)commandWithEditCommand:(PassRefPtr<EditCommand>)command;
+- (EditCommand *)command;
+
+@end
+
+@implementation WebEditCommand
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
+- (id)initWithEditCommand:(PassRefPtr<EditCommand>)command
+{
+ ASSERT(command);
+ [super init];
+ m_command = command.releaseRef();
+ return self;
+}
+
+- (void)dealloc
+{
+ m_command->deref();
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+ m_command->deref();
+ [super finalize];
+}
+
++ (WebEditCommand *)commandWithEditCommand:(PassRefPtr<EditCommand>)command
+{
+ return [[[WebEditCommand alloc] initWithEditCommand:command] autorelease];
+}
+
+- (EditCommand *)command;
+{
+ return m_command;
+}
+
+@end
+
+@interface WebEditorUndoTarget : NSObject
+{
+}
+
+- (void)undoEditing:(id)arg;
+- (void)redoEditing:(id)arg;
+
+@end
+
+@implementation WebEditorUndoTarget
+
+- (void)undoEditing:(id)arg
+{
+ ASSERT([arg isKindOfClass:[WebEditCommand class]]);
+ [arg command]->unapply();
+}
+
+- (void)redoEditing:(id)arg
+{
+ ASSERT([arg isKindOfClass:[WebEditCommand class]]);
+ [arg command]->reapply();
+}
+
+@end
+
+void WebEditorClient::pageDestroyed()
+{
+ delete this;
+}
+
+WebEditorClient::WebEditorClient(WebView *webView)
+ : m_webView(webView)
+ , m_undoTarget([[[WebEditorUndoTarget alloc] init] autorelease])
+ , m_haveUndoRedoOperations(false)
+{
+}
+
+bool WebEditorClient::isContinuousSpellCheckingEnabled()
+{
+ return [m_webView isContinuousSpellCheckingEnabled];
+}
+
+void WebEditorClient::toggleContinuousSpellChecking()
+{
+ [m_webView toggleContinuousSpellChecking:nil];
+}
+
+bool WebEditorClient::isGrammarCheckingEnabled()
+{
+#ifdef BUILDING_ON_TIGER
+ return false;
+#else
+ return [m_webView isGrammarCheckingEnabled];
+#endif
+}
+
+void WebEditorClient::toggleGrammarChecking()
+{
+#ifndef BUILDING_ON_TIGER
+ [m_webView toggleGrammarChecking:nil];
+#endif
+}
+
+int WebEditorClient::spellCheckerDocumentTag()
+{
+ return [m_webView spellCheckerDocumentTag];
+}
+
+bool WebEditorClient::isEditable()
+{
+ return [m_webView isEditable];
+}
+
+bool WebEditorClient::shouldDeleteRange(Range* range)
+{
+ return [[m_webView _editingDelegateForwarder] webView:m_webView
+ shouldDeleteDOMRange:kit(range)];
+}
+
+bool WebEditorClient::shouldShowDeleteInterface(HTMLElement* element)
+{
+ return [[m_webView _editingDelegateForwarder] webView:m_webView
+ shouldShowDeleteInterfaceForElement:kit(element)];
+}
+
+bool WebEditorClient::smartInsertDeleteEnabled()
+{
+ return [m_webView smartInsertDeleteEnabled];
+}
+
+bool WebEditorClient::shouldApplyStyle(CSSStyleDeclaration* style, Range* range)
+{
+ return [[m_webView _editingDelegateForwarder] webView:m_webView
+ shouldApplyStyle:kit(style) toElementsInDOMRange:kit(range)];
+}
+
+bool WebEditorClient::shouldMoveRangeAfterDelete(Range* range, Range* rangeToBeReplaced)
+{
+ return [[m_webView _editingDelegateForwarder] webView:m_webView
+ shouldMoveRangeAfterDelete:kit(range) replacingRange:kit(rangeToBeReplaced)];
+}
+
+bool WebEditorClient::shouldBeginEditing(Range* range)
+{
+ return [[m_webView _editingDelegateForwarder] webView:m_webView
+ shouldBeginEditingInDOMRange:kit(range)];
+
+ return false;
+}
+
+bool WebEditorClient::shouldEndEditing(Range* range)
+{
+ return [[m_webView _editingDelegateForwarder] webView:m_webView
+ shouldEndEditingInDOMRange:kit(range)];
+}
+
+bool WebEditorClient::shouldInsertText(String text, Range* range, EditorInsertAction action)
+{
+ WebView* webView = m_webView;
+ return [[webView _editingDelegateForwarder] webView:webView shouldInsertText:text replacingDOMRange:kit(range) givenAction:kit(action)];
+}
+
+bool WebEditorClient::shouldChangeSelectedRange(Range* fromRange, Range* toRange, EAffinity selectionAffinity, bool stillSelecting)
+{
+ return [m_webView _shouldChangeSelectedDOMRange:kit(fromRange) toDOMRange:kit(toRange) affinity:kit(selectionAffinity) stillSelecting:stillSelecting];
+}
+
+void WebEditorClient::didBeginEditing()
+{
+ [[NSNotificationCenter defaultCenter] postNotificationName:WebViewDidBeginEditingNotification object:m_webView];
+}
+
+void WebEditorClient::respondToChangedContents()
+{
+ NSView <WebDocumentView> *view = [[[m_webView selectedFrame] frameView] documentView];
+ if ([view isKindOfClass:[WebHTMLView class]])
+ [(WebHTMLView *)view _updateFontPanel];
+ [[NSNotificationCenter defaultCenter] postNotificationName:WebViewDidChangeNotification object:m_webView];
+}
+
+void WebEditorClient::respondToChangedSelection()
+{
+ NSView <WebDocumentView> *view = [[[m_webView selectedFrame] frameView] documentView];
+ if ([view isKindOfClass:[WebHTMLView class]])
+ [(WebHTMLView *)view _selectionChanged];
+
+ // FIXME: This quirk is needed due to <rdar://problem/5009625> - We can phase it out once Aperture can adopt the new behavior on their end
+ if (!WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITHOUT_APERTURE_QUIRK) && [[[NSBundle mainBundle] bundleIdentifier] isEqualToString:@"com.apple.Aperture"])
+ return;
+
+ [[NSNotificationCenter defaultCenter] postNotificationName:WebViewDidChangeSelectionNotification object:m_webView];
+}
+
+void WebEditorClient::didEndEditing()
+{
+ [[NSNotificationCenter defaultCenter] postNotificationName:WebViewDidEndEditingNotification object:m_webView];
+}
+
+void WebEditorClient::didWriteSelectionToPasteboard()
+{
+ [[m_webView _editingDelegateForwarder] webView:m_webView didWriteSelectionToPasteboard:[NSPasteboard generalPasteboard]];
+}
+
+void WebEditorClient::didSetSelectionTypesForPasteboard()
+{
+ [[m_webView _editingDelegateForwarder] webView:m_webView didSetSelectionTypesForPasteboard:[NSPasteboard generalPasteboard]];
+}
+
+NSData* WebEditorClient::dataForArchivedSelection(Frame* frame)
+{
+ WebArchive *archive = [WebArchiver archiveSelectionInFrame:kit(frame)];
+ return [archive data];
+}
+
+NSString* WebEditorClient::userVisibleString(NSURL *URL)
+{
+ return [URL _web_userVisibleString];
+}
+
+#ifdef BUILDING_ON_TIGER
+NSArray* WebEditorClient::pasteboardTypesForSelection(Frame* selectedFrame)
+{
+ WebFrame* frame = kit(selectedFrame);
+ return [[[frame frameView] documentView] pasteboardTypesForSelection];
+}
+#endif
+
+bool WebEditorClient::shouldInsertNode(Node *node, Range* replacingRange, EditorInsertAction givenAction)
+{
+ return [[m_webView _editingDelegateForwarder] webView:m_webView shouldInsertNode:kit(node) replacingDOMRange:kit(replacingRange) givenAction:(WebViewInsertAction)givenAction];
+}
+
+static NSString* undoNameForEditAction(EditAction editAction)
+{
+ switch (editAction) {
+ case EditActionUnspecified: return nil;
+ case EditActionSetColor: return UI_STRING_KEY("Set Color", "Set Color (Undo action name)", "Undo action name");
+ case EditActionSetBackgroundColor: return UI_STRING_KEY("Set Background Color", "Set Background Color (Undo action name)", "Undo action name");
+ case EditActionTurnOffKerning: return UI_STRING_KEY("Turn Off Kerning", "Turn Off Kerning (Undo action name)", "Undo action name");
+ case EditActionTightenKerning: return UI_STRING_KEY("Tighten Kerning", "Tighten Kerning (Undo action name)", "Undo action name");
+ case EditActionLoosenKerning: return UI_STRING_KEY("Loosen Kerning", "Loosen Kerning (Undo action name)", "Undo action name");
+ case EditActionUseStandardKerning: return UI_STRING_KEY("Use Standard Kerning", "Use Standard Kerning (Undo action name)", "Undo action name");
+ case EditActionTurnOffLigatures: return UI_STRING_KEY("Turn Off Ligatures", "Turn Off Ligatures (Undo action name)", "Undo action name");
+ case EditActionUseStandardLigatures: return UI_STRING_KEY("Use Standard Ligatures", "Use Standard Ligatures (Undo action name)", "Undo action name");
+ case EditActionUseAllLigatures: return UI_STRING_KEY("Use All Ligatures", "Use All Ligatures (Undo action name)", "Undo action name");
+ case EditActionRaiseBaseline: return UI_STRING_KEY("Raise Baseline", "Raise Baseline (Undo action name)", "Undo action name");
+ case EditActionLowerBaseline: return UI_STRING_KEY("Lower Baseline", "Lower Baseline (Undo action name)", "Undo action name");
+ case EditActionSetTraditionalCharacterShape: return UI_STRING_KEY("Set Traditional Character Shape", "Set Traditional Character Shape (Undo action name)", "Undo action name");
+ case EditActionSetFont: return UI_STRING_KEY("Set Font", "Set Font (Undo action name)", "Undo action name");
+ case EditActionChangeAttributes: return UI_STRING_KEY("Change Attributes", "Change Attributes (Undo action name)", "Undo action name");
+ case EditActionAlignLeft: return UI_STRING_KEY("Align Left", "Align Left (Undo action name)", "Undo action name");
+ case EditActionAlignRight: return UI_STRING_KEY("Align Right", "Align Right (Undo action name)", "Undo action name");
+ case EditActionCenter: return UI_STRING_KEY("Center", "Center (Undo action name)", "Undo action name");
+ case EditActionJustify: return UI_STRING_KEY("Justify", "Justify (Undo action name)", "Undo action name");
+ case EditActionSetWritingDirection: return UI_STRING_KEY("Set Writing Direction", "Set Writing Direction (Undo action name)", "Undo action name");
+ case EditActionSubscript: return UI_STRING_KEY("Subscript", "Subscript (Undo action name)", "Undo action name");
+ case EditActionSuperscript: return UI_STRING_KEY("Superscript", "Superscript (Undo action name)", "Undo action name");
+ case EditActionUnderline: return UI_STRING_KEY("Underline", "Underline (Undo action name)", "Undo action name");
+ case EditActionOutline: return UI_STRING_KEY("Outline", "Outline (Undo action name)", "Undo action name");
+ case EditActionUnscript: return UI_STRING_KEY("Unscript", "Unscript (Undo action name)", "Undo action name");
+ case EditActionDrag: return UI_STRING_KEY("Drag", "Drag (Undo action name)", "Undo action name");
+ case EditActionCut: return UI_STRING_KEY("Cut", "Cut (Undo action name)", "Undo action name");
+ case EditActionPaste: return UI_STRING_KEY("Paste", "Paste (Undo action name)", "Undo action name");
+ case EditActionPasteFont: return UI_STRING_KEY("Paste Font", "Paste Font (Undo action name)", "Undo action name");
+ case EditActionPasteRuler: return UI_STRING_KEY("Paste Ruler", "Paste Ruler (Undo action name)", "Undo action name");
+ case EditActionTyping: return UI_STRING_KEY("Typing", "Typing (Undo action name)", "Undo action name");
+ case EditActionCreateLink: return UI_STRING_KEY("Create Link", "Create Link (Undo action name)", "Undo action name");
+ case EditActionUnlink: return UI_STRING_KEY("Unlink", "Unlink (Undo action name)", "Undo action name");
+ case EditActionInsertList: return UI_STRING_KEY("Insert List", "Insert List (Undo action name)", "Undo action name");
+ case EditActionFormatBlock: return UI_STRING_KEY("Formatting", "Format Block (Undo action name)", "Undo action name");
+ case EditActionIndent: return UI_STRING_KEY("Indent", "Indent (Undo action name)", "Undo action name");
+ case EditActionOutdent: return UI_STRING_KEY("Outdent", "Outdent (Undo action name)", "Undo action name");
+ }
+ return nil;
+}
+
+void WebEditorClient::registerCommandForUndoOrRedo(PassRefPtr<EditCommand> cmd, bool isRedo)
+{
+ ASSERT(cmd);
+
+ NSUndoManager *undoManager = [m_webView undoManager];
+ NSString *actionName = undoNameForEditAction(cmd->editingAction());
+ WebEditCommand *command = [WebEditCommand commandWithEditCommand:cmd];
+ [undoManager registerUndoWithTarget:m_undoTarget.get() selector:(isRedo ? @selector(redoEditing:) : @selector(undoEditing:)) object:command];
+ if (actionName)
+ [undoManager setActionName:actionName];
+ m_haveUndoRedoOperations = YES;
+}
+
+void WebEditorClient::registerCommandForUndo(PassRefPtr<EditCommand> cmd)
+{
+ registerCommandForUndoOrRedo(cmd, false);
+}
+
+void WebEditorClient::registerCommandForRedo(PassRefPtr<EditCommand> cmd)
+{
+ registerCommandForUndoOrRedo(cmd, true);
+}
+
+void WebEditorClient::clearUndoRedoOperations()
+{
+ if (m_haveUndoRedoOperations) {
+ // workaround for <rdar://problem/4645507> NSUndoManager dies
+ // with uncaught exception when undo items cleared while
+ // groups are open
+ NSUndoManager *undoManager = [m_webView undoManager];
+ int groupingLevel = [undoManager groupingLevel];
+ for (int i = 0; i < groupingLevel; ++i)
+ [undoManager endUndoGrouping];
+
+ [undoManager removeAllActionsWithTarget:m_undoTarget.get()];
+
+ for (int i = 0; i < groupingLevel; ++i)
+ [undoManager beginUndoGrouping];
+
+ m_haveUndoRedoOperations = NO;
+ }
+}
+
+bool WebEditorClient::canUndo() const
+{
+ return [[m_webView undoManager] canUndo];
+}
+
+bool WebEditorClient::canRedo() const
+{
+ return [[m_webView undoManager] canRedo];
+}
+
+void WebEditorClient::undo()
+{
+ if (canUndo())
+ [[m_webView undoManager] undo];
+}
+
+void WebEditorClient::redo()
+{
+ if (canRedo())
+ [[m_webView undoManager] redo];
+}
+
+void WebEditorClient::handleKeyboardEvent(KeyboardEvent* event)
+{
+ Frame* frame = event->target()->toNode()->document()->frame();
+ WebHTMLView *webHTMLView = [[kit(frame) frameView] documentView];
+ if ([webHTMLView _interceptEditingKeyEvent:event shouldSaveCommand:NO])
+ event->setDefaultHandled();
+}
+
+void WebEditorClient::handleInputMethodKeydown(KeyboardEvent* event)
+{
+ Frame* frame = event->target()->toNode()->document()->frame();
+ WebHTMLView *webHTMLView = [[kit(frame) frameView] documentView];
+ if ([webHTMLView _interceptEditingKeyEvent:event shouldSaveCommand:YES])
+ event->setDefaultHandled();
+}
+
+#define FormDelegateLog(ctrl) LOG(FormDelegate, "control=%@", ctrl)
+
+void WebEditorClient::textFieldDidBeginEditing(Element* element)
+{
+ DOMHTMLInputElement* inputElement = [DOMHTMLInputElement _wrapHTMLInputElement:(HTMLInputElement*)element];
+ FormDelegateLog(inputElement);
+ CallFormDelegate(m_webView, @selector(textFieldDidBeginEditing:inFrame:), inputElement, kit(element->document()->frame()));
+}
+
+void WebEditorClient::textFieldDidEndEditing(Element* element)
+{
+ DOMHTMLInputElement* inputElement = [DOMHTMLInputElement _wrapHTMLInputElement:(HTMLInputElement*)element];
+ FormDelegateLog(inputElement);
+ CallFormDelegate(m_webView, @selector(textFieldDidEndEditing:inFrame:), inputElement, kit(element->document()->frame()));
+}
+
+void WebEditorClient::textDidChangeInTextField(Element* element)
+{
+ DOMHTMLInputElement* inputElement = [DOMHTMLInputElement _wrapHTMLInputElement:(HTMLInputElement*)element];
+ FormDelegateLog(inputElement);
+ CallFormDelegate(m_webView, @selector(textDidChangeInTextField:inFrame:), inputElement, kit(element->document()->frame()));
+}
+
+static SEL selectorForKeyEvent(KeyboardEvent* event)
+{
+ // FIXME: This helper function is for the auto-fill code so the bridge can pass a selector to the form delegate.
+ // Eventually, we should move all of the auto-fill code down to WebKit and remove the need for this function by
+ // not relying on the selector in the new implementation.
+ // The key identifiers are from <http://www.w3.org/TR/DOM-Level-3-Events/keyset.html#KeySet-Set>
+ String key = event->keyIdentifier();
+ if (key == "Up")
+ return @selector(moveUp:);
+ if (key == "Down")
+ return @selector(moveDown:);
+ if (key == "U+001B")
+ return @selector(cancel:);
+ if (key == "U+0009") {
+ if (event->shiftKey())
+ return @selector(insertBacktab:);
+ return @selector(insertTab:);
+ }
+ if (key == "Enter")
+ return @selector(insertNewline:);
+ return 0;
+}
+
+bool WebEditorClient::doTextFieldCommandFromEvent(Element* element, KeyboardEvent* event)
+{
+ DOMHTMLInputElement* inputElement = [DOMHTMLInputElement _wrapHTMLInputElement:(HTMLInputElement*)element];
+ FormDelegateLog(inputElement);
+ if (SEL commandSelector = selectorForKeyEvent(event))
+ return CallFormDelegateReturningBoolean(NO, m_webView, @selector(textField:doCommandBySelector:inFrame:), inputElement, commandSelector, kit(element->document()->frame()));
+ return NO;
+}
+
+void WebEditorClient::textWillBeDeletedInTextField(Element* element)
+{
+ DOMHTMLInputElement* inputElement = [DOMHTMLInputElement _wrapHTMLInputElement:(HTMLInputElement*)element];
+ FormDelegateLog(inputElement);
+ // We're using the deleteBackward selector for all deletion operations since the autofill code treats all deletions the same way.
+ CallFormDelegateReturningBoolean(NO, m_webView, @selector(textField:doCommandBySelector:inFrame:), inputElement, @selector(deleteBackward:), kit(element->document()->frame()));
+}
+
+void WebEditorClient::textDidChangeInTextArea(Element* element)
+{
+ DOMHTMLTextAreaElement* textAreaElement = [DOMHTMLTextAreaElement _wrapHTMLTextAreaElement:(HTMLTextAreaElement*)element];
+ FormDelegateLog(textAreaElement);
+ CallFormDelegate(m_webView, @selector(textDidChangeInTextArea:inFrame:), textAreaElement, kit(element->document()->frame()));
+}
+
+void WebEditorClient::ignoreWordInSpellDocument(const String& text)
+{
+ [[NSSpellChecker sharedSpellChecker] ignoreWord:text
+ inSpellDocumentWithTag:spellCheckerDocumentTag()];
+}
+
+void WebEditorClient::learnWord(const String& text)
+{
+ [[NSSpellChecker sharedSpellChecker] learnWord:text];
+}
+
+void WebEditorClient::checkSpellingOfString(const UChar* text, int length, int* misspellingLocation, int* misspellingLength)
+{
+ NSString* textString = [[NSString alloc] initWithCharactersNoCopy:const_cast<UChar*>(text) length:length freeWhenDone:NO];
+ NSRange range = [[NSSpellChecker sharedSpellChecker] checkSpellingOfString:textString startingAt:0 language:nil wrap:NO inSpellDocumentWithTag:spellCheckerDocumentTag() wordCount:NULL];
+ [textString release];
+ if (misspellingLocation) {
+ // WebCore expects -1 to represent "not found"
+ if (range.location == NSNotFound)
+ *misspellingLocation = -1;
+ else
+ *misspellingLocation = range.location;
+ }
+
+ if (misspellingLength)
+ *misspellingLength = range.length;
+}
+
+void WebEditorClient::checkGrammarOfString(const UChar* text, int length, Vector<GrammarDetail>& details, int* badGrammarLocation, int* badGrammarLength)
+{
+#ifndef BUILDING_ON_TIGER
+ NSArray *grammarDetails;
+ NSString* textString = [[NSString alloc] initWithCharactersNoCopy:const_cast<UChar*>(text) length:length freeWhenDone:NO];
+ NSRange range = [[NSSpellChecker sharedSpellChecker] checkGrammarOfString:textString startingAt:0 language:nil wrap:NO inSpellDocumentWithTag:spellCheckerDocumentTag() details:&grammarDetails];
+ [textString release];
+ if (badGrammarLocation)
+ // WebCore expects -1 to represent "not found"
+ *badGrammarLocation = (range.location == NSNotFound) ? -1 : range.location;
+ if (badGrammarLength)
+ *badGrammarLength = range.length;
+ for (NSDictionary *detail in grammarDetails) {
+ ASSERT(detail);
+ GrammarDetail grammarDetail;
+ NSValue *detailRangeAsNSValue = [detail objectForKey:NSGrammarRange];
+ ASSERT(detailRangeAsNSValue);
+ NSRange detailNSRange = [detailRangeAsNSValue rangeValue];
+ ASSERT(detailNSRange.location != NSNotFound && detailNSRange.length > 0);
+ grammarDetail.location = detailNSRange.location;
+ grammarDetail.length = detailNSRange.length;
+ grammarDetail.userDescription = [detail objectForKey:NSGrammarUserDescription];
+ NSArray *guesses = [detail objectForKey:NSGrammarCorrections];
+ for (NSString *guess in guesses)
+ grammarDetail.guesses.append(String(guess));
+ details.append(grammarDetail);
+ }
+#endif
+}
+
+void WebEditorClient::updateSpellingUIWithGrammarString(const String& badGrammarPhrase, const GrammarDetail& grammarDetail)
+{
+#ifndef BUILDING_ON_TIGER
+ NSMutableArray* corrections = [NSMutableArray array];
+ for (unsigned i = 0; i < grammarDetail.guesses.size(); i++) {
+ NSString* guess = grammarDetail.guesses[i];
+ [corrections addObject:guess];
+ }
+ NSRange grammarRange = NSMakeRange(grammarDetail.location, grammarDetail.length);
+ NSString* grammarUserDescription = grammarDetail.userDescription;
+ NSMutableDictionary* grammarDetailDict = [NSDictionary dictionaryWithObjectsAndKeys:[NSValue valueWithRange:grammarRange], NSGrammarRange, grammarUserDescription, NSGrammarUserDescription, corrections, NSGrammarCorrections, nil];
+
+ [[NSSpellChecker sharedSpellChecker] updateSpellingPanelWithGrammarString:badGrammarPhrase detail:grammarDetailDict];
+#endif
+}
+
+void WebEditorClient::updateSpellingUIWithMisspelledWord(const String& misspelledWord)
+{
+ [[NSSpellChecker sharedSpellChecker] updateSpellingPanelWithMisspelledWord:misspelledWord];
+}
+
+void WebEditorClient::showSpellingUI(bool show)
+{
+ NSPanel *spellingPanel = [[NSSpellChecker sharedSpellChecker] spellingPanel];
+ if (show)
+ [spellingPanel orderFront:nil];
+ else
+ [spellingPanel orderOut:nil];
+}
+
+bool WebEditorClient::spellingUIIsShowing()
+{
+ return [[[NSSpellChecker sharedSpellChecker] spellingPanel] isVisible];
+}
+
+void WebEditorClient::getGuessesForWord(const String& word, WTF::Vector<String>& guesses)
+{
+ NSArray* stringsArray = [[NSSpellChecker sharedSpellChecker] guessesForWord:word];
+ unsigned count = [stringsArray count];
+ guesses.clear();
+ if (count > 0) {
+ NSEnumerator* enumerator = [stringsArray objectEnumerator];
+ NSString* string;
+ while ((string = [enumerator nextObject]) != nil)
+ guesses.append(string);
+ }
+}
+
+void WebEditorClient::setInputMethodState(bool)
+{
+}
diff --git a/WebKit/mac/WebCoreSupport/WebFrameBridge.h b/WebKit/mac/WebCoreSupport/WebFrameBridge.h
new file mode 100644
index 0000000..05d5bc0
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebFrameBridge.h
@@ -0,0 +1,83 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/WebCoreFrameBridge.h>
+
+namespace WebCore {
+ class Page;
+}
+
+@class WebFrame;
+@class WebFrameView;
+
+@protocol WebOpenPanelResultListener;
+
+@interface WebFrameBridge : WebCoreFrameBridge <WebCoreFrameBridge>
+{
+@public
+ WebFrame *_frame;
+
+@private
+ WebCore::KeyboardUIMode _keyboardUIMode;
+ BOOL _keyboardUIModeAccessed;
+ BOOL _doingClientRedirect;
+ BOOL _haveUndoRedoOperations;
+
+ NSDictionary *lastDashboardRegions;
+}
+
+- (id)initMainFrameWithPage:(WebCore::Page*)page frameName:(NSString *)name frameView:(WebFrameView *)frameView;
+- (void)close;
+
+- (WebFrame *)webFrame;
+
+// The following methods can all move off the bridge; they're used on the WebKit side only.
+
+- (NSView *)viewForPluginWithFrame:(NSRect)frame
+ URL:(NSURL *)URL
+ attributeNames:(NSArray *)attributeNames
+ attributeValues:(NSArray *)attributeValues
+ MIMEType:(NSString *)MIMEType
+ DOMElement:(DOMElement *)element
+ loadManually:(BOOL)loadManually;
+- (NSView *)viewForJavaAppletWithFrame:(NSRect)frame
+ attributeNames:(NSArray *)attributeNames
+ attributeValues:(NSArray *)attributeValues
+ baseURL:(NSURL *)baseURL
+ DOMElement:(DOMElement *)element;
+
+- (WebCore::Frame*)createChildFrameNamed:(NSString *)frameName withURL:(NSURL *)URL referrer:(const WebCore::String&)referrer
+ ownerElement:(WebCore::HTMLFrameOwnerElement *)ownerElement allowsScrolling:(BOOL)allowsScrolling marginWidth:(int)width marginHeight:(int)height;
+
+- (void)redirectDataToPlugin:(NSView *)pluginView;
+
+- (WebCore::ObjectContentType)determineObjectFromMIMEType:(NSString*)MIMEType URL:(NSURL*)URL;
+
+- (void)windowObjectCleared;
+
+@end
diff --git a/WebKit/mac/WebCoreSupport/WebFrameBridge.mm b/WebKit/mac/WebCoreSupport/WebFrameBridge.mm
new file mode 100644
index 0000000..8e0ba51
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebFrameBridge.mm
@@ -0,0 +1,741 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebFrameBridge.h"
+
+#import "WebBackForwardList.h"
+#import "WebBaseNetscapePluginView.h"
+#import "WebBasePluginPackage.h"
+#import "WebDataSourceInternal.h"
+#import "WebDefaultUIDelegate.h"
+#import "WebEditingDelegate.h"
+#import "WebFormDelegate.h"
+#import "WebFrameInternal.h"
+#import "WebFrameLoadDelegate.h"
+#import "WebFrameLoaderClient.h"
+#import "WebFrameViewInternal.h"
+#import "WebHTMLRepresentationPrivate.h"
+#import "WebHTMLViewInternal.h"
+#import "WebHistoryItemInternal.h"
+#import "WebHistoryItemPrivate.h"
+#import "WebJavaPlugIn.h"
+#import "WebJavaScriptTextInputPanel.h"
+#import "WebKitErrorsPrivate.h"
+#import "WebKitLogging.h"
+#import "WebKitNSStringExtras.h"
+#import "WebKitPluginContainerView.h"
+#import "WebKitStatisticsPrivate.h"
+#import "WebKitSystemBits.h"
+#import "WebLocalizableStrings.h"
+#import "WebNSObjectExtras.h"
+#import "WebNSURLExtras.h"
+#import "WebNSURLRequestExtras.h"
+#import "WebNSViewExtras.h"
+#import "WebNetscapePluginEmbeddedView.h"
+#import "WebNetscapePluginPackage.h"
+#import "WebNullPluginView.h"
+#import "WebPlugin.h"
+#import "WebPluginController.h"
+#import "WebPluginDatabase.h"
+#import "WebPluginPackage.h"
+#import "WebPluginViewFactoryPrivate.h"
+#import "WebPreferencesPrivate.h"
+#import "WebResourcePrivate.h"
+#import "WebScriptDebugServerPrivate.h"
+#import "WebUIDelegatePrivate.h"
+#import "WebViewInternal.h"
+#import <Foundation/NSURLConnection.h>
+#import <Foundation/NSURLRequest.h>
+#import <Foundation/NSURLResponse.h>
+#import <JavaScriptCore/Assertions.h>
+#import <JavaScriptCore/JSLock.h>
+#import <JavaScriptCore/object.h>
+#import <JavaVM/jni.h>
+#import <WebCore/Cache.h>
+#import <WebCore/Document.h>
+#import <WebCore/DocumentLoader.h>
+#import <WebCore/DragController.h>
+#import <WebCore/Element.h>
+#import <WebCore/FoundationExtras.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/FrameLoaderClient.h>
+#import <WebCore/FrameTree.h>
+#import <WebCore/HTMLFrameOwnerElement.h>
+#import <WebCore/Page.h>
+#import <WebCore/ResourceLoader.h>
+#import <WebCore/SubresourceLoader.h>
+#import <WebCore/WebCoreObjCExtras.h>
+#import <WebKitSystemInterface.h>
+#import <wtf/RefPtr.h>
+#import <WebCore/MIMETypeRegistry.h>
+
+// For compatibility with old SPI.
+@interface NSView (OldWebPlugin)
+- (void)setIsSelected:(BOOL)f;
+@end
+
+@interface NSView (JavaPluginSecrets)
+- (jobject)pollForAppletInWindow:(NSWindow *)window;
+@end
+
+using namespace WebCore;
+
+NSString *WebPluginBaseURLKey = @"WebPluginBaseURL";
+NSString *WebPluginAttributesKey = @"WebPluginAttributes";
+NSString *WebPluginContainerKey = @"WebPluginContainer";
+
+#define KeyboardUIModeDidChangeNotification @"com.apple.KeyboardUIModeDidChange"
+#define AppleKeyboardUIMode CFSTR("AppleKeyboardUIMode")
+#define UniversalAccessDomain CFSTR("com.apple.universalaccess")
+
+@implementation WebFrameBridge
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
+- (WebView *)webView
+{
+ if (!m_frame)
+ return nil;
+
+ return kit(m_frame->page());
+}
+
+- (void)finishInitializingWithPage:(Page*)page frameName:(NSString *)name frameView:(WebFrameView *)frameView ownerElement:(HTMLFrameOwnerElement*)ownerElement
+{
+ ++WebBridgeCount;
+
+ WebView *webView = kit(page);
+
+ _frame = [[WebFrame alloc] _initWithWebFrameView:frameView webView:webView bridge:self];
+
+ m_frame = new Frame(page, ownerElement, new WebFrameLoaderClient(_frame));
+ m_frame->setBridge(self);
+ m_frame->tree()->setName(name);
+ m_frame->init();
+
+ [self setTextSizeMultiplier:[webView textSizeMultiplier]];
+}
+
+- (id)initMainFrameWithPage:(Page*)page frameName:(NSString *)name frameView:(WebFrameView *)frameView
+{
+ self = [super init];
+ [self finishInitializingWithPage:page frameName:name frameView:frameView ownerElement:0];
+ return self;
+}
+
+- (id)initSubframeWithOwnerElement:(HTMLFrameOwnerElement*)ownerElement frameName:(NSString *)name frameView:(WebFrameView *)frameView
+{
+ self = [super init];
+ [self finishInitializingWithPage:ownerElement->document()->frame()->page() frameName:name frameView:frameView ownerElement:ownerElement];
+ return self;
+}
+
+- (void)fini
+{
+ if (_keyboardUIModeAccessed) {
+ [[NSDistributedNotificationCenter defaultCenter]
+ removeObserver:self name:KeyboardUIModeDidChangeNotification object:nil];
+ [[NSNotificationCenter defaultCenter]
+ removeObserver:self name:WebPreferencesChangedNotification object:nil];
+ }
+
+ ASSERT(_frame == nil);
+ --WebBridgeCount;
+}
+
+- (void)dealloc
+{
+ [lastDashboardRegions release];
+ [_frame release];
+
+ [self fini];
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+ [self fini];
+ [super finalize];
+}
+
+- (WebPreferences *)_preferences
+{
+ return [[self webView] preferences];
+}
+
+- (void)_retrieveKeyboardUIModeFromPreferences:(NSNotification *)notification
+{
+ CFPreferencesAppSynchronize(UniversalAccessDomain);
+
+ Boolean keyExistsAndHasValidFormat;
+ int mode = CFPreferencesGetAppIntegerValue(AppleKeyboardUIMode, UniversalAccessDomain, &keyExistsAndHasValidFormat);
+
+ // The keyboard access mode is reported by two bits:
+ // Bit 0 is set if feature is on
+ // Bit 1 is set if full keyboard access works for any control, not just text boxes and lists
+ // We require both bits to be on.
+ // I do not know that we would ever get one bit on and the other off since
+ // checking the checkbox in system preferences which is marked as "Turn on full keyboard access"
+ // turns on both bits.
+ _keyboardUIMode = (mode & 0x2) ? KeyboardAccessFull : KeyboardAccessDefault;
+
+ // check for tabbing to links
+ if ([[self _preferences] tabsToLinks])
+ _keyboardUIMode = (KeyboardUIMode)(_keyboardUIMode | KeyboardAccessTabsToLinks);
+}
+
+- (KeyboardUIMode)keyboardUIMode
+{
+ if (!_keyboardUIModeAccessed) {
+ _keyboardUIModeAccessed = YES;
+ [self _retrieveKeyboardUIModeFromPreferences:nil];
+
+ [[NSDistributedNotificationCenter defaultCenter]
+ addObserver:self selector:@selector(_retrieveKeyboardUIModeFromPreferences:)
+ name:KeyboardUIModeDidChangeNotification object:nil];
+
+ [[NSNotificationCenter defaultCenter]
+ addObserver:self selector:@selector(_retrieveKeyboardUIModeFromPreferences:)
+ name:WebPreferencesChangedNotification object:nil];
+ }
+ return _keyboardUIMode;
+}
+
+- (WebFrame *)webFrame
+{
+ return _frame;
+}
+
+- (WebCoreFrameBridge *)mainFrame
+{
+ ASSERT(_frame != nil);
+ return [[[self webView] mainFrame] _bridge];
+}
+
+- (NSResponder *)firstResponder
+{
+ ASSERT(_frame != nil);
+ WebView *webView = [self webView];
+ return [[webView _UIDelegateForwarder] webViewFirstResponder:webView];
+}
+
+- (void)makeFirstResponder:(NSResponder *)view
+{
+ ASSERT(_frame != nil);
+ WebView *webView = [self webView];
+ ASSERT([view isKindOfClass:[NSView class]]);
+ ASSERT([(NSView *)view window]);
+ ASSERT([(NSView *)view window] == [webView window]);
+ [webView _pushPerformingProgrammaticFocus];
+ [[webView _UIDelegateForwarder] webView:webView makeFirstResponder:view];
+ [webView _popPerformingProgrammaticFocus];
+}
+
+- (NSWindow *)window
+{
+ ASSERT(_frame != nil);
+ return [[_frame frameView] window];
+}
+
+- (void)runOpenPanelForFileButtonWithResultListener:(id<WebCoreOpenPanelResultListener>)resultListener
+{
+ WebView *wv = [self webView];
+ [[wv _UIDelegateForwarder] webView:wv runOpenPanelForFileButtonWithResultListener:(id<WebOpenPanelResultListener>)resultListener];
+}
+
+- (WebDataSource *)dataSource
+{
+ ASSERT(_frame != nil);
+ WebDataSource *dataSource = [_frame _dataSource];
+
+ ASSERT(dataSource != nil);
+
+ return dataSource;
+}
+
+- (void)close
+{
+ [super close];
+ [_frame release];
+ _frame = nil;
+}
+
+- (Frame*)createChildFrameNamed:(NSString *)frameName
+ withURL:(NSURL *)URL
+ referrer:(const String&)referrer
+ ownerElement:(HTMLFrameOwnerElement*)ownerElement
+ allowsScrolling:(BOOL)allowsScrolling
+ marginWidth:(int)width
+ marginHeight:(int)height
+{
+ ASSERT(_frame);
+
+ WebFrameView *childView = [[WebFrameView alloc] initWithFrame:NSMakeRect(0,0,0,0)];
+ [childView setAllowsScrolling:allowsScrolling];
+ [childView _setMarginWidth:width];
+ [childView _setMarginHeight:height];
+
+ WebFrameBridge *newBridge = [[WebFrameBridge alloc] initSubframeWithOwnerElement:ownerElement frameName:frameName frameView:childView];
+ [childView release];
+
+ if (!newBridge)
+ return 0;
+
+ [_frame _addChild:[newBridge webFrame]];
+ [newBridge release];
+
+ RefPtr<Frame> newFrame = [newBridge _frame];
+
+ [_frame _loadURL:URL referrer:referrer intoChild:kit(newFrame.get())];
+
+ // The frame's onload handler may have removed it from the document.
+ if (!newFrame->tree()->parent())
+ return 0;
+
+ return newFrame.get();
+}
+
+- (NSView *)pluginViewWithPackage:(WebPluginPackage *)pluginPackage
+ attributeNames:(NSArray *)attributeNames
+ attributeValues:(NSArray *)attributeValues
+ baseURL:(NSURL *)baseURL
+ DOMElement:(DOMElement *)element
+ loadManually:(BOOL)loadManually
+{
+ WebHTMLView *docView = (WebHTMLView *)[[_frame frameView] documentView];
+ ASSERT([docView isKindOfClass:[WebHTMLView class]]);
+
+ WebPluginController *pluginController = [docView _pluginController];
+
+ // Store attributes in a dictionary so they can be passed to WebPlugins.
+ NSMutableDictionary *attributes = [[NSMutableDictionary alloc] initWithObjects:attributeValues forKeys:attributeNames];
+
+ [pluginPackage load];
+ Class viewFactory = [pluginPackage viewFactory];
+
+ NSView *view = nil;
+ NSDictionary *arguments = nil;
+
+ if ([viewFactory respondsToSelector:@selector(plugInViewWithArguments:)]) {
+ arguments = [NSDictionary dictionaryWithObjectsAndKeys:
+ baseURL, WebPlugInBaseURLKey,
+ attributes, WebPlugInAttributesKey,
+ pluginController, WebPlugInContainerKey,
+ [NSNumber numberWithInt:loadManually ? WebPlugInModeFull : WebPlugInModeEmbed], WebPlugInModeKey,
+ [NSNumber numberWithBool:!loadManually], WebPlugInShouldLoadMainResourceKey,
+ element, WebPlugInContainingElementKey,
+ nil];
+ LOG(Plugins, "arguments:\n%@", arguments);
+ } else if ([viewFactory respondsToSelector:@selector(pluginViewWithArguments:)]) {
+ arguments = [NSDictionary dictionaryWithObjectsAndKeys:
+ baseURL, WebPluginBaseURLKey,
+ attributes, WebPluginAttributesKey,
+ pluginController, WebPluginContainerKey,
+ element, WebPlugInContainingElementKey,
+ nil];
+ LOG(Plugins, "arguments:\n%@", arguments);
+ }
+
+ view = [WebPluginController plugInViewWithArguments:arguments fromPluginPackage:pluginPackage];
+ [attributes release];
+ return view;
+}
+
+- (NSString *)valueForKey:(NSString *)key keys:(NSArray *)keys values:(NSArray *)values
+{
+ unsigned count = [keys count];
+ unsigned i;
+ for (i = 0; i < count; i++)
+ if ([[keys objectAtIndex:i] _webkit_isCaseInsensitiveEqualToString:key])
+ return [values objectAtIndex:i];
+ return nil;
+}
+
+- (NSView *)viewForPluginWithFrame:(NSRect)frame
+ URL:(NSURL *)URL
+ attributeNames:(NSArray *)attributeNames
+ attributeValues:(NSArray *)attributeValues
+ MIMEType:(NSString *)MIMEType
+ DOMElement:(DOMElement *)element
+ loadManually:(BOOL)loadManually
+{
+ ASSERT([attributeNames count] == [attributeValues count]);
+
+ WebBasePluginPackage *pluginPackage = nil;
+ NSView *view = nil;
+ int errorCode = 0;
+
+ WebView *webView = [self webView];
+ SEL selector = @selector(webView:plugInViewWithArguments:);
+
+ if ([[webView UIDelegate] respondsToSelector:selector]) {
+ NSMutableDictionary *attributes = [[NSMutableDictionary alloc] initWithObjects:attributeValues forKeys:attributeNames];
+ NSDictionary *arguments = [[NSDictionary alloc] initWithObjectsAndKeys:
+ attributes, WebPlugInAttributesKey,
+ [NSNumber numberWithInt:loadManually ? WebPlugInModeFull : WebPlugInModeEmbed], WebPlugInModeKey,
+ [NSNumber numberWithBool:!loadManually], WebPlugInShouldLoadMainResourceKey,
+ element, WebPlugInContainingElementKey,
+ URL, WebPlugInBaseURLKey, // URL might be nil, so add it last
+ nil];
+
+ view = CallUIDelegate(webView, selector, arguments);
+
+ [attributes release];
+ [arguments release];
+
+ if (view)
+ return view;
+ }
+
+ if ([MIMEType length] != 0)
+ pluginPackage = [[self webView] _pluginForMIMEType:MIMEType];
+ else
+ MIMEType = nil;
+
+ NSString *extension = [[URL path] pathExtension];
+ if (!pluginPackage && [extension length] != 0) {
+ pluginPackage = [[self webView] _pluginForExtension:extension];
+ if (pluginPackage) {
+ NSString *newMIMEType = [pluginPackage MIMETypeForExtension:extension];
+ if ([newMIMEType length] != 0)
+ MIMEType = newMIMEType;
+ }
+ }
+
+ NSURL *baseURL = [self baseURL];
+ if (pluginPackage) {
+ if ([pluginPackage isKindOfClass:[WebPluginPackage class]]) {
+ view = [self pluginViewWithPackage:(WebPluginPackage *)pluginPackage
+ attributeNames:attributeNames
+ attributeValues:attributeValues
+ baseURL:baseURL
+ DOMElement:element
+ loadManually:loadManually];
+
+ }
+#ifndef __LP64__
+ else if ([pluginPackage isKindOfClass:[WebNetscapePluginPackage class]]) {
+ WebNetscapePluginEmbeddedView *embeddedView = [[[WebNetscapePluginEmbeddedView alloc] initWithFrame:frame
+ pluginPackage:(WebNetscapePluginPackage *)pluginPackage
+ URL:URL
+ baseURL:baseURL
+ MIMEType:MIMEType
+ attributeKeys:attributeNames
+ attributeValues:attributeValues
+ loadManually:loadManually
+ DOMElement:element] autorelease];
+ view = embeddedView;
+ }
+#endif
+ } else
+ errorCode = WebKitErrorCannotFindPlugIn;
+
+ if (!errorCode && !view)
+ errorCode = WebKitErrorCannotLoadPlugIn;
+
+ if (errorCode) {
+ NSString *pluginPage = [self valueForKey:@"pluginspage" keys:attributeNames values:attributeValues];
+ NSURL *pluginPageURL = pluginPage != nil ? [self URLWithAttributeString:pluginPage] : nil;
+ NSError *error = [[NSError alloc] _initWithPluginErrorCode:errorCode
+ contentURL:URL
+ pluginPageURL:pluginPageURL
+ pluginName:[pluginPackage name]
+ MIMEType:MIMEType];
+ WebNullPluginView *nullView = [[[WebNullPluginView alloc] initWithFrame:frame error:error DOMElement:element] autorelease];
+ view = nullView;
+ [error release];
+ }
+
+ ASSERT(view);
+ return view;
+}
+
+- (void)redirectDataToPlugin:(NSView *)pluginView
+{
+ WebHTMLRepresentation *representation = (WebHTMLRepresentation *)[[_frame _dataSource] representation];
+
+#ifndef __LP64__
+ if ([pluginView isKindOfClass:[WebNetscapePluginEmbeddedView class]])
+ [representation _redirectDataToManualLoader:(WebNetscapePluginEmbeddedView *)pluginView forPluginView:pluginView];
+ else {
+#else
+ {
+#endif
+ WebHTMLView *docView = (WebHTMLView *)[[_frame frameView] documentView];
+ ASSERT([docView isKindOfClass:[WebHTMLView class]]);
+
+ WebPluginController *pluginController = [docView _pluginController];
+ [representation _redirectDataToManualLoader:pluginController forPluginView:pluginView];
+ }
+
+}
+
+- (NSView *)viewForJavaAppletWithFrame:(NSRect)theFrame
+ attributeNames:(NSArray *)attributeNames
+ attributeValues:(NSArray *)attributeValues
+ baseURL:(NSURL *)baseURL
+ DOMElement:(DOMElement *)element
+{
+ NSString *MIMEType = @"application/x-java-applet";
+ WebBasePluginPackage *pluginPackage;
+ NSView *view = nil;
+
+ pluginPackage = [[self webView] _pluginForMIMEType:MIMEType];
+
+ if (pluginPackage) {
+ if ([pluginPackage isKindOfClass:[WebPluginPackage class]]) {
+ // For some reason, the Java plug-in requires that we pass the dimension of the plug-in as attributes.
+ NSMutableArray *names = [attributeNames mutableCopy];
+ NSMutableArray *values = [attributeValues mutableCopy];
+ if ([self valueForKey:@"width" keys:attributeNames values:attributeValues] == nil) {
+ [names addObject:@"width"];
+ [values addObject:[NSString stringWithFormat:@"%d", (int)theFrame.size.width]];
+ }
+ if ([self valueForKey:@"height" keys:attributeNames values:attributeValues] == nil) {
+ [names addObject:@"height"];
+ [values addObject:[NSString stringWithFormat:@"%d", (int)theFrame.size.height]];
+ }
+ view = [self pluginViewWithPackage:(WebPluginPackage *)pluginPackage
+ attributeNames:names
+ attributeValues:values
+ baseURL:baseURL
+ DOMElement:element
+ loadManually:NO];
+ [names release];
+ [values release];
+
+ }
+#ifndef __LP64__
+ else if ([pluginPackage isKindOfClass:[WebNetscapePluginPackage class]]) {
+ view = [[[WebNetscapePluginEmbeddedView alloc] initWithFrame:theFrame
+ pluginPackage:(WebNetscapePluginPackage *)pluginPackage
+ URL:nil
+ baseURL:baseURL
+ MIMEType:MIMEType
+ attributeKeys:attributeNames
+ attributeValues:attributeValues
+ loadManually:NO
+ DOMElement:element] autorelease];
+ } else {
+ ASSERT_NOT_REACHED();
+ }
+#endif
+ }
+
+ if (!view) {
+ NSError *error = [[NSError alloc] _initWithPluginErrorCode:WebKitErrorJavaUnavailable
+ contentURL:nil
+ pluginPageURL:nil
+ pluginName:[pluginPackage name]
+ MIMEType:MIMEType];
+ view = [[[WebNullPluginView alloc] initWithFrame:theFrame error:error DOMElement:element] autorelease];
+ [error release];
+ }
+
+ ASSERT(view);
+
+ return view;
+}
+
+- (ObjectContentType)determineObjectFromMIMEType:(NSString*)MIMEType URL:(NSURL*)URL
+{
+ // This is a quirk that ensures Tiger Mail's WebKit plug-in will load during layout
+ // and not attach time. (5520541)
+ static BOOL isTigerMail = WKAppVersionCheckLessThan(@"com.apple.mail", -1, 3.0);
+ if (isTigerMail && [MIMEType isEqualToString:@"application/x-apple-msg-attachment"])
+ return ObjectContentNetscapePlugin;
+
+ if ([MIMEType length] == 0) {
+ // Try to guess the MIME type based off the extension.
+ NSString *extension = [[URL path] pathExtension];
+ if ([extension length] > 0) {
+ MIMEType = WKGetMIMETypeForExtension(extension);
+ if ([MIMEType length] == 0) {
+ // If no MIME type is specified, use a plug-in if we have one that can handle the extension.
+ if (WebBasePluginPackage *package = [[self webView] _pluginForExtension:extension]) {
+ if ([package isKindOfClass:[WebPluginPackage class]])
+ return ObjectContentOtherPlugin;
+#ifndef __LP64__
+ else {
+ ASSERT([package isKindOfClass:[WebNetscapePluginPackage class]]);
+ return ObjectContentNetscapePlugin;
+ }
+#endif
+ }
+ }
+ }
+ }
+
+ if ([MIMEType length] == 0)
+ return ObjectContentFrame; // Go ahead and hope that we can display the content.
+
+ if (MIMETypeRegistry::isSupportedImageMIMEType(MIMEType))
+ return ObjectContentImage;
+
+ if (WebBasePluginPackage *package = [[self webView] _pluginForMIMEType:MIMEType]) {
+ if ([package isKindOfClass:[WebPluginPackage class]])
+ return ObjectContentOtherPlugin;
+#ifndef __LP64__
+ else {
+ ASSERT([package isKindOfClass:[WebNetscapePluginPackage class]]);
+ return ObjectContentNetscapePlugin;
+ }
+#endif
+ }
+
+ if ([WebFrameView _viewClassForMIMEType:MIMEType])
+ return ObjectContentFrame;
+
+ return ObjectContentNone;
+}
+
+- (jobject)getAppletInView:(NSView *)view
+{
+ if ([view respondsToSelector:@selector(webPlugInGetApplet)])
+ return [view webPlugInGetApplet];
+ return [self pollForAppletInView:view];
+}
+
+// NOTE: pollForAppletInView: will block until the block is ready to use, or
+// until a timeout is exceeded. It will return nil if the timeout is
+// exceeded.
+// Deprecated, use getAppletInView:.
+- (jobject)pollForAppletInView:(NSView *)view
+{
+ if ([view respondsToSelector:@selector(pollForAppletInWindow:)])
+ // The Java VM needs the containing window of the view to
+ // initialize. The view may not yet be in the window's view
+ // hierarchy, so we have to pass the window when requesting
+ // the applet.
+ return [view pollForAppletInWindow:[[self webView] window]];
+ return 0;
+}
+
+- (void)respondToChangedContents
+{
+ NSView <WebDocumentView> *view = [[_frame frameView] documentView];
+ if ([view isKindOfClass:[WebHTMLView class]])
+ [(WebHTMLView *)view _updateFontPanel];
+ [[NSNotificationCenter defaultCenter] postNotificationName:WebViewDidChangeNotification object:[self webView]];
+}
+
+- (NSUndoManager *)undoManager
+{
+ return [[self webView] undoManager];
+}
+
+- (void)issuePasteCommand
+{
+ NSView* documentView = [[_frame frameView] documentView];
+ if ([documentView isKindOfClass:[WebHTMLView class]])
+ [(WebHTMLView*)documentView paste:nil];
+}
+
+- (void)setIsSelected:(BOOL)isSelected forView:(NSView *)view
+{
+ if ([view respondsToSelector:@selector(webPlugInSetIsSelected:)])
+ [view webPlugInSetIsSelected:isSelected];
+ else if ([view respondsToSelector:@selector(setIsSelected:)])
+ [view setIsSelected:isSelected];
+}
+
+- (void)windowObjectCleared
+{
+ WebView *webView = getWebView(_frame);
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didClearWindowObjectForFrameFunc)
+ CallFrameLoadDelegate(implementations->didClearWindowObjectForFrameFunc, webView, @selector(webView:didClearWindowObject:forFrame:), m_frame->windowScriptObject(), _frame);
+ else if (implementations->windowScriptObjectAvailableFunc)
+ CallFrameLoadDelegate(implementations->windowScriptObjectAvailableFunc, webView, @selector(webView:windowScriptObjectAvailable:), m_frame->windowScriptObject());
+
+ if ([webView scriptDebugDelegate] || [WebScriptDebugServer listenerCount]) {
+ [_frame _detachScriptDebugger];
+ [_frame _attachScriptDebugger];
+ }
+}
+
+- (BOOL)_compareDashboardRegions:(NSDictionary *)regions
+{
+ return [lastDashboardRegions isEqualToDictionary:regions];
+}
+
+- (void)dashboardRegionsChanged:(NSMutableDictionary *)regions
+{
+ WebView *webView = [self webView];
+ [webView _addScrollerDashboardRegions:regions];
+
+ if (![self _compareDashboardRegions:regions]) {
+ CallUIDelegate(webView, @selector(webView:dashboardRegionsChanged:), regions);
+
+ [lastDashboardRegions release];
+ lastDashboardRegions = [regions retain];
+ }
+}
+
+- (void)willPopupMenu:(NSMenu *)menu
+{
+ CallUIDelegate([self webView], @selector(webView:willPopupMenu:), menu);
+}
+
+- (NSRect)customHighlightRect:(NSString*)type forLine:(NSRect)lineRect representedNode:(WebCore::Node *)node
+{
+ ASSERT(_frame != nil);
+ NSView *documentView = [[_frame frameView] documentView];
+ if (![documentView isKindOfClass:[WebHTMLView class]])
+ return NSZeroRect;
+
+ WebHTMLView *webHTMLView = (WebHTMLView *)documentView;
+ id<WebHTMLHighlighter> highlighter = [webHTMLView _highlighterForType:type];
+ if ([(NSObject *)highlighter respondsToSelector:@selector(highlightRectForLine:representedNode:)])
+ return [highlighter highlightRectForLine:lineRect representedNode:kit(node)];
+ return [highlighter highlightRectForLine:lineRect];
+}
+
+- (void)paintCustomHighlight:(NSString*)type forBox:(NSRect)boxRect onLine:(NSRect)lineRect behindText:(BOOL)text entireLine:(BOOL)line representedNode:(WebCore::Node *)node
+{
+ ASSERT(_frame != nil);
+ NSView *documentView = [[_frame frameView] documentView];
+ if (![documentView isKindOfClass:[WebHTMLView class]])
+ return;
+
+ WebHTMLView *webHTMLView = (WebHTMLView *)documentView;
+ id<WebHTMLHighlighter> highlighter = [webHTMLView _highlighterForType:type];
+ if ([(NSObject *)highlighter respondsToSelector:@selector(paintHighlightForBox:onLine:behindText:entireLine:representedNode:)])
+ [highlighter paintHighlightForBox:boxRect onLine:lineRect behindText:text entireLine:line representedNode:kit(node)];
+ else
+ [highlighter paintHighlightForBox:boxRect onLine:lineRect behindText:text entireLine:line];
+}
+
+@end
diff --git a/WebKit/mac/WebCoreSupport/WebFrameLoaderClient.h b/WebKit/mac/WebCoreSupport/WebFrameLoaderClient.h
new file mode 100644
index 0000000..12bcc51
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebFrameLoaderClient.h
@@ -0,0 +1,219 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/FrameLoaderClient.h>
+#import <WebCore/Timer.h>
+#import <wtf/Forward.h>
+#import <wtf/HashMap.h>
+#import <wtf/RetainPtr.h>
+
+@class WebDownload;
+@class WebFrame;
+@class WebFramePolicyListener;
+@class WebHistoryItem;
+@class WebResource;
+
+namespace WebCore {
+ class AuthenticationChallenge;
+ class CachedPage;
+ class HistoryItem;
+ class String;
+ class ResourceLoader;
+ class ResourceRequest;
+}
+
+typedef HashMap<RefPtr<WebCore::ResourceLoader>, RetainPtr<WebResource> > ResourceMap;
+
+class WebFrameLoaderClient : public WebCore::FrameLoaderClient {
+public:
+ WebFrameLoaderClient(WebFrame*);
+
+ WebFrame* webFrame() const { return m_webFrame.get(); }
+
+ virtual void frameLoaderDestroyed();
+ void receivedPolicyDecison(WebCore::PolicyAction);
+
+private:
+ virtual bool hasWebView() const; // mainly for assertions
+ virtual bool hasFrameView() const; // ditto
+
+ virtual void makeRepresentation(WebCore::DocumentLoader*);
+ virtual bool hasHTMLView() const;
+ virtual void forceLayout();
+ virtual void forceLayoutForNonHTML();
+
+ virtual void setCopiesOnScroll();
+
+ virtual void detachedFromParent2();
+ virtual void detachedFromParent3();
+ virtual void detachedFromParent4();
+
+ virtual void download(WebCore::ResourceHandle*, const WebCore::ResourceRequest&, const WebCore::ResourceRequest&, const WebCore::ResourceResponse&);
+
+ virtual void assignIdentifierToInitialRequest(unsigned long identifier, WebCore::DocumentLoader*, const WebCore::ResourceRequest&);
+
+ virtual void dispatchWillSendRequest(WebCore::DocumentLoader*, unsigned long identifier, WebCore::ResourceRequest&, const WebCore::ResourceResponse& redirectResponse);
+ virtual void dispatchDidReceiveAuthenticationChallenge(WebCore::DocumentLoader*, unsigned long identifier, const WebCore::AuthenticationChallenge&);
+ virtual void dispatchDidCancelAuthenticationChallenge(WebCore::DocumentLoader*, unsigned long identifier, const WebCore::AuthenticationChallenge&);
+ virtual void dispatchDidReceiveResponse(WebCore::DocumentLoader*, unsigned long identifier, const WebCore::ResourceResponse&);
+ virtual void dispatchDidReceiveContentLength(WebCore::DocumentLoader*, unsigned long identifier, int lengthReceived);
+ virtual void dispatchDidFinishLoading(WebCore::DocumentLoader*, unsigned long identifier);
+ virtual void dispatchDidFailLoading(WebCore::DocumentLoader*, unsigned long identifier, const WebCore::ResourceError&);
+
+ virtual NSCachedURLResponse* willCacheResponse(WebCore::DocumentLoader*, unsigned long identifier, NSCachedURLResponse*) const;
+
+ virtual void dispatchDidHandleOnloadEvents();
+ virtual void dispatchDidReceiveServerRedirectForProvisionalLoad();
+ virtual void dispatchDidCancelClientRedirect();
+ virtual void dispatchWillPerformClientRedirect(const WebCore::KURL&, double interval, double fireDate);
+ virtual void dispatchDidChangeLocationWithinPage();
+ virtual void dispatchWillClose();
+ virtual void dispatchDidReceiveIcon();
+ virtual void dispatchDidStartProvisionalLoad();
+ virtual void dispatchDidReceiveTitle(const WebCore::String& title);
+ virtual void dispatchDidCommitLoad();
+ virtual void dispatchDidFailProvisionalLoad(const WebCore::ResourceError&);
+ virtual void dispatchDidFailLoad(const WebCore::ResourceError&);
+ virtual void dispatchDidFinishDocumentLoad();
+ virtual void dispatchDidFinishLoad();
+ virtual void dispatchDidFirstLayout();
+
+ virtual WebCore::Frame* dispatchCreatePage();
+ virtual void dispatchShow();
+
+ virtual void dispatchDecidePolicyForMIMEType(WebCore::FramePolicyFunction,
+ const WebCore::String& MIMEType, const WebCore::ResourceRequest&);
+ virtual void dispatchDecidePolicyForNewWindowAction(WebCore::FramePolicyFunction,
+ const WebCore::NavigationAction&, const WebCore::ResourceRequest&, const WebCore::String& frameName);
+ virtual void dispatchDecidePolicyForNavigationAction(WebCore::FramePolicyFunction,
+ const WebCore::NavigationAction&, const WebCore::ResourceRequest&);
+ virtual void cancelPolicyCheck();
+
+ virtual void dispatchUnableToImplementPolicy(const WebCore::ResourceError&);
+
+ virtual void dispatchWillSubmitForm(WebCore::FramePolicyFunction, PassRefPtr<WebCore::FormState>);
+
+ virtual void dispatchDidLoadMainResource(WebCore::DocumentLoader*);
+ virtual void revertToProvisionalState(WebCore::DocumentLoader*);
+ virtual void setMainDocumentError(WebCore::DocumentLoader*, const WebCore::ResourceError&);
+ virtual void clearUnarchivingState(WebCore::DocumentLoader*);
+ virtual bool dispatchDidLoadResourceFromMemoryCache(WebCore::DocumentLoader*, const WebCore::ResourceRequest&, const WebCore::ResourceResponse&, int length);
+
+ virtual void willChangeEstimatedProgress();
+ virtual void didChangeEstimatedProgress();
+ virtual void postProgressStartedNotification();
+ virtual void postProgressEstimateChangedNotification();
+ virtual void postProgressFinishedNotification();
+
+ virtual void setMainFrameDocumentReady(bool);
+
+ virtual void startDownload(const WebCore::ResourceRequest&);
+
+ virtual void willChangeTitle(WebCore::DocumentLoader*);
+ virtual void didChangeTitle(WebCore::DocumentLoader*);
+
+ virtual void committedLoad(WebCore::DocumentLoader*, const char*, int);
+ virtual void finishedLoading(WebCore::DocumentLoader*);
+ virtual void finalSetupForReplace(WebCore::DocumentLoader*);
+ virtual void updateGlobalHistory(const WebCore::KURL&);
+ virtual bool shouldGoToHistoryItem(WebCore::HistoryItem*) const;
+
+ virtual WebCore::ResourceError cancelledError(const WebCore::ResourceRequest&);
+ virtual WebCore::ResourceError blockedError(const WebCore::ResourceRequest&);
+ virtual WebCore::ResourceError cannotShowURLError(const WebCore::ResourceRequest&);
+ virtual WebCore::ResourceError interruptForPolicyChangeError(const WebCore::ResourceRequest&);
+
+ virtual WebCore::ResourceError cannotShowMIMETypeError(const WebCore::ResourceResponse&);
+ virtual WebCore::ResourceError fileDoesNotExistError(const WebCore::ResourceResponse&);
+
+ virtual bool shouldFallBack(const WebCore::ResourceError&);
+
+ virtual void setDefersLoading(bool);
+
+ virtual WebCore::String userAgent(const WebCore::KURL&);
+
+ virtual void savePlatformDataToCachedPage(WebCore::CachedPage*);
+ virtual void transitionToCommittedFromCachedPage(WebCore::CachedPage*);
+ virtual void transitionToCommittedForNewPage();
+
+ virtual bool willUseArchive(WebCore::ResourceLoader*, const WebCore::ResourceRequest&, const WebCore::KURL& originalURL) const;
+ virtual bool isArchiveLoadPending(WebCore::ResourceLoader*) const;
+ virtual void cancelPendingArchiveLoad(WebCore::ResourceLoader*);
+ virtual void clearArchivedResources();
+
+ virtual bool canHandleRequest(const WebCore::ResourceRequest&) const;
+ virtual bool canShowMIMEType(const WebCore::String& MIMEType) const;
+ virtual bool representationExistsForURLScheme(const WebCore::String& URLScheme) const;
+ virtual WebCore::String generatedMIMETypeForURLScheme(const WebCore::String& URLScheme) const;
+
+ virtual void frameLoadCompleted();
+ virtual void saveViewStateToItem(WebCore::HistoryItem*);
+ virtual void restoreViewState();
+ virtual void provisionalLoadStarted();
+ virtual void didFinishLoad();
+ virtual void prepareForDataSourceReplacement();
+ virtual PassRefPtr<WebCore::DocumentLoader> createDocumentLoader(const WebCore::ResourceRequest&, const WebCore::SubstituteData&);
+
+ virtual void setTitle(const WebCore::String& title, const WebCore::KURL&);
+
+ virtual PassRefPtr<WebCore::Frame> createFrame(const WebCore::KURL& url, const WebCore::String& name, WebCore::HTMLFrameOwnerElement*,
+ const WebCore::String& referrer, bool allowsScrolling, int marginWidth, int marginHeight);
+ virtual WebCore::Widget* createPlugin(const WebCore::IntSize&, WebCore::Element*, const WebCore::KURL&, const Vector<WebCore::String>&,
+ const Vector<WebCore::String>&, const WebCore::String&, bool);
+ virtual void redirectDataToPlugin(WebCore::Widget* pluginWidget);
+
+ virtual WebCore::Widget* createJavaAppletWidget(const WebCore::IntSize&, WebCore::Element*, const WebCore::KURL& baseURL,
+ const Vector<WebCore::String>& paramNames, const Vector<WebCore::String>& paramValues);
+
+ virtual WebCore::ObjectContentType objectContentType(const WebCore::KURL& url, const WebCore::String& mimeType);
+ virtual WebCore::String overrideMediaType() const;
+
+ virtual void windowObjectCleared();
+ virtual void didPerformFirstNavigation() const;
+
+ virtual void registerForIconNotification(bool listen);
+
+ void deliverArchivedResourcesAfterDelay() const;
+ void deliverArchivedResources(WebCore::Timer<WebFrameLoaderClient>*);
+
+ void setOriginalURLForDownload(WebDownload *, const WebCore::ResourceRequest&) const;
+
+ RetainPtr<WebFramePolicyListener> setUpPolicyListener(WebCore::FramePolicyFunction);
+
+ NSDictionary *actionDictionary(const WebCore::NavigationAction&) const;
+
+ virtual bool canCachePage() const;
+
+ RetainPtr<WebFrame> m_webFrame;
+
+ RetainPtr<WebFramePolicyListener> m_policyListener;
+ WebCore::FramePolicyFunction m_policyFunction;
+
+ mutable ResourceMap m_pendingArchivedResources;
+ mutable WebCore::Timer<WebFrameLoaderClient> m_archivedResourcesDeliveryTimer;
+};
diff --git a/WebKit/mac/WebCoreSupport/WebFrameLoaderClient.mm b/WebKit/mac/WebCoreSupport/WebFrameLoaderClient.mm
new file mode 100644
index 0000000..d77fd89
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebFrameLoaderClient.mm
@@ -0,0 +1,1276 @@
+/*
+ * Copyright (C) 2006, 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebFrameLoaderClient.h"
+
+// Terrible hack; lets us get at the WebFrame private structure.
+#define private public
+#import "WebFrame.h"
+#undef private
+
+#import "DOMElementInternal.h"
+#import "WebBackForwardList.h"
+#import "WebCachedPagePlatformData.h"
+#import "WebChromeClient.h"
+#import "WebDataSourceInternal.h"
+#import "WebPolicyDelegatePrivate.h"
+#import "WebDocumentInternal.h"
+#import "WebDocumentLoaderMac.h"
+#import "WebDownloadInternal.h"
+#import "WebDynamicScrollBarsView.h"
+#import "WebElementDictionary.h"
+#import "WebFormDelegate.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebFrameLoadDelegate.h"
+#import "WebFrameViewInternal.h"
+#import "WebHTMLRepresentation.h"
+#import "WebHTMLView.h"
+#import "WebHistoryItemInternal.h"
+#import "WebHistoryItemPrivate.h"
+#import "WebHistoryPrivate.h"
+#import "WebIconDatabaseInternal.h"
+#import "WebKitErrorsPrivate.h"
+#import "WebKitLogging.h"
+#import "WebKitNSStringExtras.h"
+#import "WebNSURLExtras.h"
+#import "WebPanelAuthenticationHandler.h"
+#import "WebPolicyDelegate.h"
+#import "WebPreferences.h"
+#import "WebResourceLoadDelegate.h"
+#import "WebResourcePrivate.h"
+#import "WebScriptDebugServerPrivate.h"
+#import "WebUIDelegate.h"
+#import "WebUIDelegatePrivate.h"
+#import "WebViewInternal.h"
+#import <WebCore/AuthenticationMac.h>
+#import <WebCore/BlockExceptions.h>
+#import <WebCore/CachedPage.h>
+#import <WebCore/Chrome.h>
+#import <WebCore/Document.h>
+#import <WebCore/DocumentLoader.h>
+#import <WebCore/EventHandler.h>
+#import <WebCore/FormState.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/FrameLoaderTypes.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameTree.h>
+#import <WebCore/HistoryItem.h>
+#import <WebCore/HitTestResult.h>
+#import <WebCore/HTMLFormElement.h>
+#import <WebCore/IconDatabase.h>
+#import <WebCore/LoaderNSURLExtras.h>
+#import <WebCore/MouseEvent.h>
+#import <WebCore/Page.h>
+#import <WebCore/PlatformString.h>
+#import <WebCore/ResourceError.h>
+#import <WebCore/ResourceHandle.h>
+#import <WebCore/ResourceLoader.h>
+#import <WebCore/ResourceRequest.h>
+#import <WebCore/WebCoreFrameBridge.h>
+#import <WebCore/WebCoreObjCExtras.h>
+#import <WebCore/SharedBuffer.h>
+#import <WebCore/Widget.h>
+#import <WebKit/DOMElement.h>
+#import <WebKit/DOMHTMLFormElement.h>
+#import <wtf/PassRefPtr.h>
+
+using namespace WebCore;
+
+// SPI for NSURLDownload
+// Needed for <rdar://problem/5121850>
+@interface NSURLDownload (NSURLDownloadPrivate)
+- (void)_setOriginatingURL:(NSURL *)originatingURL;
+@end
+
+@interface WebHistoryItem (WebHistoryItemPrivate)
+- (BOOL)_wasUserGesture;
+@end
+
+@interface WebFramePolicyListener : NSObject <WebPolicyDecisionListener, WebFormSubmissionListener>
+{
+ Frame* m_frame;
+}
+- (id)initWithWebCoreFrame:(Frame*)frame;
+- (void)invalidate;
+@end
+
+static inline WebDataSource *dataSource(DocumentLoader* loader)
+{
+ return loader ? static_cast<WebDocumentLoaderMac*>(loader)->dataSource() : nil;
+}
+
+WebFrameLoaderClient::WebFrameLoaderClient(WebFrame *webFrame)
+ : m_webFrame(webFrame)
+ , m_policyFunction(0)
+ , m_archivedResourcesDeliveryTimer(this, &WebFrameLoaderClient::deliverArchivedResources)
+{
+}
+
+void WebFrameLoaderClient::frameLoaderDestroyed()
+{
+ delete this;
+}
+
+bool WebFrameLoaderClient::hasWebView() const
+{
+ return [m_webFrame.get() webView] != nil;
+}
+
+bool WebFrameLoaderClient::hasFrameView() const
+{
+ return m_webFrame->_private->webFrameView != nil;
+}
+
+
+void WebFrameLoaderClient::makeRepresentation(DocumentLoader* loader)
+{
+ [dataSource(loader) _makeRepresentation];
+}
+
+bool WebFrameLoaderClient::hasHTMLView() const
+{
+ NSView <WebDocumentView> *view = [m_webFrame->_private->webFrameView documentView];
+ return [view isKindOfClass:[WebHTMLView class]];
+}
+
+void WebFrameLoaderClient::forceLayout()
+{
+ NSView <WebDocumentView> *view = [m_webFrame->_private->webFrameView documentView];
+ if ([view isKindOfClass:[WebHTMLView class]])
+ [(WebHTMLView *)view setNeedsToApplyStyles:YES];
+ [view setNeedsLayout:YES];
+ [view layout];
+}
+
+void WebFrameLoaderClient::forceLayoutForNonHTML()
+{
+ WebFrameView *thisView = m_webFrame->_private->webFrameView;
+ NSView <WebDocumentView> *thisDocumentView = [thisView documentView];
+ ASSERT(thisDocumentView != nil);
+
+ // Tell the just loaded document to layout. This may be necessary
+ // for non-html content that needs a layout message.
+ if (!([[m_webFrame.get() _dataSource] _isDocumentHTML])) {
+ [thisDocumentView setNeedsLayout:YES];
+ [thisDocumentView layout];
+ [thisDocumentView setNeedsDisplay:YES];
+ }
+}
+
+void WebFrameLoaderClient::setCopiesOnScroll()
+{
+ [[[m_webFrame->_private->webFrameView _scrollView] contentView] setCopiesOnScroll:YES];
+}
+
+void WebFrameLoaderClient::detachedFromParent2()
+{
+ [m_webFrame->_private->webFrameView _setWebFrame:nil]; // needed for now to be compatible w/ old behavior
+}
+
+void WebFrameLoaderClient::detachedFromParent3()
+{
+ [m_webFrame->_private->webFrameView release];
+ m_webFrame->_private->webFrameView = nil;
+}
+
+void WebFrameLoaderClient::detachedFromParent4()
+{
+ m_webFrame->_private->bridge = nil;
+}
+
+void WebFrameLoaderClient::download(ResourceHandle* handle, const ResourceRequest& request, const ResourceRequest& initialRequest, const ResourceResponse& response)
+{
+ id proxy = handle->releaseProxy();
+ ASSERT(proxy);
+
+ WebView *webView = getWebView(m_webFrame.get());
+ WebDownload *download = [WebDownload _downloadWithLoadingConnection:handle->connection()
+ request:request.nsURLRequest()
+ response:response.nsURLResponse()
+ delegate:[webView downloadDelegate]
+ proxy:proxy];
+
+ setOriginalURLForDownload(download, initialRequest);
+}
+
+void WebFrameLoaderClient::setOriginalURLForDownload(WebDownload *download, const ResourceRequest& initialRequest) const
+{
+ NSURLRequest *initialURLRequest = initialRequest.nsURLRequest();
+ NSURL *originalURL = nil;
+
+ // If there was no referrer, don't traverse the back/forward history
+ // since this download was initiated directly. <rdar://problem/5294691>
+ if ([initialURLRequest valueForHTTPHeaderField:@"Referer"]) {
+ // find the first item in the history that was originated by the user
+ WebView *webView = getWebView(m_webFrame.get());
+ WebBackForwardList *history = [webView backForwardList];
+ int backListCount = [history backListCount];
+ for (int backIndex = 0; backIndex <= backListCount && !originalURL; backIndex++) {
+ WebHistoryItem *currentItem = [history itemAtIndex:-backIndex];
+ if (![currentItem respondsToSelector:@selector(_wasUserGesture)] || [currentItem _wasUserGesture])
+ originalURL = [currentItem URL];
+ }
+ }
+
+ if (!originalURL)
+ originalURL = [initialURLRequest URL];
+
+ if ([download respondsToSelector:@selector(_setOriginatingURL:)]) {
+ NSString *scheme = [originalURL scheme];
+ NSString *host = [originalURL host];
+ if (scheme && host && [scheme length] && [host length]) {
+ NSNumber *port = [originalURL port];
+ if (port && [port intValue] < 0)
+ port = nil;
+ NSString *hostOnlyURLString;
+ if (port)
+ hostOnlyURLString = [[NSString alloc] initWithFormat:@"%@://%@:%d", scheme, host, [port intValue]];
+ else
+ hostOnlyURLString = [[NSString alloc] initWithFormat:@"%@://%@", scheme, host];
+ NSURL *hostOnlyURL = [[NSURL alloc] initWithString:hostOnlyURLString];
+ [hostOnlyURLString release];
+ [download _setOriginatingURL:hostOnlyURL];
+ [hostOnlyURL release];
+ }
+ }
+}
+
+bool WebFrameLoaderClient::dispatchDidLoadResourceFromMemoryCache(DocumentLoader* loader, const ResourceRequest& request, const ResourceResponse& response, int length)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebResourceDelegateImplementationCache* implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+ if (!implementations->didLoadResourceFromMemoryCacheFunc)
+ return false;
+
+ CallResourceLoadDelegate(implementations->didLoadResourceFromMemoryCacheFunc, webView, @selector(webView:didLoadResourceFromMemoryCache:response:length:fromDataSource:), request.nsURLRequest(), response.nsURLResponse(), length, dataSource(loader));
+ return true;
+}
+
+void WebFrameLoaderClient::assignIdentifierToInitialRequest(unsigned long identifier, DocumentLoader* loader, const ResourceRequest& request)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebResourceDelegateImplementationCache* implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+
+ id object = nil;
+ BOOL shouldRelease = NO;
+ if (implementations->identifierForRequestFunc)
+ object = CallResourceLoadDelegate(implementations->identifierForRequestFunc, webView, @selector(webView:identifierForInitialRequest:fromDataSource:), request.nsURLRequest(), dataSource(loader));
+ else {
+ object = [[NSObject alloc] init];
+ shouldRelease = YES;
+ }
+
+ [webView _addObject:object forIdentifier:identifier];
+
+ if (shouldRelease)
+ [object release];
+}
+
+void WebFrameLoaderClient::dispatchWillSendRequest(DocumentLoader* loader, unsigned long identifier, ResourceRequest& request, const ResourceResponse& redirectResponse)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebResourceDelegateImplementationCache* implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+
+ if (redirectResponse.isNull())
+ static_cast<WebDocumentLoaderMac*>(loader)->increaseLoadCount(identifier);
+
+ if (implementations->willSendRequestFunc)
+ request = (NSURLRequest *)CallResourceLoadDelegate(implementations->willSendRequestFunc, webView, @selector(webView:resource:willSendRequest:redirectResponse:fromDataSource:), [webView _objectForIdentifier:identifier], request.nsURLRequest(), redirectResponse.nsURLResponse(), dataSource(loader));
+}
+
+void WebFrameLoaderClient::dispatchDidReceiveAuthenticationChallenge(DocumentLoader* loader, unsigned long identifier, const AuthenticationChallenge& challenge)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebResourceDelegateImplementationCache* implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+
+ NSURLAuthenticationChallenge *webChallenge = mac(challenge);
+
+ if (implementations->didReceiveAuthenticationChallengeFunc) {
+ if (id resource = [webView _objectForIdentifier:identifier]) {
+ CallResourceLoadDelegate(implementations->didReceiveAuthenticationChallengeFunc, webView, @selector(webView:resource:didReceiveAuthenticationChallenge:fromDataSource:), resource, webChallenge, dataSource(loader));
+ return;
+ }
+ }
+
+ NSWindow *window = [webView hostWindow] ? [webView hostWindow] : [webView window];
+ [[WebPanelAuthenticationHandler sharedHandler] startAuthentication:webChallenge window:window];
+}
+
+void WebFrameLoaderClient::dispatchDidCancelAuthenticationChallenge(DocumentLoader* loader, unsigned long identifier, const AuthenticationChallenge&challenge)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebResourceDelegateImplementationCache* implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+ NSURLAuthenticationChallenge *webChallenge = mac(challenge);
+
+ if (implementations->didCancelAuthenticationChallengeFunc) {
+ if (id resource = [webView _objectForIdentifier:identifier]) {
+ CallResourceLoadDelegate(implementations->didCancelAuthenticationChallengeFunc, webView, @selector(webView:resource:didCancelAuthenticationChallenge:fromDataSource:), resource, webChallenge, dataSource(loader));
+ return;
+ }
+ }
+
+ [(WebPanelAuthenticationHandler *)[WebPanelAuthenticationHandler sharedHandler] cancelAuthentication:webChallenge];
+}
+
+void WebFrameLoaderClient::dispatchDidReceiveResponse(DocumentLoader* loader, unsigned long identifier, const ResourceResponse& response)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebResourceDelegateImplementationCache* implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+ if (implementations->didReceiveResponseFunc) {
+ if (id resource = [webView _objectForIdentifier:identifier])
+ CallResourceLoadDelegate(implementations->didReceiveResponseFunc, webView, @selector(webView:resource:didReceiveResponse:fromDataSource:), resource, response.nsURLResponse(), dataSource(loader));
+ }
+}
+
+NSCachedURLResponse* WebFrameLoaderClient::willCacheResponse(DocumentLoader* loader, unsigned long identifier, NSCachedURLResponse* response) const
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebResourceDelegateImplementationCache* implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+
+ if (implementations->willCacheResponseFunc) {
+ if (id resource = [webView _objectForIdentifier:identifier])
+ return CallResourceLoadDelegate(implementations->willCacheResponseFunc, webView, @selector(webView:resource:willCacheResponse:fromDataSource:), resource, response, dataSource(loader));
+ }
+
+ return response;
+}
+
+void WebFrameLoaderClient::dispatchDidReceiveContentLength(DocumentLoader* loader, unsigned long identifier, int lengthReceived)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebResourceDelegateImplementationCache* implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+ if (implementations->didReceiveContentLengthFunc) {
+ if (id resource = [webView _objectForIdentifier:identifier])
+ CallResourceLoadDelegate(implementations->didReceiveContentLengthFunc, webView, @selector(webView:resource:didReceiveContentLength:fromDataSource:), resource, (NSInteger)lengthReceived, dataSource(loader));
+ }
+}
+
+void WebFrameLoaderClient::dispatchDidFinishLoading(DocumentLoader* loader, unsigned long identifier)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebResourceDelegateImplementationCache* implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+
+ if (implementations->didFinishLoadingFromDataSourceFunc) {
+ if (id resource = [webView _objectForIdentifier:identifier])
+ CallResourceLoadDelegate(implementations->didFinishLoadingFromDataSourceFunc, webView, @selector(webView:resource:didFinishLoadingFromDataSource:), resource, dataSource(loader));
+ }
+
+ [webView _removeObjectForIdentifier:identifier];
+
+ static_cast<WebDocumentLoaderMac*>(loader)->decreaseLoadCount(identifier);
+}
+
+void WebFrameLoaderClient::dispatchDidFailLoading(DocumentLoader* loader, unsigned long identifier, const ResourceError& error)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebResourceDelegateImplementationCache* implementations = WebViewGetResourceLoadDelegateImplementations(webView);
+
+ if (implementations->didFailLoadingWithErrorFromDataSourceFunc) {
+ if (id resource = [webView _objectForIdentifier:identifier])
+ CallResourceLoadDelegate(implementations->didFailLoadingWithErrorFromDataSourceFunc, webView, @selector(webView:resource:didFailLoadingWithError:fromDataSource:), resource, (NSError *)error, dataSource(loader));
+ }
+
+ [webView _removeObjectForIdentifier:identifier];
+
+ static_cast<WebDocumentLoaderMac*>(loader)->decreaseLoadCount(identifier);
+}
+
+void WebFrameLoaderClient::dispatchDidHandleOnloadEvents()
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didHandleOnloadEventsForFrameFunc)
+ CallFrameLoadDelegate(implementations->didHandleOnloadEventsForFrameFunc, webView, @selector(webView:didHandleOnloadEventsForFrame:), m_webFrame.get());
+}
+
+void WebFrameLoaderClient::dispatchDidReceiveServerRedirectForProvisionalLoad()
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didReceiveServerRedirectForProvisionalLoadForFrameFunc)
+ CallFrameLoadDelegate(implementations->didReceiveServerRedirectForProvisionalLoadForFrameFunc, webView, @selector(webView:didReceiveServerRedirectForProvisionalLoadForFrame:), m_webFrame.get());
+}
+
+void WebFrameLoaderClient::dispatchDidCancelClientRedirect()
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didCancelClientRedirectForFrameFunc)
+ CallFrameLoadDelegate(implementations->didCancelClientRedirectForFrameFunc, webView, @selector(webView:didCancelClientRedirectForFrame:), m_webFrame.get());
+}
+
+void WebFrameLoaderClient::dispatchWillPerformClientRedirect(const KURL& url, double delay, double fireDate)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->willPerformClientRedirectToURLDelayFireDateForFrameFunc) {
+ NSURL *cocoaURL = url;
+ CallFrameLoadDelegate(implementations->willPerformClientRedirectToURLDelayFireDateForFrameFunc, webView, @selector(webView:willPerformClientRedirectToURL:delay:fireDate:forFrame:), cocoaURL, delay, [NSDate dateWithTimeIntervalSince1970:fireDate], m_webFrame.get());
+ }
+}
+
+void WebFrameLoaderClient::dispatchDidChangeLocationWithinPage()
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didChangeLocationWithinPageForFrameFunc)
+ CallFrameLoadDelegate(implementations->didChangeLocationWithinPageForFrameFunc, webView, @selector(webView:didChangeLocationWithinPageForFrame:), m_webFrame.get());
+}
+
+void WebFrameLoaderClient::dispatchWillClose()
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->willCloseFrameFunc)
+ CallFrameLoadDelegate(implementations->willCloseFrameFunc, webView, @selector(webView:willCloseFrame:), m_webFrame.get());
+}
+
+void WebFrameLoaderClient::dispatchDidReceiveIcon()
+{
+ ASSERT([m_webFrame.get() _isMainFrame]);
+ WebView *webView = getWebView(m_webFrame.get());
+
+ [webView _dispatchDidReceiveIconFromWebFrame:m_webFrame.get()];
+}
+
+void WebFrameLoaderClient::dispatchDidStartProvisionalLoad()
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ [webView _didStartProvisionalLoadForFrame:m_webFrame.get()];
+
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didStartProvisionalLoadForFrameFunc)
+ CallFrameLoadDelegate(implementations->didStartProvisionalLoadForFrameFunc, webView, @selector(webView:didStartProvisionalLoadForFrame:), m_webFrame.get());
+}
+
+void WebFrameLoaderClient::dispatchDidReceiveTitle(const String& title)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didReceiveTitleForFrameFunc)
+ CallFrameLoadDelegate(implementations->didReceiveTitleForFrameFunc, webView, @selector(webView:didReceiveTitle:forFrame:), (NSString *)title, m_webFrame.get());
+}
+
+void WebFrameLoaderClient::dispatchDidCommitLoad()
+{
+ // Tell the client we've committed this URL.
+ ASSERT([m_webFrame->_private->webFrameView documentView] != nil);
+
+ WebView *webView = getWebView(m_webFrame.get());
+ [webView _didCommitLoadForFrame:m_webFrame.get()];
+
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didCommitLoadForFrameFunc)
+ CallFrameLoadDelegate(implementations->didCommitLoadForFrameFunc, webView, @selector(webView:didCommitLoadForFrame:), m_webFrame.get());
+}
+
+void WebFrameLoaderClient::dispatchDidFailProvisionalLoad(const ResourceError& error)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ [webView _didFailProvisionalLoadWithError:error forFrame:m_webFrame.get()];
+
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didFailProvisionalLoadWithErrorForFrameFunc)
+ CallFrameLoadDelegate(implementations->didFailProvisionalLoadWithErrorForFrameFunc, webView, @selector(webView:didFailProvisionalLoadWithError:forFrame:), (NSError *)error, m_webFrame.get());
+
+ [m_webFrame->_private->internalLoadDelegate webFrame:m_webFrame.get() didFinishLoadWithError:error];
+}
+
+void WebFrameLoaderClient::dispatchDidFailLoad(const ResourceError& error)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ [webView _didFailLoadWithError:error forFrame:m_webFrame.get()];
+
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didFailLoadWithErrorForFrameFunc)
+ CallFrameLoadDelegate(implementations->didFailLoadWithErrorForFrameFunc, webView, @selector(webView:didFailLoadWithError:forFrame:), (NSError *)error, m_webFrame.get());
+
+ [m_webFrame->_private->internalLoadDelegate webFrame:m_webFrame.get() didFinishLoadWithError:error];
+}
+
+void WebFrameLoaderClient::dispatchDidFinishDocumentLoad()
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didFinishDocumentLoadForFrameFunc)
+ CallFrameLoadDelegate(implementations->didFinishDocumentLoadForFrameFunc, webView, @selector(webView:didFinishDocumentLoadForFrame:), m_webFrame.get());
+}
+
+void WebFrameLoaderClient::dispatchDidFinishLoad()
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ [webView _didFinishLoadForFrame:m_webFrame.get()];
+
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didFinishLoadForFrameFunc)
+ CallFrameLoadDelegate(implementations->didFinishLoadForFrameFunc, webView, @selector(webView:didFinishLoadForFrame:), m_webFrame.get());
+
+ [m_webFrame->_private->internalLoadDelegate webFrame:m_webFrame.get() didFinishLoadWithError:nil];
+}
+
+void WebFrameLoaderClient::dispatchDidFirstLayout()
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ WebFrameLoadDelegateImplementationCache* implementations = WebViewGetFrameLoadDelegateImplementations(webView);
+ if (implementations->didFirstLayoutInFrameFunc)
+ CallFrameLoadDelegate(implementations->didFirstLayoutInFrameFunc, webView, @selector(webView:didFirstLayoutInFrame:), m_webFrame.get());
+}
+
+Frame* WebFrameLoaderClient::dispatchCreatePage()
+{
+ WebView *currentWebView = getWebView(m_webFrame.get());
+ NSDictionary *features = [[NSDictionary alloc] init];
+ WebView *newWebView = [[currentWebView _UIDelegateForwarder] webView:currentWebView
+ createWebViewWithRequest:nil
+ windowFeatures:features];
+ [features release];
+ return core([newWebView mainFrame]);
+}
+
+void WebFrameLoaderClient::dispatchShow()
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ [[webView _UIDelegateForwarder] webViewShow:webView];
+}
+
+void WebFrameLoaderClient::dispatchDecidePolicyForMIMEType(FramePolicyFunction function,
+ const String& MIMEType, const ResourceRequest& request)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+
+ [[webView _policyDelegateForwarder] webView:webView
+ decidePolicyForMIMEType:MIMEType
+ request:request.nsURLRequest()
+ frame:m_webFrame.get()
+ decisionListener:setUpPolicyListener(function).get()];
+}
+
+void WebFrameLoaderClient::dispatchDecidePolicyForNewWindowAction(FramePolicyFunction function,
+ const NavigationAction& action, const ResourceRequest& request, const String& frameName)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ [[webView _policyDelegateForwarder] webView:webView
+ decidePolicyForNewWindowAction:actionDictionary(action)
+ request:request.nsURLRequest()
+ newFrameName:frameName
+ decisionListener:setUpPolicyListener(function).get()];
+}
+
+void WebFrameLoaderClient::dispatchDecidePolicyForNavigationAction(FramePolicyFunction function,
+ const NavigationAction& action, const ResourceRequest& request)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ [[webView _policyDelegateForwarder] webView:webView
+ decidePolicyForNavigationAction:actionDictionary(action)
+ request:request.nsURLRequest()
+ frame:m_webFrame.get()
+ decisionListener:setUpPolicyListener(function).get()];
+}
+
+void WebFrameLoaderClient::cancelPolicyCheck()
+{
+ [m_policyListener.get() invalidate];
+ m_policyListener = nil;
+ m_policyFunction = 0;
+}
+
+void WebFrameLoaderClient::dispatchUnableToImplementPolicy(const ResourceError& error)
+{
+ WebView *webView = getWebView(m_webFrame.get());
+ [[webView _policyDelegateForwarder] webView:webView unableToImplementPolicyWithError:error frame:m_webFrame.get()];
+}
+
+void WebFrameLoaderClient::dispatchWillSubmitForm(FramePolicyFunction function, PassRefPtr<FormState> formState)
+{
+ id <WebFormDelegate> formDelegate = [getWebView(m_webFrame.get()) _formDelegate];
+ if (!formDelegate) {
+ (core(m_webFrame.get())->loader()->*function)(PolicyUse);
+ return;
+ }
+
+ NSMutableDictionary *dictionary = [[NSMutableDictionary alloc] initWithCapacity:formState->values().size()];
+ HashMap<String, String>::const_iterator end = formState->values().end();
+ for (HashMap<String, String>::const_iterator it = formState->values().begin(); it != end; ++it)
+ [dictionary setObject:it->second forKey:it->first];
+
+ CallFormDelegate(getWebView(m_webFrame.get()), @selector(frame:sourceFrame:willSubmitForm:withValues:submissionListener:), m_webFrame.get(), kit(formState->sourceFrame()), kit(formState->form()), dictionary, setUpPolicyListener(function).get());
+
+ [dictionary release];
+}
+
+void WebFrameLoaderClient::dispatchDidLoadMainResource(DocumentLoader* loader)
+{
+ if ([WebScriptDebugServer listenerCount])
+ [[WebScriptDebugServer sharedScriptDebugServer] webView:getWebView(m_webFrame.get()) didLoadMainResourceForDataSource:dataSource(loader)];
+}
+
+void WebFrameLoaderClient::revertToProvisionalState(DocumentLoader* loader)
+{
+ [dataSource(loader) _revertToProvisionalState];
+}
+
+void WebFrameLoaderClient::setMainDocumentError(DocumentLoader* loader, const ResourceError& error)
+{
+ [dataSource(loader) _setMainDocumentError:error];
+}
+
+void WebFrameLoaderClient::clearUnarchivingState(DocumentLoader* loader)
+{
+ [dataSource(loader) _clearUnarchivingState];
+}
+
+void WebFrameLoaderClient::willChangeEstimatedProgress()
+{
+ [getWebView(m_webFrame.get()) _willChangeValueForKey:_WebEstimatedProgressKey];
+}
+
+void WebFrameLoaderClient::didChangeEstimatedProgress()
+{
+ [getWebView(m_webFrame.get()) _didChangeValueForKey:_WebEstimatedProgressKey];
+}
+
+void WebFrameLoaderClient::postProgressStartedNotification()
+{
+ [[NSNotificationCenter defaultCenter] postNotificationName:WebViewProgressStartedNotification object:getWebView(m_webFrame.get())];
+}
+
+void WebFrameLoaderClient::postProgressEstimateChangedNotification()
+{
+ [[NSNotificationCenter defaultCenter] postNotificationName:WebViewProgressEstimateChangedNotification object:getWebView(m_webFrame.get())];
+}
+
+void WebFrameLoaderClient::postProgressFinishedNotification()
+{
+ [[NSNotificationCenter defaultCenter] postNotificationName:WebViewProgressFinishedNotification object:getWebView(m_webFrame.get())];
+}
+
+void WebFrameLoaderClient::setMainFrameDocumentReady(bool ready)
+{
+ [getWebView(m_webFrame.get()) setMainFrameDocumentReady:ready];
+}
+
+void WebFrameLoaderClient::startDownload(const ResourceRequest& request)
+{
+ // FIXME: Should download full request.
+ WebDownload *download = [getWebView(m_webFrame.get()) _downloadURL:request.url()];
+
+ setOriginalURLForDownload(download, request);
+}
+
+void WebFrameLoaderClient::willChangeTitle(DocumentLoader* loader)
+{
+ // FIXME: Should do this only in main frame case, right?
+ [getWebView(m_webFrame.get()) _willChangeValueForKey:_WebMainFrameTitleKey];
+}
+
+void WebFrameLoaderClient::didChangeTitle(DocumentLoader* loader)
+{
+ // FIXME: Should do this only in main frame case, right?
+ [getWebView(m_webFrame.get()) _didChangeValueForKey:_WebMainFrameTitleKey];
+}
+
+void WebFrameLoaderClient::committedLoad(DocumentLoader* loader, const char* data, int length)
+{
+ NSData *nsData = [[NSData alloc] initWithBytesNoCopy:(void*)data length:length freeWhenDone:NO];
+ [dataSource(loader) _receivedData:nsData];
+ [nsData release];
+}
+
+void WebFrameLoaderClient::finishedLoading(DocumentLoader* loader)
+{
+ [dataSource(loader) _finishedLoading];
+}
+
+void WebFrameLoaderClient::finalSetupForReplace(DocumentLoader* loader)
+{
+ [dataSource(loader) _clearUnarchivingState];
+}
+
+void WebFrameLoaderClient::updateGlobalHistory(const KURL& url)
+{
+ NSURL *cocoaURL = url;
+ WebHistoryItem *entry = [[WebHistory optionalSharedHistory] addItemForURL:cocoaURL];
+ const String& pageTitle = core(m_webFrame.get())->loader()->documentLoader()->title();
+ if (!pageTitle.isEmpty())
+ [entry setTitle:pageTitle];
+}
+
+bool WebFrameLoaderClient::shouldGoToHistoryItem(HistoryItem* item) const
+{
+ WebView* view = getWebView(m_webFrame.get());
+ WebHistoryItem *webItem = kit(item);
+
+ return [[view _policyDelegateForwarder] webView:view shouldGoToHistoryItem:webItem];
+}
+
+ResourceError WebFrameLoaderClient::cancelledError(const ResourceRequest& request)
+{
+ return [NSError _webKitErrorWithDomain:NSURLErrorDomain code:NSURLErrorCancelled URL:request.url()];
+}
+
+ResourceError WebFrameLoaderClient::blockedError(const ResourceRequest& request)
+{
+ return [NSError _webKitErrorWithDomain:WebKitErrorDomain code:WebKitErrorCannotUseRestrictedPort URL:request.url()];
+}
+
+ResourceError WebFrameLoaderClient::cannotShowURLError(const ResourceRequest& request)
+{
+ return [NSError _webKitErrorWithDomain:WebKitErrorDomain code:WebKitErrorCannotShowURL URL:request.url()];
+}
+
+ResourceError WebFrameLoaderClient::interruptForPolicyChangeError(const ResourceRequest& request)
+{
+ return [NSError _webKitErrorWithDomain:WebKitErrorDomain code:WebKitErrorFrameLoadInterruptedByPolicyChange URL:request.url()];
+}
+
+ResourceError WebFrameLoaderClient::cannotShowMIMETypeError(const ResourceResponse& response)
+{
+ return [NSError _webKitErrorWithDomain:NSURLErrorDomain code:WebKitErrorCannotShowMIMEType URL:response.url()];
+}
+
+ResourceError WebFrameLoaderClient::fileDoesNotExistError(const ResourceResponse& response)
+{
+ return [NSError _webKitErrorWithDomain:NSURLErrorDomain code:NSURLErrorFileDoesNotExist URL:response.url()];
+}
+
+bool WebFrameLoaderClient::shouldFallBack(const ResourceError& error)
+{
+ // FIXME: Needs to check domain.
+ // FIXME: WebKitErrorPlugInWillHandleLoad is a workaround for the cancel we do to prevent
+ // loading plugin content twice. See <rdar://problem/4258008>
+ return error.errorCode() != NSURLErrorCancelled && error.errorCode() != WebKitErrorPlugInWillHandleLoad;
+}
+
+void WebFrameLoaderClient::setDefersLoading(bool defers)
+{
+ if (!defers)
+ deliverArchivedResourcesAfterDelay();
+}
+
+bool WebFrameLoaderClient::willUseArchive(ResourceLoader* loader, const ResourceRequest& request, const KURL& originalURL) const
+{
+ if (request.url() != originalURL)
+ return false;
+
+ WebResource *resource = [dataSource(core(m_webFrame.get())->loader()->activeDocumentLoader()) _archivedSubresourceForURL:originalURL];
+ if (!resource)
+ return false;
+
+ m_pendingArchivedResources.set(loader, resource);
+ // Deliver the resource after a delay because callers don't expect to receive callbacks while calling this method.
+ deliverArchivedResourcesAfterDelay();
+
+ return true;
+}
+
+bool WebFrameLoaderClient::isArchiveLoadPending(ResourceLoader* loader) const
+{
+ return m_pendingArchivedResources.contains(loader);
+}
+
+void WebFrameLoaderClient::cancelPendingArchiveLoad(ResourceLoader* loader)
+{
+ if (m_pendingArchivedResources.isEmpty())
+ return;
+ m_pendingArchivedResources.remove(loader);
+ if (m_pendingArchivedResources.isEmpty())
+ m_archivedResourcesDeliveryTimer.stop();
+}
+
+void WebFrameLoaderClient::clearArchivedResources()
+{
+ m_pendingArchivedResources.clear();
+ m_archivedResourcesDeliveryTimer.stop();
+}
+
+bool WebFrameLoaderClient::canHandleRequest(const ResourceRequest& request) const
+{
+ return [WebView _canHandleRequest:request.nsURLRequest()];
+}
+
+bool WebFrameLoaderClient::canShowMIMEType(const String& MIMEType) const
+{
+ return [WebView canShowMIMEType:MIMEType];
+}
+
+bool WebFrameLoaderClient::representationExistsForURLScheme(const String& URLScheme) const
+{
+ return [WebView _representationExistsForURLScheme:URLScheme];
+}
+
+String WebFrameLoaderClient::generatedMIMETypeForURLScheme(const String& URLScheme) const
+{
+ return [WebView _generatedMIMETypeForURLScheme:URLScheme];
+}
+
+void WebFrameLoaderClient::frameLoadCompleted()
+{
+ // Note: Can be called multiple times.
+ // Even if already complete, we might have set a previous item on a frame that
+ // didn't do any data loading on the past transaction. Make sure to clear these out.
+ NSScrollView *sv = [m_webFrame->_private->webFrameView _scrollView];
+ if ([getWebView(m_webFrame.get()) drawsBackground])
+ [sv setDrawsBackground:YES];
+ core(m_webFrame.get())->loader()->setPreviousHistoryItem(0);
+}
+
+
+void WebFrameLoaderClient::saveViewStateToItem(HistoryItem* item)
+{
+ if (!item)
+ return;
+
+ NSView <WebDocumentView> *docView = [m_webFrame->_private->webFrameView documentView];
+
+ // we might already be detached when this is called from detachFromParent, in which
+ // case we don't want to override real data earlier gathered with (0,0)
+ if ([docView superview] && [docView conformsToProtocol:@protocol(_WebDocumentViewState)])
+ item->setViewState([(id <_WebDocumentViewState>)docView viewState]);
+}
+
+void WebFrameLoaderClient::restoreViewState()
+{
+ HistoryItem* currentItem = core(m_webFrame.get())->loader()->currentHistoryItem();
+ ASSERT(currentItem);
+
+ // FIXME: As the ASSERT attests, it seems we should always have a currentItem here.
+ // One counterexample is <rdar://problem/4917290>
+ // For now, to cover this issue in release builds, there is no technical harm to returning
+ // early and from a user standpoint - as in the above radar - the previous page load failed
+ // so there *is* no scroll state to restore!
+ if (!currentItem)
+ return;
+
+ NSView <WebDocumentView> *docView = [m_webFrame->_private->webFrameView documentView];
+ if ([docView conformsToProtocol:@protocol(_WebDocumentViewState)]) {
+ id state = currentItem->viewState();
+ if (state) {
+ [(id <_WebDocumentViewState>)docView setViewState:state];
+ }
+ }
+}
+
+void WebFrameLoaderClient::provisionalLoadStarted()
+{
+ // FIXME: This is OK as long as no one resizes the window,
+ // but in the case where someone does, it means garbage outside
+ // the occupied part of the scroll view.
+ [[m_webFrame->_private->webFrameView _scrollView] setDrawsBackground:NO];
+}
+
+void WebFrameLoaderClient::didFinishLoad()
+{
+ [m_webFrame->_private->internalLoadDelegate webFrame:m_webFrame.get() didFinishLoadWithError:nil];
+}
+
+void WebFrameLoaderClient::prepareForDataSourceReplacement()
+{
+ if (![m_webFrame.get() _dataSource]) {
+ ASSERT(!core(m_webFrame.get())->tree()->childCount());
+ return;
+ }
+
+ // Make sure that any work that is triggered by resigning first reponder can get done.
+ // The main example where this came up is the textDidEndEditing that is sent to the
+ // FormsDelegate (3223413). We need to do this before _detachChildren, since that will
+ // remove the views as a side-effect of freeing the bridge, at which point we can't
+ // post the FormDelegate messages.
+ //
+ // Note that this can also take FirstResponder away from a child of our frameView that
+ // is not in a child frame's view. This is OK because we are in the process
+ // of loading new content, which will blow away all editors in this top frame, and if
+ // a non-editor is firstReponder it will not be affected by endEditingFor:.
+ // Potentially one day someone could write a DocView whose editors were not all
+ // replaced by loading new content, but that does not apply currently.
+ NSView *frameView = m_webFrame->_private->webFrameView;
+ NSWindow *window = [frameView window];
+ NSResponder *firstResp = [window firstResponder];
+ if ([firstResp isKindOfClass:[NSView class]] && [(NSView *)firstResp isDescendantOf:frameView])
+ [window endEditingFor:firstResp];
+}
+
+PassRefPtr<DocumentLoader> WebFrameLoaderClient::createDocumentLoader(const ResourceRequest& request, const SubstituteData& substituteData)
+{
+ RefPtr<WebDocumentLoaderMac> loader = new WebDocumentLoaderMac(request, substituteData);
+
+ WebDataSource *dataSource = [[WebDataSource alloc] _initWithDocumentLoader:loader.get()];
+ loader->setDataSource(dataSource, getWebView(m_webFrame.get()));
+ [dataSource release];
+
+ return loader.release();
+}
+
+// FIXME: <rdar://problem/4880065> - Push Global History into WebCore
+// Once that task is complete, this will go away
+void WebFrameLoaderClient::setTitle(const String& title, const KURL& URL)
+{
+ NSURL* nsURL = URL;
+ nsURL = [nsURL _webkit_canonicalize];
+ if(!nsURL)
+ return;
+ NSString *titleNSString = title;
+ [[[WebHistory optionalSharedHistory] itemForURL:nsURL] setTitle:titleNSString];
+}
+
+void WebFrameLoaderClient::deliverArchivedResourcesAfterDelay() const
+{
+ if (m_pendingArchivedResources.isEmpty())
+ return;
+ if (core(m_webFrame.get())->page()->defersLoading())
+ return;
+ if (!m_archivedResourcesDeliveryTimer.isActive())
+ m_archivedResourcesDeliveryTimer.startOneShot(0);
+}
+
+void WebFrameLoaderClient::deliverArchivedResources(Timer<WebFrameLoaderClient>*)
+{
+ if (m_pendingArchivedResources.isEmpty())
+ return;
+ if (core(m_webFrame.get())->page()->defersLoading())
+ return;
+
+ const ResourceMap copy = m_pendingArchivedResources;
+ m_pendingArchivedResources.clear();
+
+ ResourceMap::const_iterator end = copy.end();
+ for (ResourceMap::const_iterator it = copy.begin(); it != end; ++it) {
+ RefPtr<ResourceLoader> loader = it->first;
+ WebResource *resource = it->second.get();
+ NSData *data = [[resource data] retain];
+ loader->didReceiveResponse([resource _response]);
+ loader->didReceiveData((const char*)[data bytes], [data length], [data length], true);
+ [data release];
+ loader->didFinishLoading();
+ }
+}
+
+void WebFrameLoaderClient::savePlatformDataToCachedPage(CachedPage* cachedPage)
+{
+ WebCachedPagePlatformData* webPlatformData = new WebCachedPagePlatformData([m_webFrame->_private->webFrameView documentView]);
+ cachedPage->setCachedPagePlatformData(webPlatformData);
+}
+
+void WebFrameLoaderClient::transitionToCommittedFromCachedPage(CachedPage* cachedPage)
+{
+ WebCachedPagePlatformData* platformData = reinterpret_cast<WebCachedPagePlatformData*>(cachedPage->cachedPagePlatformData());
+ NSView <WebDocumentView> *cachedView = platformData->webDocumentView();
+ ASSERT(cachedView != nil);
+ ASSERT(cachedPage->documentLoader());
+ [cachedView setDataSource:dataSource(cachedPage->documentLoader())];
+ [m_webFrame->_private->webFrameView _setDocumentView:cachedView];
+}
+
+void WebFrameLoaderClient::transitionToCommittedForNewPage()
+{
+ WebFrameView *v = m_webFrame->_private->webFrameView;
+ WebDataSource *ds = [m_webFrame.get() _dataSource];
+
+ bool willProduceHTMLView = [[WebFrameView class] _viewClassForMIMEType:[ds _responseMIMEType]] == [WebHTMLView class];
+ bool canSkipCreation = [m_webFrame.get() _frameLoader]->committingFirstRealLoad() && willProduceHTMLView;
+ if (canSkipCreation) {
+ [[v documentView] setDataSource:ds];
+ return;
+ }
+
+ // Don't suppress scrollbars before the view creation if we're making the view for a non-HTML view.
+ if (!willProduceHTMLView)
+ [[v _scrollView] setScrollBarsSuppressed:NO repaintOnUnsuppress:NO];
+
+ NSView <WebDocumentView> *documentView = [v _makeDocumentViewForDataSource:ds];
+ if (!documentView)
+ return;
+
+ WebFrameBridge *bridge = m_webFrame->_private->bridge;
+
+ // FIXME: We could save work and not do this for a top-level view that is not a WebHTMLView.
+ [bridge createFrameViewWithNSView:documentView marginWidth:[v _marginWidth] marginHeight:[v _marginHeight]];
+ [m_webFrame.get() _updateBackground];
+ [bridge installInFrame:[v _scrollView]];
+
+ // Call setDataSource on the document view after it has been placed in the view hierarchy.
+ // This what we for the top-level view, so should do this for views in subframes as well.
+ [documentView setDataSource:ds];
+}
+
+RetainPtr<WebFramePolicyListener> WebFrameLoaderClient::setUpPolicyListener(FramePolicyFunction function)
+{
+ // FIXME: <rdar://5634381> We need to support multiple active policy listeners.
+
+ [m_policyListener.get() invalidate];
+
+ WebFramePolicyListener *listener = [[WebFramePolicyListener alloc] initWithWebCoreFrame:core(m_webFrame.get())];
+ m_policyListener = listener;
+ [listener release];
+ m_policyFunction = function;
+
+ return listener;
+}
+
+void WebFrameLoaderClient::receivedPolicyDecison(PolicyAction action)
+{
+ ASSERT(m_policyListener);
+ ASSERT(m_policyFunction);
+
+ FramePolicyFunction function = m_policyFunction;
+
+ m_policyListener = nil;
+ m_policyFunction = 0;
+
+ (core(m_webFrame.get())->loader()->*function)(action);
+}
+
+String WebFrameLoaderClient::userAgent(const KURL& url)
+{
+ return [getWebView(m_webFrame.get()) _userAgentForURL:url];
+}
+
+static const MouseEvent* findMouseEvent(const Event* event)
+{
+ for (const Event* e = event; e; e = e->underlyingEvent())
+ if (e->isMouseEvent())
+ return static_cast<const MouseEvent*>(e);
+ return 0;
+}
+
+NSDictionary *WebFrameLoaderClient::actionDictionary(const NavigationAction& action) const
+{
+ unsigned modifierFlags = 0;
+ const Event* event = action.event();
+ if (const UIEventWithKeyState* keyStateEvent = findEventWithKeyState(const_cast<Event*>(event))) {
+ if (keyStateEvent->ctrlKey())
+ modifierFlags |= NSControlKeyMask;
+ if (keyStateEvent->altKey())
+ modifierFlags |= NSAlternateKeyMask;
+ if (keyStateEvent->shiftKey())
+ modifierFlags |= NSShiftKeyMask;
+ if (keyStateEvent->metaKey())
+ modifierFlags |= NSCommandKeyMask;
+ }
+ NSURL *originalURL = action.url();
+ if (const MouseEvent* mouseEvent = findMouseEvent(event)) {
+ IntPoint point(mouseEvent->pageX(), mouseEvent->pageY());
+ WebElementDictionary *element = [[WebElementDictionary alloc]
+ initWithHitTestResult:core(m_webFrame.get())->eventHandler()->hitTestResultAtPoint(point, false)];
+ NSDictionary *result = [NSDictionary dictionaryWithObjectsAndKeys:
+ [NSNumber numberWithInt:action.type()], WebActionNavigationTypeKey,
+ element, WebActionElementKey,
+ [NSNumber numberWithInt:mouseEvent->button()], WebActionButtonKey,
+ [NSNumber numberWithInt:modifierFlags], WebActionModifierFlagsKey,
+ originalURL, WebActionOriginalURLKey,
+ nil];
+ [element release];
+ return result;
+ }
+ return [NSDictionary dictionaryWithObjectsAndKeys:
+ [NSNumber numberWithInt:action.type()], WebActionNavigationTypeKey,
+ [NSNumber numberWithInt:modifierFlags], WebActionModifierFlagsKey,
+ originalURL, WebActionOriginalURLKey,
+ nil];
+}
+
+bool WebFrameLoaderClient::canCachePage() const
+{
+ // We can only cache HTML pages right now
+ return [[[m_webFrame.get() _dataSource] representation] isKindOfClass:[WebHTMLRepresentation class]];
+}
+
+PassRefPtr<Frame> WebFrameLoaderClient::createFrame(const KURL& url, const String& name, HTMLFrameOwnerElement* ownerElement,
+ const String& referrer, bool allowsScrolling, int marginWidth, int marginHeight)
+{
+ WebFrameBridge* bridge = m_webFrame->_private->bridge;
+ BEGIN_BLOCK_OBJC_EXCEPTIONS;
+
+ return [bridge createChildFrameNamed:name
+ withURL:url
+ referrer:referrer
+ ownerElement:ownerElement
+ allowsScrolling:allowsScrolling
+ marginWidth:marginWidth
+ marginHeight:marginHeight];
+
+ END_BLOCK_OBJC_EXCEPTIONS;
+ return 0;
+}
+
+ObjectContentType WebFrameLoaderClient::objectContentType(const KURL& url, const String& mimeType)
+{
+ WebFrameBridge* bridge = m_webFrame->_private->bridge;
+ BEGIN_BLOCK_OBJC_EXCEPTIONS;
+ return [bridge determineObjectFromMIMEType:mimeType URL:url];
+ END_BLOCK_OBJC_EXCEPTIONS;
+ return ObjectContentNone;
+}
+
+static NSArray* nsArray(const Vector<String>& vector)
+{
+ unsigned len = vector.size();
+ NSMutableArray* array = [NSMutableArray arrayWithCapacity:len];
+ for (unsigned x = 0; x < len; x++)
+ [array addObject:vector[x]];
+ return array;
+}
+
+Widget* WebFrameLoaderClient::createPlugin(const IntSize& size, Element* element, const KURL& url, const Vector<String>& paramNames,
+ const Vector<String>& paramValues, const String& mimeType, bool loadManually)
+{
+ WebFrameBridge* bridge = m_webFrame->_private->bridge;
+
+ BEGIN_BLOCK_OBJC_EXCEPTIONS;
+ return new Widget([bridge viewForPluginWithFrame:NSMakeRect(0, 0, size.width(), size.height())
+ URL:url
+ attributeNames:nsArray(paramNames)
+ attributeValues:nsArray(paramValues)
+ MIMEType:mimeType
+ DOMElement:[DOMElement _wrapElement:element]
+ loadManually:loadManually]);
+ END_BLOCK_OBJC_EXCEPTIONS;
+
+ return 0;
+}
+
+void WebFrameLoaderClient::redirectDataToPlugin(Widget* pluginWidget)
+{
+ BEGIN_BLOCK_OBJC_EXCEPTIONS;
+ [m_webFrame->_private->bridge redirectDataToPlugin:pluginWidget->getView()];
+ END_BLOCK_OBJC_EXCEPTIONS;
+}
+
+Widget* WebFrameLoaderClient::createJavaAppletWidget(const IntSize& size, Element* element, const KURL& baseURL,
+ const Vector<String>& paramNames, const Vector<String>& paramValues)
+{
+ Widget* result = new Widget;
+
+ BEGIN_BLOCK_OBJC_EXCEPTIONS;
+ WebFrameBridge* bridge = m_webFrame->_private->bridge;
+ result->setView([bridge viewForJavaAppletWithFrame:NSMakeRect(0, 0, size.width(), size.height())
+ attributeNames:nsArray(paramNames)
+ attributeValues:nsArray(paramValues)
+ baseURL:baseURL
+ DOMElement:[DOMElement _wrapElement:element]]);
+ END_BLOCK_OBJC_EXCEPTIONS;
+
+ return result;
+}
+
+String WebFrameLoaderClient::overrideMediaType() const
+{
+ NSString* overrideType = [getWebView(m_webFrame.get()) mediaStyle];
+ if (overrideType)
+ return overrideType;
+ return String();
+}
+
+void WebFrameLoaderClient::windowObjectCleared()
+{
+ [m_webFrame->_private->bridge windowObjectCleared];
+}
+
+void WebFrameLoaderClient::registerForIconNotification(bool listen)
+{
+ [[m_webFrame.get() webView] _registerForIconNotification:listen];
+}
+
+void WebFrameLoaderClient::didPerformFirstNavigation() const
+{
+ WebPreferences *preferences = [[m_webFrame.get() webView] preferences];
+ if ([preferences automaticallyDetectsCacheModel] && [preferences cacheModel] < WebCacheModelDocumentBrowser)
+ [preferences setCacheModel:WebCacheModelDocumentBrowser];
+}
+
+@implementation WebFramePolicyListener
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
+- (id)initWithWebCoreFrame:(Frame*)frame
+{
+ self = [self init];
+ if (!self)
+ return nil;
+ frame->ref();
+ m_frame = frame;
+ return self;
+}
+
+- (void)invalidate
+{
+ if (m_frame) {
+ m_frame->deref();
+ m_frame = 0;
+ }
+}
+
+- (void)dealloc
+{
+ if (m_frame)
+ m_frame->deref();
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+ if (m_frame)
+ m_frame->deref();
+ [super finalize];
+}
+
+- (void)receivedPolicyDecision:(PolicyAction)action
+{
+ RefPtr<Frame> frame = adoptRef(m_frame);
+ m_frame = 0;
+ if (frame)
+ static_cast<WebFrameLoaderClient*>(frame->loader()->client())->receivedPolicyDecison(action);
+}
+
+- (void)ignore
+{
+ [self receivedPolicyDecision:PolicyIgnore];
+}
+
+- (void)download
+{
+ [self receivedPolicyDecision:PolicyDownload];
+}
+
+- (void)use
+{
+ [self receivedPolicyDecision:PolicyUse];
+}
+
+- (void)continue
+{
+ [self receivedPolicyDecision:PolicyUse];
+}
+
+@end
diff --git a/WebKit/mac/WebCoreSupport/WebIconDatabaseClient.h b/WebKit/mac/WebCoreSupport/WebIconDatabaseClient.h
new file mode 100644
index 0000000..e908242
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebIconDatabaseClient.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/IconDatabaseClient.h>
+
+namespace WebCore {
+ class String;
+}
+
+class WebIconDatabaseClient : public WebCore::IconDatabaseClient {
+public:
+ virtual bool performImport();
+ virtual void dispatchDidRemoveAllIcons();
+ virtual void dispatchDidAddIconForPageURL(const WebCore::String& pageURL);
+};
diff --git a/WebKit/mac/WebCoreSupport/WebIconDatabaseClient.mm b/WebKit/mac/WebCoreSupport/WebIconDatabaseClient.mm
new file mode 100644
index 0000000..43202b0
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebIconDatabaseClient.mm
@@ -0,0 +1,58 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebIconDatabaseClient.h"
+
+#import "WebIconDatabaseInternal.h"
+
+#import <WebCore/FoundationExtras.h>
+#import <WebCore/PlatformString.h>
+
+
+bool WebIconDatabaseClient::performImport()
+{
+ NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
+ bool result = importToWebCoreFormat();
+ [pool drain];
+ return result;
+}
+
+void WebIconDatabaseClient::dispatchDidRemoveAllIcons()
+{
+ NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
+ [[WebIconDatabase sharedIconDatabase] _sendDidRemoveAllIconsNotification];
+ [pool drain];
+}
+
+void WebIconDatabaseClient::dispatchDidAddIconForPageURL(const WebCore::String& pageURL)
+{
+ // This is a quick notification that is likely to fire in a rapidly iterating loop
+ // Therefore we let WebCore handle autorelease by draining its pool "from time to time"
+ // instead of us doing it every iteration
+ [[WebIconDatabase sharedIconDatabase] _sendNotificationForURL:pageURL];
+}
diff --git a/WebKit/mac/WebCoreSupport/WebImageRendererFactory.m b/WebKit/mac/WebCoreSupport/WebImageRendererFactory.m
new file mode 100644
index 0000000..36e25b7
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebImageRendererFactory.m
@@ -0,0 +1,47 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// Have to leave this class with these two methods in because versions of Safari up to 3.0.4
+// call the methods from the Debug menu. Once we don't need compatibility with those versions
+// of Safari, we can remove this.
+
+@interface WebImageRendererFactory : NSObject
+@end
+
+@implementation WebImageRendererFactory
+
++ (BOOL)shouldUseThreadedDecoding
+{
+ return NO;
+}
+
++ (void)setShouldUseThreadedDecoding:(BOOL)threadedDecode
+{
+}
+
+@end
diff --git a/WebKit/mac/WebCoreSupport/WebInspectorClient.h b/WebKit/mac/WebCoreSupport/WebInspectorClient.h
new file mode 100644
index 0000000..45cd1f9
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebInspectorClient.h
@@ -0,0 +1,62 @@
+/*
+ * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/InspectorClient.h>
+#import <WebCore/PlatformString.h>
+
+#import <wtf/RetainPtr.h>
+
+@class WebInspectorWindowController;
+@class WebView;
+
+class WebInspectorClient : public WebCore::InspectorClient {
+public:
+ WebInspectorClient(WebView *);
+
+ virtual void inspectorDestroyed();
+
+ virtual WebCore::Page* createPage();
+ virtual WebCore::String localizedStringsURL();
+
+ virtual void showWindow();
+ virtual void closeWindow();
+
+ virtual void attachWindow();
+ virtual void detachWindow();
+
+ virtual void highlight(WebCore::Node*);
+ virtual void hideHighlight();
+ virtual void inspectedURLChanged(const WebCore::String& newURL);
+
+private:
+ void updateWindowTitle() const;
+
+ WebView *m_webView;
+ RetainPtr<WebInspectorWindowController> m_windowController;
+ WebCore::String m_inspectedURL;
+};
diff --git a/WebKit/mac/WebCoreSupport/WebInspectorClient.mm b/WebKit/mac/WebCoreSupport/WebInspectorClient.mm
new file mode 100644
index 0000000..255e51e
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebInspectorClient.mm
@@ -0,0 +1,535 @@
+/*
+ * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebInspectorClient.h"
+
+#import "WebFrameInternal.h"
+#import "WebFrameView.h"
+#import "WebLocalizableStrings.h"
+#import "WebNodeHighlight.h"
+#import "WebPreferences.h"
+#import "WebTypesInternal.h"
+#import "WebView.h"
+#import "WebViewInternal.h"
+#import "WebViewPrivate.h"
+
+#import <AppKit/NSWindowController.h>
+
+#import <WebCore/InspectorController.h>
+#import <WebCore/Page.h>
+
+#import <WebKit/DOMCore.h>
+#import <WebKit/DOMExtensions.h>
+#import <WebKit/WebUIDelegate.h>
+
+#import <WebKitSystemInterface.h>
+
+using namespace WebCore;
+
+@interface WebInspectorWindowController : NSWindowController {
+@private
+ WebView *_inspectedWebView;
+ WebView *_webView;
+ NSImageView *_shadowView;
+ WebNodeHighlight *_currentHighlight;
+ BOOL _attachedToInspectedWebView;
+ BOOL _shouldAttach;
+ BOOL _visible;
+ BOOL _movingWindows;
+}
+- (id)initWithInspectedWebView:(WebView *)webView;
+- (BOOL)inspectorVisible;
+- (WebView *)webView;
+- (void)attach;
+- (void)detach;
+- (void)highlightAndScrollToNode:(DOMNode *)node;
+- (void)highlightNode:(DOMNode *)node;
+- (void)hideHighlight;
+@end
+
+#pragma mark -
+
+WebInspectorClient::WebInspectorClient(WebView *webView)
+: m_webView(webView)
+{
+}
+
+void WebInspectorClient::inspectorDestroyed()
+{
+ [[m_windowController.get() webView] close];
+ delete this;
+}
+
+Page* WebInspectorClient::createPage()
+{
+ if (!m_windowController)
+ m_windowController.adoptNS([[WebInspectorWindowController alloc] initWithInspectedWebView:m_webView]);
+
+ return core([m_windowController.get() webView]);
+}
+
+String WebInspectorClient::localizedStringsURL()
+{
+ NSString *path = [[NSBundle bundleWithIdentifier:@"com.apple.WebCore"] pathForResource:@"InspectorLocalizedStrings" ofType:@"js"];
+ if (path)
+ return [[NSURL fileURLWithPath:path] absoluteString];
+ return String();
+}
+
+void WebInspectorClient::showWindow()
+{
+ updateWindowTitle();
+ [m_windowController.get() showWindow:nil];
+}
+
+void WebInspectorClient::closeWindow()
+{
+ [m_windowController.get() close];
+}
+
+void WebInspectorClient::attachWindow()
+{
+ [m_windowController.get() attach];
+}
+
+void WebInspectorClient::detachWindow()
+{
+ [m_windowController.get() detach];
+}
+
+void WebInspectorClient::highlight(Node* node)
+{
+ [m_windowController.get() highlightAndScrollToNode:kit(node)];
+}
+
+void WebInspectorClient::hideHighlight()
+{
+ [m_windowController.get() hideHighlight];
+}
+
+void WebInspectorClient::inspectedURLChanged(const String& newURL)
+{
+ m_inspectedURL = newURL;
+ updateWindowTitle();
+}
+
+void WebInspectorClient::updateWindowTitle() const
+{
+ NSString *title = [NSString stringWithFormat:UI_STRING("Web Inspector — %@", "Web Inspector window title"), (NSString *)m_inspectedURL];
+ [[m_windowController.get() window] setTitle:title];
+}
+
+#pragma mark -
+
+#define WebKitInspectorAttachedViewHeightKey @"WebKitInspectorAttachedViewHeight"
+
+@implementation WebInspectorWindowController
+- (id)init
+{
+ if (![super initWithWindow:nil])
+ return nil;
+
+ // Keep preferences separate from the rest of the client, making sure we are using expected preference values.
+ // One reason this is good is that it keeps the inspector out of history via "private browsing".
+
+ WebPreferences *preferences = [[WebPreferences alloc] init];
+ [preferences setAutosaves:NO];
+ [preferences setPrivateBrowsingEnabled:YES];
+ [preferences setLoadsImagesAutomatically:YES];
+ [preferences setAuthorAndUserStylesEnabled:YES];
+ [preferences setJavaScriptEnabled:YES];
+ [preferences setAllowsAnimatedImages:YES];
+ [preferences setPlugInsEnabled:NO];
+ [preferences setJavaEnabled:NO];
+ [preferences setUserStyleSheetEnabled:NO];
+ [preferences setTabsToLinks:NO];
+ [preferences setMinimumFontSize:0];
+ [preferences setMinimumLogicalFontSize:9];
+
+ _webView = [[WebView alloc] init];
+ [_webView setPreferences:preferences];
+ [_webView setDrawsBackground:NO];
+ [_webView setProhibitsMainFrameScrolling:YES];
+ [_webView setUIDelegate:self];
+
+ [preferences release];
+
+ NSString *path = [[NSBundle bundleWithIdentifier:@"com.apple.WebCore"] pathForResource:@"inspector" ofType:@"html" inDirectory:@"inspector"];
+ NSURLRequest *request = [[NSURLRequest alloc] initWithURL:[NSURL fileURLWithPath:path]];
+ [[_webView mainFrame] loadRequest:request];
+ [request release];
+
+ [self setWindowFrameAutosaveName:@"Web Inspector 2"];
+ return self;
+}
+
+- (id)initWithInspectedWebView:(WebView *)webView
+{
+ if (![self init])
+ return nil;
+
+ // Don't retain to avoid a circular reference
+ _inspectedWebView = webView;
+ return self;
+}
+
+- (void)dealloc
+{
+ [_shadowView release];
+ [_webView release];
+ [super dealloc];
+}
+
+#pragma mark -
+
+- (BOOL)inspectorVisible
+{
+ return _visible;
+}
+
+- (WebView *)webView
+{
+ return _webView;
+}
+
+- (NSWindow *)window
+{
+ NSWindow *window = [super window];
+ if (window)
+ return window;
+
+ NSUInteger styleMask = (NSTitledWindowMask | NSClosableWindowMask | NSMiniaturizableWindowMask | NSResizableWindowMask);
+
+#ifndef BUILDING_ON_TIGER
+ styleMask |= NSTexturedBackgroundWindowMask;
+#endif
+
+ window = [[NSWindow alloc] initWithContentRect:NSMakeRect(60.0, 200.0, 750.0, 650.0) styleMask:styleMask backing:NSBackingStoreBuffered defer:YES];
+ [window setDelegate:self];
+ [window setMinSize:NSMakeSize(400.0, 400.0)];
+
+#ifndef BUILDING_ON_TIGER
+ [window setAutorecalculatesContentBorderThickness:NO forEdge:NSMaxYEdge];
+ [window setContentBorderThickness:40. forEdge:NSMaxYEdge];
+
+ WKNSWindowMakeBottomCornersSquare(window);
+#endif
+
+ [self setWindow:window];
+ [window release];
+
+ return window;
+}
+
+#pragma mark -
+
+- (BOOL)windowShouldClose:(id)sender
+{
+ _visible = NO;
+
+ [_inspectedWebView page]->inspectorController()->setWindowVisible(false);
+
+ [_currentHighlight detachHighlight];
+ [_currentHighlight setDelegate:nil];
+ [_currentHighlight release];
+ _currentHighlight = nil;
+
+ return YES;
+}
+
+- (void)close
+{
+ if (!_visible)
+ return;
+
+ _visible = NO;
+
+ [_inspectedWebView page]->inspectorController()->setWindowVisible(false);
+
+ if (!_movingWindows) {
+ [_currentHighlight detachHighlight];
+ [_currentHighlight setDelegate:nil];
+ [_currentHighlight release];
+ _currentHighlight = nil;
+ }
+
+ if (_attachedToInspectedWebView) {
+ if ([_inspectedWebView _isClosed])
+ return;
+
+ WebFrameView *frameView = [[_inspectedWebView mainFrame] frameView];
+
+ NSRect frameViewRect = [frameView frame];
+ NSRect finalFrameViewRect = NSMakeRect(0, 0, NSWidth(frameViewRect), NSHeight([_inspectedWebView frame]));
+ NSMutableDictionary *frameViewAnimationInfo = [[NSMutableDictionary alloc] init];
+ [frameViewAnimationInfo setObject:frameView forKey:NSViewAnimationTargetKey];
+ [frameViewAnimationInfo setObject:[NSValue valueWithRect:finalFrameViewRect] forKey:NSViewAnimationEndFrameKey];
+
+ ASSERT(_shadowView);
+ NSRect shadowFrame = [_shadowView frame];
+ shadowFrame = NSMakeRect(0, NSMinY(frameViewRect) - NSHeight(shadowFrame), NSWidth(frameViewRect), NSHeight(shadowFrame));
+ [_shadowView setFrame:shadowFrame];
+
+ [_shadowView removeFromSuperview];
+ [_inspectedWebView addSubview:_shadowView positioned:NSWindowAbove relativeTo:_webView];
+
+ NSRect finalShadowRect = NSMakeRect(0, -NSHeight(shadowFrame), NSWidth(shadowFrame), NSHeight(shadowFrame));
+ NSMutableDictionary *shadowAnimationInfo = [[NSMutableDictionary alloc] init];
+ [shadowAnimationInfo setObject:_shadowView forKey:NSViewAnimationTargetKey];
+ [shadowAnimationInfo setObject:[NSValue valueWithRect:finalShadowRect] forKey:NSViewAnimationEndFrameKey];
+
+ NSArray *animationInfo = [[NSArray alloc] initWithObjects:frameViewAnimationInfo, shadowAnimationInfo, nil];
+ [frameViewAnimationInfo release];
+ [shadowAnimationInfo release];
+
+ NSViewAnimation *slideAnimation = [[NSViewAnimation alloc] initWithViewAnimations:animationInfo]; // released in animationDidEnd
+ [animationInfo release];
+
+ [slideAnimation setAnimationBlockingMode:NSAnimationBlocking];
+ [slideAnimation setDelegate:self];
+
+ [[_inspectedWebView window] display]; // display once to make sure we start in a good state
+ [slideAnimation startAnimation];
+ } else {
+ [super close];
+ }
+}
+
+- (IBAction)showWindow:(id)sender
+{
+ if (_visible) {
+ if (!_attachedToInspectedWebView)
+ [super showWindow:sender]; // call super so the window will be ordered front if needed
+ return;
+ }
+
+ _visible = YES;
+
+ [_inspectedWebView page]->inspectorController()->setWindowVisible(true);
+
+ if (_shouldAttach) {
+ WebFrameView *frameView = [[_inspectedWebView mainFrame] frameView];
+
+ NSRect frameViewRect = [frameView frame];
+ float attachedHeight = [[NSUserDefaults standardUserDefaults] integerForKey:WebKitInspectorAttachedViewHeightKey];
+ attachedHeight = MAX(300.0, MIN(attachedHeight, (NSHeight(frameViewRect) * 0.6)));
+
+ [_webView removeFromSuperview];
+ [_inspectedWebView addSubview:_webView positioned:NSWindowBelow relativeTo:(NSView*)frameView];
+ [_webView setFrame:NSMakeRect(0, 0, NSWidth(frameViewRect), attachedHeight)];
+ [_webView setAutoresizingMask:(NSViewWidthSizable | NSViewHeightSizable | NSViewMaxYMargin)];
+
+ [frameView setAutoresizingMask:(NSViewWidthSizable | NSViewHeightSizable | NSViewMinYMargin)];
+
+ NSRect finalFrameViewRect = NSMakeRect(0, attachedHeight, NSWidth(frameViewRect), NSHeight(frameViewRect) - attachedHeight);
+ NSMutableDictionary *frameViewAnimationInfo = [[NSMutableDictionary alloc] init];
+ [frameViewAnimationInfo setObject:frameView forKey:NSViewAnimationTargetKey];
+ [frameViewAnimationInfo setObject:[NSValue valueWithRect:finalFrameViewRect] forKey:NSViewAnimationEndFrameKey];
+
+ if (!_shadowView) {
+ NSString *imagePath = [[NSBundle bundleWithIdentifier:@"com.apple.WebCore"] pathForResource:@"attachedShadow" ofType:@"png" inDirectory:@"inspector/Images"];
+ NSImage *image = [[NSImage alloc] initWithContentsOfFile:imagePath];
+ _shadowView = [[NSImageView alloc] initWithFrame:NSMakeRect(0, -[image size].height, NSWidth(frameViewRect), [image size].height)];
+ [_shadowView setImage:image];
+ [_shadowView setImageScaling:NSScaleToFit];
+ [_shadowView setImageFrameStyle:NSImageFrameNone];
+ [_shadowView setAutoresizingMask:(NSViewWidthSizable | NSViewHeightSizable | NSViewMaxYMargin)];
+ }
+
+ NSRect shadowFrame = [_shadowView frame];
+ shadowFrame = NSMakeRect(0, -NSHeight(shadowFrame), NSWidth(frameViewRect), NSHeight(shadowFrame));
+ [_shadowView setFrame:shadowFrame];
+
+ [_shadowView removeFromSuperview];
+ [_inspectedWebView addSubview:_shadowView positioned:NSWindowAbove relativeTo:_webView];
+
+ NSRect finalShadowRect = NSMakeRect(0, attachedHeight - NSHeight(shadowFrame), NSWidth(shadowFrame), NSHeight(shadowFrame));
+ NSMutableDictionary *shadowAnimationInfo = [[NSMutableDictionary alloc] init];
+ [shadowAnimationInfo setObject:_shadowView forKey:NSViewAnimationTargetKey];
+ [shadowAnimationInfo setObject:[NSValue valueWithRect:finalShadowRect] forKey:NSViewAnimationEndFrameKey];
+
+ NSArray *animationInfo = [[NSArray alloc] initWithObjects:frameViewAnimationInfo, shadowAnimationInfo, nil];
+ [frameViewAnimationInfo release];
+ [shadowAnimationInfo release];
+
+ NSViewAnimation *slideAnimation = [[NSViewAnimation alloc] initWithViewAnimations:animationInfo]; // released in animationDidEnd
+ [animationInfo release];
+
+ [slideAnimation setAnimationBlockingMode:NSAnimationBlocking];
+ [slideAnimation setDelegate:self];
+
+ _attachedToInspectedWebView = YES;
+
+ [[_inspectedWebView window] display]; // display once to make sure we start in a good state
+ [slideAnimation startAnimation];
+ } else {
+ _attachedToInspectedWebView = NO;
+
+ NSView *contentView = [[self window] contentView];
+ [_webView setFrame:[contentView frame]];
+ [_webView setAutoresizingMask:(NSViewWidthSizable | NSViewHeightSizable)];
+ [_webView removeFromSuperview];
+ [contentView addSubview:_webView];
+
+ [super showWindow:nil];
+ }
+}
+
+#pragma mark -
+
+- (void)attach
+{
+ if (_attachedToInspectedWebView)
+ return;
+
+ _shouldAttach = YES;
+
+ if (_visible) {
+ _movingWindows = YES;
+ [self close];
+ _movingWindows = NO;
+ }
+
+ [self showWindow:nil];
+}
+
+- (void)detach
+{
+ if (!_attachedToInspectedWebView)
+ return;
+
+ _shouldAttach = NO;
+
+ if (_visible) {
+ _movingWindows = YES; // set back to NO in animationDidEnd
+ [self close];
+ } else {
+ [self showWindow:nil];
+ }
+}
+
+#pragma mark -
+
+- (void)highlightAndScrollToNode:(DOMNode *)node
+{
+ NSRect bounds = [node boundingBox];
+ if (!NSIsEmptyRect(bounds)) {
+ // FIXME: this needs to use the frame the node coordinates are in
+ NSRect visible = [[[[_inspectedWebView mainFrame] frameView] documentView] visibleRect];
+ BOOL needsScroll = !NSContainsRect(visible, bounds) && !NSContainsRect(bounds, visible);
+
+ // only scroll if the bounds isn't in the visible rect and dosen't contain the visible rect
+ if (needsScroll) {
+ // scroll to the parent element if we aren't focused on an element
+ DOMElement *element;
+ if ([node isKindOfClass:[DOMElement class]])
+ element = (DOMElement *)node;
+ else
+ element = (DOMElement *)[node parentNode];
+ [element scrollIntoViewIfNeeded:YES];
+
+ // give time for the scroll to happen
+ [self performSelector:@selector(highlightNode:) withObject:node afterDelay:0.25];
+ } else
+ [self highlightNode:node];
+ }
+}
+
+- (void)highlightNode:(DOMNode *)node
+{
+ // The scrollview's content view stays around between page navigations, so target it
+ NSView *view = [[[[[_inspectedWebView mainFrame] frameView] documentView] enclosingScrollView] contentView];
+ if (![view window])
+ return; // skip the highlight if we have no window (e.g. hidden tab)
+
+ if (!_currentHighlight) {
+ _currentHighlight = [[WebNodeHighlight alloc] initWithTargetView:view];
+ [_currentHighlight setDelegate:self];
+ [_currentHighlight attachHighlight];
+ }
+
+ [_currentHighlight show];
+
+ [_currentHighlight setHighlightedNode:node];
+
+ // FIXME: this is a hack until we hook up a didDraw and didScroll call in WebHTMLView
+ [[_currentHighlight highlightView] setNeedsDisplay:YES];
+}
+
+- (void)hideHighlight
+{
+ if (!_currentHighlight)
+ return;
+ [_currentHighlight hide];
+ [_currentHighlight setHighlightedNode:nil];
+}
+
+#pragma mark -
+#pragma mark Animation delegate
+
+- (void)animationDidEnd:(NSAnimation*)animation
+{
+ [animation release];
+
+ [_shadowView removeFromSuperview];
+
+ if (_movingWindows) {
+ _movingWindows = NO;
+ [self showWindow:nil];
+ }
+}
+
+#pragma mark -
+#pragma mark UI delegate
+
+- (unsigned)webView:(WebView *)sender dragDestinationActionMaskForDraggingInfo:(id <NSDraggingInfo>)draggingInfo
+{
+ return WebDragDestinationActionNone;
+}
+
+#pragma mark -
+
+// These methods can be used by UI elements such as menu items and toolbar buttons when the inspector is the key window.
+
+// This method is really only implemented to keep any UI elements enabled.
+- (void)showWebInspector:(id)sender
+{
+ [_inspectedWebView page]->inspectorController()->show();
+}
+
+- (void)showErrorConsole:(id)sender
+{
+ [_inspectedWebView page]->inspectorController()->showConsole();
+}
+
+- (void)showNetworkTimeline:(id)sender
+{
+ [_inspectedWebView page]->inspectorController()->showTimeline();
+}
+
+@end
diff --git a/WebKit/mac/WebCoreSupport/WebJavaScriptTextInputPanel.h b/WebKit/mac/WebCoreSupport/WebJavaScriptTextInputPanel.h
new file mode 100644
index 0000000..1dfd2e4
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebJavaScriptTextInputPanel.h
@@ -0,0 +1,43 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@interface WebJavaScriptTextInputPanel : NSWindowController
+{
+ IBOutlet NSTextField *prompt;
+ IBOutlet NSTextField *textInput;
+}
+
+- (id)initWithPrompt:(NSString *)prompt text:(NSString *)text;
+- (NSString *)text;
+
+- (IBAction)pressedCancel:(id)sender;
+- (IBAction)pressedOK:(id)sender;
+
+@end
diff --git a/WebKit/mac/WebCoreSupport/WebJavaScriptTextInputPanel.m b/WebKit/mac/WebCoreSupport/WebJavaScriptTextInputPanel.m
new file mode 100644
index 0000000..573dc84
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebJavaScriptTextInputPanel.m
@@ -0,0 +1,71 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebJavaScriptTextInputPanel.h"
+
+#import <JavaScriptCore/Assertions.h>
+
+#import <WebKit/WebNSControlExtras.h>
+#import <WebKit/WebNSWindowExtras.h>
+
+@implementation WebJavaScriptTextInputPanel
+
+- (id)initWithPrompt:(NSString *)p text:(NSString *)t
+{
+ [self initWithWindowNibName:@"WebJavaScriptTextInputPanel"];
+ NSWindow *window = [self window];
+
+ // This must be done after the call to [self window], because
+ // until then, prompt and textInput will be nil.
+ ASSERT(prompt);
+ ASSERT(textInput);
+ [prompt setStringValue:p];
+ [textInput setStringValue:t];
+
+ [prompt sizeToFitAndAdjustWindowHeight];
+ [window centerOverMainWindow];
+
+ return self;
+}
+
+- (NSString *)text
+{
+ return [textInput stringValue];
+}
+
+- (IBAction)pressedCancel:(id)sender
+{
+ [NSApp stopModalWithCode:NO];
+}
+
+- (IBAction)pressedOK:(id)sender
+{
+ [NSApp stopModalWithCode:YES];
+}
+
+@end
diff --git a/WebKit/mac/WebCoreSupport/WebKeyGenerator.h b/WebKit/mac/WebCoreSupport/WebKeyGenerator.h
new file mode 100644
index 0000000..ed2ff77
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebKeyGenerator.h
@@ -0,0 +1,47 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+typedef enum {
+ WebCertificateParseResultSucceeded = 0,
+ WebCertificateParseResultFailed = 1,
+ WebCertificateParseResultPKCS7 = 2,
+} WebCertificateParseResult;
+
+#ifdef __OBJC__
+
+#import <WebCore/WebCoreKeyGenerator.h>
+
+@interface WebKeyGenerator : WebCoreKeyGenerator
+{
+ NSArray *strengthMenuItemTitles;
+}
++ (void)createSharedGenerator;
+- (WebCertificateParseResult)addCertificatesToKeychainFromData:(NSData *)data;
+@end
+
+#endif
diff --git a/WebKit/mac/WebCoreSupport/WebKeyGenerator.m b/WebKit/mac/WebCoreSupport/WebKeyGenerator.m
new file mode 100644
index 0000000..782a6f4
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebKeyGenerator.m
@@ -0,0 +1,89 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebKeyGenerator.h>
+
+#import <JavaScriptCore/Assertions.h>
+#import <WebKit/WebLocalizableStrings.h>
+#import <WebKitSystemInterface.h>
+
+@implementation WebKeyGenerator
+
++ (void)createSharedGenerator
+{
+ if (![self sharedGenerator]) {
+ [[[self alloc] init] release];
+ }
+ ASSERT([[self sharedGenerator] isKindOfClass:self]);
+}
+
+- (void)dealloc
+{
+ [strengthMenuItemTitles release];
+ [super dealloc];
+}
+
+- (NSArray *)strengthMenuItemTitles
+{
+ if (!strengthMenuItemTitles) {
+ strengthMenuItemTitles = [[NSArray alloc] initWithObjects:
+ UI_STRING("2048 (High Grade)", "Menu item title for KEYGEN pop-up menu"),
+ UI_STRING("1024 (Medium Grade)", "Menu item title for KEYGEN pop-up menu"),
+ UI_STRING("512 (Low Grade)", "Menu item title for KEYGEN pop-up menu"), nil];
+ }
+ return strengthMenuItemTitles;
+}
+
+- (NSString *)signedPublicKeyAndChallengeStringWithStrengthIndex:(unsigned)index challenge:(NSString *)challenge pageURL:(NSURL *)pageURL
+{
+ // This switch statement must always be synced with the UI strings returned by strengthMenuItemTitles.
+ UInt32 keySize;
+ switch (index) {
+ case 0:
+ keySize = 2048;
+ break;
+ case 1:
+ keySize = 1024;
+ break;
+ case 2:
+ keySize = 512;
+ break;
+ default:
+ return nil;
+ }
+
+ NSString *keyDescription = [NSString stringWithFormat:UI_STRING("Key from %@", "name of keychain key generated by the KEYGEN tag"), [pageURL host]];
+ return [(NSString *)WKSignedPublicKeyAndChallengeString(keySize, (CFStringRef)challenge, (CFStringRef)keyDescription) autorelease];
+}
+
+- (WebCertificateParseResult)addCertificatesToKeychainFromData:(NSData *)data
+{
+ return WKAddCertificatesToKeychainFromData([data bytes], [data length]);
+}
+
+@end
diff --git a/WebKit/mac/WebCoreSupport/WebNetscapePlugInStreamLoaderClient.h b/WebKit/mac/WebCoreSupport/WebNetscapePlugInStreamLoaderClient.h
new file mode 100644
index 0000000..3f74097
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebNetscapePlugInStreamLoaderClient.h
@@ -0,0 +1,50 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebPlugInStreamLoaderDelegate.h>
+#import <WebCore/NetscapePlugInStreamLoader.h>
+#import <wtf/RetainPtr.h>
+
+namespace WebCore {
+ class NetscapePlugInStreamLoader;
+ class ResourceResponse;
+};
+
+typedef id <WebPlugInStreamLoaderDelegate> PlugInStreamLoaderDelegate;
+
+class WebNetscapePlugInStreamLoaderClient : public WebCore::NetscapePlugInStreamLoaderClient {
+public:
+ WebNetscapePlugInStreamLoaderClient(PlugInStreamLoaderDelegate delegate) : m_stream(delegate) { }
+ virtual void didReceiveResponse(WebCore::NetscapePlugInStreamLoader*, const WebCore::ResourceResponse&);
+ virtual void didReceiveData(WebCore::NetscapePlugInStreamLoader*, const char*, int);
+ virtual void didFail(WebCore::NetscapePlugInStreamLoader*, const WebCore::ResourceError&);
+ virtual void didFinishLoading(WebCore::NetscapePlugInStreamLoader*);
+
+private:
+ RetainPtr<PlugInStreamLoaderDelegate> m_stream;
+};
diff --git a/WebKit/mac/WebCoreSupport/WebNetscapePlugInStreamLoaderClient.mm b/WebKit/mac/WebCoreSupport/WebNetscapePlugInStreamLoaderClient.mm
new file mode 100644
index 0000000..fcb3fbe
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebNetscapePlugInStreamLoaderClient.mm
@@ -0,0 +1,57 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebNetscapePlugInStreamLoaderClient.h>
+#import <WebCore/NetscapePlugInStreamLoader.h>
+#import <WebCore/ResourceResponse.h>
+
+using namespace WebCore;
+
+void WebNetscapePlugInStreamLoaderClient::didReceiveResponse(NetscapePlugInStreamLoader*, const ResourceResponse& theResponse)
+{
+ [m_stream.get() startStreamWithResponse:theResponse.nsURLResponse()];
+}
+
+void WebNetscapePlugInStreamLoaderClient::didReceiveData(NetscapePlugInStreamLoader*, const char* data, int length)
+{
+ NSData *nsData = [[NSData alloc] initWithBytesNoCopy:(void*)data length:length freeWhenDone:NO];
+ [m_stream.get() receivedData:nsData];
+ [nsData release];
+}
+
+void WebNetscapePlugInStreamLoaderClient::didFail(NetscapePlugInStreamLoader*, const ResourceError& error)
+{
+ [m_stream.get() destroyStreamWithError:error];
+ m_stream = 0;
+}
+
+void WebNetscapePlugInStreamLoaderClient::didFinishLoading(NetscapePlugInStreamLoader*)
+{
+ [m_stream.get() finishedLoading];
+ m_stream = 0;
+}
diff --git a/WebKit/mac/WebCoreSupport/WebPasteboardHelper.h b/WebKit/mac/WebCoreSupport/WebPasteboardHelper.h
new file mode 100644
index 0000000..94ff676
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebPasteboardHelper.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef WebPasteboardHelper_h
+#define WebPasteboardHelper_h
+
+#import <WebCore/PasteboardHelper.h>
+
+@class WebHTMLView;
+
+class WebPasteboardHelper : public WebCore::PasteboardHelper
+{
+public:
+ WebPasteboardHelper(WebHTMLView* view) : m_view(view) {}
+ virtual WebCore::String urlFromPasteboard(const NSPasteboard*, WebCore::String* title) const;
+ virtual WebCore::String plainTextFromPasteboard(const NSPasteboard*) const;
+ virtual DOMDocumentFragment* fragmentFromPasteboard(const NSPasteboard*) const;
+ virtual NSArray* insertablePasteboardTypes() const;
+ private:
+ WebHTMLView* m_view;
+};
+
+#endif
diff --git a/WebKit/mac/WebCoreSupport/WebPasteboardHelper.mm b/WebKit/mac/WebCoreSupport/WebPasteboardHelper.mm
new file mode 100644
index 0000000..2da6654
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebPasteboardHelper.mm
@@ -0,0 +1,99 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
+ * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR
+ * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
+ * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
+ * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY
+ * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebArchive.h"
+#import "WebHTMLViewInternal.h"
+#import "WebNSPasteboardExtras.h"
+#import "WebNSURLExtras.h"
+#import "WebPasteboardHelper.h"
+
+#import <WebCore/DOMDocument.h>
+#import <WebCore/DOMDocumentFragment.h>
+#import <WebCore/PlatformString.h>
+#import <wtf/RetainPtr.h>
+
+using namespace WebCore;
+
+String WebPasteboardHelper::urlFromPasteboard(const NSPasteboard* pasteboard, String* title) const
+{
+ NSURL *URL = [pasteboard _web_bestURL];
+ if (title) {
+ if (NSString *URLTitleString = [pasteboard stringForType:WebURLNamePboardType])
+ *title = URLTitleString;
+ }
+
+ return [URL _web_originalDataAsString];
+}
+
+String WebPasteboardHelper::plainTextFromPasteboard(const NSPasteboard *pasteboard) const
+{
+ NSArray *types = [pasteboard types];
+
+ if ([types containsObject:NSStringPboardType])
+ return [pasteboard stringForType:NSStringPboardType];
+
+ NSAttributedString *attributedString = nil;
+ NSString *string;
+
+ if ([types containsObject:NSRTFDPboardType])
+ attributedString = [[NSAttributedString alloc] initWithRTFD:[pasteboard dataForType:NSRTFDPboardType] documentAttributes:nil];
+ if (!attributedString && [types containsObject:NSRTFPboardType])
+ attributedString = [[NSAttributedString alloc] initWithRTF:[pasteboard dataForType:NSRTFPboardType] documentAttributes:nil];
+ if (attributedString) {
+ string = [[attributedString string] copy];
+ [attributedString release];
+ return [string autorelease];
+ }
+
+ if ([types containsObject:NSFilenamesPboardType]) {
+ string = [[pasteboard propertyListForType:NSFilenamesPboardType] componentsJoinedByString:@"\n"];
+ if (string)
+ return string;
+ }
+
+ NSURL *URL;
+
+ if ((URL = [NSURL URLFromPasteboard:pasteboard])) {
+ string = [URL _web_userVisibleString];
+ if ([string length] > 0)
+ return string;
+ }
+
+ return String();
+}
+
+DOMDocumentFragment *WebPasteboardHelper::fragmentFromPasteboard(const NSPasteboard *pasteboard) const
+{
+ return [m_view _documentFragmentFromPasteboard:pasteboard];
+}
+
+NSArray *WebPasteboardHelper::insertablePasteboardTypes() const
+{
+ static RetainPtr<NSArray> types = [[NSArray alloc] initWithObjects:WebArchivePboardType, NSHTMLPboardType,
+ NSFilenamesPboardType, NSTIFFPboardType, NSPICTPboardType, NSURLPboardType,
+ NSRTFDPboardType, NSRTFPboardType, NSStringPboardType, NSColorPboardType, nil];
+
+ return types.get();
+}
diff --git a/WebKit/mac/WebCoreSupport/WebSystemInterface.h b/WebKit/mac/WebCoreSupport/WebSystemInterface.h
new file mode 100644
index 0000000..6e20279
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebSystemInterface.h
@@ -0,0 +1,37 @@
+/*
+ * Copyright 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifdef __cplusplus
+extern "C" {
+#endif
+
+void InitWebCoreSystemInterface(void);
+
+#ifdef __cplusplus
+}
+#endif
diff --git a/WebKit/mac/WebCoreSupport/WebSystemInterface.m b/WebKit/mac/WebCoreSupport/WebSystemInterface.m
new file mode 100644
index 0000000..2e8376c
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebSystemInterface.m
@@ -0,0 +1,99 @@
+/*
+ * Copyright 2006, 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebSystemInterface.h"
+
+#import <WebCore/WebCoreSystemInterface.h>
+#import <WebKitSystemInterface.h>
+
+#define INIT(function) wk##function = WK##function
+
+void InitWebCoreSystemInterface(void)
+{
+ static bool didInit;
+ if (didInit)
+ return;
+
+ INIT(CGContextGetShouldSmoothFonts);
+ INIT(ClearGlyphVector);
+ INIT(ConvertCharToGlyphs);
+ INIT(CreateCustomCFReadStream);
+ INIT(CreateNSURLConnectionDelegateProxy);
+ INIT(DrawCapsLockIndicator);
+ INIT(DrawBezeledTextArea);
+ INIT(DrawBezeledTextFieldCell);
+ INIT(DrawFocusRing);
+ INIT(DrawMediaFullscreenButton);
+ INIT(DrawMediaMuteButton);
+ INIT(DrawMediaPauseButton);
+ INIT(DrawMediaPlayButton);
+ INIT(DrawMediaSeekBackButton);
+ INIT(DrawMediaSeekForwardButton);
+ INIT(DrawMediaSliderTrack);
+ INIT(DrawMediaSliderThumb);
+ INIT(DrawMediaUnMuteButton);
+ INIT(DrawTextFieldCellFocusRing);
+ INIT(FontSmoothingModeIsLCD);
+ INIT(GetATSStyleGroup);
+ INIT(GetCGFontFromNSFont);
+ INIT(GetExtensionsForMIMEType);
+ INIT(GetFontInLanguageForCharacter);
+ INIT(GetFontInLanguageForRange);
+ INIT(GetGlyphTransformedAdvances);
+ INIT(GetGlyphVectorFirstRecord);
+ INIT(GetGlyphVectorNumGlyphs);
+ INIT(GetGlyphVectorRecordSize);
+ INIT(GetMIMETypeForExtension);
+ INIT(GetNSFontATSUFontId);
+ INIT(GetNSURLResponseLastModifiedDate);
+ INIT(GetPreferredExtensionForMIMEType);
+ INIT(GetWheelEventDeltas);
+ INIT(InitializeGlyphVector);
+ INIT(PopupMenu);
+ INIT(ReleaseStyleGroup);
+ INIT(SetCGFontRenderingMode);
+ INIT(SetDragImage);
+ INIT(SetNSURLConnectionDefersCallbacks);
+ INIT(SetNSURLRequestShouldContentSniff);
+ INIT(SetPatternBaseCTM);
+ INIT(SetPatternPhaseInUserSpace);
+ INIT(SetUpFontCache);
+ INIT(SignalCFReadStreamEnd);
+ INIT(SignalCFReadStreamError);
+ INIT(SignalCFReadStreamHasBytes);
+ INIT(QTMovieDataRate);
+ INIT(QTMovieMaxTimeLoaded);
+ INIT(QTMovieViewSetDrawSynchronously);
+
+#ifdef BUILDING_ON_TIGER
+ INIT(GetFontMetrics);
+ INIT(SupportsMultipartXMixedReplace);
+#endif
+
+ didInit = true;
+}
diff --git a/WebKit/mac/WebCoreSupport/WebViewFactory.h b/WebKit/mac/WebCoreSupport/WebViewFactory.h
new file mode 100644
index 0000000..4030a10
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebViewFactory.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/WebCoreViewFactory.h>
+
+@interface WebViewFactory : WebCoreViewFactory <WebCoreViewFactory>
+
++ (void)createSharedFactory;
+
+@end
diff --git a/WebKit/mac/WebCoreSupport/WebViewFactory.mm b/WebKit/mac/WebCoreSupport/WebViewFactory.mm
new file mode 100644
index 0000000..c524b4b
--- /dev/null
+++ b/WebKit/mac/WebCoreSupport/WebViewFactory.mm
@@ -0,0 +1,487 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebViewFactory.h>
+
+#import <JavaScriptCore/Assertions.h>
+#import <WebKit/WebFrameBridge.h>
+#import <WebKit/WebFrameInternal.h>
+#import <WebKit/WebViewInternal.h>
+#import <WebKit/WebHTMLViewInternal.h>
+#import <WebKit/WebLocalizableStrings.h>
+#import <WebKit/WebNSUserDefaultsExtras.h>
+#import <WebKit/WebNSObjectExtras.h>
+#import <WebKit/WebNSViewExtras.h>
+#import <WebKit/WebPluginDatabase.h>
+#import <WebKitSystemInterface.h>
+
+@interface NSMenu (WebViewFactoryAdditions)
+- (NSMenuItem *)addItemWithTitle:(NSString *)title action:(SEL)action tag:(int)tag;
+@end
+
+@implementation NSMenu (WebViewFactoryAdditions)
+
+- (NSMenuItem *)addItemWithTitle:(NSString *)title action:(SEL)action tag:(int)tag
+{
+ NSMenuItem *item = [[[NSMenuItem alloc] initWithTitle:title action:action keyEquivalent:@""] autorelease];
+ [item setTag:tag];
+ [self addItem:item];
+ return item;
+}
+
+@end
+
+@implementation WebViewFactory
+
++ (void)createSharedFactory
+{
+ if (![self sharedFactory]) {
+ [[[self alloc] init] release];
+ }
+ ASSERT([[self sharedFactory] isKindOfClass:self]);
+}
+
+- (NSArray *)pluginsInfo
+{
+ return [[WebPluginDatabase sharedDatabase] plugins];
+}
+
+- (NSString *)pluginNameForMIMEType:(NSString *)MIMEType
+{
+ return [[[WebPluginDatabase sharedDatabase] pluginForMIMEType:MIMEType] name];
+}
+
+- (void)refreshPlugins:(BOOL)reloadPages
+{
+ [[WebPluginDatabase sharedDatabase] refresh];
+ if (reloadPages) {
+ [WebView _makeAllWebViewsPerformSelector:@selector(_reloadForPluginChanges)];
+ }
+}
+
+- (BOOL)pluginSupportsMIMEType:(NSString *)MIMEType
+{
+ return [[WebPluginDatabase sharedDatabase] pluginForMIMEType:MIMEType] != nil;
+}
+
+- (WebCoreFrameBridge *)bridgeForView:(NSView *)v
+{
+ NSView *aView = [v superview];
+
+ while (aView) {
+ if ([aView isKindOfClass:[WebHTMLView class]]) {
+ return [[[(WebHTMLView *)aView _frame] _dataSource] _bridge];
+ }
+ aView = [aView superview];
+ }
+ return nil;
+}
+
+- (NSString *)inputElementAltText
+{
+ return UI_STRING_KEY("Submit", "Submit (input element)", "alt text for <input> elements with no alt, title, or value");
+}
+
+- (NSString *)resetButtonDefaultLabel
+{
+ return UI_STRING("Reset", "default label for Reset buttons in forms on web pages");
+}
+
+- (NSString *)searchableIndexIntroduction
+{
+ return UI_STRING("This is a searchable index. Enter search keywords: ",
+ "text that appears at the start of nearly-obsolete web pages in the form of a 'searchable index'");
+}
+
+- (NSString *)submitButtonDefaultLabel
+{
+ return UI_STRING("Submit", "default label for Submit buttons in forms on web pages");
+}
+
+- (NSString *)fileButtonChooseFileLabel
+{
+ return UI_STRING("Choose File", "title for file button used in HTML forms");
+}
+
+- (NSString *)fileButtonNoFileSelectedLabel
+{
+ return UI_STRING("no file selected", "text to display in file button used in HTML forms when no file is selected");
+}
+
+- (NSString *)copyImageUnknownFileLabel
+{
+ return UI_STRING("unknown", "Unknown filename");
+}
+
+- (NSString *)searchMenuNoRecentSearchesText
+{
+ return UI_STRING("No recent searches", "Label for only item in menu that appears when clicking on the search field image, when no searches have been performed");
+}
+
+- (NSString *)searchMenuRecentSearchesText
+{
+ return UI_STRING("Recent Searches", "label for first item in the menu that appears when clicking on the search field image, used as embedded menu title");
+}
+
+- (NSString *)searchMenuClearRecentSearchesText
+{
+ return UI_STRING("Clear Recent Searches", "menu item in Recent Searches menu that empties menu's contents");
+}
+
+- (NSString *)defaultLanguageCode
+{
+ return [NSUserDefaults _webkit_preferredLanguageCode];
+}
+
+- (NSString *)contextMenuItemTagOpenLinkInNewWindow
+{
+ return UI_STRING("Open Link in New Window", "Open in New Window context menu item");
+}
+
+- (NSString *)contextMenuItemTagDownloadLinkToDisk
+{
+ return UI_STRING("Download Linked File", "Download Linked File context menu item");
+}
+
+- (NSString *)contextMenuItemTagCopyLinkToClipboard
+{
+ return UI_STRING("Copy Link", "Copy Link context menu item");
+}
+
+- (NSString *)contextMenuItemTagOpenImageInNewWindow
+{
+ return UI_STRING("Open Image in New Window", "Open Image in New Window context menu item");
+}
+
+- (NSString *)contextMenuItemTagDownloadImageToDisk
+{
+ return UI_STRING("Download Image", "Download Image context menu item");
+}
+
+- (NSString *)contextMenuItemTagCopyImageToClipboard
+{
+ return UI_STRING("Copy Image", "Copy Image context menu item");
+}
+
+- (NSString *)contextMenuItemTagOpenFrameInNewWindow
+{
+ return UI_STRING("Open Frame in New Window", "Open Frame in New Window context menu item");
+}
+
+- (NSString *)contextMenuItemTagCopy
+{
+ return UI_STRING("Copy", "Copy context menu item");
+}
+
+- (NSString *)contextMenuItemTagGoBack
+{
+ return UI_STRING("Back", "Back context menu item");
+}
+
+- (NSString *)contextMenuItemTagGoForward
+{
+ return UI_STRING("Forward", "Forward context menu item");
+}
+
+- (NSString *)contextMenuItemTagStop
+{
+ return UI_STRING("Stop", "Stop context menu item");
+}
+
+- (NSString *)contextMenuItemTagReload
+{
+ return UI_STRING("Reload", "Reload context menu item");
+}
+
+- (NSString *)contextMenuItemTagCut
+{
+ return UI_STRING("Cut", "Cut context menu item");
+}
+
+- (NSString *)contextMenuItemTagPaste
+{
+ return UI_STRING("Paste", "Paste context menu item");
+}
+
+- (NSString *)contextMenuItemTagNoGuessesFound
+{
+ return UI_STRING("No Guesses Found", "No Guesses Found context menu item");
+}
+
+- (NSString *)contextMenuItemTagIgnoreSpelling
+{
+ return UI_STRING("Ignore Spelling", "Ignore Spelling context menu item");
+}
+
+- (NSString *)contextMenuItemTagLearnSpelling
+{
+ return UI_STRING("Learn Spelling", "Learn Spelling context menu item");
+}
+
+- (NSString *)contextMenuItemTagSearchInSpotlight
+{
+ return UI_STRING("Search in Spotlight", "Search in Spotlight context menu item");
+}
+
+- (NSString *)contextMenuItemTagSearchWeb
+{
+ return UI_STRING("Search in Google", "Search in Google context menu item");
+}
+
+- (NSString *)contextMenuItemTagLookUpInDictionary
+{
+ return UI_STRING("Look Up in Dictionary", "Look Up in Dictionary context menu item");
+}
+
+- (NSString *)contextMenuItemTagOpenLink
+{
+ return UI_STRING("Open Link", "Open Link context menu item");
+}
+
+- (NSString *)contextMenuItemTagIgnoreGrammar
+{
+ return UI_STRING("Ignore Grammar", "Ignore Grammar context menu item");
+}
+
+- (NSString *)contextMenuItemTagSpellingMenu
+{
+#ifndef BUILDING_ON_TIGER
+ return UI_STRING("Spelling and Grammar", "Spelling and Grammar context sub-menu item");
+#else
+ return UI_STRING("Spelling", "Spelling context sub-menu item");
+#endif
+}
+
+- (NSString *)contextMenuItemTagShowSpellingPanel:(bool)show
+{
+#ifndef BUILDING_ON_TIGER
+ if (show)
+ return UI_STRING("Show Spelling and Grammar", "menu item title");
+ return UI_STRING("Hide Spelling and Grammar", "menu item title");
+#else
+ return UI_STRING("Spelling...", "menu item title");
+#endif
+}
+
+- (NSString *)contextMenuItemTagCheckSpelling
+{
+#ifndef BUILDING_ON_TIGER
+ return UI_STRING("Check Document Now", "Check spelling context menu item");
+#else
+ return UI_STRING("Check Spelling", "Check spelling context menu item");
+#endif
+}
+
+- (NSString *)contextMenuItemTagCheckSpellingWhileTyping
+{
+#ifndef BUILDING_ON_TIGER
+ return UI_STRING("Check Spelling While Typing", "Check spelling while typing context menu item");
+#else
+ return UI_STRING("Check Spelling as You Type", "Check spelling while typing context menu item");
+#endif
+}
+
+- (NSString *)contextMenuItemTagCheckGrammarWithSpelling
+{
+ return UI_STRING("Check Grammar With Spelling", "Check grammar with spelling context menu item");
+}
+
+- (NSString *)contextMenuItemTagFontMenu
+{
+ return UI_STRING("Font", "Font context sub-menu item");
+}
+
+- (NSString *)contextMenuItemTagShowFonts
+{
+ return UI_STRING("Show Fonts", "Show fonts context menu item");
+}
+
+- (NSString *)contextMenuItemTagBold
+{
+ return UI_STRING("Bold", "Bold context menu item");
+}
+
+- (NSString *)contextMenuItemTagItalic
+{
+ return UI_STRING("Italic", "Italic context menu item");
+}
+
+- (NSString *)contextMenuItemTagUnderline
+{
+ return UI_STRING("Underline", "Underline context menu item");
+}
+
+- (NSString *)contextMenuItemTagOutline
+{
+ return UI_STRING("Outline", "Outline context menu item");
+}
+
+- (NSString *)contextMenuItemTagStyles
+{
+ return UI_STRING("Styles...", "Styles context menu item");
+}
+
+- (NSString *)contextMenuItemTagShowColors
+{
+ return UI_STRING("Show colors", "Show colors context menu item");
+}
+
+- (NSString *)contextMenuItemTagSpeechMenu
+{
+ return UI_STRING("Speech", "Speech context sub-menu item");
+}
+
+- (NSString *)contextMenuItemTagStartSpeaking
+{
+ return UI_STRING("Start Speaking", "Start speaking context menu item");
+}
+
+- (NSString *)contextMenuItemTagStopSpeaking
+{
+ return UI_STRING("Stop Speaking", "Stop speaking context menu item");
+}
+
+- (NSString *)contextMenuItemTagWritingDirectionMenu
+{
+ return UI_STRING("Writing Direction", "Writing direction context sub-menu item");
+}
+
+- (NSString *)contextMenuItemTagDefaultDirection
+{
+ return UI_STRING("Default", "Default writing direction context menu item");
+}
+
+- (NSString *)contextMenuItemTagLeftToRight
+{
+ return UI_STRING("Left to Right", "Left to Right context menu item");
+}
+
+- (NSString *)contextMenuItemTagRightToLeft
+{
+ return UI_STRING("Right to Left", "Right to Left context menu item");
+}
+
+- (NSString *)contextMenuItemTagInspectElement
+{
+ return UI_STRING("Inspect Element", "Inspect Element context menu item");
+}
+
+- (BOOL)objectIsTextMarker:(id)object
+{
+ return object != nil && CFGetTypeID(object) == WKGetAXTextMarkerTypeID();
+}
+
+- (BOOL)objectIsTextMarkerRange:(id)object
+{
+ return object != nil && CFGetTypeID(object) == WKGetAXTextMarkerRangeTypeID();
+}
+
+- (WebCoreTextMarker *)textMarkerWithBytes:(const void *)bytes length:(size_t)length
+{
+ return WebCFAutorelease(WKCreateAXTextMarker(bytes, length));
+}
+
+- (BOOL)getBytes:(void *)bytes fromTextMarker:(WebCoreTextMarker *)textMarker length:(size_t)length
+{
+ return WKGetBytesFromAXTextMarker(textMarker, bytes, length);
+}
+
+- (WebCoreTextMarkerRange *)textMarkerRangeWithStart:(WebCoreTextMarker *)start end:(WebCoreTextMarker *)end
+{
+ ASSERT(start != nil);
+ ASSERT(end != nil);
+ ASSERT(CFGetTypeID(start) == WKGetAXTextMarkerTypeID());
+ ASSERT(CFGetTypeID(end) == WKGetAXTextMarkerTypeID());
+ return WebCFAutorelease(WKCreateAXTextMarkerRange(start, end));
+}
+
+- (WebCoreTextMarker *)startOfTextMarkerRange:(WebCoreTextMarkerRange *)range
+{
+ ASSERT(range != nil);
+ ASSERT(CFGetTypeID(range) == WKGetAXTextMarkerRangeTypeID());
+ return WebCFAutorelease(WKCopyAXTextMarkerRangeStart(range));
+}
+
+- (WebCoreTextMarker *)endOfTextMarkerRange:(WebCoreTextMarkerRange *)range
+{
+ ASSERT(range != nil);
+ ASSERT(CFGetTypeID(range) == WKGetAXTextMarkerRangeTypeID());
+ return WebCFAutorelease(WKCopyAXTextMarkerRangeEnd(range));
+}
+
+- (void)accessibilityHandleFocusChanged
+{
+ WKAccessibilityHandleFocusChanged();
+}
+
+- (AXUIElementRef)AXUIElementForElement:(id)element
+{
+ return WKCreateAXUIElementRef(element);
+}
+
+- (void)unregisterUniqueIdForUIElement:(id)element
+{
+ WKUnregisterUniqueIdForElement(element);
+}
+
+- (NSString *)AXWebAreaText
+{
+ return UI_STRING("web area", "accessibility role description for web area");
+}
+
+- (NSString *)AXLinkText
+{
+ return UI_STRING("link", "accessibility role description for link");
+}
+
+- (NSString *)AXListMarkerText
+{
+ return UI_STRING("list marker", "accessibility role description for list marker");
+}
+
+- (NSString *)AXImageMapText
+{
+ return UI_STRING("image map", "accessibility role description for image map");
+}
+
+- (NSString *)AXHeadingText
+{
+ return UI_STRING("heading", "accessibility role description for headings");
+}
+
+- (NSString *)unknownFileSizeText
+{
+ return UI_STRING("Unknown", "Unknown filesize FTP directory listing item");
+}
+
+- (NSString*)imageTitleForFilename:(NSString*)filename size:(NSSize)size
+{
+ return [NSString stringWithFormat:UI_STRING("%@ %.0f×%.0f pixels", "window title for a standalone image (uses multiplication symbol, not x)"), filename, size.width, size.height];
+}
+
+@end
diff --git a/WebKit/mac/WebInspector/WebInspector.h b/WebKit/mac/WebInspector/WebInspector.h
new file mode 100644
index 0000000..ba4911a
--- /dev/null
+++ b/WebKit/mac/WebInspector/WebInspector.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/NSObject.h>
+
+@class WebView;
+
+@interface WebInspector : NSObject
+{
+ WebView *_webView;
+}
+- (id)initWithWebView:(WebView *)webView;
+- (void)webViewClosed;
+- (void)show:(id)sender;
+- (void)showConsole:(id)sender;
+- (void)showTimeline:(id)sender;
+- (void)close:(id)sender;
+- (void)attach:(id)sender;
+- (void)detach:(id)sender;
+@end
diff --git a/WebKit/mac/WebInspector/WebInspector.mm b/WebKit/mac/WebInspector/WebInspector.mm
new file mode 100644
index 0000000..563f723
--- /dev/null
+++ b/WebKit/mac/WebInspector/WebInspector.mm
@@ -0,0 +1,139 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebInspector.h"
+#import "WebFrameInternal.h"
+#import "WebView.h"
+
+#include <WebCore/Document.h>
+#include <WebCore/Frame.h>
+#include <WebCore/InspectorController.h>
+#include <WebCore/Page.h>
+
+using namespace WebCore;
+
+@implementation WebInspector
+- (id)initWithWebView:(WebView *)webView
+{
+ if (!(self = [super init]))
+ return nil;
+ _webView = webView; // not retained to prevent a cycle
+ return self;
+}
+
+- (void)webViewClosed
+{
+ _webView = nil;
+}
+
+- (void)show:(id)sender
+{
+ if (Page* page = core(_webView))
+ page->inspectorController()->show();
+}
+
+- (void)showConsole:(id)sender
+{
+ if (Page* page = core(_webView))
+ page->inspectorController()->showConsole();
+}
+
+- (void)showTimeline:(id)sender
+{
+ if (Page* page = core(_webView))
+ page->inspectorController()->showTimeline();
+}
+
+- (void)close:(id)sender
+{
+ if (Page* page = core(_webView))
+ page->inspectorController()->close();
+}
+
+- (void)attach:(id)sender
+{
+ if (Page* page = core(_webView))
+ page->inspectorController()->attachWindow();
+}
+
+- (void)detach:(id)sender
+{
+ if (Page* page = core(_webView))
+ page->inspectorController()->detachWindow();
+}
+@end
+
+@implementation WebInspector (Obsolete)
++ (WebInspector *)webInspector
+{
+ // Safari 3.0 calls this method
+ static BOOL logged = NO;
+ if (!logged) {
+ NSLog(@"+[WebInspector webInspector]: this method is obsolete.");
+ logged = YES;
+ }
+
+ return [[[WebInspector alloc] init] autorelease];
+}
+
+- (void)setWebFrame:(WebFrame *)frame
+{
+ // Safari 3.0 calls this method
+ static BOOL logged = NO;
+ if (!logged) {
+ NSLog(@"-[WebInspector setWebFrame:]: this method is obsolete.");
+ logged = YES;
+ }
+
+ _webView = [frame webView];
+}
+
+- (NSWindow *)window
+{
+ // Shiira calls this internal method, return nil since we can't easily return the window
+ static BOOL logged = NO;
+ if (!logged) {
+ NSLog(@"-[WebInspector window]: this method is obsolete and now returns nil.");
+ logged = YES;
+ }
+
+ return nil;
+}
+
+- (void)showWindow:(id)sender
+{
+ // Safari 3.0 calls this method
+ static BOOL logged = NO;
+ if (!logged) {
+ NSLog(@"-[WebInspector showWindow:]: this method is obsolete.");
+ logged = YES;
+ }
+
+ [self show:sender];
+}
+@end
diff --git a/WebKit/mac/WebInspector/WebNodeHighlight.h b/WebKit/mac/WebInspector/WebNodeHighlight.h
new file mode 100644
index 0000000..b0c11bb
--- /dev/null
+++ b/WebKit/mac/WebInspector/WebNodeHighlight.h
@@ -0,0 +1,67 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+@class WebNodeHighlightView;
+@class DOMNode;
+
+@interface WebNodeHighlight : NSObject {
+ NSView *_targetView;
+ NSWindow *_highlightWindow;
+ WebNodeHighlightView *_highlightView;
+ NSAnimation *_fadeInAnimation;
+ DOMNode *_highlightNode;
+ id _delegate;
+}
+- (id)initWithTargetView:(NSView *)targetView;
+
+- (void)setDelegate:(id)delegate;
+- (id)delegate;
+
+- (void)attachHighlight;
+- (void)detachHighlight;
+
+- (void)show;
+- (void)hide;
+
+- (NSView *)targetView;
+- (WebNodeHighlightView *)highlightView;
+
+- (void)setHighlightedNode:(DOMNode *)node;
+- (DOMNode *)highlightedNode;
+
+// Controls whether mouse events are ignored (passed to underlying view). By default mouse events are ignored.
+- (BOOL)ignoresMouseEvents;
+- (void)setIgnoresMouseEvents:(BOOL)newValue;
+
+- (void)setHolesNeedUpdateInTargetViewRect:(NSRect)rect;
+@end
+
+@interface NSObject (WebNodeHighlightDelegate)
+- (void)didAttachWebNodeHighlight:(WebNodeHighlight *)highlight;
+- (void)willDetachWebNodeHighlight:(WebNodeHighlight *)highlight;
+@end
diff --git a/WebKit/mac/WebInspector/WebNodeHighlight.m b/WebKit/mac/WebInspector/WebNodeHighlight.m
new file mode 100644
index 0000000..071f0cb
--- /dev/null
+++ b/WebKit/mac/WebInspector/WebNodeHighlight.m
@@ -0,0 +1,266 @@
+/*
+ * Copyright (C) 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNodeHighlight.h"
+#import "WebNodeHighlightView.h"
+#import "WebNSViewExtras.h"
+
+#import <JavaScriptCore/Assertions.h>
+
+#define FADE_ANIMATION_DURATION 0.2
+
+@interface WebNodeHighlightFadeInAnimation : NSAnimation
+@end
+
+@interface WebNodeHighlight (FileInternal)
+- (NSRect)_computeHighlightWindowFrame;
+- (void)_repositionHighlightWindow;
+- (void)_animateFadeIn:(WebNodeHighlightFadeInAnimation *)animation;
+@end
+
+@implementation WebNodeHighlightFadeInAnimation
+
+- (void)setCurrentProgress:(NSAnimationProgress)progress
+{
+ [super setCurrentProgress:progress];
+ [(WebNodeHighlight *)[self delegate] _animateFadeIn:self];
+}
+
+@end
+
+@implementation WebNodeHighlight
+
+- (id)initWithTargetView:(NSView *)targetView
+{
+ self = [super init];
+ if (!self)
+ return nil;
+
+ _targetView = [targetView retain];
+
+ int styleMask = NSBorderlessWindowMask;
+ NSRect contentRect = [NSWindow contentRectForFrameRect:[self _computeHighlightWindowFrame] styleMask:styleMask];
+ _highlightWindow = [[NSWindow alloc] initWithContentRect:contentRect styleMask:styleMask backing:NSBackingStoreBuffered defer:NO];
+ [_highlightWindow setBackgroundColor:[NSColor clearColor]];
+ [_highlightWindow setOpaque:NO];
+ [_highlightWindow setIgnoresMouseEvents:YES];
+ [_highlightWindow setReleasedWhenClosed:NO];
+
+ _highlightView = [[WebNodeHighlightView alloc] initWithWebNodeHighlight:self];
+ [_highlightView setFractionFadedIn:0.0];
+ [_highlightWindow setContentView:_highlightView];
+ [_highlightView release];
+
+ return self;
+}
+
+- (void)setHighlightedNode:(DOMNode *)node
+{
+ id old = _highlightNode;
+ _highlightNode = [node retain];
+ [old release];
+}
+
+- (DOMNode *)highlightedNode
+{
+ return _highlightNode;
+}
+
+- (void)dealloc
+{
+ // FIXME: Bad to do all this work in dealloc. What about under GC?
+
+ [self detachHighlight];
+
+ ASSERT(!_highlightWindow);
+ ASSERT(!_targetView);
+
+ [_fadeInAnimation setDelegate:nil];
+ [_fadeInAnimation stopAnimation];
+ [_fadeInAnimation release];
+
+ [_highlightNode release];
+
+ [super dealloc];
+}
+
+- (void)attachHighlight
+{
+ ASSERT(_targetView);
+ ASSERT([_targetView window]);
+ ASSERT(_highlightWindow);
+
+ // Disable screen updates so the highlight moves in sync with the view.
+ [[_targetView window] disableScreenUpdatesUntilFlush];
+ [[_targetView window] addChildWindow:_highlightWindow ordered:NSWindowAbove];
+
+ // Observe both frame-changed and bounds-changed notifications because either one could leave
+ // the highlight incorrectly positioned with respect to the target view. We need to do this for
+ // the entire superview hierarchy to handle scrolling, bars coming and going, etc.
+ // (without making concrete assumptions about the view hierarchy).
+ NSNotificationCenter *notificationCenter = [NSNotificationCenter defaultCenter];
+ for (NSView *v = _targetView; v; v = [v superview]) {
+ [notificationCenter addObserver:self selector:@selector(_repositionHighlightWindow) name:NSViewFrameDidChangeNotification object:v];
+ [notificationCenter addObserver:self selector:@selector(_repositionHighlightWindow) name:NSViewBoundsDidChangeNotification object:v];
+ }
+
+ if (_delegate && [_delegate respondsToSelector:@selector(didAttachWebNodeHighlight:)])
+ [_delegate didAttachWebNodeHighlight:self];
+}
+
+- (id)delegate
+{
+ return _delegate;
+}
+
+- (void)detachHighlight
+{
+ if (!_highlightWindow) {
+ ASSERT(!_targetView);
+ return;
+ }
+
+ if (_delegate && [_delegate respondsToSelector:@selector(willDetachWebNodeHighlight:)])
+ [_delegate willDetachWebNodeHighlight:self];
+
+ // FIXME: is this necessary while detaching? Should test.
+ [[_targetView window] disableScreenUpdatesUntilFlush];
+
+ NSNotificationCenter *notificationCenter = [NSNotificationCenter defaultCenter];
+ [notificationCenter removeObserver:self name:NSViewFrameDidChangeNotification object:nil];
+ [notificationCenter removeObserver:self name:NSViewBoundsDidChangeNotification object:nil];
+
+ [[_highlightWindow parentWindow] removeChildWindow:_highlightWindow];
+
+ [_highlightWindow release];
+ _highlightWindow = nil;
+
+ [_targetView release];
+ _targetView = nil;
+
+ // We didn't retain _highlightView, but we do need to tell it to forget about us, so it doesn't
+ // try to send our delegate messages after we've been dealloc'ed, e.g.
+ [_highlightView detachFromWebNodeHighlight];
+ _highlightView = nil;
+}
+
+- (void)show
+{
+ ASSERT(!_fadeInAnimation);
+ if (_fadeInAnimation || [_highlightView fractionFadedIn] == 1.0)
+ return;
+
+ _fadeInAnimation = [[WebNodeHighlightFadeInAnimation alloc] initWithDuration:FADE_ANIMATION_DURATION animationCurve:NSAnimationEaseInOut];
+ [_fadeInAnimation setAnimationBlockingMode:NSAnimationNonblocking];
+ [_fadeInAnimation setDelegate:self];
+ [_fadeInAnimation startAnimation];
+}
+
+- (void)hide
+{
+ [_highlightView setFractionFadedIn:0.0];
+}
+
+- (void)animationDidEnd:(NSAnimation *)animation
+{
+ ASSERT(animation == _fadeInAnimation);
+ [_fadeInAnimation release];
+ _fadeInAnimation = nil;
+}
+
+- (BOOL)ignoresMouseEvents
+{
+ ASSERT(_highlightWindow);
+ return [_highlightWindow ignoresMouseEvents];
+}
+
+- (WebNodeHighlightView *)highlightView
+{
+ return _highlightView;
+}
+
+- (void)setDelegate:(id)delegate
+{
+ // The delegate is not retained, as usual in Cocoa.
+ _delegate = delegate;
+}
+
+- (void)setHolesNeedUpdateInTargetViewRect:(NSRect)rect
+{
+ ASSERT(_targetView);
+
+ [_highlightView setHolesNeedUpdateInRect:[_targetView _web_convertRect:rect toView:_highlightView]];
+
+ // Redraw highlight view immediately so it updates in sync with the target view
+ // if we called disableScreenUpdatesUntilFlush on the target view earlier. This
+ // is especially visible when resizing the window.
+ [_highlightView displayIfNeeded];
+}
+
+- (void)setIgnoresMouseEvents:(BOOL)newValue
+{
+ ASSERT(_highlightWindow);
+ [_highlightWindow setIgnoresMouseEvents:newValue];
+}
+
+- (NSView *)targetView
+{
+ return _targetView;
+}
+
+@end
+
+@implementation WebNodeHighlight (FileInternal)
+
+- (NSRect)_computeHighlightWindowFrame
+{
+ ASSERT(_targetView);
+ ASSERT([_targetView window]);
+
+ NSRect highlightWindowFrame = [_targetView convertRect:[_targetView visibleRect] toView:nil];
+ highlightWindowFrame.origin = [[_targetView window] convertBaseToScreen:highlightWindowFrame.origin];
+
+ return highlightWindowFrame;
+}
+
+- (void)_repositionHighlightWindow
+{
+ ASSERT([_targetView window]);
+
+ // Disable screen updates so the highlight moves in sync with the view.
+ [[_targetView window] disableScreenUpdatesUntilFlush];
+
+ [_highlightWindow setFrame:[self _computeHighlightWindowFrame] display:YES];
+}
+
+- (void)_animateFadeIn:(WebNodeHighlightFadeInAnimation *)animation
+{
+ [_highlightView setFractionFadedIn:[animation currentValue]];
+}
+
+@end
diff --git a/WebKit/mac/WebInspector/WebNodeHighlightView.h b/WebKit/mac/WebInspector/WebNodeHighlightView.h
new file mode 100644
index 0000000..70d1a5a
--- /dev/null
+++ b/WebKit/mac/WebInspector/WebNodeHighlightView.h
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+@class WebNodeHighlight;
+
+@interface WebNodeHighlightView : NSView {
+ WebNodeHighlight *_webNodeHighlight;
+ float _fractionFadedIn;
+}
+- (id)initWithWebNodeHighlight:(WebNodeHighlight *)webNodeHighlight;
+
+- (WebNodeHighlight *)webNodeHighlight;
+- (void)detachFromWebNodeHighlight;
+
+// Value between 0.0 (completely faded out of view) and 1.0 (completely faded into view) that represents
+// the progress of the fading animation.
+- (float)fractionFadedIn;
+- (void)setFractionFadedIn:(float)alpha;
+
+- (void)setHolesNeedUpdateInRect:(NSRect)rect;
+@end
diff --git a/WebKit/mac/WebInspector/WebNodeHighlightView.m b/WebKit/mac/WebInspector/WebNodeHighlightView.m
new file mode 100644
index 0000000..cd5a7a7
--- /dev/null
+++ b/WebKit/mac/WebInspector/WebNodeHighlightView.m
@@ -0,0 +1,175 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebNodeHighlightView.h"
+#import "WebNodeHighlight.h"
+#import "WebNSViewExtras.h"
+
+#import <WebKit/DOMCore.h>
+#import <WebKit/DOMExtensions.h>
+
+#import <JavaScriptCore/Assertions.h>
+
+#define OVERLAY_MAX_ALPHA 0.7
+#define OVERLAY_WHITE_VALUE 0.1
+
+#define WHITE_FRAME_THICKNESS 1.0
+
+@interface WebNodeHighlightView (FileInternal)
+- (NSArray *)_holes;
+@end
+
+@implementation WebNodeHighlightView
+
+- (id)initWithWebNodeHighlight:(WebNodeHighlight *)webNodeHighlight
+{
+ self = [self initWithFrame:NSZeroRect];
+ if (!self)
+ return nil;
+
+ _webNodeHighlight = [webNodeHighlight retain];
+
+ return self;
+}
+
+- (void)dealloc
+{
+ [self detachFromWebNodeHighlight];
+ [super dealloc];
+}
+
+- (void)detachFromWebNodeHighlight
+{
+ [_webNodeHighlight release];
+ _webNodeHighlight = nil;
+}
+
+- (void)drawRect:(NSRect)rect
+{
+ [NSGraphicsContext saveGraphicsState];
+
+ // draw translucent gray fill, out of which we will cut holes
+ [[NSColor colorWithCalibratedWhite:OVERLAY_WHITE_VALUE alpha:(_fractionFadedIn * OVERLAY_MAX_ALPHA)] set];
+ NSRectFill(rect);
+
+ // determine set of holes
+ NSArray *holes = [self _holes];
+ int holeCount = [holes count];
+ int holeIndex;
+
+ // Draw white frames around holes in first pass, so they will be erased in
+ // places where holes overlap or abut.
+ [[NSColor colorWithCalibratedWhite:1.0 alpha:_fractionFadedIn] set];
+
+ // white frame is just outside of the hole that the delegate returned
+ for (holeIndex = 0; holeIndex < holeCount; ++holeIndex) {
+ NSRect hole = [[holes objectAtIndex:holeIndex] rectValue];
+ hole = NSInsetRect(hole, -WHITE_FRAME_THICKNESS, -WHITE_FRAME_THICKNESS);
+ NSRectFill(hole);
+ }
+
+ [[NSColor clearColor] set];
+
+ // Erase holes in second pass.
+ for (holeIndex = 0; holeIndex < holeCount; ++holeIndex)
+ NSRectFill([[holes objectAtIndex:holeIndex] rectValue]);
+
+ [NSGraphicsContext restoreGraphicsState];
+}
+
+- (WebNodeHighlight *)webNodeHighlight
+{
+ return _webNodeHighlight;
+}
+
+- (float)fractionFadedIn
+{
+ return _fractionFadedIn;
+}
+
+- (void)setFractionFadedIn:(float)fraction
+{
+ ASSERT_ARG(fraction, fraction >= 0.0 && fraction <= 1.0);
+
+ if (_fractionFadedIn == fraction)
+ return;
+
+ _fractionFadedIn = fraction;
+ [self setNeedsDisplay:YES];
+}
+
+- (void)setHolesNeedUpdateInRect:(NSRect)rect
+{
+ // Redisplay a slightly larger rect to account for white border around holes
+ rect = NSInsetRect(rect, -1 * WHITE_FRAME_THICKNESS,
+ -1 * WHITE_FRAME_THICKNESS);
+
+ [self setNeedsDisplayInRect:rect];
+}
+
+@end
+
+@implementation WebNodeHighlightView (FileInternal)
+
+- (NSArray *)_holes
+{
+ DOMNode *node = [_webNodeHighlight highlightedNode];
+
+ // FIXME: node view needs to be the correct frame document view, it isn't always the main frame
+ NSView *nodeView = [_webNodeHighlight targetView];
+
+ NSArray *lineBoxRects = nil;
+ if ([node isKindOfClass:[DOMElement class]]) {
+ DOMCSSStyleDeclaration *style = [[node ownerDocument] getComputedStyle:(DOMElement *)node pseudoElement:@""];
+ if ([[style getPropertyValue:@"display"] isEqualToString:@"inline"])
+ lineBoxRects = [node lineBoxRects];
+ } else if ([node isKindOfClass:[DOMText class]]) {
+#if ENABLE(SVG)
+ if (![[node parentNode] isKindOfClass:NSClassFromString(@"DOMSVGElement")])
+#endif
+ lineBoxRects = [node lineBoxRects];
+ }
+
+ if (![lineBoxRects count]) {
+ NSRect boundingBox = [nodeView _web_convertRect:[node boundingBox] toView:self];
+ return [NSArray arrayWithObject:[NSValue valueWithRect:boundingBox]];
+ }
+
+ NSMutableArray *rects = [[NSMutableArray alloc] initWithCapacity:[lineBoxRects count]];
+
+ unsigned lineBoxRectCount = [lineBoxRects count];
+ for (unsigned lineBoxRectIndex = 0; lineBoxRectIndex < lineBoxRectCount; ++lineBoxRectIndex) {
+ NSRect r = [[lineBoxRects objectAtIndex:lineBoxRectIndex] rectValue];
+ NSRect overlayViewRect = [nodeView _web_convertRect:r toView:self];
+ [rects addObject:[NSValue valueWithRect:overlayViewRect]];
+ }
+
+ return [rects autorelease];
+}
+
+@end
diff --git a/WebKit/mac/WebKit.exp b/WebKit/mac/WebKit.exp
new file mode 100644
index 0000000..df5e130
--- /dev/null
+++ b/WebKit/mac/WebKit.exp
@@ -0,0 +1,113 @@
+.objc_class_name_WebArchive
+.objc_class_name_WebBackForwardList
+.objc_class_name_WebBaseNetscapePluginView
+.objc_class_name_WebCache
+.objc_class_name_WebCoreScrollView
+.objc_class_name_WebCoreStatistics
+.objc_class_name_WebDataSource
+.objc_class_name_WebDatabaseManager
+.objc_class_name_WebDefaultPolicyDelegate
+.objc_class_name_WebDownload
+.objc_class_name_WebDynamicScrollBarsView
+.objc_class_name_WebFormDelegate
+.objc_class_name_WebFrame
+.objc_class_name_WebFrameView
+.objc_class_name_WebHTMLRepresentation
+.objc_class_name_WebHTMLView
+.objc_class_name_WebHistory
+.objc_class_name_WebHistoryItem
+.objc_class_name_WebIconDatabase
+.objc_class_name_WebInspector
+.objc_class_name_WebJavaScriptTextInputPanel
+.objc_class_name_WebKeyGenerator
+.objc_class_name_WebKitStatistics
+.objc_class_name_WebPanelAuthenticationHandler
+.objc_class_name_WebPluginDatabase
+.objc_class_name_WebPreferences
+.objc_class_name_WebRenderNode
+.objc_class_name_WebResource
+.objc_class_name_WebScriptCallFrame
+.objc_class_name_WebSecurityOrigin
+.objc_class_name_WebStringTruncator
+.objc_class_name_WebURLsWithTitles
+.objc_class_name_WebView
+_HIWebViewCreate
+_HIWebViewGetWebView
+_WebActionButtonKey
+_WebActionElementKey
+_WebActionModifierFlagsKey
+_WebActionNavigationTypeKey
+_WebActionOriginalURLKey
+_WebArchivePboardType
+_WebConvertNSImageToCGImageRef
+_WebDatabaseDidModifyDatabaseNotification
+_WebDatabaseDidModifyOriginNotification
+_WebDatabaseDirectoryDefaultsKey
+_WebDatabaseDisplayNameKey
+_WebDatabaseExpectedSizeKey
+_WebDatabaseIdentifierKey
+_WebDatabaseUsageKey
+_WebElementDOMNodeKey
+_WebElementFrameKey
+_WebElementImageAltStringKey
+_WebElementImageKey
+_WebElementImageRectKey
+_WebElementImageURLKey
+_WebElementIsSelectedKey
+_WebElementLinkIsLiveKey
+_WebElementLinkLabelKey
+_WebElementLinkTargetFrameKey
+_WebElementLinkTitleKey
+_WebElementLinkURLKey
+_WebHistoryAllItemsRemovedNotification
+_WebHistoryItemChangedNotification
+_WebHistoryItemsAddedNotification
+_WebHistoryItemsDiscardedWhileLoadingNotification
+_WebHistoryItemsKey
+_WebHistoryItemsRemovedNotification
+_WebHistoryLoadedNotification
+_WebHistorySavedNotification
+_WebIconDatabaseDidAddIconNotification
+_WebIconDatabaseDidRemoveAllIconsNotification
+_WebIconDatabaseDirectoryDefaultsKey
+_WebIconDatabaseImportDirectoryDefaultsKey
+_WebIconLargeSize
+_WebIconMediumSize
+_WebIconNotificationUserInfoURLKey
+_WebIconSmallSize
+_WebInitForCarbon
+_WebKitErrorDomain
+_WebKitErrorMIMETypeKey
+_WebKitErrorPlugInNameKey
+_WebKitErrorPlugInPageURLStringKey
+_WebLocalizedString
+_WebPlugInAttributesKey
+_WebPlugInBaseURLKey
+_WebPlugInContainerKey
+_WebPlugInContainingElementKey
+_WebPlugInModeKey
+_WebPlugInShouldLoadMainResourceKey
+_WebPluginWillPresentNativeUserInterfaceNotification
+_WebPreferencesChangedNotification
+_WebReportAssertionFailure
+_WebReportError
+_WebScriptDebugServerDidLoadNotification
+_WebScriptDebugServerProcessBundleIdentifierKey
+_WebScriptDebugServerProcessIdentifierKey
+_WebScriptDebugServerProcessNameKey
+_WebScriptDebugServerQueryNotification
+_WebScriptDebugServerQueryReplyNotification
+_WebScriptDebugServerWillUnloadNotification
+_WebScriptErrorDescriptionKey
+_WebScriptErrorDomain
+_WebScriptErrorLineNumberKey
+_WebURLNamePboardType
+_WebURLPboardType
+_WebViewDidBeginEditingNotification
+_WebViewDidChangeNotification
+_WebViewDidChangeSelectionNotification
+_WebViewDidChangeTypingStyleNotification
+_WebViewDidEndEditingNotification
+_WebViewProgressEstimateChangedNotification
+_WebViewProgressFinishedNotification
+_WebViewProgressStartedNotification
diff --git a/WebKit/mac/WebKit.order b/WebKit/mac/WebKit.order
new file mode 100644
index 0000000..6bb0178
--- /dev/null
+++ b/WebKit/mac/WebKit.order
@@ -0,0 +1,1899 @@
++[WebPreferences initialize]
+_contains
+_WebKitLinkedOnOrAfter
+_WebKitLinkTimeVersion
++[WebPreferences standardPreferences]
+-[WebPreferences initWithIdentifier:]
++[WebPreferences(WebInternal) _IBCreatorID]
++[WebPreferences(WebPrivate) _getInstanceForIdentifier:]
++[WebPreferences(WebPrivate) _setInstance:forIdentifier:]
+-[WebPreferences(WebPrivate) _postPreferencesChangesNotification]
+-[WebPreferences setAutosaves:]
++[WebIconDatabase delayDatabaseCleanup]
+-[NSString(WebKitExtras) _web_stringByAbbreviatingWithTildeInPath]
++[WebIconDatabase sharedIconDatabase]
+-[WebIconDatabase init]
+__Z13defaultClientv
+-[WebIconDatabase(WebInternal) _databaseDirectory]
+-[WebPreferences privateBrowsingEnabled]
+-[WebPreferences _boolValueForKey:]
+-[WebPreferences _integerValueForKey:]
+-[WebPreferences _valueForKey:]
++[WebView initialize]
++[WebView(WebPrivate) _registerViewClass:representationClass:forURLScheme:]
++[WebView(WebPrivate) _generatedMIMETypeForURLScheme:]
++[WebView registerViewClass:representationClass:forMIMEType:]
++[WebFrameView(WebInternal) _viewTypesAllowImageTypeOmission:]
++[WebHTMLView initialize]
++[WebHTMLView(WebPrivate) _insertablePasteboardTypes]
++[WebHTMLView(WebPrivate) _selectionPasteboardTypes]
++[WebHTMLView(WebPrivate) supportedNonImageMIMETypes]
++[WebHTMLRepresentation supportedNonImageMIMETypes]
+__Z11stringArrayRKN3WTF7HashSetIN7WebCore6StringENS1_10StringHashENS_10HashTraitsIS2_EEEE
++[WebPDFView supportedMIMETypes]
++[WebPDFRepresentation supportedMIMETypes]
++[WebPDFRepresentation postScriptMIMETypes]
++[WebDataSource(WebInternal) _repTypesAllowImageTypeOmission:]
++[WebView registerURLSchemeAsLocal:]
+-[WebIconDatabase retainIconForURL:]
+-[WebIconDatabase(WebInternal) _isEnabled]
+_WebLocalizedString
+-[WebView initWithFrame:frameName:groupName:]
++[WebViewPrivate initialize]
+-[WebViewPrivate init]
+-[WebView _commonInitializationWithFrameName:groupName:]
+-[WebPreferences(WebPrivate) willAddToWebView]
+-[WebFrameView initWithFrame:]
+_InitWebCoreSystemInterface
++[WebViewFactory createSharedFactory]
++[WebKeyGenerator createSharedGenerator]
+_WKDisableCGDeferredUpdates
+-[WebFrameViewPrivate init]
+-[WebClipView initWithFrame:]
+_WebKitInitializeLoggingChannelsIfNecessary
+_initializeLogChannel
++[WebHistoryItem initialize]
++[WebHistoryItem(WebInternal) initWindowWatcherIfNecessary]
+__Z36WebKitInitializeDatabasesIfNecessaryv
+__ZN24WebDatabaseTrackerClient30sharedWebDatabaseTrackerClientEv
+__ZN24WebDatabaseTrackerClientC1Ev
+__ZN15WebChromeClientC2EP7WebView
+__ZN20WebContextMenuClientC2EP7WebView
+__ZN15WebEditorClientC2EP7WebView
+__ZN13WebDragClientC2EP7WebView
+__ZN18WebInspectorClientC2EP7WebView
++[WebFrameBridge initialize]
+-[WebFrameBridge initMainFrameWithPage:frameName:frameView:]
+-[WebFrameBridge finishInitializingWithPage:frameName:frameView:ownerElement:]
+__Z3kitPN7WebCore4PageE
+-[WebFrame(WebInternal) _initWithWebFrameView:webView:bridge:]
+-[WebFramePrivate setWebFrameView:]
+-[WebFrameView(WebInternal) _setWebFrame:]
+__ZN20WebFrameLoaderClientC2EP8WebFrame
+__ZN20WebFrameLoaderClient20createDocumentLoaderERKN7WebCore15ResourceRequestERKNS0_14SubstituteDataE
+__ZN20WebDocumentLoaderMacC2ERKN7WebCore15ResourceRequestERKNS0_14SubstituteDataE
+-[WebDataSource(WebInternal) _initWithDocumentLoader:]
++[WebDataSourcePrivate initialize]
+__Z10getWebViewP8WebFrame
+__Z4coreP8WebFrame
+__ZN20WebDocumentLoaderMac13setDataSourceEP13WebDataSourceP7WebView
+__ZN20WebDocumentLoaderMac16retainDataSourceEv
+-[WebView resourceLoadDelegate]
+-[WebView downloadDelegate]
+__ZN20WebDocumentLoaderMac13attachToFrameEv
+__ZN20WebFrameLoaderClient22provisionalLoadStartedEv
+-[WebFrameView(WebInternal) _scrollView]
+__ZN20WebFrameLoaderClient25setMainFrameDocumentReadyEb
+-[WebView(WebPendingPublic) setMainFrameDocumentReady:]
+__ZN20WebFrameLoaderClient17setCopiesOnScrollEv
+__ZN20WebFrameLoaderClient31prepareForDataSourceReplacementEv
+-[WebFrame(WebInternal) _dataSource]
+-[WebFrame(WebInternal) _frameLoader]
+__ZN20WebFrameLoaderClient31transitionToCommittedForNewPageEv
+__ZNK20WebDocumentLoaderMac10dataSourceEv
+-[WebDataSource(WebPrivate) _responseMIMEType]
+-[WebDataSource response]
+-[WebDataSource(WebFileInternal) _MIMETypeOfResponse:]
++[WebFrameView(WebInternal) _viewClassForMIMEType:]
++[WebView(WebPrivate) _viewClass:andRepresentationClass:forMIMEType:]
+-[NSDictionary(WebNSDictionaryExtras) _webkit_objectForMIMEType:]
++[WebHTMLView(WebPrivate) unsupportedTextMIMETypes]
+-[WebFrameView(WebInternal) _makeDocumentViewForDataSource:]
+-[WebDataSource representation]
+-[WebHTMLView initWithFrame:]
++[WebHTMLViewPrivate initialize]
+-[WebPluginController initWithDocumentView:]
+-[WebFrameView(WebInternal) _setDocumentView:]
+-[WebFrameView(WebInternal) _webView]
+-[WebFrame webView]
+__Z4coreP7WebView
+-[WebView(WebPrivate) page]
+-[WebDynamicScrollBarsView setSuppressLayout:]
+-[WebHTMLView viewWillMoveToSuperview:]
+-[WebHTMLView removeSuperviewObservers]
+-[WebHTMLView setNeedsDisplay:]
+-[WebHTMLView visibleRect]
+-[WebClipView hasAdditionalClip]
+-[WebHTMLView viewDidMoveToSuperview]
+-[WebHTMLView(WebHTMLViewFileInternal) _updateTextSizeMultiplier]
+-[WebHTMLView(WebHTMLViewFileInternal) _bridge]
+-[WebHTMLView(WebHTMLViewFileInternal) _webView]
+-[WebHTMLView addSuperviewObservers]
+-[WebHTMLView isFlipped]
+-[WebDynamicScrollBarsView reflectScrolledClipView:]
+-[WebHTMLView respondsToSelector:]
+-[WebFrameView(WebInternal) _marginHeight]
+-[WebFrameView(WebInternal) _marginWidth]
+-[WebFrame(WebInternal) _updateBackground]
+-[WebView drawsBackground]
+-[WebView(WebPrivate) backgroundColor]
+-[WebFrameBridge webFrame]
+-[WebFrame frameView]
+-[WebFrameView documentView]
+-[WebDynamicScrollBarsView horizontalScrollingMode]
+-[WebDynamicScrollBarsView setScrollingMode:]
+-[WebDynamicScrollBarsView setScrollingMode:andLock:]
+-[WebHTMLView setDataSource:]
+-[WebPluginController setDataSource:]
+-[WebHTMLView addMouseMovedObserver]
+-[WebHTMLView(WebHTMLViewFileInternal) _isTopHTMLView]
+-[WebHTMLView(WebHTMLViewFileInternal) _topHTMLView]
+-[WebDataSource(WebInternal) _webView]
+-[WebDataSource webFrame]
+-[WebView mainFrame]
+__Z3kitPN7WebCore5FrameE
+-[WebView(WebPrivate) _dashboardBehavior:]
+__ZN15WebEditorClient23clearUndoRedoOperationsEv
+__ZN15WebChromeClient16setStatusbarTextERKN7WebCore6StringE
+__Z14CallUIDelegateP7WebViewP13objc_selectorP11objc_object
+__Z12CallDelegateP7WebViewP11objc_objectP13objc_selectorS2_
+__ZN20WebFrameLoaderClient15finishedLoadingEPN7WebCore14DocumentLoaderE
+-[WebDataSource(WebInternal) _finishedLoading]
+__ZN20WebFrameLoaderClient18frameLoadCompletedEv
+__ZN20WebFrameLoaderClient21forceLayoutForNonHTMLEv
+-[WebDataSource(WebInternal) _isDocumentHTML]
++[WebView canShowMIMETypeAsHTML:]
++[WebFrameView(WebInternal) _canShowMIMETypeAsHTML:]
+__ZNK20WebFrameLoaderClient17overrideMediaTypeEv
+-[WebView mediaStyle]
+-[WebView textSizeMultiplier]
+-[WebView(AllWebViews) _addToAllWebViewsSet]
+-[WebView setGroupName:]
+-[WebView _registerDraggedTypes]
++[NSPasteboard(WebExtras) _web_dragTypesForURL]
++[WebView(WebPrivate) _scriptDebuggerEnabled]
+-[WebView preferences]
+-[WebIconDatabase(WebInternal) _resetCachedWebPreferences:]
++[WebView(WebFileInternal) _preferencesChangedNotification:]
+-[WebPreferences cacheModel]
++[WebView(WebFileInternal) _didSetCacheModel]
++[WebView(WebFileInternal) _setCacheModel:]
+_WKCopyFoundationCacheDirectory
+_WebMemorySize
+_initCapabilities
+_WebVolumeFreeSize
+-[WebView(WebPrivate) _preferencesChangedNotification:]
+-[WebPreferences(WebPrivate) _useSiteSpecificSpoofing]
+-[WebPreferences cursiveFontFamily]
+-[WebPreferences _stringValueForKey:]
+-[WebPreferences defaultFixedFontSize]
+-[WebPreferences defaultFontSize]
+-[WebPreferences defaultTextEncodingName]
+-[WebPreferences fantasyFontFamily]
+-[WebPreferences fixedFontFamily]
+-[WebPreferences(WebPrivate) _forceFTPDirectoryListings]
+-[WebPreferences(WebPrivate) _ftpDirectoryTemplatePath]
+-[WebPreferences isJavaEnabled]
+-[WebPreferences isJavaScriptEnabled]
+-[WebPreferences javaScriptCanOpenWindowsAutomatically]
+-[WebPreferences minimumFontSize]
+-[WebPreferences minimumLogicalFontSize]
+-[WebPreferences arePlugInsEnabled]
+-[WebPreferences sansSerifFontFamily]
+-[WebPreferences serifFontFamily]
+-[WebPreferences standardFontFamily]
+-[WebPreferences loadsImagesAutomatically]
+-[WebPreferences shouldPrintBackgrounds]
+-[WebPreferences(WebPrivate) textAreasAreResizable]
+-[WebPreferences(WebPrivate) shrinksStandaloneImagesToFit]
+-[WebPreferences(WebPrivate) editableLinkBehavior]
+__Z4core26WebKitEditableLinkBehavior
+-[WebPreferences(WebPrivate) isDOMPasteAllowed]
+-[WebView(WebPrivate) usesPageCache]
+-[WebPreferences usesPageCache]
+-[WebPreferences(WebPrivate) showsURLsInToolTips]
+-[WebPreferences(WebPrivate) developerExtrasEnabled]
+-[WebPreferences(WebPrivate) authorAndUserStylesEnabled]
+-[WebPreferences userStyleSheetEnabled]
+-[WebView(WebPrivate) _needsAdobeFrameReloadingQuirk]
+_WKAppVersionCheckLessThan
+-[WebView(WebPrivate) _needsKeyboardEventDisambiguationQuirks]
+-[WebView setMaintainsBackForwardList:]
+-[WebView setUIDelegate:]
+-[WebView backForwardList]
+__Z3kitPN7WebCore15BackForwardListE
+__Z16backForwardListsv
++[WebBackForwardList initialize]
+-[WebBackForwardList(WebBackForwardListInternal) initWithBackForwardList:]
+__Z4coreP18WebBackForwardList
+__ZNK3WTF7HashMapIPN7WebCore15BackForwardListEP18WebBackForwardListNS_7PtrHashIS3_EENS_10HashTraitsIS3_EENS8_IS5_EEE3getERKS3_
+__ZN3WTF9HashTableIiSt4pairIiiENS_18PairFirstExtractorIS2_EENS_7IntHashIiEENS_14PairHashTraitsINS_10HashTraitsIiEES9_EES9_E47removeAndInvalidateWithoutEntryConsistencyCheckEPS2_
+-[WebBackForwardList setCapacity:]
+-[WebView setFrameLoadDelegate:]
+-[WebView(WebPrivate) _cacheFrameLoadDelegateImplementations]
+-[WebView setPolicyDelegate:]
+-[WebView(WebViewEditing) setEditingDelegate:]
+-[WebView(WebViewEditing) registerForEditingDelegateNotification:selector:]
+-[WebView setResourceLoadDelegate:]
+-[WebView(WebPrivate) _cacheResourceLoadDelegateImplementations]
+-[WebView setDownloadDelegate:]
+-[WebView setApplicationNameForUserAgent:]
+-[WebView setHostWindow:]
+-[WebView(WebPrivate) _setFormDelegate:]
++[WebStringTruncator initialize]
++[WebStringTruncator centerTruncateString:toWidth:withFont:]
+__Z14fontFromNSFontP6NSFont
+_WKGetCGFontFromNSFont
+_WKGetNSFontATSUFontId
+_WKGetATSStyleGroup
+_WKGetFontMetrics
+_WKInitializeGlyphVector
+_WKConvertCharToGlyphs
+_WKGetGlyphVectorNumGlyphs
+_WKGetGlyphVectorFirstRecord
+_WKGetGlyphVectorRecordSize
+_WKClearGlyphVector
+_WKGetGlyphTransformedAdvances
+-[WebIconDatabase defaultIconWithSize:]
+-[WebFrameView setFrameSize:]
+-[WebFrameView webFrame]
+-[WebFrame provisionalDataSource]
+-[WebFrame dataSource]
+-[WebView viewWillMoveToWindow:]
+_WKSetNSWindowShouldPostEventNotifications
+-[WebHTMLView viewWillMoveToWindow:]
+-[WebHTMLView removeMouseMovedObserverUnconditionally]
+_WKMouseMovedNotification
+-[WebHTMLView removeWindowObservers]
+-[WebHTMLView(WebHTMLViewFileInternal) _cancelUpdateMouseoverTimer]
+-[WebHTMLView(WebHTMLViewFileInternal) _cancelUpdateFocusedAndActiveStateTimer]
+-[WebHTMLView(WebPrivate) _pluginController]
+-[WebPluginController stopAllPlugins]
+-[WebHTMLView viewDidMoveToWindow]
+-[WebHTMLView(WebPrivate) _stopAutoscrollTimer]
+-[WebHTMLView addWindowObservers]
+-[WebHTMLView(WebPrivate) _frameOrBoundsChanged]
+-[WebHTMLView setNeedsLayout:]
+-[WebPluginController startAllPlugins]
+-[WebIconDatabase iconForURL:withSize:]
+-[WebIconDatabase iconForURL:withSize:cache:]
+-[NSString(WebNSURLExtras) _webkit_isFileURL]
+-[WebIconDatabase defaultIconForURL:withSize:]
+-[WebView setNextKeyView:]
+-[WebFrameView setNextKeyView:]
+-[NSString(WebKitExtras) _webkit_hasCaseInsensitivePrefix:]
++[NSURL(WebNSURLExtras) _web_URLWithUserTypedString:]
++[NSURL(WebNSURLExtras) _web_URLWithUserTypedString:relativeToURL:]
+-[NSString(WebKitExtras) _webkit_stringByTrimmingWhitespace]
+__Z12mapHostNamesP8NSStringa
++[NSURL(WebNSURLExtras) _web_URLWithData:relativeToURL:]
+-[NSURL(WebNSURLExtras) _webkit_canonicalize]
+_WKNSURLProtocolClassForRequest
+-[NSURL(WebNSURLExtras) _web_originalDataAsString]
++[NSURL(WebNSURLExtras) _web_URLWithDataAsString:]
++[NSURL(WebNSURLExtras) _web_URLWithDataAsString:relativeToURL:]
+-[NSView(WebExtras) _web_superviewOfClass:]
+-[WebFrame loadRequest:]
+__ZN20WebFrameLoaderClient9userAgentERKN7WebCore4KURLE
+-[WebView(WebViewInternal) _userAgentForURL:]
+-[WebView(WebViewInternal) _userAgentWithApplicationName:andWebKitVersion:]
++[NSUserDefaults(WebNSUserDefaultsExtras) _webkit_preferredLanguageCode]
++[NSUserDefaults(WebNSUserDefaultsExtras) _webkit_ensureAndLockPreferredLanguageLock]
+_makeLock
+-[NSString(WebNSUserDefaultsPrivate) _webkit_HTTPStyleLanguageCode]
+_WKCopyCFLocalizationPreferredName
++[NSUserDefaults(WebNSUserDefaultsExtras) _webkit_addDefaultsChangeObserver]
+_addDefaultsChangeObserver
+__ZN20WebFrameLoaderClient17cancelPolicyCheckEv
+__ZN20WebFrameLoaderClient39dispatchDecidePolicyForNavigationActionEMN7WebCore11FrameLoaderEFvNS0_12PolicyActionEERKNS0_16NavigationActionERKNS0_15ResourceRequestE
+-[WebView(WebPrivate) _policyDelegateForwarder]
++[WebDefaultPolicyDelegate sharedPolicyDelegate]
+-[_WebSafeForwarder initWithTarget:defaultTarget:catchExceptions:]
+__ZN20WebFrameLoaderClient19setUpPolicyListenerEMN7WebCore11FrameLoaderEFvNS0_12PolicyActionEE
++[WebFramePolicyListener initialize]
+-[WebFramePolicyListener initWithWebCoreFrame:]
+_WKSupportsMultipartXMixedReplace
+__ZNK20WebFrameLoaderClient16actionDictionaryERKN7WebCore16NavigationActionE
+-[_WebSafeForwarder methodSignatureForSelector:]
+-[_WebSafeForwarder forwardInvocation:]
++[WebView(WebPrivate) _canHandleRequest:]
+-[WebFramePolicyListener use]
+-[WebFramePolicyListener receivedPolicyDecision:]
+__ZN20WebFrameLoaderClient21receivedPolicyDecisonEN7WebCore12PolicyActionE
+__ZNK20WebFrameLoaderClient16canHandleRequestERKN7WebCore15ResourceRequestE
+__ZN15WebChromeClient30canRunBeforeUnloadConfirmPanelEv
+-[WebView UIDelegate]
+__ZN20WebFrameLoaderClient22clearArchivedResourcesEv
+__ZN3WTF9HashTableIiSt4pairIiNS_9RetainPtrI11WebResourceEEENS_18PairFirstExtractorIS5_EENS_7IntHashIiEENS_14PairHashTraitsINS_10HashTraitsIiEENSB_IS4_EEEESC_E47removeAndInvalidateWithoutEntryConsistencyCheckEPS5_
+__ZN20WebFrameLoaderClient27willChangeEstimatedProgressEv
+-[WebView(WebPrivate) _willChangeValueForKey:]
+-[WebView(WebPrivate) observationInfo]
+__ZN20WebFrameLoaderClient31postProgressStartedNotificationEv
+__ZN20WebFrameLoaderClient26didChangeEstimatedProgressEv
+-[WebView(WebPrivate) _didChangeValueForKey:]
+__ZN20WebFrameLoaderClient31dispatchDidStartProvisionalLoadEv
+-[WebView(WebPrivate) _didStartProvisionalLoadForFrame:]
+-[WebView(WebPrivate) _willChangeBackForwardKeys]
+__Z42WebViewGetFrameLoadDelegateImplementationsP7WebView
+__Z21CallFrameLoadDelegatePFP11objc_objectS0_P13objc_selectorzEP7WebViewS2_S0_
+__Z12CallDelegatePFP11objc_objectS0_P13objc_selectorzEP7WebViewS0_S2_S0_
+-[WebDataSource isLoading]
+-[WebDataSource request]
+-[NSURL(WebNSURLExtras) _web_hostString]
+-[NSURL(WebNSURLExtras) _web_hostData]
+-[NSURL(WebNSURLExtras) _web_dataForURLComponentType:]
+-[NSURL(WebNSURLExtras) _web_schemeData]
+-[NSData(WebNSDataExtras) _web_isCaseInsensitiveEqualToCString:]
+-[NSString(WebNSURLExtras) _web_decodeHostName]
+-[NSString(WebNSURLExtras) _web_mapHostNameWithRange:encode:makeString:]
+-[WebDataSource unreachableURL]
+-[NSString(WebKitExtras) _webkit_isCaseInsensitiveEqualToString:]
+__ZN20WebFrameLoaderClient32assignIdentifierToInitialRequestEmPN7WebCore14DocumentLoaderERKNS0_15ResourceRequestE
+__Z45WebViewGetResourceLoadDelegateImplementationsP7WebView
+-[WebView(WebViewInternal) _addObject:forIdentifier:]
+__ZN3WTF9HashTableImSt4pairImNS_9RetainPtrIP11objc_objectEEENS_18PairFirstExtractorIS6_EENS_7IntHashImEENS_14PairHashTraitsINS_10HashTraitsImEENSC_IS5_EEEESD_E3addImS5_NS_17HashMapTranslatorILb1ES6_NS_18PairBaseHashTraitsISD_SE_EESF_SA_EEEES1_INS_17HashTableIteratorImS6_S8_SA_SF_SD_EEbERKT_RKT0_
+__ZN3WTF9HashTableImSt4pairImNS_9RetainPtrIP11objc_objectEEENS_18PairFirstExtractorIS6_EENS_7IntHashImEENS_14PairHashTraitsINS_10HashTraitsImEENSC_IS5_EEEESD_E47removeAndInvalidateWithoutEntryConsistencyCheckEPS6_
+__ZN20WebFrameLoaderClient23dispatchWillSendRequestEPN7WebCore14DocumentLoaderEmRNS0_15ResourceRequestERKNS0_16ResourceResponseE
+__ZN20WebDocumentLoaderMac17increaseLoadCountEm
+__ZNK3WTF9HashTableImmNS_17IdentityExtractorImEENS_7IntHashImEENS_10HashTraitsImEES6_E8containsImNS_22IdentityHashTranslatorImmS4_EEEEbRKT_
+__ZN3WTF7HashSetImNS_7IntHashImEENS_10HashTraitsImEEE3addERKm
+__ZN3WTF9HashTableImmNS_17IdentityExtractorImEENS_7IntHashImEENS_10HashTraitsImEES6_E3addImmNS_17HashSetTranslatorILb1EmS6_S6_S4_EEEESt4pairINS_17HashTableIteratorImmS2_S4_S6_S6_EEbERKT_RKT0_
+__ZN3WTF9HashTableImmNS_17IdentityExtractorImEENS_7IntHashImEENS_10HashTraitsImEES6_E6expandEv
+-[WebView(WebViewInternal) _objectForIdentifier:]
+__ZN3WTF7HashMapImNS_9RetainPtrIP11objc_objectEENS_7IntHashImEENS_10HashTraitsImEENS7_IS4_EEE3setERKmRKS4_
+__ZN3WTF23HashTableRefCounterBaseILb1ENS_9HashTableIPN7WebCore10StringImplESt4pairIS4_iENS_18PairFirstExtractorIS6_EENS2_15CaseFoldingHashENS_14PairHashTraitsINS_10HashTraitsIS4_EENSB_IiEEEESC_EENS_18PairBaseHashTraitsINSB_INS2_6StringEEESI_EEE6refAllERSF_
+__ZN3WTF9HashTableIPN7WebCore10StringImplESt4pairIS3_iENS_18PairFirstExtractorIS5_EENS1_15CaseFoldingHashENS_14PairHashTraitsINS_10HashTraitsIS3_EENSA_IiEEEESB_EC1ERKSE_
+__ZNK20WebFrameLoaderClient32representationExistsForURLSchemeERKN7WebCore6StringE
++[WebView(WebPrivate) _representationExistsForURLScheme:]
+_WKCreateNSURLConnectionDelegateProxy
+-[WebFramePolicyListener dealloc]
+-[WebFrameView isOpaque]
+-[WebFrameView drawRect:]
+-[WebHTMLView(WebPrivate) _recursiveDisplayAllDirtyWithLockFocus:visRect:]
+-[WebHTMLView(WebPrivate) _setAsideSubviews]
+-[WebHTMLView(WebPrivate) _restoreSubviews]
+-[WebFrame(WebInternal) _viewWillMoveToHostWindow:]
+-[WebHTMLView viewWillMoveToHostWindow:]
+-[NSArray(WebHTMLView) _web_makePluginViewsPerformSelector:withObject:]
+-[WebFrame(WebInternal) _viewDidMoveToHostWindow]
+-[WebHTMLView viewDidMoveToHostWindow]
+-[WebPreferences(WebPrivate) setRespectStandardStyleKeyEquivalents:]
+-[WebPreferences _setBoolValue:forKey:]
+-[WebPreferences setPrivateBrowsingEnabled:]
+-[WebPreferences(WebPrivate) setDOMPasteAllowed:]
++[WebPreferences(WebPrivate) _setInitialDefaultTextEncodingToSystemEncoding]
++[WebPreferences(WebPrivate) _systemCFStringEncoding]
+_WKGetWebDefaultCFStringEncoding
++[NSUserDefaults(WebNSUserDefaultsExtras) _webkit_defaultsDidChange]
+-[WebHistory init]
++[WebHistoryPrivate initialize]
+-[WebHistoryPrivate init]
+-[WebHistory setHistoryAgeInDaysLimit:]
+-[WebHistoryPrivate setHistoryAgeInDaysLimit:]
+-[WebHistory setHistoryItemLimit:]
+-[WebHistoryPrivate setHistoryItemLimit:]
+-[WebHistory loadFromURL:error:]
+-[WebHistoryPrivate loadFromURL:collectDiscardedItemsInto:error:]
+-[WebHistoryPrivate _loadHistoryGutsFromURL:savedItemsCount:collectDiscardedItemsInto:error:]
+-[WebHistoryPrivate historyItemLimit]
+-[WebHistoryPrivate _ageLimitDate]
+-[WebHistoryPrivate historyAgeInDaysLimit]
+-[WebHistoryItem(WebInternal) initFromDictionaryRepresentation:]
+-[NSDictionary(WebNSDictionaryExtras) _webkit_stringForKey:]
+-[WebHistoryItem(WebInternal) initWithURLString:title:displayTitle:lastVisitedTimeInterval:]
+-[WebHistoryItem(WebInternal) initWithWebCoreHistoryItem:]
+__Z19historyItemWrappersv
+__ZNK3WTF7HashMapIPN7WebCore11HistoryItemEP14WebHistoryItemNS_7PtrHashIS3_EENS_10HashTraitsIS3_EENS8_IS5_EEE3getERKS3_
+-[NSDictionary(WebNSDictionaryExtras) _webkit_intForKey:]
+-[NSDictionary(WebNSDictionaryExtras) _webkit_numberForKey:]
+-[WebHistoryItem URLString]
+-[WebHistoryItem lastVisitedTimeInterval]
+-[WebHistoryPrivate addItem:]
+-[WebHistoryPrivate _addItemToDateCaches:]
+-[WebHistoryPrivate findKey:forDay:]
+__Z29timeIntervalForBeginningOfDayd
+__ZNK3WTF9HashTableIxSt4pairIxNS_9RetainPtrI14NSMutableArrayEEENS_18PairFirstExtractorIS5_EENS_7IntHashIyEENS_14PairHashTraitsINS_10HashTraitsIxEENSB_IS4_EEEESC_E8containsIxNS_22IdentityHashTranslatorIxS5_S9_EEEEbRKT_
+__ZNK3WTF7HashMapIxNS_9RetainPtrI14NSMutableArrayEENS_7IntHashIyEENS_10HashTraitsIxEENS6_IS3_EEE3getERKx
+__ZN3WTF9HashTableIxSt4pairIxNS_9RetainPtrI14NSMutableArrayEEENS_18PairFirstExtractorIS5_EENS_7IntHashIyEENS_14PairHashTraitsINS_10HashTraitsIxEENSB_IS4_EEEESC_E3addIxS4_NS_17HashMapTranslatorILb1ES5_NS_18PairBaseHashTraitsISC_SD_EESE_S9_EEEES1_INS_17HashTableIteratorIxS5_S7_S9_SE_SC_EEbERKT_RKT0_
+__ZN3WTF9HashTableIxSt4pairIxNS_9RetainPtrI14NSMutableArrayEEENS_18PairFirstExtractorIS5_EENS_7IntHashIyEENS_14PairHashTraitsINS_10HashTraitsIxEENSB_IS4_EEEESC_E47removeAndInvalidateWithoutEntryConsistencyCheckEPS5_
+-[WebHistoryPrivate insertItem:forDateKey:]
++[WebHistory setOptionalSharedHistory:]
+-[_WebCoreHistoryProvider initWithHistory:]
++[WebIconDatabase allowDatabaseCleanup]
+-[WebBackForwardList dealloc]
+__ZN3WTF9HashTableIiSt4pairIiiENS_18PairFirstExtractorIS2_EENS_7IntHashIiEENS_14PairHashTraitsINS_10HashTraitsIiEES9_EES9_E4findIiNS_22IdentityHashTranslatorIiS2_S6_EEEENS_17HashTableIteratorIiS2_S4_S6_SA_S9_EERKT_
+__ZN20WebFrameLoaderClient31dispatchDecidePolicyForMIMETypeEMN7WebCore11FrameLoaderEFvNS0_12PolicyActionEERKNS0_6StringERKNS0_15ResourceRequestE
++[WebView canShowMIMEType:]
+__ZNK20WebFrameLoaderClient15canShowMIMETypeERKN7WebCore6StringE
+__ZN20WebFrameLoaderClient26dispatchDidReceiveResponseEPN7WebCore14DocumentLoaderEmRKNS0_16ResourceResponseE
+__ZN20WebFrameLoaderClient17dispatchWillCloseEv
+__ZN20WebFrameLoaderClient18makeRepresentationEPN7WebCore14DocumentLoaderE
+-[WebDataSource(WebInternal) _makeRepresentation]
++[WebDataSource(WebFileInternal) _representationClassForMIMEType:]
+-[WebHTMLRepresentation init]
+-[WebDataSource(WebFileInternal) _setRepresentation:]
+-[WebHTMLRepresentation setDataSource:]
+-[WebFrame(WebInternal) _bridge]
+__ZN20WebDocumentLoaderMac15detachFromFrameEv
+__ZN20WebDocumentLoaderMac17releaseDataSourceEv
+__ZN20WebFrameLoaderClient34updateGlobalHistoryForStandardLoadERKN7WebCore4KURLE
++[WebHistory optionalSharedHistory]
+-[WebHistory addItemForURL:]
+-[WebHistoryItem(WebPrivate) initWithURL:title:]
+-[WebHistoryItem initWithURLString:title:lastVisitedTimeInterval:]
+-[WebHistoryItem(WebPrivate) _setLastVisitedTimeInterval:]
+-[WebHistory addItem:]
+-[WebHistoryPrivate removeItemForURLString:]
+-[WebHistoryPrivate _removeItemFromDateCaches:]
+__ZN3WTF9HashTableIxSt4pairIxNS_9RetainPtrI14NSMutableArrayEEENS_18PairFirstExtractorIS5_EENS_7IntHashIyEENS_14PairHashTraitsINS_10HashTraitsIxEENSB_IS4_EEEESC_E4findIxNS_22IdentityHashTranslatorIxS5_S9_EEEENS_17HashTableIteratorIxS5_S7_S9_SE_SC_EERKT_
+-[WebHistoryItem(WebInternal) _mergeAutoCompleteHints:]
+-[WebHistoryItem dealloc]
+-[WebHistory _sendNotification:entries:]
+__Z26WKNotifyHistoryItemChangedv
+-[WebDynamicScrollBarsView setScrollBarsSuppressed:repaintOnUnsuppress:]
+-[WebDataSource dealloc]
+-[WebDataSourcePrivate dealloc]
+__ZN20WebDocumentLoaderMac16detachDataSourceEv
+__ZNK20WebFrameLoaderClient11hasHTMLViewEv
+__ZN20WebFrameLoaderClient13committedLoadEPN7WebCore14DocumentLoaderEPKci
+-[WebDataSource(WebInternal) _receivedData:]
+-[WebHTMLRepresentation receivedData:withDataSource:]
+-[WebHTMLRepresentation _isDisplayingWebArchive]
+__ZN20WebFrameLoaderClient21dispatchDidCommitLoadEv
+-[WebView(WebPrivate) _didCommitLoadForFrame:]
+-[WebDataSource pageTitle]
+-[WebHTMLRepresentation title]
+-[WebDataSource(WebInternal) _documentLoader]
+-[WebBackForwardList currentItem]
+__Z3kitPN7WebCore11HistoryItemE
+-[WebHistoryItem(WebPrivate) _transientPropertyForKey:]
+-[WebFrameView becomeFirstResponder]
+-[WebHTMLView acceptsFirstResponder]
+-[WebHTMLView becomeFirstResponder]
+-[WebView(WebPrivate) _isPerformingProgrammaticFocus]
+-[WebHTMLView(WebPrivate) _updateFocusedAndActiveState]
+-[WebHTMLView(WebInternal) _frame]
+-[WebHTMLView(WebInternal) _updateFontPanel]
+-[WebHTMLView(WebPrivate) _canEdit]
+-[WebHTMLView _arrowKeyDownEventSelectorIfPreprocessing]
+-[NSURL(WebNSURLExtras) _web_userVisibleString]
+-[NSURL(WebNSURLExtras) _web_originalData]
+__Z10isHexDigitc
+__Z13hexDigitValuec
+__ZN20WebFrameLoaderClient15willChangeTitleEPN7WebCore14DocumentLoaderE
+__ZN20WebFrameLoaderClient14didChangeTitleEPN7WebCore14DocumentLoaderE
+__ZN20WebFrameLoaderClient8setTitleERKN7WebCore6StringERKNS0_4KURLE
+-[WebHistory itemForURL:]
+-[WebHistoryPrivate itemForURL:]
+-[WebHistoryPrivate itemForURLString:]
+-[WebHistoryItem(WebInternal) setTitle:]
+__ZN20WebFrameLoaderClient23dispatchDidReceiveTitleERKN7WebCore6StringE
+__Z21CallFrameLoadDelegatePFP11objc_objectS0_P13objc_selectorzEP7WebViewS2_S0_S0_
+__ZN20WebFrameLoaderClient22dispatchDidFailLoadingEPN7WebCore14DocumentLoaderEmRKNS0_13ResourceErrorE
+__ZN20WebFrameLoaderClient29dispatchDidHandleOnloadEventsEv
+-[WebDynamicScrollBarsView verticalScrollingMode]
+-[WebDynamicScrollBarsView setVerticalScrollingMode:]
+-[WebDynamicScrollBarsView setVerticalScrollingMode:andLock:]
+-[WebDynamicScrollBarsView updateScrollers]
+-[WebDynamicScrollBarsView setHorizontalScrollingMode:]
+-[WebDynamicScrollBarsView setHorizontalScrollingMode:andLock:]
+__ZN15WebEditorClient10isEditableEv
+-[WebHTMLView layout]
+-[WebHTMLView layoutToMinimumPageWidth:maximumPageWidth:adjustingViewSize:]
+-[WebHTMLView reapplyStyles]
+-[WebDataSource(WebInternal) _bridge]
+__ZN20WebFrameLoaderClient22dispatchDidFirstLayoutEv
+__ZN20WebFrameLoaderClient21dispatchDidFinishLoadEv
+-[WebView(WebPrivate) _didFinishLoadForFrame:]
+-[WebView(WebPrivate) _didChangeBackForwardKeys]
+-[WebFrame DOMDocument]
+__Z3kitPN7WebCore8DocumentE
+__ZN20WebFrameLoaderClient32postProgressFinishedNotificationEv
+-[WebHTMLView(WebPrivate) viewWillDraw]
+-[WebHTMLView(WebInternal) _web_layoutIfNeededRecursive]
+-[WebHTMLView(WebInternal) _layoutIfNeeded]
+-[NSView(WebHTMLViewFileInternal) _web_addDescendantWebHTMLViewsToArray:]
+-[WebHTMLView isOpaque]
+-[WebHTMLView drawRect:]
+-[WebHTMLView drawSingleRect:]
+-[WebClipView setAdditionalClip:]
+-[WebHTMLView(WebPrivate) _transparentBackground]
+-[WebHistoryItem originalURLString]
+-[WebFrame(WebPrivate) _isFrameSet]
+-[WebHTMLView(WebDocumentPrivateProtocols) string]
+-[WebHTMLView(WebHTMLViewFileInternal) _documentRange]
+-[DOMDocument(WebDOMDocumentOperationsPrivate) _documentRange]
+-[DOMDocument(WebDOMDocumentOperationsPrivate) _createRangeWithNode:]
+-[WebHTMLView _windowChangedKeyState]
+-[WebHTMLView updateCell:]
+-[WebHTMLView windowDidBecomeKey:]
+-[WebHTMLView(WebNSTextInputSupport) inputContext]
+-[WebHTMLView(WebNSTextInputSupport) validAttributesForMarkedText]
+__Z9setCursorP8NSWindowP13objc_selector8_NSPoint
+-[NSWindow(BorderViewAccess) _web_borderView]
+-[WebHTMLView nextResponder]
+-[WebHTMLView mouseMovedNotification:]
+-[NSView(WebExtras) _web_dragShouldBeginFromMouseDown:withExpiration:xHysteresis:yHysteresis:]
+-[NSString(WebNSURLExtras) _webkit_scriptIfJavaScriptURL]
+-[NSString(WebNSURLExtras) _webkit_isJavaScriptURL]
+__ZNK20WebFrameLoaderClient12canCachePageEv
+__ZN20WebFrameLoaderClient19windowObjectClearedEv
+-[WebFrameBridge windowObjectCleared]
+-[WebView(WebPendingPublic) scriptDebugDelegate]
+__ZN20WebFrameLoaderClient28savePlatformDataToCachedPageEPN7WebCore10CachedPageE
+-[WebHistoryItem hash]
+__ZNK20WebFrameLoaderClient25didPerformFirstNavigationEv
+-[WebPreferences(WebPrivate) automaticallyDetectsCacheModel]
+__ZN20WebFrameLoaderClient19saveViewStateToItemEPN7WebCore11HistoryItemE
+-[WebHTMLView resignFirstResponder]
+-[WebHTMLView maintainsInactiveSelection]
+-[WebView(WebViewEditing) maintainsInactiveSelection]
+-[WebHTMLView(WebDocumentPrivateProtocols) deselectAll]
+-[WebHTMLView clearFocus]
+__ZNK20WebFrameLoaderClient17willCacheResponseEPN7WebCore14DocumentLoaderEmP19NSCachedURLResponse
+__ZN21WebIconDatabaseClient28dispatchDidAddIconForPageURLERKN7WebCore6StringE
+-[WebIconDatabase(WebInternal) _sendNotificationForURL:]
+-[NSNotificationCenter(WebNSNotificationCenterExtras) postNotificationOnMainThreadWithName:object:userInfo:]
+-[NSNotificationCenter(WebNSNotificationCenterExtras) postNotificationOnMainThreadWithName:object:userInfo:waitUntilDone:]
+__ZN20WebFrameLoaderClient27registerForIconNotificationEb
+-[WebView(WebViewInternal) _registerForIconNotification:]
+-[WebBasePluginPackage isNativeLibraryData:]
+-[WebBasePluginPackage getPluginInfoFromPLists]
+-[WebNetscapePluginPackage stringForStringListID:andIndex:]
++[NSString(WebKitExtras) _web_encodingForResource:]
+-[WebNetscapePluginPackage closeResourceFile:]
+-[WebBasePluginPackage pListForPath:createFile:]
+-[WebBasePluginPackage load]
+-[WebPluginDatabase(Internal) _addPlugin:]
+-[WebBasePluginPackage path]
+-[WebBasePluginPackage wasAddedToPluginDatabase:]
+-[WebBasePluginPackage MIMETypeEnumerator]
+-[WebPluginDatabase pluginForMIMEType:]
+-[WebPluginDatabase pluginForKey:withEnumeratorSelector:]
+-[WebNetscapePluginPackage executableType]
+_checkCandidate
+-[WebBasePluginPackage isQuickTimePlugIn]
+-[WebBasePluginPackage bundle]
+-[WebBasePluginPackage isJavaPlugIn]
++[WebHTMLView(WebPrivate) supportedImageMIMETypes]
++[WebHTMLRepresentation supportedImageMIMETypes]
+__ZN3WTF7HashSetIN7WebCore6StringENS1_10StringHashENS_10HashTraitsIS2_EEE3addERKS2_
+__ZN3WTF9HashTableIPN7WebCore10StringImplES3_NS_17IdentityExtractorIS3_EENS1_10StringHashENS_10HashTraitsIS3_EES8_E3addINS1_6StringESB_NS_17HashSetTranslatorILb0ESB_NS7_ISB_EES8_S6_EEEESt4pairINS_17HashTableIteratorIS3_S3_S5_S6_S8_S8_EEbERKT_RKT0_
+__ZN3WTF9HashTableIPN7WebCore10StringImplES3_NS_17IdentityExtractorIS3_EENS1_10StringHashENS_10HashTraitsIS3_EES8_E6expandEv
+__ZN3WTF9HashTableIPN7WebCore10StringImplES3_NS_17IdentityExtractorIS3_EENS1_10StringHashENS_10HashTraitsIS3_EES8_E4findIS3_NS_22IdentityHashTranslatorIS3_S3_S6_EEEENS_17HashTableIteratorIS3_S3_S5_S6_S8_S8_EERKT_
+-[WebPluginDatabase plugins]
+-[WebBasePluginPackage name]
+-[WebBasePluginPackage pluginDescription]
+-[WebBasePluginPackage extensionsForMIMEType:]
+-[WebBasePluginPackage descriptionForMIMEType:]
+-[WebView estimatedProgress]
+_WKSetNSURLRequestShouldContentSniff
+-[WebHistoryItem isEqual:]
+__ZN20WebFrameLoaderClient17objectContentTypeERKN7WebCore4KURLERKNS0_6StringE
+-[WebFrameBridge determineObjectFromMIMEType:URL:]
+-[WebFrameBridge webView]
+-[WebView _pluginForMIMEType:]
+__ZN20WebFrameLoaderClient12createPluginERKN7WebCore7IntSizeEPNS0_7ElementERKNS0_4KURLERKN3WTF6VectorINS0_6StringELm0EEESE_RKSB_b
+__Z7nsArrayRKN3WTF6VectorIN7WebCore6StringELm0EEE
+-[WebFrameBridge viewForPluginWithFrame:URL:attributeNames:attributeValues:MIMEType:DOMElement:loadManually:]
++[WebBaseNetscapePluginView initialize]
+_WKSendUserChangeNotifications
+-[WebBaseNetscapePluginView initWithFrame:pluginPackage:URL:baseURL:MIMEType:attributeKeys:attributeValues:loadManually:DOMElement:]
+-[WebNetscapePluginPackage load]
+-[WebNetscapePluginPackage _applyDjVuWorkaround]
+-[WebBaseNetscapePluginView setPluginPackage:]
+-[WebNetscapePluginPackage NPP_New]
+-[WebNetscapePluginPackage NPP_Destroy]
+-[WebNetscapePluginPackage NPP_SetWindow]
+-[WebNetscapePluginPackage NPP_NewStream]
+-[WebNetscapePluginPackage NPP_WriteReady]
+-[WebNetscapePluginPackage NPP_Write]
+-[WebNetscapePluginPackage NPP_StreamAsFile]
+-[WebNetscapePluginPackage NPP_DestroyStream]
+-[WebNetscapePluginPackage NPP_HandleEvent]
+-[WebNetscapePluginPackage NPP_URLNotify]
+-[WebNetscapePluginPackage NPP_GetValue]
+-[WebNetscapePluginPackage NPP_SetValue]
+-[WebNetscapePluginPackage NPP_Print]
+-[WebBaseNetscapePluginView setMIMEType:]
+-[WebBaseNetscapePluginView setBaseURL:]
+-[WebBaseNetscapePluginView setAttributeKeys:andValues:]
+-[WebBaseNetscapePluginView setMode:]
+-[WebHTMLView addSubview:]
+-[WebBaseNetscapePluginView viewWillMoveToSuperview:]
+-[WebBaseNetscapePluginView visibleRect]
+-[WebBaseNetscapePluginView isFlipped]
+-[WebBaseNetscapePluginView viewWillMoveToWindow:]
+-[WebBaseNetscapePluginView tellQuickTimeToChill]
+-[WebBaseNetscapePluginView removeTrackingRect]
+-[WebBaseNetscapePluginView removeWindowObservers]
+-[WebBaseNetscapePluginView setHasFocus:]
+-[WebBaseNetscapePluginView viewDidMoveToWindow]
+-[WebBaseNetscapePluginView resetTrackingRect]
+-[WebBaseNetscapePluginView start]
+-[WebBaseNetscapePluginView canStart]
+-[WebBaseNetscapePluginView webView]
+-[WebBaseNetscapePluginView webFrame]
+-[WebBaseNetscapePluginView dataSource]
+__Z4coreP10DOMElement
+-[WebNetscapePluginPackage open]
+-[WebBaseNetscapePluginView(Internal) _createPlugin]
++[WebBaseNetscapePluginView setCurrentPluginView:]
+_NPN_UserAgent
+_pluginViewForInstance
++[WebBaseNetscapePluginView currentPluginView]
+-[WebBaseNetscapePluginView(WebNPPCallbacks) userAgent]
+-[WebView userAgentForURL:]
+_NPN_GetValue
+-[WebBaseNetscapePluginView(WebNPPCallbacks) getVariable:value:]
+_NPN_SetValue
+-[WebBaseNetscapePluginView(WebNPPCallbacks) setVariable:value:]
+_NPN_InvalidateRect
+-[WebBaseNetscapePluginView(WebNPPCallbacks) invalidateRect:]
+-[WebBaseNetscapePluginView updateAndSetWindow]
+-[WebBaseNetscapePluginView saveAndSetNewPortState]
+-[WebBaseNetscapePluginView saveAndSetNewPortStateForUpdate:]
+-[WebBaseNetscapePluginView currentWindow]
+-[WebBaseNetscapePluginView superviewsHaveSuperviews]
+-[WebBaseNetscapePluginView(WebNPPCallbacks) isOpaque]
+__ZN3WTF6VectorI6CGRectLm16EE6resizeEm
+-[WebBaseNetscapePluginView setWindowIfNecessary]
+-[WebBaseNetscapePluginView isNewWindowEqualToOldWindow]
+-[WebBaseNetscapePluginView willCallPlugInFunction]
+-[WebBaseNetscapePluginView didCallPlugInFunction]
+-[WebBaseNetscapePluginView restorePortState:]
+-[WebBaseNetscapePluginView addWindowObservers]
+-[WebBaseNetscapePluginView sendActivateEvent:]
+-[WebBaseNetscapePluginView getCarbonEvent:]
++[WebBaseNetscapePluginView getCarbonEvent:]
+-[WebBaseNetscapePluginView sendEvent:]
+_WKSetNSURLConnectionDefersCallbacks
+__ZN20WebFrameLoaderClient16setDefersLoadingEb
+__ZNK20WebFrameLoaderClient34deliverArchivedResourcesAfterDelayEv
+-[WebBaseNetscapePluginView restartNullEvents]
+-[WebBaseNetscapePluginView didStart]
+-[NSURL(WebNSURLExtras) _web_isEmpty]
+-[NSMutableURLRequest(WebNSURLRequestExtras) _web_setHTTPReferrer:]
+-[WebBaseNetscapePluginView(WebNPPCallbacks) loadRequest:inTarget:withNotifyData:sendNotification:]
+-[NSURL(WebNSURLExtras) _webkit_scriptIfJavaScriptURL]
++[WebBaseNetscapePluginStream initialize]
++[WebNetscapePluginStream initialize]
+-[WebNetscapePluginStream initWithRequest:plugin:notifyData:sendNotification:]
+-[WebBaseNetscapePluginStream initWithRequestURL:plugin:notifyData:sendNotification:]
+-[WebBaseNetscapePluginStream setRequestURL:]
+-[WebBaseNetscapePluginStream setPlugin:]
+-[WebBaseNetscapePluginView pluginPackage]
+__Z7streamsv
+__ZN3WTF7HashMapIP9_NPStreamP4_NPPNS_7PtrHashIS2_EENS_10HashTraitsIS2_EENS7_IS4_EEE3addERKS2_RKS4_
+__ZN3WTF9HashTableIiSt4pairIiiENS_18PairFirstExtractorIS2_EENS_7IntHashIiEENS_14PairHashTraitsINS_10HashTraitsIiEES9_EES9_E3addIPN7WebCore11HistoryItemEP14WebHistoryItemNS_17HashMapTranslatorILb1ES1_ISF_SH_ENS_18PairBaseHashTraitsINS8_ISF_EENS8_ISH_EEEESA_NS_7PtrHashISF_EEEEEES1_INS_17HashTableIteratorIiS2_S4_S6_SA_S9_EEbERKT_RKT0_
+-[WebNetscapePluginStream start]
+-[WebBaseNetscapePluginView stopNullEvents]
++[WebPluginController isPlugInView:]
+-[WebBaseNetscapePluginView renewGState]
+-[WebBaseNetscapePluginView(Internal) _viewHasMoved]
+-[WebFrameBridge firstResponder]
+__ZN15WebEditorClient19setInputMethodStateEb
+__ZN15WebEditorClient32isContinuousSpellCheckingEnabledEv
+-[WebView(WebViewEditing) isContinuousSpellCheckingEnabled]
+-[WebView(WebFileInternal) _continuousCheckingAllowed]
+__ZN15WebEditorClient24isGrammarCheckingEnabledEv
+-[WebView(WebViewGrammarChecking) isGrammarCheckingEnabled]
+__ZN15WebEditorClient25respondToChangedSelectionEv
+-[WebView selectedFrame]
+-[WebView(WebFileInternal) _focusedFrame]
+__Z19containingFrameViewP6NSView
+-[WebHTMLView(WebInternal) _selectionChanged]
+-[WebHTMLView(WebNSTextInputSupport) _updateSelectionForInputManager]
+-[WebClipView additionalClip]
+-[WebBaseNetscapePluginView drawRect:]
+-[WebBaseNetscapePluginView sendUpdateEvent]
+__ZN3WTF6VectorI6CGRectLm16EE6shrinkEm
+__ZN20WebFrameLoaderClient22dispatchDidReceiveIconEv
+-[WebBaseNetscapePluginView sendNullEvent]
+__ZN35WebNetscapePlugInStreamLoaderClient18didReceiveResponseEPN7WebCore26NetscapePlugInStreamLoaderERKNS0_16ResourceResponseE
+-[WebBaseNetscapePluginStream startStreamWithResponse:]
+_WKGetNSURLResponseLastModifiedDate
+-[WebBaseNetscapePluginStream startStreamResponseURL:expectedContentLength:lastModifiedDate:MIMEType:headers:]
+-[WebBaseNetscapePluginStream setResponseURL:]
+-[WebBaseNetscapePluginStream setMIMEType:]
+-[NSURL(WebNSURLExtras) _web_URLCString]
+__ZN35WebNetscapePlugInStreamLoaderClient14didReceiveDataEPN7WebCore26NetscapePlugInStreamLoaderEPKci
+-[WebBaseNetscapePluginStream receivedData:]
+-[WebBaseNetscapePluginStream _deliverData]
+__ZN35WebNetscapePlugInStreamLoaderClient16didFinishLoadingEPN7WebCore26NetscapePlugInStreamLoaderE
+-[WebBaseNetscapePluginStream finishedLoading]
+-[WebBaseNetscapePluginStream _destroyStreamWithReason:]
+-[WebBaseNetscapePluginStream _destroyStream]
+-[WebBaseNetscapePluginView disconnectStream:]
+-[WebNetscapePluginStream dealloc]
+__ZN35WebNetscapePlugInStreamLoaderClientD1Ev
+-[WebBaseNetscapePluginStream dealloc]
+__ZN20WebFrameLoaderClient14cancelledErrorERKN7WebCore15ResourceRequestE
++[NSError(WebKitExtras) _webKitErrorWithDomain:code:URL:]
++[NSError(WebKitExtras) _registerWebKitErrors]
+_registerErrors
++[NSError(WebKitExtras) _webkit_addErrorsWithCodesAndDescriptions:inDomain:]
++[NSError(WebKitExtras) _webkit_errorWithDomain:code:URL:]
+-[NSError(WebKitExtras) _webkit_initWithDomain:code:URL:]
+__ZN20WebFrameLoaderClient20setMainDocumentErrorEPN7WebCore14DocumentLoaderERKNS0_13ResourceErrorE
+-[WebDataSource(WebInternal) _setMainDocumentError:]
+__ZN20WebFrameLoaderClient24cancelPendingArchiveLoadEPN7WebCore14ResourceLoaderE
+__ZN15WebEditorClient22textFieldDidEndEditingEPN7WebCore7ElementE
+__Z16CallFormDelegateP7WebViewP13objc_selectorP11objc_objectS4_
+-[WebView hostWindow]
+-[WebBaseNetscapePluginView stop]
+-[WebBaseNetscapePluginView(Internal) _destroyPlugin]
+-[WebNetscapePluginPackage close]
+-[WebBaseNetscapePluginView removeKeyEventHandler]
+-[WebHTMLView willRemoveSubview:]
+-[WebBaseNetscapePluginView dealloc]
+-[WebBaseNetscapePluginView fini]
+-[WebHTMLView dealloc]
+-[WebHTMLView(WebPrivate) close]
+-[WebHTMLView(WebPrivate) _clearLastHitViewIfSelf]
+-[WebPluginController destroyAllPlugins]
+-[WebPluginController _cancelOutstandingChecks]
+-[WebHTMLViewPrivate clear]
+-[WebPluginController dealloc]
+-[WebHTMLRepresentation dealloc]
+-[WebHTMLRepresentationPrivate dealloc]
+-[WebHTMLViewPrivate dealloc]
+__ZN20WebFrameLoaderClient11createFrameERKN7WebCore4KURLERKNS0_6StringEPNS0_21HTMLFrameOwnerElementES6_bii
+-[WebFrameBridge createChildFrameNamed:withURL:referrer:ownerElement:allowsScrolling:marginWidth:marginHeight:]
+-[WebFrameView setAllowsScrolling:]
+-[WebDynamicScrollBarsView setAllowsScrolling:]
+-[WebFrameView(WebInternal) _setMarginWidth:]
+-[WebFrameView(WebInternal) _setMarginHeight:]
+-[WebFrameBridge initSubframeWithOwnerElement:frameName:frameView:]
+-[WebFrame(WebInternal) _addChild:]
+-[WebFrame(WebInternal) _loadURL:referrer:intoChild:]
+-[WebFrame name]
+-[WebDataSource(WebInternal) _popSubframeArchiveWithName:]
+-[WebFrame parentFrame]
+_WKGetFontInLanguageForRange
+_WKDrawFocusRing
+__Z41_updateFocusedAndActiveStateTimerCallbackP16__CFRunLoopTimerPv
+-[WebHTMLView(WebHTMLViewFileInternal) _frameView]
+-[WebHTMLView keyDown:]
+__ZN15WebEditorClient24handleInputMethodKeydownEPN7WebCore13KeyboardEventE
+-[WebHTMLView(WebInternal) _interceptEditingKeyEvent:shouldSaveCommand:]
+-[WebHTMLView(WebNSTextInputSupport) hasMarkedText]
+-[WebHTMLView(WebNSTextInputSupport) insertText:]
+__ZN3WTF6VectorIN7WebCore15KeypressCommandELm0EE14expandCapacityEmPKS2_
+__ZN3WTF6VectorIN7WebCore15KeypressCommandELm0EE14expandCapacityEm
+__ZN3WTF6VectorIN7WebCore15KeypressCommandELm0EE15reserveCapacityEm
+__ZN15WebEditorClient27doTextFieldCommandFromEventEPN7WebCore7ElementEPNS0_13KeyboardEventE
+__ZN15WebEditorClient19handleKeyboardEventEPN7WebCore13KeyboardEventE
+-[WebHTMLView coreCommandBySelector:]
+__ZN15WebEditorClient16shouldInsertTextEN7WebCore6StringEPNS0_5RangeENS0_18EditorInsertActionE
+-[WebView(WebPrivate) _editingDelegateForwarder]
++[WebDefaultEditingDelegate sharedEditingDelegate]
+__Z3kitN7WebCore18EditorInsertActionE
+__Z3kitPN7WebCore5RangeE
+-[WebDefaultEditingDelegate webView:shouldInsertText:replacingDOMRange:givenAction:]
+__ZN15WebEditorClient24textFieldDidBeginEditingEPN7WebCore7ElementE
+-[WebHTMLRepresentation formForElement:]
+-[WebHTMLRepresentation controlsInForm:]
+-[WebHTMLRepresentation elementIsPassword:]
+-[WebHTMLRepresentation elementDoesAutoComplete:]
+__ZN15WebEditorClient24textDidChangeInTextFieldEPN7WebCore7ElementE
+-[DOMDocument(WebDOMDocumentOperations) webFrame]
+-[DOMNode(WebDOMNodeOperations) _bridge]
+__ZN15WebEditorClient25shouldChangeSelectedRangeEPN7WebCore5RangeES2_NS0_9EAffinityEb
+-[WebView(WebViewEditing) _shouldChangeSelectedDOMRange:toDOMRange:affinity:stillSelecting:]
+-[WebDefaultEditingDelegate webView:shouldChangeSelectedDOMRange:toDOMRange:affinity:stillSelecting:]
+__ZN15WebEditorClient22registerCommandForUndoEN3WTF10PassRefPtrIN7WebCore11EditCommandEEE
+__ZN15WebEditorClient28registerCommandForUndoOrRedoEN3WTF10PassRefPtrIN7WebCore11EditCommandEEEb
+-[WebView(WebViewEditing) undoManager]
++[WebEditCommand initialize]
++[WebEditCommand commandWithEditCommand:]
+-[WebEditCommand initWithEditCommand:]
+__ZN15WebEditorClient24respondToChangedContentsEv
+-[WebHTMLView keyUp:]
+__ZN15WebEditorClient21checkSpellingOfStringEPKtiPiS2_
+__ZN15WebEditorClient23spellCheckerDocumentTagEv
+-[WebView(WebViewEditing) spellCheckerDocumentTag]
+-[WebHTMLRepresentation matchLabels:againstElement:]
+-[WebHTMLRepresentation searchForLabels:beforeElement:]
+-[WebHTMLView(WebNSTextInputSupport) doCommandBySelector:]
+-[WebDefaultEditingDelegate webView:doCommandBySelector:]
+__ZN15WebEditorClient17shouldDeleteRangeEPN7WebCore5RangeE
+-[WebDefaultEditingDelegate webView:shouldDeleteDOMRange:]
+__ZN15WebEditorClient28textWillBeDeletedInTextFieldEPN7WebCore7ElementE
+__Z32CallFormDelegateReturningBooleanaP7WebViewP13objc_selectorP11objc_objectS2_S4_
+-[WebHistoryItem title]
++[WebHTMLView(WebPrivate) _postFlagsChangedEvent:]
+-[WebHTMLView flagsChanged:]
+-[WebHistory saveToURL:error:]
+-[WebHistoryPrivate saveToURL:error:]
+-[WebHistoryPrivate _saveHistoryGuts:URL:error:]
+-[WebHistoryPrivate arrayRepresentation]
+__ZN3WTF6VectorIiLm0EE15reserveCapacityEm
+__ZSt16__introsort_loopIPiiEvT_S1_T0_
+__ZSt22__final_insertion_sortIPiEvT_S1_
+__ZSt16__insertion_sortIPiEvT_S1_
+-[WebHistoryItem(WebPrivate) dictionaryRepresentation]
+__ZN3WTF6VectorIiLm0EE6shrinkEm
+_WKSetPatternPhaseInUserSpace
+-[WebElementDictionary _domNode]
+__Z3kitPN7WebCore4NodeE
+__ZN20WebFrameLoaderClient22dispatchWillSubmitFormEMN7WebCore11FrameLoaderEFvNS0_12PolicyActionEEN3WTF10PassRefPtrINS0_9FormStateEEE
+-[WebView(WebPrivate) _formDelegate]
+__Z3kitPN7WebCore11HTMLElementE
+__Z16CallFormDelegateP7WebViewP13objc_selectorP11objc_objectS4_S4_S4_S4_
+-[WebHTMLRepresentation elementWithName:inForm:]
+-[WebFramePolicyListener continue]
+__ZN15WebChromeClient5focusEv
+-[WebEditCommand dealloc]
+-[WebFrame(WebPrivate) _isDescendantOfFrame:]
+-[WebHTMLView(WebDocumentInternalProtocols) elementAtPoint:allowShadowContent:]
+-[WebElementDictionary _webFrame]
+-[WebElementDictionary _targetWebFrame]
+-[NSURL(WebNSURLExtras) _webkit_URLByRemovingFragment]
+-[WebHTMLView shouldDelayWindowOrderingForEvent:]
+-[WebHTMLView(WebHTMLViewFileInternal) _hitViewForEvent:]
+-[WebHTMLView _isSelectionEvent:]
+-[WebElementDictionary _isSelected]
+-[WebHTMLView mouseDown:]
+-[WebHTMLView(WebHTMLViewFileInternal) _setMouseDownEvent:]
+-[WebHTMLView mouseUp:]
+__ZN20WebFrameLoaderClient33dispatchWillPerformClientRedirectERKN7WebCore4KURLEdd
+__Z21CallFrameLoadDelegatePFP11objc_objectS0_P13objc_selectorzEP7WebViewS2_S0_dS0_S0_
+__Z12CallDelegatePFP11objc_objectS0_P13objc_selectorzEP7WebViewS0_S2_S0_dS0_S0_
+__ZN20WebFrameLoaderClient31dispatchDidCancelClientRedirectEv
++[WebStringTruncator centerTruncateString:toWidth:]
+__Z15defaultMenuFontv
+-[WebViewFactory pluginSupportsMIMEType:]
+-[WebHTMLView(WebPrivate) addTrackingRect:owner:userData:assumeInside:]
+-[WebHTMLView(WebPrivate) _sendToolTipMouseEntered]
+-[WebHTMLView(WebPrivate) _sendToolTipMouseExited]
+-[WebHTMLView(WebPrivate) removeTrackingRect:]
+-[WebHTMLView mouseDragged:]
+-[WebViewFactory bridgeForView:]
+-[WebBaseNetscapePluginView createPluginScriptableObject]
+-[WebBaseNetscapePluginView isStarted]
+_NPN_MemFree
+-[WebBaseNetscapePluginView mouseEntered:]
+-[WebBaseNetscapePluginView getCarbonEvent:withEvent:]
+_WKConvertNSEventToCarbonEvent
+-[WebBaseNetscapePluginView modifiersForEvent:]
+_NPN_GetURLNotify
+-[WebBaseNetscapePluginView(WebNPPCallbacks) getURLNotify:target:notifyData:]
+-[WebBaseNetscapePluginView(WebNPPCallbacks) requestWithURLCString:]
+-[NSString(WebKitExtras) _web_stringByStrippingReturnCharacters]
+-[WebBaseNetscapePluginView mouseExited:]
+-[WebHTMLView scrollWheel:]
+_WKGetWheelEventDeltas
+-[WebClipView scrollWheel:]
+-[WebDynamicScrollBarsView scrollWheel:]
+-[WebDynamicScrollBarsView allowsVerticalScrolling]
+-[WebHTMLView performKeyEquivalent:]
+-[WebHTMLView _handleStyleKeyEquivalent:]
+-[WebPreferences(WebPrivate) respectStandardStyleKeyEquivalents]
+-[WebBaseNetscapePluginView acceptsFirstResponder]
+-[WebFrameBridge makeFirstResponder:]
+-[WebView(WebPrivate) _pushPerformingProgrammaticFocus]
+-[WebBaseNetscapePluginView becomeFirstResponder]
+-[WebBaseNetscapePluginView installKeyEventHandler]
+-[WebView(WebPrivate) _popPerformingProgrammaticFocus]
+-[WebBaseNetscapePluginView mouseDown:]
+-[WebBaseNetscapePluginView mouseUp:]
+-[WebBaseNetscapePluginView mouseDragged:]
+-[WebBaseNetscapePluginView resignFirstResponder]
+-[WebHTMLView(WebPrivate) _removeTrackingRects:count:]
+-[WebHTMLView(WebPrivate) _addTrackingRect:owner:userData:assumeInside:useTrackingNum:]
+__ZN20WebFrameLoaderClient19detachedFromParent2Ev
+__ZN20WebFrameLoaderClient19detachedFromParent3Ev
+-[WebFrameBridge close]
+__ZN20WebFrameLoaderClient19detachedFromParent4Ev
+-[WebFrameBridge dealloc]
+-[WebFrameBridge fini]
+__ZN20WebFrameLoaderClient20frameLoaderDestroyedEv
+-[WebFrame dealloc]
+-[WebFramePrivate dealloc]
+-[WebFrameView dealloc]
+-[WebFrameViewPrivate dealloc]
+-[WebNetscapePluginStream stop]
+-[WebBaseNetscapePluginStream cancelLoadAndDestroyStreamWithError:]
+-[WebNetscapePluginStream cancelLoadWithError:]
+__ZN35WebNetscapePlugInStreamLoaderClient7didFailEPN7WebCore26NetscapePlugInStreamLoaderERKNS0_13ResourceErrorE
+-[WebBaseNetscapePluginStream destroyStreamWithError:]
++[WebBaseNetscapePluginStream reasonForError:]
+_NPN_GetURL
+-[WebBaseNetscapePluginView(WebNPPCallbacks) getURL:target:]
+-[NSString(WebNSURLExtras) _webkit_stringByReplacingValidPercentEscapes]
+-[WebFrame findFrameNamed:]
+-[WebPluginRequest initWithRequest:frameName:notifyData:sendNotification:didStartFromUserGesture:]
+-[WebBaseNetscapePluginView(WebNPPCallbacks) loadPluginRequest:]
+-[WebPluginRequest request]
+-[WebPluginRequest frameName]
+-[WebBaseNetscapePluginView(WebNPPCallbacks) evaluateJavaScriptPluginRequest:]
+-[WebPluginRequest isCurrentEventUserGesture]
+-[WebPluginRequest sendNotification]
+-[WebPluginRequest dealloc]
+-[WebViewFactory defaultLanguageCode]
+-[WebDynamicScrollBarsView autoforwardsScrollWheelEvents]
+__ZN20WebFrameLoaderClient14shouldFallBackERKN7WebCore13ResourceErrorE
+__ZN20WebFrameLoaderClient30dispatchDidFailProvisionalLoadERKN7WebCore13ResourceErrorE
+-[WebView(WebPrivate) _didFailProvisionalLoadWithError:forFrame:]
+-[WebHistoryItem alternateTitle]
+-[WebHistoryItem setAlternateTitle:]
+-[WebHTMLView(WebPrivate) view:stringForToolTip:point:userData:]
+-[WebHTMLView windowDidResignKey:]
+-[WebHTMLView removeMouseMovedObserver]
+-[WebBaseNetscapePluginView windowResignedKey:]
+-[WebBaseNetscapePluginView windowBecameKey:]
+-[WebView(WebIBActions) goBack:]
+-[WebView goBack]
+__ZNK20WebFrameLoaderClient21shouldGoToHistoryItemEPN7WebCore11HistoryItemE
+-[WebHistoryItem(WebPrivate) URL]
+__ZN20WebFrameLoaderClient16restoreViewStateEv
+-[WebWindowWatcher windowWillClose:]
+-[WebHTMLView needsPanelToBecomeKey]
+-[WebHTMLView acceptsFirstMouse:]
+__ZN20WebFrameLoaderClient50dispatchDidReceiveServerRedirectForProvisionalLoadEv
+__ZN15WebChromeClient19addMessageToConsoleERKN7WebCore6StringEjS3_
+__ZN13WebDragClient28dragSourceActionMaskForPointERKN7WebCore8IntPointE
+-[WebDefaultUIDelegate webView:dragSourceActionMaskForPoint:]
+-[WebFrameBridge willPopupMenu:]
+_WKPopupMenu
+-[WebHTMLView _accessibilityParentForSubview:]
+-[WebHTMLView accessibilityAttributeValue:]
+-[WebClipView _focusRingVisibleRect]
+-[WebFrameBridge window]
+-[WebViewFactory accessibilityHandleFocusChanged]
+_WKAccessibilityHandleFocusChanged
+-[WebViewFactory unregisterUniqueIdForUIElement:]
+_WKUnregisterUniqueIdForElement
+__ZN25WebCachedPagePlatformData5clearEv
+-[WebHTMLView(WebInternal) closeIfNotCurrentView]
+_WKGetFontInLanguageForCharacter
+__ZN20WebFrameLoaderClient35dispatchDidChangeLocationWithinPageEv
+__ZN20WebFrameLoaderClient13didFinishLoadEv
+-[WebView(WebPendingPublic) shouldClose]
+-[WebView _windowWillClose:]
+-[WebView shouldCloseWithWindow]
+-[WebHTMLView windowWillClose:]
+-[WebView(WebPrivate) _isClosed]
+-[WebView close]
+-[WebFrame childFrames]
+-[WebView(WebPrivate) _clearUndoRedoOperations]
+-[WebView(WebPrivate) _close]
+-[WebView(AllWebViews) _removeFromAllWebViewsSet]
+-[WebView(WebPendingPublic) setScriptDebugDelegate:]
+-[WebView(WebPrivate) _detachScriptDebuggerFromAllFrames]
+-[WebView removeDragCaret]
+__ZN15WebEditorClient13pageDestroyedEv
+__ZN18WebInspectorClient18inspectorDestroyedEv
+__ZN20WebContextMenuClient20contextMenuDestroyedEv
+__ZN13WebDragClient23dragControllerDestroyedEv
+__ZN15WebChromeClient15chromeDestroyedEv
+-[WebView preferencesIdentifier]
+-[WebPreferences identifier]
++[WebPreferences(WebPrivate) _removeReferenceForIdentifier:]
+-[WebPreferences(WebPrivate) didRemoveFromWebView]
++[WebView(WebFileInternal) _preferencesRemovedNotification:]
++[WebView(WebFileInternal) _cacheModel]
++[WebView(WebFileInternal) _maxCacheModelInAnyInstance]
+-[WebView dealloc]
+-[WebViewPrivate dealloc]
+__ZN20WebFrameLoaderClient38dispatchDidLoadResourceFromMemoryCacheEPN7WebCore14DocumentLoaderERKNS0_15ResourceRequestERKNS0_16ResourceResponseEi
+__Z24CallResourceLoadDelegatePFP11objc_objectS0_P13objc_selectorzEP7WebViewS2_S0_S0_S0_S0_
+__Z12CallDelegatePFP11objc_objectS0_P13objc_selectorzEP7WebViewS0_S2_S0_S0_S0_S0_
+-[WebViewFactory inputElementAltText]
+__ZN20WebFrameLoaderClient35transitionToCommittedFromCachedPageEPN7WebCore10CachedPageE
+__ZN20WebFrameLoaderClient11forceLayoutEv
+-[WebHTMLView setNeedsToApplyStyles:]
+_WKDrawBezeledTextArea
+__ZN15WebEditorClient23textDidChangeInTextAreaEPN7WebCore7ElementE
+-[WebPreferences setJavaScriptCanOpenWindowsAutomatically:]
+-[NSMutableDictionary(WebNSDictionaryExtras) _webkit_setBool:forKey:]
+__ZN20WebFrameLoaderClient28updateGlobalHistoryForReloadERKN7WebCore4KURLE
+-[WebHistory setLastVisitedTimeInterval:forItem:]
+-[WebHistoryPrivate setLastVisitedTimeInterval:forItem:]
+-[WebDynamicScrollBarsView allowsHorizontalScrolling]
+__ZN15WebChromeClient10windowRectEv
+__ZN15WebChromeClient11scaleFactorEv
+__ZN15WebChromeClient11canRunModalEv
+__ZN20WebFrameLoaderClient19dispatchDidFailLoadERKN7WebCore13ResourceErrorE
+-[WebView(WebPrivate) _didFailLoadWithError:forFrame:]
+__ZN15WebChromeClient12createWindowEPN7WebCore5FrameERKNS0_16FrameLoadRequestERKNS0_14WindowFeaturesE
+__Z14CallUIDelegateP7WebViewP13objc_selectorP11objc_objectS4_
+__Z12CallDelegateP7WebViewP11objc_objectP13objc_selectorS2_S2_
+-[WebBaseNetscapePluginView preferencesHaveChanged:]
+__ZN15WebChromeClient18setToolbarsVisibleEb
+-[WebView becomeFirstResponder]
+-[WebFrameView acceptsFirstResponder]
+__ZN15WebChromeClient19setStatusbarVisibleEb
+__ZN15WebChromeClient20setScrollbarsVisibleEb
+__ZN15WebChromeClient17setMenubarVisibleEb
+__ZN15WebChromeClient12setResizableEb
+__ZN15WebChromeClient8pageRectEv
+__ZN15WebChromeClient13setWindowRectERKN7WebCore9FloatRectE
+__ZN15WebChromeClient4showEv
+-[WebFramePolicyListener invalidate]
+__ZN20WebFrameLoaderClient29interruptForPolicyChangeErrorERKN7WebCore15ResourceRequestE
+-[WebFramePolicyListener ignore]
++[NSObject(WebScripting) isKeyExcludedFromWebScript:]
+-[WebIconDatabase iconURLForURL:]
+-[WebHistoryItem(WebPrivate) RSSFeedReferrer]
+-[WebView(WebIBActions) reload:]
+-[WebFrame reload]
+__ZN15WebChromeClient7unfocusEv
+-[WebDefaultUIDelegate webViewUnfocus:]
+__ZN15WebChromeClient15closeWindowSoonEv
+-[WebView(WebPrivate) _closeWindow]
+-[WebBaseNetscapePluginView windowWillClose:]
+-[WebFrameBridge valueForKey:keys:values:]
+-[NSError(WebKitExtras) _initWithPluginErrorCode:contentURL:pluginPageURL:pluginName:MIMEType:]
+-[WebNullPluginView initWithFrame:error:DOMElement:]
+-[WebNullPluginView viewDidMoveToWindow]
+-[WebNullPluginView reportFailure]
+-[WebFrameBridge getAppletInView:]
+-[WebFrameBridge pollForAppletInView:]
+-[WebNullPluginView dealloc]
+__ZN20WebFrameLoaderClient21fileDoesNotExistErrorERKN7WebCore16ResourceResponseE
+__ZN20WebFrameLoaderClient38dispatchDecidePolicyForNewWindowActionEMN7WebCore11FrameLoaderEFvNS0_12PolicyActionEERKNS0_16NavigationActionERKNS0_15ResourceRequestERKNS0_6StringE
+__ZN20WebFrameLoaderClient18dispatchCreatePageEv
+__ZN20WebFrameLoaderClient12dispatchShowEv
+__ZN3WTF6VectorI6CGRectLm16EE14expandCapacityEm
+__ZN3WTF6VectorI6CGRectLm16EE15reserveCapacityEm
+-[WebViewFactory refreshPlugins:]
+-[WebBackForwardList forwardItem]
+-[WebBackForwardList backItem]
+-[NSString(WebKitExtras) _web_drawAtPoint:font:textColor:]
+_canUseFastRenderer
+-[NSEvent(WebExtras) _web_isOptionTabKeyEvent]
+-[NSString(WebNSURLExtras) _webkit_rangeOfURLScheme]
+-[WebFrame loadAlternateHTMLString:baseURL:forUnreachableURL:]
+-[WebFrame _loadHTMLString:baseURL:unreachableURL:]
+-[WebFrame _loadData:MIMEType:textEncodingName:baseURL:unreachableURL:]
+-[WebBaseNetscapePluginStream _pluginCancelledConnectionError]
+-[WebPluginRequest notifyData]
+__ZNK15WebChromeClient11tabsToLinksEv
+-[WebPreferences tabsToLinks]
+-[WebFrameBridge keyboardUIMode]
+-[WebFrameBridge _retrieveKeyboardUIModeFromPreferences:]
+-[WebFrameBridge _preferences]
+_WKGetMIMETypeForExtension
+-[WebView _pluginForExtension:]
+-[WebPluginDatabase pluginForExtension:]
+-[WebBasePluginPackage extensionEnumerator]
+-[WebBasePluginPackage MIMETypeForExtension:]
+-[WebDataSource(WebPrivate) _mainDocumentError]
+-[WebHTMLView validateUserInterfaceItem:]
+-[WebHTMLView validateUserInterfaceItemWithoutDelegate:]
+__Z3kitN7WebCore8TriStateE
+__Z30CallUIDelegateReturningBooleanaP7WebViewP13objc_selectorP11objc_objecta
+__Z28CallDelegateReturningBooleanaP7WebViewP11objc_objectP13objc_selectorS2_a
+-[WebFrame(WebPrivate) _isDisplayingStandaloneImage]
+-[WebHTMLView(WebPrivate) _hasSelection]
+-[WebHTMLView(WebPrivate) _isEditable]
+-[WebView(WebIBActions) validateUserInterfaceItem:]
+-[WebView(WebIBActions) validateUserInterfaceItemWithoutDelegate:]
+-[WebHTMLView(WebInternal) isGrammarCheckingEnabled]
+-[WebView(WebIBActions) canMakeTextLarger]
+-[WebView(WebFileInternal) _performTextSizingSelector:withObject:onTrackingDocs:selForNonTrackingDocs:newScaleFactor:]
+-[WebFrame(WebInternal) _documentViews]
+-[WebHTMLView(WebTextSizing) _tracksCommonSizeFactor]
+-[WebView(WebIBActions) canMakeTextStandardSize]
+-[WebView(WebIBActions) canMakeTextSmaller]
+-[WebHTMLRepresentation canProvideDocumentSource]
+-[WebView supportsTextEncoding]
+-[WebHTMLView(WebDocumentPrivateProtocols) supportsTextEncoding]
+-[WebView customTextEncodingName]
+-[WebView _mainFrameOverrideEncoding]
+-[WebHistory orderedLastVisitedDays]
+-[WebHistoryPrivate orderedLastVisitedDays]
+-[WebHistory orderedItemsLastVisitedOnDay:]
+-[WebHistoryPrivate orderedItemsLastVisitedOnDay:]
+-[WebHistoryItem icon]
+-[WebView(WebIBActions) goForward:]
+-[WebView goForward]
+__ZN13WebDragClient24declareAndWriteDragImageEP12NSPasteboardP10DOMElementP5NSURLP8NSStringPN7WebCore5FrameE
+__Z14getTopHTMLViewPN7WebCore5FrameE
+-[DOMNode(WebDOMNodeOperations) webArchive]
++[WebArchiver archiveNode:]
++[WebArchiver _archiveWithMarkupString:fromFrame:nodes:]
+-[WebResource initWithData:URL:MIMEType:textEncodingName:frameName:]
+-[WebResource(WebResourcePrivate) _initWithData:URL:MIMEType:textEncodingName:frameName:response:copyData:]
+-[WebResource init]
+-[DOMHTMLImageElement(WebDOMHTMLImageElementOperationsPrivate) _subresourceURLs]
+-[DOMNode(WebDOMNodeOperations) _URLsFromSelectors:]
+-[DOMDocument(WebDOMDocumentOperations) URLWithAttributeString:]
+-[WebDataSource subresourceForURL:]
+-[WebResource(WebResourcePrivate) _initWithData:URL:response:MIMEType:]
+-[WebArchive initWithMainResource:subresources:subframeArchives:]
+-[WebArchive init]
+-[NSPasteboard(WebExtras) _web_declareAndWriteDragImageForElement:URL:title:archive:source:]
++[NSPasteboard(WebExtras) _web_writableTypesForImageIncludingArchive:]
+__Z33_writableTypesForImageWithArchivev
+__Z36_writableTypesForImageWithoutArchivev
++[NSPasteboard(WebExtras) _web_writableTypesForURL]
+-[NSPasteboard(WebExtras) _web_writeImage:element:URL:title:archive:types:source:]
+-[NSPasteboard(WebExtras) _web_writeURL:andTitle:types:]
++[WebURLsWithTitles writeURLs:andTitles:toPasteboard:]
++[WebURLsWithTitles arrayWithIFURLsWithTitlesPboardType]
+__Z16imageFromElementP10DOMElement
+-[WebHTMLView(WebInternal) setPromisedDragTIFFDataSource:]
+__Z18promisedDataClientv
+__ZN7WebCore20CachedResourceClient12imageChangedEPNS_11CachedImageE
+__ZN7WebCore20CachedResourceClient14notifyFinishedEPNS_14CachedResourceE
+-[WebArchive data]
+-[WebArchive _propertyListRepresentation]
+-[WebResource(WebResourcePrivate) _propertyListRepresentation]
++[WebResource(WebResourcePrivate) _propertyListsFromResources:]
+_WKGetPreferredExtensionForMIMEType
+__ZN13WebDragClient27willPerformDragSourceActionEN7WebCore16DragSourceActionERKNS0_8IntPointEPNS0_9ClipboardE
+-[WebDefaultUIDelegate webView:willPerformDragSourceAction:fromPoint:withPasteboard:]
+__ZN13WebDragClient9startDragEN3WTF9RetainPtrI7NSImageEERKN7WebCore8IntPointES7_PNS4_9ClipboardEPNS4_5FrameEb
+-[WebHTMLView(WebInternal) _mouseDownEvent]
+-[WebHTMLView dragImage:at:offset:event:pasteboard:source:slideBack:]
+-[WebHTMLView draggingSourceOperationMaskForLocal:]
+-[WebView _hitTest:dragTypes:]
+-[WebView draggingEntered:]
+-[WebView documentViewAtWindowPoint:]
+-[WebView(WebFileInternal) _frameViewAtWindowPoint:]
+__ZN13WebDragClient17actionMaskForDragEPN7WebCore8DragDataE
+-[WebDefaultUIDelegate webView:dragDestinationActionMaskForDraggingInfo:]
+__ZNK19WebPasteboardHelper25insertablePasteboardTypesEv
+-[WebView draggingUpdated:]
+-[WebView _shouldAutoscrollForDraggingInfo:]
+-[WebHTMLView draggedImage:movedTo:]
+-[WebView draggingExited:]
+-[WebHTMLView draggedImage:endedAt:operation:]
+-[WebArchive dealloc]
+-[WebArchivePrivate dealloc]
+-[WebResource dealloc]
+-[WebResourcePrivate dealloc]
+-[WebView acceptsFirstResponder]
+-[WebHTMLRepresentation receivedError:withDataSource:]
+-[WebFrameBridge imageTitleForFilename:size:]
+-[WebFrameBridge pluginViewWithPackage:attributeNames:attributeValues:baseURL:DOMElement:loadManually:]
+-[WebPluginPackage viewFactory]
++[WebPluginController plugInViewWithArguments:fromPluginPackage:]
+-[WebPluginController webFrame]
+-[WebView(WebPrivate) defersCallbacks]
+-[WebView(WebPrivate) setDefersCallbacks:]
+-[WebPluginController addPlugin:]
++[NSObject(WebScripting) isSelectorExcludedFromWebScript:]
+-[WebPluginController destroyPlugin:]
+-[WebIconDatabase(WebInternal) _applicationWillTerminate:]
++[WebView _applicationWillTerminate]
+-[WebHTMLView(WebPrivate) pasteboard:provideDataForType:]
+-[WebHTMLView(WebInternal) promisedDragTIFFDataSource]
+-[WebArchive initWithData:]
+-[WebArchive _initWithPropertyList:]
+-[WebResource(WebResourcePrivate) _initWithPropertyList:]
++[WebResource(WebResourcePrivate) _resourcesFromPropertyLists:]
+-[NSPasteboard(WebExtras) _web_writePromisedRTFDFromArchive:containsImage:]
+-[WebArchive subresources]
+-[WebArchive mainResource]
+-[WebResource MIMEType]
+-[WebResource(WebResourcePrivate) _fileWrapperRepresentation]
+-[NSPasteboard(WebExtras) _web_writeFileWrapperAsRTFDAttachment:]
++[WebPluginDatabase closeSharedDatabase]
+-[WebPluginDatabase close]
+-[WebPluginDatabase(Internal) _removePlugin:]
++[WebView(WebPrivate) _unregisterViewClassAndRepresentationClassForMIMEType:]
+-[WebBasePluginPackage wasRemovedFromPluginDatabase:]
+-[WebNetscapePluginPackage wasRemovedFromPluginDatabase:]
+-[WebNetscapePluginPackage(Internal) _unloadWithShutdown:]
+___tcf_3
+___tcf_0
+___tcf_2
+_WKDrawBezeledTextFieldCell
+-[WebView(WebPrivate) _UIDelegateForwarder]
++[WebDefaultUIDelegate sharedUIDelegate]
+-[WebClipView resetAdditionalClip]
+-[WebView(WebIBActions) canGoBack]
+-[WebView(WebIBActions) canGoForward]
+-[WebHTMLView(WebPrivate) hitTest:]
++[WebElementDictionary initialize]
+-[WebElementDictionary initWithHitTestResult:]
++[WebElementDictionary initializeLookupTable]
+__Z12addLookupKeyP8NSStringP13objc_selector
+-[WebElementDictionary objectForKey:]
+-[WebElementDictionary dealloc]
+-[WebView(WebPendingPublic) isHoverFeedbackSuspended]
+__ZN15WebChromeClient23mouseDidMoveOverElementERKN7WebCore13HitTestResultEj
+-[WebView(WebPrivate) _mouseDidMoveOverElement:modifierFlags:]
+__Z14CallUIDelegateP7WebViewP13objc_selectorP11objc_objectj
+__Z12CallDelegateP7WebViewP11objc_objectP13objc_selectorS2_j
+-[WebElementDictionary _absoluteLinkURL]
+__ZN15WebChromeClient10setToolTipERKN7WebCore6StringE
+-[WebHTMLView(WebPrivate) _setToolTip:]
+_WKCGContextGetShouldSmoothFonts
+_WKSetCGFontRenderingMode
+__Z29_updateMouseoverTimerCallbackP16__CFRunLoopTimerPv
+-[WebHTMLView(WebPrivate) _updateMouseoverWithFakeEvent]
+-[WebHTMLView(WebPrivate) _updateMouseoverWithEvent:]
+-[WebIconDatabase(WebInternal) _iconForFileURL:withSize:]
+-[WebIconDatabase(WebInternal) _iconsBySplittingRepresentationsOfIcon:]
+-[WebIconDatabase(WebInternal) _iconFromDictionary:forSize:cache:]
+-[WebHTMLView(WebPrivate) _recursiveDisplayRectIfNeededIgnoringOpacity:isVisibleRect:rectIsVisibleRectForView:topView:]
+__ZN20WebFrameLoaderClient29dispatchDidFinishDocumentLoadEv
+__ZN20WebFrameLoaderClient27dispatchDidLoadMainResourceEPN7WebCore14DocumentLoaderE
++[WebScriptDebugServer listenerCount]
+__ZN20WebFrameLoaderClient24dispatchDidFinishLoadingEPN7WebCore14DocumentLoaderEm
+-[WebView(WebViewInternal) _removeObjectForIdentifier:]
+__ZN3WTF9HashTableImSt4pairImNS_9RetainPtrIP11objc_objectEEENS_18PairFirstExtractorIS6_EENS_7IntHashImEENS_14PairHashTraitsINS_10HashTraitsImEENSC_IS5_EEEESD_E4findImNS_22IdentityHashTranslatorImS6_SA_EEEENS_17HashTableIteratorImS6_S8_SA_SF_SD_EERKT_
+__ZN20WebDocumentLoaderMac17decreaseLoadCountEm
+__ZN3WTF9HashTableImmNS_17IdentityExtractorImEENS_7IntHashImEENS_10HashTraitsImEES6_E4findImNS_22IdentityHashTranslatorImmS4_EEEENS_17HashTableIteratorImmS2_S4_S6_S6_EERKT_
++[WebPluginDatabase sharedDatabase]
+-[WebPluginDatabase init]
++[WebPluginDatabase(Internal) _defaultPlugInPaths]
+-[WebPluginDatabase setPlugInPaths:]
+-[WebPluginDatabase refresh]
+-[WebPluginDatabase(Internal) _scanForNewPlugins]
+-[WebPluginDatabase(Internal) _plugInPaths]
++[WebBasePluginPackage initialize]
++[WebBasePluginPackage pluginWithPath:]
+-[WebPluginPackage initWithPath:]
+-[WebBasePluginPackage initWithPath:]
+-[WebBasePluginPackage pathByResolvingSymlinksAndAliasesInPath:]
+-[WebBasePluginPackage dealloc]
++[WebNetscapePluginPackage initialize]
+_WebLMGetCurApRefNum
+_WebLMSetCurApRefNum
+-[WebNetscapePluginPackage initWithPath:]
+-[WebNetscapePluginPackage _initWithPath:]
+-[WebBasePluginPackage getPluginInfoFromBundleAndMIMEDictionary:]
+-[NSArray(WebPluginExtensions) _web_lowercaseStrings]
+-[WebBasePluginPackage setMIMEToExtensionsDictionary:]
+-[WebBasePluginPackage setMIMEToDescriptionDictionary:]
+-[WebBasePluginPackage filename]
+-[WebBasePluginPackage setName:]
+-[WebBasePluginPackage setPluginDescription:]
+-[WebNetscapePluginPackage getPluginInfoFromResources]
+-[WebNetscapePluginPackage openResourceFile]
++[WebBasePluginPackage preferredLocalizationName]
+-[WebPluginPackage load]
+__Z13webGetNSImagePN7WebCore5ImageE7_NSSize
++[NSNotificationCenter(WebNSNotificationCenterExtras) _postNotificationName:]
+-[NSView(WebExtras) _web_dragShouldBeginFromMouseDown:withExpiration:]
+-[NSString(WebNSURLExtras) _web_isUserVisibleURL]
+-[NSString(WebNSURLExtras) _webkit_looksLikeAbsoluteURL]
+-[WebHistoryItem(WebPrivate) visitCount]
+-[WebDynamicScrollBarsView setAllowsHorizontalScrolling:]
+-[WebView(WebViewInternal) _dispatchDidReceiveIconFromWebFrame:]
+__ZNK19WebPasteboardHelper17urlFromPasteboardEPK12NSPasteboardPN7WebCore6StringE
+-[NSPasteboard(WebExtras) _web_bestURL]
++[WebURLsWithTitles URLsFromPasteboard:]
++[WebView(WebPrivate) canShowFile:]
++[WebView(WebPrivate) _MIMETypeForFile:]
+-[WebIconDatabase releaseIconForURL:]
+-[NSView(WebExtras) _web_dragOperationForDraggingInfo:]
+-[WebHistory removeAllItems]
+-[WebHistoryPrivate removeAllItems]
++[WebCache empty]
+-[WebBackForwardList pageCacheSize]
+-[WebBackForwardList setPageCacheSize:]
+-[WebView(WebPrivate) setUsesPageCache:]
+-[WebIconDatabase(WebPendingPublic) removeAllIcons]
+__ZN21WebIconDatabaseClient25dispatchDidRemoveAllIconsEv
+-[WebIconDatabase(WebInternal) _sendDidRemoveAllIconsNotification]
+__ZN21WebIconDatabaseClient13performImportEv
+__Z21importToWebCoreFormatv
++[ThreadEnabler enableThreading]
+__Z20objectFromPathForKeyP8NSStringP11objc_object
+-[ThreadEnabler threadEnablingSelector:]
+-[NSString(WebKitExtras) _webkit_fixedCarbonPOSIXPath]
+-[WebViewFactory pluginsInfo]
+-[WebFrameView keyDown:]
+_NPN_PostURLNotify
+-[WebBaseNetscapePluginView(WebNPPCallbacks) postURLNotify:target:len:buf:file:notifyData:]
+-[WebBaseNetscapePluginView(WebNPPCallbacks) _postURL:target:len:buf:file:notifyData:sendNotification:allowHeaders:]
+-[NSData(PluginExtras) _web_startsWithBlankLine]
+-[NSData(PluginExtras) _web_locationAfterFirstBlankLine]
+-[NSData(WebNSDataExtras) _webkit_parseRFC822HeaderFields]
+-[NSString(WebNSDataExtrasInternal) _web_capitalizeRFC822HeaderFieldName]
+__ZN3WTF6VectorIN7WebCore15FormDataElementELm0EE6shrinkEm
+__ZN3WTF6VectorIcLm0EE6shrinkEm
+-[NSString(WebKitExtras) _web_widthWithFont:]
+-[WebView(WebViewInternal) _receivedIconChangedNotification:]
+-[WebView mainFrameURL]
+-[WebHTMLView menuForEvent:]
+-[WebViewFactory contextMenuItemTagOpenLink]
+-[WebViewFactory contextMenuItemTagOpenLinkInNewWindow]
+-[WebViewFactory contextMenuItemTagDownloadLinkToDisk]
+-[WebViewFactory contextMenuItemTagCopyLinkToClipboard]
+-[WebViewFactory contextMenuItemTagOpenImageInNewWindow]
+-[WebViewFactory contextMenuItemTagDownloadImageToDisk]
+-[WebViewFactory contextMenuItemTagCopyImageToClipboard]
+-[WebViewFactory contextMenuItemTagSearchInSpotlight]
+-[WebViewFactory contextMenuItemTagLookUpInDictionary]
+-[WebViewFactory contextMenuItemTagSearchWeb]
+-[WebViewFactory contextMenuItemTagCopy]
+-[WebViewFactory contextMenuItemTagGoBack]
+-[WebViewFactory contextMenuItemTagGoForward]
+-[WebViewFactory contextMenuItemTagStop]
+-[WebViewFactory contextMenuItemTagReload]
+-[WebViewFactory contextMenuItemTagOpenFrameInNewWindow]
+-[WebViewFactory contextMenuItemTagNoGuessesFound]
+-[WebViewFactory contextMenuItemTagIgnoreSpelling]
+-[WebViewFactory contextMenuItemTagLearnSpelling]
+-[WebViewFactory contextMenuItemTagIgnoreGrammar]
+-[WebViewFactory contextMenuItemTagCut]
+-[WebViewFactory contextMenuItemTagPaste]
+__ZN20WebContextMenuClient29getCustomMenuFromDefaultItemsEPN7WebCore11ContextMenuE
+__Z19isPreVersion3Clientv
+__Z28isPreInspectElementTagClientv
+-[WebDataSource(WebPrivate) _fileWrapperForURL:]
+-[WebView(WebPrivate) _cachedResponseForURL:]
+-[NSMutableURLRequest(WebNSURLRequestExtras) _web_setHTTPUserAgent:]
+-[WebElementDictionary _absoluteImageURL]
+-[WebElementDictionary _image]
+-[WebElementDictionary _titleDisplayString]
+__Z13NSStringOrNilN7WebCore6StringE
+-[WebElementDictionary _textContent]
+__ZNK20WebFrameLoaderClient29generatedMIMETypeForURLSchemeERKN7WebCore6StringE
+-[WebHistory removeItems:]
+-[WebHistoryPrivate removeItems:]
+-[WebHistoryPrivate removeItem:]
+-[NSView(WebExtras) _web_parentWebFrameView]
+-[WebHTMLView validRequestorForSendType:returnType:]
+-[WebHTMLView(WebDocumentPrivateProtocols) pasteboardTypesForSelection]
+-[WebHTMLView(WebInternal) _canSmartCopyOrDelete]
+-[WebView(WebViewEditing) smartInsertDeleteEnabled]
+-[WebBackForwardList containsItem:]
+__Z4coreP14WebHistoryItem
+-[WebView goToBackForwardItem:]
+-[WebFrame(WebInternal) _findFrameWithSelection]
+-[WebFrame(WebInternal) _hasSelection]
+-[WebView(WebIBActions) stopLoading:]
+-[WebFrame stopLoading]
+-[NSURL(WebNSURLExtras) _web_URLWithLowercasedScheme]
++[NSPasteboard(WebExtras) _web_setFindPasteboardString:withOwner:]
+-[WebView(WebPendingPublic) searchFor:direction:caseSensitive:wrap:startInSelection:]
+-[WebView(WebFileInternal) _selectedOrMainFrame]
+__Z14incrementFrameP8WebFrameaa
+-[WebHistory _itemForURLString:]
+-[WebView(WebPendingPublic) canMarkAllTextMatches]
+-[WebHistoryItem(WebPrivate) _lastVisitedDate]
+-[WebView prepareForDragOperation:]
+-[WebView performDragOperation:]
+__ZN13WebDragClient32willPerformDragDestinationActionEN7WebCore21DragDestinationActionEPNS0_8DragDataE
+-[WebDefaultUIDelegate webView:willPerformDragDestinationAction:forDraggingInfo:]
+-[NSString(WebKitExtras) _webkit_filenameByFixingIllegalCharacters]
+-[WebIconDatabase(WebInternal) _scaleIcon:toSize:]
+-[WebPDFRepresentation setDataSource:]
+-[WebPDFView initWithFrame:]
++[WebPDFView(FileInternal) _PDFPreviewViewClass]
++[WebPDFView PDFKitBundle]
+-[PDFPrefUpdatingProxy initWithView:]
+-[WebPDFView setNextKeyView:]
+-[WebPDFView viewWillMoveToWindow:]
+-[WebPDFView viewDidMoveToWindow]
+-[WebPDFView(FileInternal) _trackFirstResponder]
+-[WebPDFView(FileInternal) _clipViewForPDFDocumentView]
+-[WebPDFView becomeFirstResponder]
+-[WebPDFView setDataSource:]
+-[WebPDFView setNeedsLayout:]
+-[WebPDFView layout]
+-[WebPDFRepresentation title]
+-[WebPDFView acceptsFirstResponder]
+-[WebFrame(WebInternal) _clearSelectionInOtherFrames]
+-[WebPDFView selectedString]
+-[WebPDFRepresentation receivedData:withDataSource:]
+-[WebPDFView dataSourceUpdated:]
+-[WebPDFRepresentation finishedLoadingWithDataSource:]
+-[WebDataSource data]
++[WebPDFRepresentation PDFDocumentClass]
+-[WebPDFView setPDFDocument:]
+-[WebPDFView(FileInternal) _scaleOrDisplayModeOrPageChanged:]
+-[WebPDFView(FileInternal) _applyPDFDefaults]
+-[WebPreferences(WebPrivate) PDFScaleFactor]
+-[WebPreferences _floatValueForKey:]
+-[WebPreferences(WebPrivate) PDFDisplayMode]
+-[WebPDFView hitTest:]
+-[WebPDFView string]
+-[WebPDFView(FileInternal) _PDFDocumentViewMightHaveScrolled:]
+-[NSView(WebExtras) _webView]
+-[WebPDFView(FileInternal) _updatePreferencesSoon]
+-[WebPDFView(FileInternal) _updatePreferences:]
+-[WebPreferences(WebPrivate) setPDFScaleFactor:]
+-[WebPreferences _setFloatValue:forKey:]
+-[NSMutableDictionary(WebNSDictionaryExtras) _webkit_setFloat:forKey:]
+-[WebPreferences(WebPrivate) setPDFDisplayMode:]
+-[WebPreferences _setIntegerValue:forKey:]
+-[WebPDFView PDFViewSavePDFToDownloadFolder:]
+__Z14CallUIDelegateP7WebViewP13objc_selectorP11objc_objecta
+__Z12CallDelegateP7WebViewP11objc_objectP13objc_selectorS2_a
+-[NSFileManager(WebNSFileManagerExtras) _webkit_setMetadataURL:referrer:atPath:]
+_WKSetMetadataURL
+-[WebPDFView PDFViewOpenPDFInNativeApplication:]
+-[WebPDFView(FileInternal) _openWithFinder:]
+-[WebPDFView(FileInternal) _path]
+-[WebPDFView(FileInternal) _temporaryPDFDirectoryPath]
+-[WebPDFView menuForEvent:]
+-[WebPDFView(FileInternal) _menuItemsFromPDFKitForEvent:]
+-[NSMutableArray(WebExtras) _webkit_removeUselessMenuItemSeparators]
+-[WebPDFView elementAtPoint:]
+-[WebPDFView(FileInternal) _pointIsInSelection:]
+-[WebView(WebPrivate) _menuForElement:defaultItems:]
+-[WebDefaultUIDelegate(WebContextMenu) webView:contextMenuItemsForElement:defaultMenuItems:]
+-[WebDefaultUIDelegate(WebContextMenu) menuItemWithTag:target:representedObject:]
+-[WebDefaultUIDelegate(WebContextMenu) appendDefaultItems:toArray:]
+-[WebPDFRepresentation canProvideDocumentSource]
+-[WebPDFView(FileInternal) _anyPDFTagsFoundInMenu:]
+-[WebPDFView validateUserInterfaceItem:]
+-[WebPDFView validateUserInterfaceItemWithoutDelegate:]
+-[PDFPrefUpdatingProxy methodSignatureForSelector:]
+-[WebPDFView(FileInternal) _PDFSubview]
+-[PDFPrefUpdatingProxy forwardInvocation:]
+-[WebPDFView viewState]
+-[WebPDFView dealloc]
+-[WebPDFView setViewState:]
+-[NSMutableDictionary(WebNSDictionaryExtras) _webkit_setInt:forKey:]
+-[WebPDFView deselectAll]
+-[WebView(WebPendingPublic) markAllMatchesForText:caseSensitive:highlight:limit:]
+-[WebPDFView setMarkedTextMatchesAreHighlighted:]
+-[WebPDFView markAllMatchesForText:caseSensitive:limit:]
+-[WebPDFView(FileInternal) _nextMatchFor:direction:caseSensitive:wrap:fromSelection:startInSelection:]
+-[WebPDFView(FileInternal) _setTextMatches:]
+-[WebPDFView searchFor:direction:caseSensitive:wrap:startInSelection:]
+-[WebView(WebPendingPublic) unmarkAllTextMatches]
+-[WebPDFView unmarkAllTextMatches]
+-[WebView(WebViewEditingActions) scrollLineDown:]
+-[WebView(WebViewEditingActions) _performResponderOperation:with:]
+-[WebView(WebFileInternal) _responderForResponderOperations]
+-[NSView(WebExtras) _web_firstResponderIsSelfOrDescendantView]
+-[WebPDFView scrollLineDown:]
+-[WebPDFView(FileInternal) _fakeKeyEventWithFunctionKey:]
+-[WebHTMLView namesOfPromisedFilesDroppedAtDestination:]
+-[NSFileManager(WebNSFileManagerExtras) _webkit_pathWithUniqueFilenameForPath:]
+-[WebView _autoscrollForDraggingInfo:timeDelta:]
+-[WebHTMLView(WebPrivate) pasteboardChangedOwner:]
+-[_WebCoreHistoryProvider containsURL:length:]
+-[WebHistory containsItemForURLString:]
+-[WebHistoryPrivate containsItemForURLString:]
+_WKSetUpFontCache
+-[WebHTMLView dataSourceUpdated:]
+__ZN20WebFrameLoaderClient39postProgressEstimateChangedNotificationEv
+__ZN20WebFrameLoaderClient31dispatchDidReceiveContentLengthEPN7WebCore14DocumentLoaderEmi
+__Z24CallResourceLoadDelegatePFP11objc_objectS0_P13objc_selectorzEP7WebViewS2_S0_iS0_
+__Z12CallDelegatePFP11objc_objectS0_P13objc_selectorzEP7WebViewS0_S2_S0_iS0_
+-[WebHTMLRepresentation finishedLoadingWithDataSource:]
+-[WebView(WebViewEditing) isEditable]
+-[WebBaseNetscapePluginView viewWillMoveToHostWindow:]
+-[WebBaseNetscapePluginView viewDidMoveToHostWindow]
+__ZN20WebContextMenuClient11downloadURLERKN7WebCore4KURLE
+-[WebView(WebPrivate) _downloadURL:]
+-[WebDownload _initWithRequest:delegate:directory:]
+-[WebDownload _setRealDelegate:]
+-[WebDownloadInternal setRealDelegate:]
+-[WebDownload initWithRequest:delegate:]
+-[WebDownload init]
+-[WebDownloadInternal respondsToSelector:]
+-[WebDownloadInternal downloadDidBegin:]
+-[WebDownloadInternal download:didReceiveResponse:]
+-[WebDownloadInternal download:decideDestinationWithSuggestedFilename:]
+-[WebDownloadInternal download:didCreateDestination:]
+-[WebDownloadInternal download:didReceiveDataOfLength:]
+-[WebDownloadInternal downloadDidFinish:]
+-[WebDownload dealloc]
+-[WebDownloadInternal dealloc]
+-[WebFramePolicyListener download]
+__ZN20WebFrameLoaderClient8downloadEPN7WebCore14ResourceHandleERKNS0_15ResourceRequestES5_RKNS0_16ResourceResponseE
+-[WebDownload _initWithLoadingConnection:request:response:delegate:proxy:]
+__ZNK20WebFrameLoaderClient25setOriginalURLForDownloadEP11WebDownloadRKN7WebCore15ResourceRequestE
++[WebStringTruncator widthOfString:font:]
+-[WebBackForwardList backListCount]
+-[WebBackForwardList itemAtIndex:]
+-[NSEvent(WebExtras) _web_isDeleteKeyEvent]
+-[NSEvent(WebExtras) _web_isKeyEvent:]
+-[WebBaseNetscapePluginView keyDown:]
+_WKSendKeyEventToTSM
+__Z15TSMEventHandlerP25OpaqueEventHandlerCallRefP14OpaqueEventRefPv
+-[WebBaseNetscapePluginView keyUp:]
+__ZN20WebFrameLoaderClient22createJavaAppletWidgetERKN7WebCore7IntSizeEPNS0_7ElementERKNS0_4KURLERKN3WTF6VectorINS0_6StringELm0EEESE_
+-[WebFrameBridge viewForJavaAppletWithFrame:attributeNames:attributeValues:baseURL:DOMElement:]
+-[WebPluginController webPlugInContainerShowStatus:]
+-[NSEvent(WebExtras) _web_isEscapeKeyEvent]
+-[WebView(WebIBActions) makeTextSmaller:]
+-[WebHTMLView(WebTextSizing) _makeTextSmaller:]
+-[WebView(WebIBActions) makeTextStandardSize:]
+-[WebHTMLView(WebTextSizing) _makeTextStandardSize:]
+-[WebView(WebIBActions) makeTextLarger:]
+-[WebHTMLView(WebTextSizing) _makeTextLarger:]
+-[WebView initWithCoder:]
+-[WebFrameView initWithCoder:]
+-[WebPreferences initWithCoder:]
++[WebPreferences(WebInternal) _concatenateKeyWithIBCreatorID:]
+-[WebView setPreferences:]
+-[WebPreferences setMinimumFontSize:]
+-[WebHTMLRepresentation documentSource]
+-[WebFrame loadData:MIMEType:textEncodingName:baseURL:]
+-[WebView(WebViewInternal) _userVisibleBundleVersionFromFullVersion:]
+-[WebDefaultPolicyDelegate webView:decidePolicyForNavigationAction:request:frame:decisionListener:]
++[WebPreferences(WebPrivate) _checkLastReferenceForIdentifier:]
+-[WebPreferences dealloc]
+-[WebPreferencesPrivate dealloc]
+-[WebBackForwardList backListWithLimit:]
+__Z15vectorToNSArrayRN3WTF6VectorINS_6RefPtrIN7WebCore11HistoryItemEEELm0EEE
+__ZN3WTF6VectorINS_6RefPtrIN7WebCore11HistoryItemEEELm0EE6shrinkEm
+-[WebHistoryItem(WebPrivate) targetItem]
+-[WebHTMLView(WebDocumentInternalProtocols) setMarkedTextMatchesAreHighlighted:]
+-[WebHTMLView(WebDocumentInternalProtocols) markAllMatchesForText:caseSensitive:limit:]
+-[WebHTMLView(WebDocumentPrivateProtocols) searchFor:direction:caseSensitive:wrap:startInSelection:]
+-[WebHTMLView(WebDocumentInternalProtocols) unmarkAllTextMatches]
+-[WebFrameView(WebPrivate) _contentView]
+-[WebHTMLView(WebDocumentPrivateProtocols) selectionView]
+-[WebView(WebPendingPublic) rectsForTextMatches]
+-[WebHTMLView(WebDocumentInternalProtocols) rectsForTextMatches]
+-[WebHTMLView(WebDocumentPrivateProtocols) selectionRect]
+-[WebHTMLView(WebDocumentPrivateProtocols) selectionTextRects]
+__ZN3WTF6VectorIN7WebCore9FloatRectELm0EE6shrinkEm
+-[WebHTMLView(WebDocumentPrivateProtocols) selectionImageForcingBlackText:]
+-[WebHTMLView(WebDocumentPrivateProtocols) selectedString]
+__Z8hexDigiti
+__ZNK20WebFrameLoaderClient14willUseArchiveEPN7WebCore14ResourceLoaderERKNS0_15ResourceRequestERKNS0_4KURLE
+__ZNK20WebFrameLoaderClient22canUseArchivedResourceEP12NSURLRequest
+-[WebDataSource(WebInternal) _archivedSubresourceForURL:]
++[WebHistoryItem(WebPrivate) _releaseAllPendingPageCaches]
+-[WebView initWithFrame:]
+-[WebView stringByEvaluatingJavaScriptFromString:]
+-[WebFrameView(WebPrivate) _hasScrollBars]
+-[WebFrameView(WebPrivate) _largestChildWithScrollBars]
+__ZN15WebEditorClient17userVisibleStringEP5NSURL
+_WKGetExtensionsForMIMEType
+_WKSetPatternBaseCTM
+-[DOMNode(WebDOMNodeOperations) _subresourceURLs]
+-[DOMHTMLScriptElement(WebDOMHTMLScriptElementOperationsPrivate) _subresourceURLs]
+-[DOMHTMLLinkElement(WebDOMHTMLLinkElementOperationsPrivate) _subresourceURLs]
+-[DOMHTMLBodyElement(WebDOMHTMLBodyElementOperationsPrivate) _subresourceURLs]
+-[DOMHTMLInputElement(WebDOMHTMLInputElementOperationsPrivate) _subresourceURLs]
++[WebView(WebPrivate) _decodeData:]
+-[WebPreferences userStyleSheetLocation]
+-[WebPreferences setUserStyleSheetEnabled:]
+-[WebPreferences(WebPrivate) setDeveloperExtrasEnabled:]
+__ZN18WebInspectorClient19inspectedURLChangedERKN7WebCore6StringE
+__ZNK18WebInspectorClient17updateWindowTitleEv
+-[WebView(WebPrivate) inspector]
+-[WebInspector initWithWebView:]
+-[WebInspector show:]
+__ZN18WebInspectorClient10createPageEv
+-[WebInspectorWindowController initWithInspectedWebView:]
+-[WebInspectorWindowController init]
+-[WebPreferences init]
+-[WebPreferences setLoadsImagesAutomatically:]
+-[WebPreferences(WebPrivate) setAuthorAndUserStylesEnabled:]
+-[WebPreferences setJavaScriptEnabled:]
+-[WebPreferences setAllowsAnimatedImages:]
+-[WebPreferences setPlugInsEnabled:]
+-[WebPreferences setJavaEnabled:]
+-[WebPreferences setTabsToLinks:]
+-[WebPreferences setMinimumLogicalFontSize:]
+-[WebView setDrawsBackground:]
+-[WebView(WebPrivate) setProhibitsMainFrameScrolling:]
+-[WebInspectorWindowController webView]
+-[WebDefaultPolicyDelegate webView:decidePolicyForMIMEType:request:frame:decisionListener:]
+__ZN18WebInspectorClient19localizedStringsURLEv
+__ZN18WebInspectorClient10showWindowEv
+-[WebInspectorWindowController window]
+_WKNSWindowMakeBottomCornersSquare
+-[WebInspectorWindowController showWindow:]
+-[WebDefaultUIDelegate webViewFirstResponder:]
+-[WebDefaultUIDelegate webView:didDrawRect:]
+-[WebInspectorWindowController windowShouldClose:]
+-[WebInspector showConsole:]
+-[WebDefaultUIDelegate webView:makeFirstResponder:]
+__ZN18WebInspectorClient12attachWindowEv
+-[WebInspectorWindowController attach]
+-[WebInspectorWindowController close]
+-[WebInspectorWindowController animationDidEnd:]
+__ZN18WebInspectorClient12detachWindowEv
+-[WebInspectorWindowController detach]
+-[WebView setShouldCloseWithWindow:]
+-[WebFrame globalContext]
+__ZN15WebEditorClient18shouldBeginEditingEPN7WebCore5RangeE
+-[WebDefaultEditingDelegate webView:shouldBeginEditingInDOMRange:]
+__ZN15WebEditorClient15didBeginEditingEv
+__ZN15WebEditorClient25shouldShowDeleteInterfaceEPN7WebCore11HTMLElementE
+-[WebDefaultEditingDelegate webView:shouldShowDeleteInterfaceForElement:]
+-[WebDefaultEditingDelegate undoManagerForWebView:]
+__ZN15WebEditorClient16shouldEndEditingEPN7WebCore5RangeE
+-[WebDefaultEditingDelegate webView:shouldEndEditingInDOMRange:]
+__ZN15WebEditorClient13didEndEditingEv
+-[WebView(WebFileInternal) _isLoading]
+-[WebDefaultUIDelegate webView:didScrollDocumentInFrameView:]
+-[WebFrameBridge setIsSelected:forView:]
+-[WebViewFactory contextMenuItemTagInspectElement]
+__ZN18WebInspectorClient9highlightEPN7WebCore4NodeE
+-[WebInspectorWindowController highlightAndScrollToNode:]
+-[WebInspectorWindowController highlightNode:]
+-[WebNodeHighlight initWithTargetView:]
+-[WebNodeHighlight(FileInternal) _computeHighlightWindowFrame]
+-[WebNodeHighlightView initWithWebNodeHighlight:]
+-[WebNodeHighlightView setFractionFadedIn:]
+-[WebNodeHighlight setDelegate:]
+-[WebNodeHighlight attachHighlight]
+-[WebNodeHighlightView drawRect:]
+-[WebNodeHighlightView(FileInternal) _holes]
+-[WebNodeHighlight highlightedNode]
+-[WebNodeHighlight targetView]
+-[NSView(WebExtras) _web_convertRect:toView:]
+-[WebNodeHighlight show]
+-[WebNodeHighlightView fractionFadedIn]
+-[WebNodeHighlight setHighlightedNode:]
+-[WebNodeHighlight highlightView]
+-[WebNodeHighlightFadeInAnimation setCurrentProgress:]
+-[WebNodeHighlight(FileInternal) _animateFadeIn:]
+-[WebNodeHighlight animationDidEnd:]
+-[WebNodeHighlight(FileInternal) _repositionHighlightWindow]
+-[WebFrameView _goBack]
+__ZN18WebInspectorClient13hideHighlightEv
+-[WebInspectorWindowController hideHighlight]
+-[WebNodeHighlight hide]
+-[WebInspector webViewClosed]
+__ZN18WebInspectorClient11closeWindowEv
+-[WebNodeHighlight detachHighlight]
+-[WebNodeHighlightView detachFromWebNodeHighlight]
+-[WebNodeHighlight dealloc]
+-[WebInspectorWindowController dealloc]
+-[WebNodeHighlightView dealloc]
+-[WebView customUserAgent]
++[WebCoreStatistics setShouldPrintExceptions:]
++[WebKitStatistics webViewCount]
++[WebKitStatistics frameCount]
++[WebKitStatistics dataSourceCount]
++[WebKitStatistics viewCount]
++[WebKitStatistics HTMLRepresentationCount]
++[WebKitStatistics bridgeCount]
++[WebCoreStatistics javaScriptProtectedGlobalObjectsCount]
++[WebCoreStatistics statistics]
++[WebCache statistics]
++[WebCoreStatistics javaScriptObjectsCount]
++[WebCoreStatistics javaScriptGlobalObjectsCount]
++[WebCoreStatistics javaScriptProtectedObjectsCount]
++[WebCoreStatistics javaScriptProtectedObjectTypeCounts]
++[WebCoreStatistics iconPageURLMappingCount]
++[WebCoreStatistics iconRetainedPageURLCount]
++[WebCoreStatistics iconRecordCount]
++[WebCoreStatistics iconsWithDataCount]
++[WebCoreStatistics garbageCollectJavaScriptObjects]
+-[WebHTMLView(WebPrivate) _hasInsertionPoint]
+-[WebHTMLRepresentation canSaveAsWebArchive]
++[WebView(WebPrivate) suggestedFileExtensionForMIMEType:]
+-[WebHTMLRepresentation DOMDocument]
+-[WebFrameView documentViewShouldHandlePrint]
+-[WebFrameView printOperationWithPrintInfo:]
+-[WebFrameView canPrintHeadersAndFooters]
+-[WebHTMLView canPrintHeadersAndFooters]
+-[WebHTMLView knowsPageRange:]
+-[WebHTMLView _availablePaperWidthForPrintOperation:]
+-[WebHTMLView _setPrinting:minimumPageWidth:maximumPageWidth:adjustViewSize:]
+-[WebView(WebViewPrintingPrivate) _adjustPrintingMarginsForHeaderAndFooter]
+-[NSPrintOperation(WebKitExtras) _web_pageSetupScaleFactor]
+-[WebView(WebViewPrintingPrivate) _headerHeight]
+__Z28CallUIDelegateReturningFloatP7WebViewP13objc_selector
+__Z26CallDelegateReturningFloatP7WebViewP11objc_objectP13objc_selector
+-[WebView(WebViewPrintingPrivate) _footerHeight]
+-[WebHTMLView _scaleFactorForPrintOperation:]
+-[WebHTMLView(WebHTMLViewFileInternal) _calculatePrintHeight]
+-[WebHTMLView _provideTotalScaleFactorForPrintOperation:]
+-[WebHTMLView beginDocument]
+-[WebHTMLView rectForPage:]
+-[WebHTMLView endDocument]
+-[WebHTMLView _endPrintMode]
+-[WebHTMLView drawPageBorderWithSize:]
+-[WebView(WebViewPrintingPrivate) _drawHeaderAndFooter]
+-[WebView(WebViewPrintingPrivate) _drawHeaderInRect:]
+__Z14CallUIDelegateP7WebViewP13objc_selector7_NSRect
+__Z12CallDelegateP7WebViewP11objc_objectP13objc_selector7_NSRect
+-[WebView(WebViewPrintingPrivate) _drawFooterInRect:]
+_NPN_MemAlloc
+-[WebBaseNetscapePluginView fixWindowPort]
+_WKCGContextIsBitmapContext
+_WKCallDrawingNotification
+__ZN20WebFrameLoaderClient41dispatchDidReceiveAuthenticationChallengeEPN7WebCore14DocumentLoaderEmRKNS0_23AuthenticationChallengeE
++[WebPanelAuthenticationHandler sharedHandler]
+-[WebPanelAuthenticationHandler init]
+-[WebPanelAuthenticationHandler startAuthentication:window:]
+-[WebAuthenticationPanel initWithCallback:selector:]
+-[NSMutableDictionary(WebNSDictionaryExtras) _webkit_setObject:forUncopiedKey:]
+-[WebAuthenticationPanel runAsSheetOnWindow:withChallenge:]
+-[WebAuthenticationPanel setUpForChallenge:]
+-[WebAuthenticationPanel loadNib]
+-[NSControl(WebExtras) sizeToFitAndAdjustWindowHeight]
+-[WebAuthenticationPanel logIn:]
+-[WebAuthenticationPanel sheetDidEnd:returnCode:contextInfo:]
+-[WebPanelAuthenticationHandler _authenticationDoneWithChallenge:result:]
+-[WebAuthenticationPanel dealloc]
+-[WebPanelAuthenticationHandler tryNextChallengeForWindow:]
+-[WebDownloadInternal download:shouldDecodeSourceDataOfMIMEType:]
+__ZN20WebFrameLoaderClient20redirectDataToPluginEPN7WebCore6WidgetE
+-[WebFrameBridge redirectDataToPlugin:]
+-[WebHTMLRepresentation _redirectDataToManualLoader:forPluginView:]
+-[WebPluginController pluginView:receivedResponse:]
+-[WebPluginController pluginView:receivedError:]
+-[WebPluginController pluginView:receivedData:]
+__ZN15WebChromeClient12canTakeFocusEN7WebCore14FocusDirectionE
+__ZN15WebChromeClient9takeFocusEN7WebCore14FocusDirectionE
+-[WebView(WebViewInternal) _becomingFirstResponderFromOutside]
+-[WebPluginController _webPluginContainerCheckIfAllowedToLoadRequest:inFrame:resultObject:selector:]
++[WebPluginContainerCheck checkWithRequest:target:resultObject:selector:controller:]
+-[WebPluginContainerCheck initWithRequest:target:resultObject:selector:controller:]
+-[WebPluginContainerCheck start]
+-[WebPluginContainerCheck _isForbiddenFileLoad]
+-[WebPluginController bridge]
+-[WebPluginContainerCheck _askPolicyDelegate]
+-[WebPluginController webView]
+-[WebPluginContainerCheck _actionInformationWithURL:]
+-[WebPolicyDecisionListener _initWithTarget:action:]
+-[WebPolicyDecisionListenerPrivate initWithTarget:action:]
+-[WebPolicyDecisionListener use]
+-[WebPolicyDecisionListener _usePolicy:]
+-[WebPluginContainerCheck _continueWithPolicy:]
+-[WebPluginController _webPluginContainerCancelCheckIfAllowedToLoadRequest:]
+-[WebPluginContainerCheck cancel]
+-[WebPolicyDecisionListener _invalidate]
+-[WebPolicyDecisionListener dealloc]
+-[WebPolicyDecisionListenerPrivate dealloc]
+-[WebPluginContainerCheck dealloc]
+-[WebBaseNetscapePluginView(Internal) _redeliverStream]
+-[WebBaseNetscapePluginView pluginView:receivedResponse:]
+-[WebNetscapePluginStream initWithFrameLoader:]
+-[WebBaseNetscapePluginView pluginView:receivedData:]
+-[WebBaseNetscapePluginStream plugin]
+-[WebBaseNetscapePluginView plugin]
+-[WebBaseNetscapePluginView pluginViewFinishedLoading:]
+__ZN13WebDragClient22createDragImageForLinkERN7WebCore4KURLERKNS0_6StringEPNS0_5FrameE
+-[WebHTMLView(WebPrivate) _dragImageForURL:withLabel:]
+-[NSString(WebKitExtras) _web_drawDoubledAtPoint:withTopColor:bottomColor:font:]
+-[WebViewFactory fileButtonChooseFileLabel]
+-[WebViewFactory fileButtonNoFileSelectedLabel]
+-[WebViewFactory submitButtonDefaultLabel]
+__ZN15WebChromeClient19runJavaScriptPromptEPN7WebCore5FrameERKNS0_6StringES5_RS3_
+__Z14CallUIDelegateP7WebViewP13objc_selectorP11objc_objectS4_S4_
+__Z12CallDelegateP7WebViewP11objc_objectP13objc_selectorS2_S2_S2_
+-[WebJavaScriptTextInputPanel initWithPrompt:text:]
+-[NSWindow(WebExtras) centerOverMainWindow]
+-[WebJavaScriptTextInputPanel pressedOK:]
+-[WebJavaScriptTextInputPanel text]
+__ZN15WebEditorClient26shouldMoveRangeAfterDeleteEPN7WebCore5RangeES2_
+-[WebDefaultEditingDelegate webView:shouldMoveRangeAfterDelete:replacingRange:]
+__ZN15WebChromeClient18runJavaScriptAlertEPN7WebCore5FrameERKNS0_6StringE
+__ZN15WebChromeClient27runBeforeUnloadConfirmPanelERKN7WebCore6StringEPNS0_5FrameE
+__Z30CallUIDelegateReturningBooleanaP7WebViewP13objc_selectorP11objc_objectS4_
+__Z28CallDelegateReturningBooleanaP7WebViewP11objc_objectP13objc_selectorS2_S2_
+__ZN15WebEditorClient34updateSpellingUIWithMisspelledWordERKN7WebCore6StringE
+__ZN15WebEditorClient17getGuessesForWordERKN7WebCore6StringERN3WTF6VectorIS1_Lm0EEE
+__ZN3WTF6VectorIN7WebCore6StringELm0EE14expandCapacityEm
+__ZN3WTF6VectorIN7WebCore6StringELm0EE15reserveCapacityEm
+-[WebViewFactory contextMenuItemTagSpellingMenu]
+-[WebViewFactory contextMenuItemTagShowSpellingPanel:]
+-[WebViewFactory contextMenuItemTagCheckSpelling]
+-[WebViewFactory contextMenuItemTagCheckSpellingWhileTyping]
+-[WebViewFactory contextMenuItemTagCheckGrammarWithSpelling]
+__ZN15WebEditorClient19spellingUIIsShowingEv
+-[WebViewFactory contextMenuItemTagFontMenu]
+-[WebViewFactory contextMenuItemTagShowFonts]
+-[WebViewFactory contextMenuItemTagBold]
+-[WebViewFactory contextMenuItemTagItalic]
+-[WebViewFactory contextMenuItemTagUnderline]
+-[WebViewFactory contextMenuItemTagOutline]
+-[WebViewFactory contextMenuItemTagStyles]
+-[WebViewFactory contextMenuItemTagShowColors]
+-[WebViewFactory contextMenuItemTagSpeechMenu]
+-[WebViewFactory contextMenuItemTagStartSpeaking]
+-[WebViewFactory contextMenuItemTagStopSpeaking]
+-[WebViewFactory contextMenuItemTagWritingDirectionMenu]
+-[WebViewFactory contextMenuItemTagDefaultDirection]
+-[WebViewFactory contextMenuItemTagLeftToRight]
+-[WebViewFactory contextMenuItemTagRightToLeft]
+__ZN15WebEditorClient21toggleGrammarCheckingEv
+-[WebView(WebViewGrammarChecking) toggleGrammarChecking:]
+-[WebView(WebViewGrammarChecking) setGrammarCheckingEnabled:]
+__ZN15WebEditorClient20checkGrammarOfStringEPKtiRN3WTF6VectorIN7WebCore13GrammarDetailELm0EEEPiS8_
+__ZN3WTF6VectorIN7WebCore13GrammarDetailELm0EE14expandCapacityEmPKS2_
+__ZN3WTF6VectorIN7WebCore13GrammarDetailELm0EE14expandCapacityEm
+__ZN3WTF6VectorIN7WebCore13GrammarDetailELm0EE15reserveCapacityEm
+__ZN3WTF6VectorIN7WebCore6StringELm0EEC2ERKS3_
+__ZN3WTF6VectorIN7WebCore6StringELm0EE14expandCapacityEmPKS2_
+__ZN3WTF6VectorIN7WebCore6StringELm0EE6shrinkEm
+-[WebHTMLView selectAll:]
+-[WebHTMLView executeCoreCommandBySelector:]
+-[WebHTMLView callDelegateDoCommandBySelectorIfNeeded:]
+-[WebHTMLView showGuessPanel:]
+-[WebHTMLView ignoreSpelling:]
+-[WebHTMLView checkSpelling:]
+__ZN15WebEditorClient33updateSpellingUIWithGrammarStringERKN7WebCore6StringERKNS0_13GrammarDetailE
+-[WebHTMLView changeSpelling:]
+-[WebHTMLView _changeSpellingToWord:]
+-[WebHTMLView(WebHTMLViewFileInternal) _shouldReplaceSelectionWithText:givenAction:]
+-[WebHTMLView(WebHTMLViewFileInternal) _selectedRange]
+-[WebHTMLView(WebHTMLViewFileInternal) _shouldInsertText:replacingDOMRange:givenAction:]
+-[WebView windowScriptObject]
+-[WebView setCustomTextEncodingName:]
+-[WebPreferences setStandardFontFamily:]
+-[WebPreferences _setStringValue:forKey:]
+-[WebPreferences setDefaultFontSize:]
+-[WebPreferences setDefaultTextEncodingName:]
++[WebDatabaseManager sharedWebDatabaseManager]
+-[WebDatabaseManager origins]
+-[WebFrameBridge runOpenPanelForFileButtonWithResultListener:]
+_WKCreateCustomCFReadStream
+_WKSignalCFReadStreamHasBytes
+_WKSignalCFReadStreamEnd
+-[WebHTMLView copy:]
+__ZN15WebEditorClient24smartInsertDeleteEnabledEv
+__ZN15WebEditorClient33didSetSelectionTypesForPasteboardEv
+-[WebDefaultEditingDelegate webView:didSetSelectionTypesForPasteboard:]
+__ZN15WebEditorClient24dataForArchivedSelectionEPN7WebCore5FrameE
++[WebArchiver archiveSelectionInFrame:]
+-[DOMHTMLTableCellElement(WebDOMHTMLTableCellElementOperationsPrivate) _subresourceURLs]
+-[DOMHTMLTableCellElement(WebDOMHTMLTableCellElementOperationsPrivate) _web_background]
+-[DOMHTMLTableElement(WebDOMHTMLTableElementOperationsPrivate) _subresourceURLs]
+-[DOMHTMLTableElement(WebDOMHTMLTableElementOperationsPrivate) _web_background]
+__ZN15WebEditorClient29didWriteSelectionToPasteboardEv
+-[WebDefaultEditingDelegate webView:didWriteSelectionToPasteboard:]
+-[WebView(WebPendingPublic) setHoverFeedbackSuspended:]
+-[WebHTMLView(WebInternal) _hoverFeedbackSuspendedChanged]
+-[WebView elementAtPoint:]
+-[WebView _elementAtWindowPoint:]
+-[WebHTMLView(WebDocumentInternalProtocols) elementAtPoint:]
++[WebIconDatabase(WebPrivate) _checkIntegrityBeforeOpening]
+-[WebPDFRepresentation receivedError:withDataSource:]
+-[WebViewFactory resetButtonDefaultLabel]
+_NPN_GetJavaEnv
+_NPN_GetJavaPeer
+__ZNK15WebEditorClient7canUndoEv
+__ZN15WebEditorClient4undoEv
+-[WebEditorUndoTarget undoEditing:]
+-[WebEditCommand command]
+__ZN15WebEditorClient22registerCommandForRedoEN3WTF10PassRefPtrIN7WebCore11EditCommandEEE
+__ZN15WebChromeClient5printEPN7WebCore5FrameE
+__ZNK15WebEditorClient7canRedoEv
+__ZN15WebEditorClient4redoEv
+-[WebEditorUndoTarget redoEditing:]
+-[WebFrameBridge customHighlightRect:forLine:representedNode:]
+-[WebHTMLView(WebInternal) _highlighterForType:]
+-[WebFrameBridge paintCustomHighlight:forBox:onLine:behindText:entireLine:representedNode:]
+_WKQTMovieViewSetDrawSynchronously
+-[WebViewFactory searchableIndexIntroduction]
+_WKDrawMediaMuteButton
+_drawMediaImage
+_WKDrawMediaPlayButton
+_WKDrawMediaSliderTrack
+_WKDrawMediaSliderThumb
+_WKDrawMediaSeekBackButton
+_WKDrawMediaSeekForwardButton
+_WKQTMovieMaxTimeLoaded
+__ZN20WebFrameLoaderClient12blockedErrorERKN7WebCore15ResourceRequestE
+__ZN15WebChromeClient21exceededDatabaseQuotaEPN7WebCore5FrameERKNS0_6StringE
+-[WebSecurityOrigin(WebInternal) _initWithWebCoreSecurityOrigin:]
+-[WebSecurityOrigin quota]
+-[WebDatabaseManager detailsForDatabase:withOrigin:]
+-[WebSecurityOrigin(WebInternal) _core]
+-[WebSecurityOrigin setQuota:]
+__ZN24WebDatabaseTrackerClient23dispatchDidModifyOriginEPN7WebCore14SecurityOriginE
+-[WebSecurityOrigin dealloc]
+__ZN24WebDatabaseTrackerClient25dispatchDidModifyDatabaseEPN7WebCore14SecurityOriginERKNS0_6StringE
+_WKReleaseStyleGroup
+-[WebKeyGenerator strengthMenuItemTitles]
+__ZN15WebChromeClient20runJavaScriptConfirmEPN7WebCore5FrameERKNS0_6StringE
+__ZN15WebChromeClient15toolbarsVisibleEv
+__Z30CallUIDelegateReturningBooleanaP7WebViewP13objc_selector
+__Z28CallDelegateReturningBooleanaP7WebViewP11objc_objectP13objc_selector
+__ZN15WebChromeClient14menubarVisibleEv
+__ZN15WebChromeClient17scrollbarsVisibleEv
+-[WebFrameView allowsScrolling]
+-[WebDynamicScrollBarsView allowsScrolling]
+__ZN15WebChromeClient16statusbarVisibleEv
+__ZSt25__unguarded_linear_insertIPiiEvT_T0_
+-[WebFrame(WebInternal) _internalLoadDelegate]
+-[WebFrame(WebInternal) _setInternalLoadDelegate:]
+-[WebBaseNetscapePluginView(WebNPPCallbacks) webFrame:didFinishLoadWithError:]
+-[WebBaseNetscapePluginView(WebNPPCallbacks) webFrame:didFinishLoadWithReason:]
diff --git a/WebKit/mac/WebKitPrefix.h b/WebKit/mac/WebKitPrefix.h
new file mode 100644
index 0000000..73a1048
--- /dev/null
+++ b/WebKit/mac/WebKitPrefix.h
@@ -0,0 +1,83 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifdef __cplusplus
+#define NULL __null
+#else
+#define NULL ((void *)0)
+#endif
+
+#import <stddef.h>
+#import <stdio.h>
+#import <fcntl.h>
+#import <errno.h>
+#import <unistd.h>
+#import <signal.h>
+#import <sys/types.h>
+#import <sys/time.h>
+#import <sys/resource.h>
+
+#import <pthread.h>
+
+#import <CoreGraphics/CoreGraphics.h>
+
+#ifdef __cplusplus
+
+#include <algorithm> // needed for exception_defines.h
+#include <cstddef>
+#include <new>
+
+#endif
+
+#import <ApplicationServices/ApplicationServices.h>
+#import <Carbon/Carbon.h>
+
+#ifdef __OBJC__
+#import <Cocoa/Cocoa.h>
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define BUILDING_ON_TIGER 1
+#endif
+#endif
+
+#include <JavaScriptCore/Platform.h>
+
+#ifdef __LP64__
+#define WTF_USE_NPOBJECT 0
+#else
+#define WTF_USE_NPOBJECT 1
+#endif
+
+#ifdef __cplusplus
+#include <wtf/FastMalloc.h>
+#endif
+
+#include <wtf/DisallowCType.h>
+
+/* Work around bug with C++ library that screws up Objective-C++ when exception support is disabled. */
+#undef try
+#undef catch
diff --git a/WebKit/mac/WebView/WebArchive.h b/WebKit/mac/WebView/WebArchive.h
new file mode 100644
index 0000000..cf54da5
--- /dev/null
+++ b/WebKit/mac/WebView/WebArchive.h
@@ -0,0 +1,97 @@
+/*
+ * Copyright (C) 2004, 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@class WebArchivePrivate;
+@class WebResource;
+
+/*!
+ @const WebArchivePboardType
+ @abstract The pasteboard type constant used when adding or accessing a WebArchive on the pasteboard.
+*/
+extern NSString *WebArchivePboardType;
+
+/*!
+ @class WebArchive
+ @discussion WebArchive represents a main resource as well as all the subresources and subframes associated with the main resource.
+ The main resource can be an entire web page, a portion of a web page, or some other kind of data such as an image.
+ This class can be used for saving standalone web pages, representing portions of a web page on the pasteboard, or any other
+ application where one class is needed to represent rich web content.
+*/
+@interface WebArchive : NSObject <NSCoding, NSCopying>
+{
+ @private
+ WebArchivePrivate *_private;
+}
+
+/*!
+ @method initWithMainResource:subresources:subframeArchives:
+ @abstract The initializer for WebArchive.
+ @param mainResource The main resource of the archive.
+ @param subresources The subresources of the archive (can be nil).
+ @param subframeArchives The archives representing the subframes of the archive (can be nil).
+ @result An initialized WebArchive.
+*/
+- (id)initWithMainResource:(WebResource *)mainResource subresources:(NSArray *)subresources subframeArchives:(NSArray *)subframeArchives;
+
+/*!
+ @method initWithData:
+ @abstract The initializer for creating a WebArchive from data.
+ @param data The data representing the archive. This can be obtained using WebArchive's data method.
+ @result An initialized WebArchive.
+*/
+- (id)initWithData:(NSData *)data;
+
+/*!
+ @method mainResource
+ @result The main resource of the archive.
+*/
+- (WebResource *)mainResource;
+
+/*!
+ @method subresources
+ @result The subresource of the archive (can be nil).
+*/
+- (NSArray *)subresources;
+
+/*!
+ @method subframeArchives
+ @result The archives representing the subframes of the archive (can be nil).
+*/
+- (NSArray *)subframeArchives;
+
+/*!
+ @method data
+ @result The data representation of the archive.
+ @discussion The data returned by this method can be used to save a web archive to a file or to place a web archive on the pasteboard
+ using WebArchivePboardType. To create a WebArchive using the returned data, call initWithData:.
+*/
+- (NSData *)data;
+
+@end
diff --git a/WebKit/mac/WebView/WebArchive.m b/WebKit/mac/WebView/WebArchive.m
new file mode 100644
index 0000000..bb4bd59
--- /dev/null
+++ b/WebKit/mac/WebView/WebArchive.m
@@ -0,0 +1,255 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebArchive.h"
+
+#import "WebKitLogging.h"
+#import "WebResourcePrivate.h"
+#import "WebTypesInternal.h"
+
+NSString *WebArchivePboardType = @"Apple Web Archive pasteboard type";
+
+static NSString * const WebMainResourceKey = @"WebMainResource";
+static NSString * const WebSubresourcesKey = @"WebSubresources";
+static NSString * const WebSubframeArchivesKey = @"WebSubframeArchives";
+
+@interface WebArchivePrivate : NSObject
+{
+ @public
+ WebResource *mainResource;
+ NSArray *subresources;
+ NSArray *subframeArchives;
+}
+@end
+
+@implementation WebArchivePrivate
+
+- (void)dealloc
+{
+ [mainResource release];
+ [subresources release];
+ [subframeArchives release];
+ [super dealloc];
+}
+
+@end
+
+static BOOL isArrayOfClass(id object, Class elementClass)
+{
+ if (![object isKindOfClass:[NSArray class]])
+ return NO;
+ NSArray *array = (NSArray *)object;
+ NSUInteger count = [array count];
+ for (NSUInteger i = 0; i < count; ++i)
+ if (![[array objectAtIndex:i] isKindOfClass:elementClass])
+ return NO;
+ return YES;
+}
+
+@implementation WebArchive
+
+- (id)init
+{
+ self = [super init];
+ if (!self)
+ return nil;
+ _private = [[WebArchivePrivate alloc] init];
+ return self;
+}
+
+- (id)initWithMainResource:(WebResource *)mainResource subresources:(NSArray *)subresources subframeArchives:(NSArray *)subframeArchives
+{
+ self = [self init];
+ if (!self)
+ return nil;
+
+ _private->mainResource = [mainResource retain];
+ _private->subresources = [subresources retain];
+ _private->subframeArchives = [subframeArchives retain];
+
+ if (!_private->mainResource) {
+ [self release];
+ return nil;
+ }
+
+ return self;
+}
+
+- (id)_initWithPropertyList:(id)propertyList
+{
+ self = [self init];
+ if (!self)
+ return nil;
+
+ if (![propertyList isKindOfClass:[NSDictionary class]]) {
+ [self release];
+ return nil;
+ }
+
+ _private->mainResource = [[WebResource alloc] _initWithPropertyList:[propertyList objectForKey:WebMainResourceKey]];
+ if (!_private->mainResource) {
+ [self release];
+ return nil;
+ }
+
+ _private->subresources = [[WebResource _resourcesFromPropertyLists:[propertyList objectForKey:WebSubresourcesKey]] retain];
+
+ NSEnumerator *enumerator = [[propertyList objectForKey:WebSubframeArchivesKey] objectEnumerator];
+ NSMutableArray *subframeArchives = [[NSMutableArray alloc] init];
+ NSDictionary *archivePropertyList;
+ while ((archivePropertyList = [enumerator nextObject]) != nil) {
+ WebArchive *archive = [[WebArchive alloc] _initWithPropertyList:archivePropertyList];
+ if (archive) {
+ [subframeArchives addObject:archive];
+ [archive release];
+ }
+ }
+ _private->subframeArchives = subframeArchives;
+
+ return self;
+}
+
+- (id)initWithData:(NSData *)data
+{
+#if !LOG_DISABLED
+ CFAbsoluteTime start = CFAbsoluteTimeGetCurrent();
+#endif
+ NSDictionary *propertyList = [NSPropertyListSerialization propertyListFromData:data
+ mutabilityOption:NSPropertyListImmutable
+ format:nil
+ errorDescription:nil];
+#if !LOG_DISABLED
+ CFAbsoluteTime end = CFAbsoluteTimeGetCurrent();
+ CFAbsoluteTime duration = end - start;
+#endif
+ LOG(Timing, "Parsing web archive with [NSPropertyListSerialization propertyListFromData::::] took %f seconds", duration);
+
+ return [self _initWithPropertyList:propertyList];
+}
+
+- (id)initWithCoder:(NSCoder *)decoder
+{
+ self = [self init];
+ if (!self)
+ return nil;
+
+ @try {
+ id object = [decoder decodeObjectForKey:WebMainResourceKey];
+ if ([object isKindOfClass:[WebResource class]])
+ _private->mainResource = [object retain];
+ object = [decoder decodeObjectForKey:WebSubresourcesKey];
+ if (isArrayOfClass(object, [WebResource class]))
+ _private->subresources = [object retain];
+ object = [decoder decodeObjectForKey:WebSubframeArchivesKey];
+ if (isArrayOfClass(object, [WebArchive class]))
+ _private->subframeArchives = [object retain];
+ } @catch(id) {
+ [self release];
+ return nil;
+ }
+
+ if (!_private->mainResource) {
+ [self release];
+ return nil;
+ }
+
+ return self;
+}
+
+- (void)encodeWithCoder:(NSCoder *)encoder
+{
+ [encoder encodeObject:_private->mainResource forKey:WebMainResourceKey];
+ [encoder encodeObject:_private->subresources forKey:WebSubresourcesKey];
+ [encoder encodeObject:_private->subframeArchives forKey:WebSubframeArchivesKey];
+}
+
+- (void)dealloc
+{
+ [_private release];
+ [super dealloc];
+}
+
+- (id)copyWithZone:(NSZone *)zone
+{
+ return [self retain];
+}
+
+- (WebResource *)mainResource
+{
+ return [[_private->mainResource retain] autorelease];
+}
+
+- (NSArray *)subresources
+{
+ return [[_private->subresources retain] autorelease];
+}
+
+- (NSArray *)subframeArchives
+{
+ return [[_private->subframeArchives retain] autorelease];
+}
+
+- (NSDictionary *)_propertyListRepresentation
+{
+ NSMutableDictionary *propertyList = [NSMutableDictionary dictionary];
+ if (_private->mainResource) {
+ [propertyList setObject:[_private->mainResource _propertyListRepresentation] forKey:WebMainResourceKey];
+ }
+ NSArray *propertyLists = [WebResource _propertyListsFromResources:_private->subresources];
+ if ([propertyLists count] > 0) {
+ [propertyList setObject:propertyLists forKey:WebSubresourcesKey];
+ }
+ NSEnumerator *enumerator = [_private->subframeArchives objectEnumerator];
+ NSMutableArray *subarchivePropertyLists = [[NSMutableArray alloc] init];
+ WebArchive *archive;
+ while ((archive = [enumerator nextObject]) != nil) {
+ [subarchivePropertyLists addObject:[archive _propertyListRepresentation]];
+ }
+ if ([subarchivePropertyLists count] > 0) {
+ [propertyList setObject:subarchivePropertyLists forKey:WebSubframeArchivesKey];
+ }
+ [subarchivePropertyLists release];
+ return propertyList;
+}
+
+- (NSData *)data
+{
+ NSDictionary *propertyList = [self _propertyListRepresentation];
+#if !LOG_DISABLED
+ CFAbsoluteTime start = CFAbsoluteTimeGetCurrent();
+#endif
+ NSData *data = [NSPropertyListSerialization dataFromPropertyList:propertyList format:NSPropertyListBinaryFormat_v1_0 errorDescription:nil];
+#if !LOG_DISABLED
+ CFAbsoluteTime end = CFAbsoluteTimeGetCurrent();
+ CFAbsoluteTime duration = end - start;
+#endif
+ LOG(Timing, "Serializing web archive with [NSPropertyListSerialization dataFromPropertyList:::] took %f seconds", duration);
+ return data;
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebArchiver.h b/WebKit/mac/WebView/WebArchiver.h
new file mode 100644
index 0000000..c91ce5f
--- /dev/null
+++ b/WebKit/mac/WebView/WebArchiver.h
@@ -0,0 +1,46 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@class DOMNode;
+@class DOMRange;
+@class WebArchive;
+@class WebFrame;
+
+@interface WebArchiver : NSObject
+{
+}
+
++ (WebArchive *)archiveNode:(DOMNode *)node;
++ (WebArchive *)archiveRange:(DOMRange *)range;
++ (WebArchive *)archiveSelectionInFrame:(WebFrame *)frame;
++ (WebArchive *)archiveFrame:(WebFrame *)frame;
++ (WebArchive *)archiveMainResourceForFrame:(WebFrame *)frame;
+
+@end
diff --git a/WebKit/mac/WebView/WebArchiver.mm b/WebKit/mac/WebView/WebArchiver.mm
new file mode 100644
index 0000000..19d5f1c
--- /dev/null
+++ b/WebKit/mac/WebView/WebArchiver.mm
@@ -0,0 +1,189 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebArchiver.h"
+
+#import "WebArchive.h"
+#import "WebDOMOperationsPrivate.h"
+#import "WebDataSource.h"
+#import "WebDocument.h"
+#import "WebFrame.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebResource.h"
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/Frame.h>
+#import <WebCore/SelectionController.h>
+#import <WebKit/DOM.h>
+
+using namespace WebCore;
+
+@implementation WebArchiver
+
++ (NSArray *)_subframeArchivesForFrame:(WebFrame *)frame
+{
+ NSEnumerator *enumerator = [[frame childFrames] objectEnumerator];
+ NSMutableArray *subframeArchives = [NSMutableArray array];
+ WebFrame *childFrame;
+ while ((childFrame = [enumerator nextObject])) {
+ WebArchive *childFrameArchive = [self archiveFrame:childFrame];
+ if (childFrameArchive)
+ [subframeArchives addObject:childFrameArchive];
+ }
+
+ return subframeArchives;
+}
+
++ (WebArchive *)archiveFrame:(WebFrame *)frame;
+{
+ return [[[WebArchive alloc] initWithMainResource:[[frame _dataSource] mainResource]
+ subresources:[[frame _dataSource] subresources]
+ subframeArchives:[self _subframeArchivesForFrame:frame]] autorelease];
+}
+
++ (WebArchive *)archiveMainResourceForFrame:(WebFrame *)frame;
+{
+ return [[[WebArchive alloc] initWithMainResource:[[frame _dataSource] mainResource]
+ subresources:nil
+ subframeArchives:nil] autorelease];
+}
+
++ (WebArchive *)_archiveCurrentStateForFrame:(WebFrame *)frame
+{
+ if ([frame DOMDocument])
+ return [self archiveNode:[frame DOMDocument]];
+
+ return [self archiveFrame:frame];
+}
+
++ (WebArchive *)_archiveWithMarkupString:(NSString *)markupString fromFrame:(WebFrame *)frame nodes:(NSArray *)nodes
+{
+ NSURLResponse *response = [[frame _dataSource] response];
+ NSURL *responseURL = [response URL];
+
+ // it's possible to have a response without a URL here
+ // <rdar://problem/5454935>
+ if (!responseURL)
+ responseURL = [NSURL URLWithString:@""];
+
+ WebResource *mainResource = [[WebResource alloc] initWithData:[markupString dataUsingEncoding:NSUTF8StringEncoding]
+ URL:responseURL
+ MIMEType:[response MIMEType]
+ textEncodingName:@"UTF-8"
+ frameName:[frame name]];
+
+ NSMutableArray *subframeArchives = [[NSMutableArray alloc] init];
+ NSMutableArray *subresources = [[NSMutableArray alloc] init];
+ NSMutableSet *uniqueSubresources = [[NSMutableSet alloc] init];
+ NSEnumerator *enumerator = [nodes objectEnumerator];
+ DOMNode *node;
+ while ((node = [enumerator nextObject]) != nil) {
+ WebFrame *childFrame;
+ if (([node isKindOfClass:[DOMHTMLFrameElement class]] ||
+ [node isKindOfClass:[DOMHTMLIFrameElement class]] ||
+ [node isKindOfClass:[DOMHTMLObjectElement class]]) &&
+ ((childFrame = [(DOMHTMLFrameElement *)node contentFrame]) != nil)) {
+ [subframeArchives addObject:[self _archiveCurrentStateForFrame:childFrame]];
+ } else {
+ NSEnumerator *enumerator = [[node _subresourceURLs] objectEnumerator];
+ NSURL *URL;
+ while ((URL = [enumerator nextObject]) != nil) {
+ if ([uniqueSubresources containsObject:URL])
+ continue;
+ [uniqueSubresources addObject:URL];
+ WebResource *subresource = [[frame _dataSource] subresourceForURL:URL];
+ if (subresource)
+ [subresources addObject:subresource];
+ else
+ // FIXME: should do something better than spew to console here
+ LOG_ERROR("Failed to archive subresource for %@", URL);
+ }
+ }
+ }
+
+ WebArchive *archive = [[[WebArchive alloc] initWithMainResource:mainResource subresources:subresources subframeArchives:subframeArchives] autorelease];
+ [mainResource release];
+ [uniqueSubresources release];
+ [subresources release];
+ [subframeArchives release];
+
+ return archive;
+}
+
++ (WebArchive *)archiveRange:(DOMRange *)range
+{
+ WebFrameBridge *bridge = [range _bridge];
+ WebFrame *frame = [bridge webFrame];
+ NSArray *nodes;
+ NSString *markupString = [bridge markupStringFromRange:range nodes:&nodes];
+ return [self _archiveWithMarkupString:markupString fromFrame:frame nodes:nodes];
+}
+
++ (WebArchive *)archiveNode:(DOMNode *)node
+{
+ WebFrame *frame = [[node ownerDocument] webFrame];
+ WebFrameBridge *bridge = [frame _bridge];
+ NSArray *nodes;
+ NSString *markupString = [bridge markupStringFromNode:node nodes:&nodes];
+ return [self _archiveWithMarkupString:markupString fromFrame:frame nodes:nodes];
+}
+
++ (WebArchive *)archiveSelectionInFrame:(WebFrame *)frame
+{
+ Frame* coreFrame = core(frame);
+ if (!coreFrame)
+ return nil;
+
+ WebFrameBridge *bridge = [frame _bridge];
+ NSArray *nodes;
+ NSString *markupString = [bridge markupStringFromRange:kit(coreFrame->selectionController()->toRange().get()) nodes:&nodes];
+ WebArchive *archive = [self _archiveWithMarkupString:markupString fromFrame:frame nodes:nodes];
+
+ if (coreFrame->isFrameSet()) {
+ // Wrap the frameset document in an iframe so it can be pasted into
+ // another document (which will have a body or frameset of its own).
+
+ NSString *iframeMarkup = [[NSString alloc] initWithFormat:@"<iframe frameborder=\"no\" marginwidth=\"0\" marginheight=\"0\" width=\"98%%\" height=\"98%%\" src=\"%@\"></iframe>", [[[frame _dataSource] response] URL]];
+ WebResource *iframeResource = [[WebResource alloc] initWithData:[iframeMarkup dataUsingEncoding:NSUTF8StringEncoding]
+ URL:blankURL()
+ MIMEType:@"text/html"
+ textEncodingName:@"UTF-8"
+ frameName:nil];
+
+ NSArray *subframeArchives = [NSArray arrayWithObject:archive];
+ archive = [[[WebArchive alloc] initWithMainResource:iframeResource subresources:nil subframeArchives:subframeArchives] autorelease];
+
+ [iframeResource release];
+ [iframeMarkup release];
+ }
+
+ return archive;
+}
+
+@end
+
diff --git a/WebKit/mac/WebView/WebClipView.h b/WebKit/mac/WebView/WebClipView.h
new file mode 100644
index 0000000..76cc50c
--- /dev/null
+++ b/WebKit/mac/WebView/WebClipView.h
@@ -0,0 +1,42 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <AppKit/AppKit.h>
+
+@interface WebClipView : NSClipView
+{
+ BOOL _haveAdditionalClip;
+ NSRect _additionalClip;
+}
+
+- (void)setAdditionalClip:(NSRect)additionalClip;
+- (void)resetAdditionalClip;
+- (BOOL)hasAdditionalClip;
+- (NSRect)additionalClip;
+
+@end
diff --git a/WebKit/mac/WebView/WebClipView.m b/WebKit/mac/WebView/WebClipView.m
new file mode 100644
index 0000000..9231932
--- /dev/null
+++ b/WebKit/mac/WebView/WebClipView.m
@@ -0,0 +1,116 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebClipView.h"
+
+#import <JavaScriptCore/Assertions.h>
+#import <WebKit/WebHTMLView.h>
+#import <WebKit/WebNSViewExtras.h>
+#import <WebKit/WebViewPrivate.h>
+
+// WebClipView's entire reason for existing is to set the clip used by focus ring redrawing.
+// There's no easy way to prevent the focus ring from drawing outside the passed-in clip rectangle
+// because it expects to have to draw outside the bounds of the view it's being drawn for.
+// But it looks for the enclosing clip view, which gives us a hook we can use to control it.
+// The "additional clip" is a clip for focus ring redrawing.
+
+// FIXME: Change terminology from "additional clip" to "focus ring clip".
+
+@interface NSView (WebViewMethod)
+- (WebView *)_webView;
+@end
+
+@implementation WebClipView
+
+- (id)initWithFrame:(NSRect)frame
+{
+ self = [super initWithFrame:frame];
+ if (!self)
+ return nil;
+
+ // In WebHTMLView, we set a clip. This is not typical to do in an
+ // NSView, and while correct for any one invocation of drawRect:,
+ // it causes some bad problems if that clip is cached between calls.
+ // The cached graphics state, which clip views keep around, does
+ // cache the clip in this undesirable way. Consequently, we want to
+ // release the GState for all clip views for all views contained in
+ // a WebHTMLView. Here we do it for subframes, which use WebClipView.
+ // See these bugs for more information:
+ // <rdar://problem/3409315>: REGRESSSION (7B58-7B60)?: Safari draws blank frames on macosx.apple.com perf page
+ [self releaseGState];
+
+ return self;
+}
+
+- (void)resetAdditionalClip
+{
+ ASSERT(_haveAdditionalClip);
+ _haveAdditionalClip = NO;
+}
+
+- (void)setAdditionalClip:(NSRect)additionalClip
+{
+ ASSERT(!_haveAdditionalClip);
+ _haveAdditionalClip = YES;
+ _additionalClip = additionalClip;
+}
+
+- (BOOL)hasAdditionalClip
+{
+ return _haveAdditionalClip;
+}
+
+- (NSRect)additionalClip
+{
+ ASSERT(_haveAdditionalClip);
+ return _additionalClip;
+}
+
+- (NSRect)_focusRingVisibleRect
+{
+ NSRect rect = [self visibleRect];
+ if (_haveAdditionalClip) {
+ rect = NSIntersectionRect(rect, _additionalClip);
+ }
+ return rect;
+}
+
+- (void)scrollWheel:(NSEvent *)event
+{
+ NSView *docView = [self documentView];
+ if ([docView respondsToSelector:@selector(_webView)]) {
+ WebView *wv = [docView _webView];
+ if ([wv _dashboardBehavior:WebDashboardBehaviorAllowWheelScrolling]) {
+ [super scrollWheel:event];
+ }
+ return;
+ }
+ [super scrollWheel:event];
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebDataSource.h b/WebKit/mac/WebView/WebDataSource.h
new file mode 100644
index 0000000..1ffd339
--- /dev/null
+++ b/WebKit/mac/WebView/WebDataSource.h
@@ -0,0 +1,180 @@
+/*
+ * Copyright (C) 2003, 2004, 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+#import <WebKit/WebDocument.h>
+
+@class NSMutableURLRequest;
+@class NSURLConnection;
+@class NSURLRequest;
+@class NSURLResponse;
+@class WebArchive;
+@class WebDataSourcePrivate;
+@class WebFrame;
+@class WebResource;
+
+/*!
+ @class WebDataSource
+ @discussion A WebDataSource represents the data associated with a web page.
+ A datasource has a WebDocumentRepresentation which holds an appropriate
+ representation of the data. WebDataSources manage a hierarchy of WebFrames.
+ WebDataSources are typically related to a view by their containing WebFrame.
+*/
+@interface WebDataSource : NSObject
+{
+@private
+ WebDataSourcePrivate *_private;
+}
+
+/*!
+ @method initWithRequest:
+ @abstract The designated initializer for WebDataSource.
+ @param request The request to use in creating a datasource.
+ @result Returns an initialized WebDataSource.
+*/
+- (id)initWithRequest:(NSURLRequest *)request;
+
+/*!
+ @method data
+ @discussion The data will be incomplete until the datasource has completely loaded.
+ @result Returns the raw data associated with the datasource. Returns nil
+ if the datasource hasn't loaded any data.
+*/
+- (NSData *)data;
+
+/*!
+ @method representation
+ @discussion A representation holds a type specific representation
+ of the datasource's data. The representation class is determined by mapping
+ a MIME type to a class. The representation is created once the MIME type
+ of the datasource content has been determined.
+ @result Returns the representation associated with this datasource.
+ Returns nil if the datasource hasn't created it's representation.
+*/
+- (id <WebDocumentRepresentation>)representation;
+
+/*!
+ @method webFrame
+ @result Return the frame that represents this data source.
+*/
+- (WebFrame *)webFrame;
+
+/*!
+ @method initialRequest
+ @result Returns a reference to the original request that created the
+ datasource. This request will be unmodified by WebKit.
+*/
+- (NSURLRequest *)initialRequest;
+
+/*!
+ @method request
+ @result Returns the request that was used to create this datasource.
+*/
+- (NSMutableURLRequest *)request;
+
+/*!
+ @method response
+ @result returns the WebResourceResponse for the data source.
+*/
+- (NSURLResponse *)response;
+
+/*!
+ @method textEncodingName
+ @result Returns either the override encoding, as set on the WebView for this
+ dataSource or the encoding from the response.
+*/
+- (NSString *)textEncodingName;
+
+/*!
+ @method isLoading
+ @discussion Returns YES if there are any pending loads.
+*/
+- (BOOL)isLoading;
+
+/*!
+ @method pageTitle
+ @result Returns nil or the page title.
+*/
+- (NSString *)pageTitle;
+
+/*!
+ @method unreachableURL
+ @discussion This will be non-nil only for dataSources created by calls to the
+ WebFrame method loadAlternateHTMLString:baseURL:forUnreachableURL:.
+ @result returns the unreachableURL for which this dataSource is showing alternate content, or nil
+*/
+- (NSURL *)unreachableURL;
+
+/*!
+ @method webArchive
+ @result A WebArchive representing the data source, its subresources and child frames.
+ @description This method constructs a WebArchive using the original downloaded data.
+ In the case of HTML, if the current state of the document is preferred, webArchive should be
+ called on the DOM document instead.
+*/
+- (WebArchive *)webArchive;
+
+/*!
+ @method mainResource
+ @result A WebResource representing the data source.
+ @description This method constructs a WebResource using the original downloaded data.
+ This method can be used to construct a WebArchive in case the archive returned by
+ WebDataSource's webArchive isn't sufficient.
+*/
+- (WebResource *)mainResource;
+
+/*!
+ @method subresources
+ @abstract Returns all the subresources associated with the data source.
+ @description The returned array only contains subresources that have fully downloaded.
+*/
+- (NSArray *)subresources;
+
+/*!
+ method subresourceForURL:
+ @abstract Returns a subresource for a given URL.
+ @param URL The URL of the subresource.
+ @description Returns non-nil if the data source has fully downloaded a subresource with the given URL.
+*/
+- (WebResource *)subresourceForURL:(NSURL *)URL;
+
+/*!
+ @method addSubresource:
+ @abstract Adds a subresource to the data source.
+ @param subresource The subresource to be added.
+ @description addSubresource: adds a subresource to the data source's list of subresources.
+ Later, if something causes the data source to load the URL of the subresource, the data source
+ will load the data from the subresource instead of from the network. For example, if one wants to add
+ an image that is already downloaded to a web page, addSubresource: can be called so that the data source
+ uses the downloaded image rather than accessing the network. NOTE: If the data source already has a
+ subresource with the same URL, addSubresource: will replace it.
+*/
+- (void)addSubresource:(WebResource *)subresource;
+
+@end
diff --git a/WebKit/mac/WebView/WebDataSource.mm b/WebKit/mac/WebView/WebDataSource.mm
new file mode 100644
index 0000000..7be4aff
--- /dev/null
+++ b/WebKit/mac/WebView/WebDataSource.mm
@@ -0,0 +1,528 @@
+/*
+ * Copyright (C) 2005, 2006, 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebDataSource.h"
+
+#import "WebArchive.h"
+#import "WebArchiver.h"
+#import "WebDataSourceInternal.h"
+#import "WebDocument.h"
+#import "WebDocumentLoaderMac.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebFrameLoadDelegate.h"
+#import "WebFrameLoaderClient.h"
+#import "WebHTMLRepresentation.h"
+#import "WebKitErrorsPrivate.h"
+#import "WebKitLogging.h"
+#import "WebKitStatisticsPrivate.h"
+#import "WebNSURLExtras.h"
+#import "WebNSURLRequestExtras.h"
+#import "WebPDFRepresentation.h"
+#import "WebResourceLoadDelegate.h"
+#import "WebResourcePrivate.h"
+#import "WebUnarchivingState.h"
+#import "WebViewInternal.h"
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/KURL.h>
+#import <WebCore/MIMETypeRegistry.h>
+#import <WebCore/ResourceRequest.h>
+#import <WebCore/SharedBuffer.h>
+#import <WebCore/WebCoreObjCExtras.h>
+#import <WebCore/WebCoreURLResponse.h>
+#import <WebKit/DOMHTML.h>
+#import <WebKit/DOMPrivate.h>
+
+using namespace WebCore;
+
+@interface WebDataSourcePrivate : NSObject {
+@public
+ WebDocumentLoaderMac* loader;
+
+ id <WebDocumentRepresentation> representation;
+
+ WebUnarchivingState *unarchivingState;
+ BOOL representationFinishedLoading;
+}
+@end
+
+@implementation WebDataSourcePrivate
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
+- (void)dealloc
+{
+ ASSERT(!loader->isLoading());
+ loader->detachDataSource();
+ loader->deref();
+
+ [representation release];
+ [unarchivingState release];
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+
+ ASSERT(!loader->isLoading());
+ loader->detachDataSource();
+ loader->deref();
+
+ [super finalize];
+}
+
+@end
+
+@interface WebDataSource (WebFileInternal)
+@end
+
+@implementation WebDataSource (WebFileInternal)
+
+- (void)_setRepresentation:(id<WebDocumentRepresentation>)representation
+{
+ [_private->representation release];
+ _private->representation = [representation retain];
+ _private->representationFinishedLoading = NO;
+}
+
+static inline void addTypesFromClass(NSMutableDictionary *allTypes, Class objCClass, NSArray *supportTypes)
+{
+ NSEnumerator *enumerator = [supportTypes objectEnumerator];
+ ASSERT(enumerator != nil);
+ NSString *mime = nil;
+ while ((mime = [enumerator nextObject]) != nil) {
+ // Don't clobber previously-registered classes.
+ if ([allTypes objectForKey:mime] == nil)
+ [allTypes setObject:objCClass forKey:mime];
+ }
+}
+
++ (Class)_representationClassForMIMEType:(NSString *)MIMEType
+{
+ Class repClass;
+ return [WebView _viewClass:nil andRepresentationClass:&repClass forMIMEType:MIMEType] ? repClass : nil;
+}
+@end
+
+@implementation WebDataSource (WebPrivate)
+
+- (NSError *)_mainDocumentError
+{
+ return _private->loader->mainDocumentError();
+}
+
+- (void)_addSubframeArchives:(NSArray *)subframeArchives
+{
+ NSEnumerator *enumerator = [subframeArchives objectEnumerator];
+ WebArchive *archive;
+ while ((archive = [enumerator nextObject]) != nil)
+ [self _addToUnarchiveState:archive];
+}
+
+- (NSFileWrapper *)_fileWrapperForURL:(NSURL *)URL
+{
+ if ([URL isFileURL]) {
+ NSString *path = [[URL path] stringByResolvingSymlinksInPath];
+ return [[[NSFileWrapper alloc] initWithPath:path] autorelease];
+ }
+
+ WebResource *resource = [self subresourceForURL:URL];
+ if (resource)
+ return [resource _fileWrapperRepresentation];
+
+ NSCachedURLResponse *cachedResponse = [[self _webView] _cachedResponseForURL:URL];
+ if (cachedResponse) {
+ NSFileWrapper *wrapper = [[[NSFileWrapper alloc] initRegularFileWithContents:[cachedResponse data]] autorelease];
+ [wrapper setPreferredFilename:[[cachedResponse response] suggestedFilename]];
+ return wrapper;
+ }
+
+ return nil;
+}
+
+- (NSString *)_responseMIMEType
+{
+ return [[self response] _webcore_MIMEType];
+}
+
+@end
+
+@implementation WebDataSource (WebInternal)
+
+- (void)_finishedLoading
+{
+ _private->representationFinishedLoading = YES;
+ [[self representation] finishedLoadingWithDataSource:self];
+}
+
+- (void)_receivedData:(NSData *)data
+{
+ // protect self temporarily, as the bridge receivedData call could remove our last ref
+ RetainPtr<WebDataSource*> protect(self);
+
+ [[self representation] receivedData:data withDataSource:self];
+ [[[[self webFrame] frameView] documentView] dataSourceUpdated:self];
+}
+
+- (void)_setMainDocumentError:(NSError *)error
+{
+ if (!_private->representationFinishedLoading) {
+ _private->representationFinishedLoading = YES;
+ [[self representation] receivedError:error withDataSource:self];
+ }
+}
+
+- (void)_clearUnarchivingState
+{
+ [_private->unarchivingState release];
+ _private->unarchivingState = nil;
+}
+
+- (void)_revertToProvisionalState
+{
+ [self _setRepresentation:nil];
+}
+
++ (NSMutableDictionary *)_repTypesAllowImageTypeOmission:(BOOL)allowImageTypeOmission
+{
+ static NSMutableDictionary *repTypes = nil;
+ static BOOL addedImageTypes = NO;
+
+ if (!repTypes) {
+ repTypes = [[NSMutableDictionary alloc] init];
+ addTypesFromClass(repTypes, [WebHTMLRepresentation class], [WebHTMLRepresentation supportedNonImageMIMETypes]);
+
+ // Since this is a "secret default" we don't both registering it.
+ BOOL omitPDFSupport = [[NSUserDefaults standardUserDefaults] boolForKey:@"WebKitOmitPDFSupport"];
+ if (!omitPDFSupport)
+ addTypesFromClass(repTypes, [WebPDFRepresentation class], [WebPDFRepresentation supportedMIMETypes]);
+ }
+
+ if (!addedImageTypes && !allowImageTypeOmission) {
+ addTypesFromClass(repTypes, [WebHTMLRepresentation class], [WebHTMLRepresentation supportedImageMIMETypes]);
+ addedImageTypes = YES;
+ }
+
+ return repTypes;
+}
+
+- (WebResource *)_archivedSubresourceForURL:(NSURL *)URL
+{
+ return [_private->unarchivingState archivedResourceForURL:URL];
+}
+
+- (void)_replaceSelectionWithArchive:(WebArchive *)archive selectReplacement:(BOOL)selectReplacement
+{
+ DOMDocumentFragment *fragment = [self _documentFragmentWithArchive:archive];
+ if (fragment)
+ [[self _bridge] replaceSelectionWithFragment:fragment selectReplacement:selectReplacement smartReplace:NO matchStyle:NO];
+}
+
+- (DOMDocumentFragment *)_documentFragmentWithArchive:(WebArchive *)archive
+{
+ ASSERT(archive);
+ WebResource *mainResource = [archive mainResource];
+ if (mainResource) {
+ NSString *MIMEType = [mainResource MIMEType];
+ if ([WebView canShowMIMETypeAsHTML:MIMEType]) {
+ NSString *markupString = [[NSString alloc] initWithData:[mainResource data] encoding:NSUTF8StringEncoding];
+ // FIXME: seems poor form to do this as a side effect of getting a document fragment
+ [self _addToUnarchiveState:archive];
+ DOMDocumentFragment *fragment = [[self _bridge] documentFragmentWithMarkupString:markupString baseURLString:[[mainResource URL] _web_originalDataAsString]];
+ [markupString release];
+ return fragment;
+ } else if (MIMETypeRegistry::isSupportedImageMIMEType(MIMEType)) {
+ return [self _documentFragmentWithImageResource:mainResource];
+
+ }
+ }
+ return nil;
+}
+
+- (DOMDocumentFragment *)_documentFragmentWithImageResource:(WebResource *)resource
+{
+ DOMElement *imageElement = [self _imageElementWithImageResource:resource];
+ if (!imageElement)
+ return 0;
+ DOMDocumentFragment *fragment = [[[self webFrame] DOMDocument] createDocumentFragment];
+ [fragment appendChild:imageElement];
+ return fragment;
+}
+
+- (DOMElement *)_imageElementWithImageResource:(WebResource *)resource
+{
+ if (!resource)
+ return 0;
+
+ [self addSubresource:resource];
+
+ DOMElement *imageElement = [[[self webFrame] DOMDocument] createElement:@"img"];
+
+ // FIXME: calling _web_originalDataAsString on a file URL returns an absolute path. Workaround this.
+ NSURL *URL = [resource URL];
+ [imageElement setAttribute:@"src" value:[URL isFileURL] ? [URL absoluteString] : [URL _web_originalDataAsString]];
+
+ return imageElement;
+}
+
+// May return nil if not initialized with a URL.
+- (NSURL *)_URL
+{
+ KURL url = _private->loader->url();
+ if (url.isEmpty())
+ return nil;
+ return url;
+}
+
+- (WebArchive *)_popSubframeArchiveWithName:(NSString *)frameName
+{
+ return [_private->unarchivingState popSubframeArchiveWithFrameName:frameName];
+}
+
+- (WebFrameBridge *)_bridge
+{
+ ASSERT(_private->loader->isCommitted());
+ return [[self webFrame] _bridge];
+}
+
+- (WebView *)_webView
+{
+ return [[self webFrame] webView];
+}
+
+- (BOOL)_isDocumentHTML
+{
+ NSString *MIMEType = [self _responseMIMEType];
+ return [WebView canShowMIMETypeAsHTML:MIMEType];
+}
+
+-(void)_makeRepresentation
+{
+ Class repClass = [[self class] _representationClassForMIMEType:[self _responseMIMEType]];
+
+ // Check if the data source was already bound?
+ if (![[self representation] isKindOfClass:repClass]) {
+ id newRep = repClass != nil ? [[repClass alloc] init] : nil;
+ [self _setRepresentation:(id <WebDocumentRepresentation>)newRep];
+ [newRep release];
+ }
+
+ [_private->representation setDataSource:self];
+}
+
+- (void)_addToUnarchiveState:(WebArchive *)archive
+{
+ if (!_private->unarchivingState)
+ _private->unarchivingState = [[WebUnarchivingState alloc] init];
+ [_private->unarchivingState addArchive:archive];
+}
+
+- (DocumentLoader*)_documentLoader
+{
+ return _private->loader;
+}
+
+- (id)_initWithDocumentLoader:(WebDocumentLoaderMac *)loader
+{
+ self = [super init];
+ if (!self)
+ return nil;
+
+ _private = [[WebDataSourcePrivate alloc] init];
+
+ _private->loader = loader;
+ loader->ref();
+
+ LOG(Loading, "creating datasource for %@", static_cast<NSURL *>(_private->loader->request().url()));
+
+ ++WebDataSourceCount;
+
+ return self;
+}
+
+@end
+
+@implementation WebDataSource
+
+- (id)initWithRequest:(NSURLRequest *)request
+{
+ return [self _initWithDocumentLoader:new WebDocumentLoaderMac(request, SubstituteData())];
+}
+
+- (void)dealloc
+{
+ --WebDataSourceCount;
+
+ [_private release];
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ --WebDataSourceCount;
+
+ [super finalize];
+}
+
+- (NSData *)data
+{
+ RefPtr<SharedBuffer> mainResourceData = _private->loader->mainResourceData();
+ if (!mainResourceData)
+ return nil;
+ return [mainResourceData->createNSData() autorelease];
+}
+
+- (id <WebDocumentRepresentation>)representation
+{
+ return _private->representation;
+}
+
+- (WebFrame *)webFrame
+{
+ FrameLoader* frameLoader = _private->loader->frameLoader();
+ if (!frameLoader)
+ return nil;
+ return static_cast<WebFrameLoaderClient*>(frameLoader->client())->webFrame();
+}
+
+- (NSURLRequest *)initialRequest
+{
+ return _private->loader->initialRequest().nsURLRequest();
+}
+
+- (NSMutableURLRequest *)request
+{
+ FrameLoader* frameLoader = _private->loader->frameLoader();
+ if (!frameLoader || !frameLoader->frameHasLoaded())
+ return nil;
+
+ // FIXME: this cast is dubious
+ return (NSMutableURLRequest *)_private->loader->request().nsURLRequest();
+}
+
+- (NSURLResponse *)response
+{
+ return _private->loader->response().nsURLResponse();
+}
+
+- (NSString *)textEncodingName
+{
+ NSString *textEncodingName = _private->loader->overrideEncoding();
+ if (!textEncodingName)
+ textEncodingName = [[self response] textEncodingName];
+ return textEncodingName;
+}
+
+- (BOOL)isLoading
+{
+ return _private->loader->isLoadingInAPISense();
+}
+
+// Returns nil or the page title.
+- (NSString *)pageTitle
+{
+ return [[self representation] title];
+}
+
+- (NSURL *)unreachableURL
+{
+ KURL unreachableURL = _private->loader->unreachableURL();
+ if (unreachableURL.isEmpty())
+ return nil;
+ return unreachableURL;
+}
+
+- (WebArchive *)webArchive
+{
+ // it makes no sense to grab a WebArchive from an uncommitted document.
+ if (!_private->loader->isCommitted())
+ return nil;
+ return [WebArchiver archiveFrame:[self webFrame]];
+}
+
+- (WebResource *)mainResource
+{
+ NSURLResponse *response = [self response];
+ return [[[WebResource alloc] initWithData:[self data]
+ URL:[response URL]
+ MIMEType:[self _responseMIMEType]
+ textEncodingName:[response textEncodingName]
+ frameName:[[self webFrame] name]] autorelease];
+}
+
+- (NSArray *)subresources
+{
+ if (!_private->loader->isCommitted())
+ return [NSMutableArray array];
+
+ NSArray *datas;
+ NSArray *responses;
+ [[self _bridge] getAllResourceDatas:&datas andResponses:&responses];
+ ASSERT([datas count] == [responses count]);
+
+ NSMutableArray *subresources = [[NSMutableArray alloc] initWithCapacity:[datas count]];
+ for (unsigned i = 0; i < [datas count]; ++i) {
+ NSURLResponse *response = [responses objectAtIndex:i];
+ [subresources addObject:[[[WebResource alloc] _initWithData:[datas objectAtIndex:i] URL:[response URL] response:response] autorelease]];
+ }
+
+ return [subresources autorelease];
+}
+
+- (WebResource *)subresourceForURL:(NSURL *)URL
+{
+ if (!_private->loader->isCommitted())
+ return nil;
+
+ NSData *data;
+ NSURLResponse *response;
+ if (![[self _bridge] getData:&data andResponse:&response forURL:[URL _web_originalDataAsString]])
+ return [self _archivedSubresourceForURL:URL];
+
+ return [[[WebResource alloc] _initWithData:data URL:URL response:response] autorelease];
+}
+
+- (void)addSubresource:(WebResource *)subresource
+{
+ if (subresource) {
+ if (!_private->unarchivingState)
+ _private->unarchivingState = [[WebUnarchivingState alloc] init];
+ [_private->unarchivingState addResource:subresource];
+ }
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebDataSourceInternal.h b/WebKit/mac/WebView/WebDataSourceInternal.h
new file mode 100644
index 0000000..94a6fd1
--- /dev/null
+++ b/WebKit/mac/WebView/WebDataSourceInternal.h
@@ -0,0 +1,74 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebDataSourcePrivate.h"
+
+#ifdef __cplusplus
+namespace WebCore {
+ class DocumentLoader;
+}
+typedef WebCore::DocumentLoader WebCoreDocumentLoader;
+class WebDocumentLoaderMac;
+#else
+@class WebCoreDocumentLoader;
+@class WebDocumentLoaderMac;
+#endif
+
+@class DOMDocumentFragment;
+@class DOMElement;
+@class NSError;
+@class NSURL;
+@class WebArchive;
+@class WebFrameBridge;
+@class WebResource;
+@class WebView;
+
+@protocol WebDocumentRepresentation;
+
+@interface WebDataSource (WebInternal)
+- (void)_addToUnarchiveState:(WebArchive *)archive;
+- (void)_makeRepresentation;
+- (BOOL)_isDocumentHTML;
+- (WebView *)_webView;
+- (WebFrameBridge *)_bridge;
+- (WebArchive *)_popSubframeArchiveWithName:(NSString *)frameName;
+- (NSURL *)_URL;
+- (DOMElement *)_imageElementWithImageResource:(WebResource *)resource;
+- (DOMDocumentFragment *)_documentFragmentWithImageResource:(WebResource *)resource;
+- (DOMDocumentFragment *)_documentFragmentWithArchive:(WebArchive *)archive;
++ (NSMutableDictionary *)_repTypesAllowImageTypeOmission:(BOOL)allowImageTypeOmission;
+- (void)_replaceSelectionWithArchive:(WebArchive *)archive selectReplacement:(BOOL)selectReplacement;
+- (WebResource *)_archivedSubresourceForURL:(NSURL *)URL;
+- (id)_initWithDocumentLoader:(WebDocumentLoaderMac*)loader;
+- (void)_finishedLoading;
+- (void)_receivedData:(NSData *)data;
+- (void)_revertToProvisionalState;
+- (void)_setMainDocumentError:(NSError *)error;
+- (void)_clearUnarchivingState;
+- (WebCoreDocumentLoader*)_documentLoader;
+@end
diff --git a/WebKit/mac/WebView/WebDataSourcePrivate.h b/WebKit/mac/WebView/WebDataSourcePrivate.h
new file mode 100644
index 0000000..a394b53
--- /dev/null
+++ b/WebKit/mac/WebView/WebDataSourcePrivate.h
@@ -0,0 +1,40 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebDataSource.h>
+
+@interface WebDataSource (WebPrivate)
+
+- (NSFileWrapper *)_fileWrapperForURL:(NSURL *)URL;
+
+- (void)_addSubframeArchives:(NSArray *) archives;
+
+- (NSError *)_mainDocumentError;
+
+- (NSString *)_responseMIMEType;
+@end
diff --git a/WebKit/mac/WebView/WebDocument.h b/WebKit/mac/WebView/WebDocument.h
new file mode 100644
index 0000000..b18215a
--- /dev/null
+++ b/WebKit/mac/WebView/WebDocument.h
@@ -0,0 +1,209 @@
+/*
+ * Copyright (C) 2003, 2004, 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@class NSError;
+@class WebDataSource;
+
+/*!
+ @protocol WebDocumentView
+ @discussion Protocol implemented by the document view of WebFrameView
+*/
+@protocol WebDocumentView <NSObject>
+
+/*!
+ @method setDataSource:
+ @abstract Called when the corresponding data source has been created.
+ @param dataSource The corresponding data source.
+*/
+- (void)setDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method dataSourceUpdated:
+ @abstract Called when the corresponding data source has received data.
+ @param dataSource The corresponding data source.
+*/
+- (void)dataSourceUpdated:(WebDataSource *)dataSource;
+
+/*!
+ @method setNeedsLayout:
+ @discussion Called when WebKit has determined that the document view needs to layout.
+ This method should simply set a flag and call layout from drawRect if the flag is YES.
+ @param flag YES to cause a layout, no to not cause a layout.
+*/
+- (void)setNeedsLayout:(BOOL)flag;
+
+/*!
+ @method layout
+ @discussion Called when the document view must immediately layout. For simple views,
+ setting the frame is a sufficient implementation of this method.
+*/
+- (void)layout;
+
+/*!
+ @method viewWillMoveToHostWindow:
+ @param hostWindow The host window for the document view.
+ @abstract Called before the host window is set on the parent web view.
+*/
+- (void)viewWillMoveToHostWindow:(NSWindow *)hostWindow;
+
+/*!
+ @method viewDidMoveToHostWindow
+ @abstract Called after the host window is set on the parent web view.
+*/
+- (void)viewDidMoveToHostWindow;
+
+@end
+
+
+/*!
+ @protocol WebDocumentSearching
+ @discussion Optional protocol for searching document view of WebFrameView.
+*/
+@protocol WebDocumentSearching <NSObject>
+/*!
+ @method searchFor:direction:caseSensitive:wrap:
+ @abstract Searches a document view for a string and highlights the string if it is found.
+ @param string The string to search for.
+ @param forward YES to search forward, NO to seach backwards.
+ @param caseFlag YES to for case-sensitive search, NO for case-insensitive search.
+ @param wrapFlag YES to wrap around, NO to avoid wrapping.
+ @result YES if found, NO if not found.
+*/
+- (BOOL)searchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag;
+@end
+
+
+/*!
+ @protocol WebDocumentText
+ @discussion Optional protocol for supporting text operations.
+*/
+@protocol WebDocumentText <NSObject>
+
+/*!
+ @method supportsTextEncoding
+ @result YES if the document view support text encoding, NO if it doesn't.
+*/
+- (BOOL)supportsTextEncoding;
+
+/*!
+ @method string
+ @result String that represents the entire document.
+*/
+- (NSString *)string;
+
+/*!
+ @method attributedString
+ @result Attributed string that represents the entire document.
+*/
+- (NSAttributedString *)attributedString;
+
+/*!
+ @method selectedString
+ @result String that represents the current selection.
+*/
+- (NSString *)selectedString;
+
+/*!
+ @method selectedAttributedString
+ @result Attributed string that represents the current selection.
+*/
+- (NSAttributedString *)selectedAttributedString;
+
+
+/*!
+ @method selectAll
+ @abstract Selects all the text in the document.
+*/
+- (void)selectAll;
+
+/*!
+ @method deselectText
+ @abstract Causes a text selection to lose its selection.
+*/
+- (void)deselectAll;
+
+@end
+
+
+/*!
+ @protocol WebDocumentRepresentation
+ @discussion Protocol implemented by the document representation of a data source.
+*/
+@protocol WebDocumentRepresentation <NSObject>
+/*!
+ @method setDataSource:
+ @abstract Called soon after the document representation is created.
+ @param dataSource The data source that is set.
+*/
+- (void)setDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method receivedData:withDataSource:
+ @abstract Called when the data source has received data.
+ @param data The data that the data source has received.
+ @param dataSource The data source that has received data.
+*/
+- (void)receivedData:(NSData *)data withDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method receivedError:withDataSource:
+ @abstract Called when the data source has received an error.
+ @param error The error that the data source has received.
+ @param dataSource The data source that has received the error.
+*/
+- (void)receivedError:(NSError *)error withDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method finishedLoadingWithDataSource:
+ @abstract Called when the data source has finished loading.
+ @param dataSource The datasource that has finished loading.
+*/
+- (void)finishedLoadingWithDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method canProvideDocumentSource
+ @result Returns true if the representation can provide document source.
+*/
+- (BOOL)canProvideDocumentSource;
+
+/*!
+ @method documentSource
+ @result Returns the textual source representation of the document. For HTML documents
+ this is the original HTML source.
+*/
+- (NSString *)documentSource;
+
+/*!
+ @method title
+ @result Return the title for the document.
+*/
+- (NSString *)title;
+
+@end
diff --git a/WebKit/mac/WebView/WebDocumentInternal.h b/WebKit/mac/WebView/WebDocumentInternal.h
new file mode 100644
index 0000000..81e961a
--- /dev/null
+++ b/WebKit/mac/WebView/WebDocumentInternal.h
@@ -0,0 +1,90 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebDocumentPrivate.h>
+#import <WebKit/WebHTMLView.h>
+
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define WebNSUInteger unsigned int
+#else
+#define WebNSUInteger NSUInteger
+#endif
+
+/*!
+@protocol _WebDocumentTextSizing
+@discussion Optional protocol for making text larger and smaller.
+*/
+@protocol _WebDocumentTextSizing <NSObject>
+
+// Methods to perform the actual commands
+- (IBAction)_makeTextSmaller:(id)sender;
+- (IBAction)_makeTextLarger:(id)sender;
+- (IBAction)_makeTextStandardSize:(id)sender;
+
+// Views that do text sizing come in two flavors. Some will track the common textSizeMultiplier factor stored
+// in the WebView. Others (see PDFView) keep their own scaling factor, but still want to play along loosely
+// with the smaller/larger commands, which in the user model operate across all frames of the WebView.
+- (BOOL)_tracksCommonSizeFactor;
+
+// Views that track the common size factor need to be told when the WebView itself changed the value.
+- (void)_textSizeMultiplierChanged;
+
+// Views that do not track the common size factor must answer for themselves if they are able to zoom in
+// or out. Views that do track it are not sent these messages.
+- (BOOL)_canMakeTextSmaller;
+- (BOOL)_canMakeTextLarger;
+- (BOOL)_canMakeTextStandardSize;
+
+@end
+
+@protocol WebDocumentElement <NSObject>
+- (NSDictionary *)elementAtPoint:(NSPoint)point;
+- (NSDictionary *)elementAtPoint:(NSPoint)point allowShadowContent:(BOOL)allow;
+@end
+
+@protocol WebMultipleTextMatches <NSObject>
+- (void)setMarkedTextMatchesAreHighlighted:(BOOL)newValue;
+- (BOOL)markedTextMatchesAreHighlighted;
+- (WebNSUInteger)markAllMatchesForText:(NSString *)string caseSensitive:(BOOL)caseFlag limit:(WebNSUInteger)limit;
+- (void)unmarkAllTextMatches;
+- (NSArray *)rectsForTextMatches;
+@end
+
+
+/* Used to save and restore state in the view, typically when going back/forward */
+@protocol _WebDocumentViewState <NSObject>
+- (NSPoint)scrollPoint;
+- (void)setScrollPoint:(NSPoint)p;
+- (id)viewState;
+- (void)setViewState:(id)statePList;
+@end
+
+@interface WebHTMLView (WebDocumentInternalProtocols) <WebDocumentElement, WebMultipleTextMatches>
+@end
+
+#undef WebNSUInteger
diff --git a/WebKit/mac/WebView/WebDocumentLoaderMac.h b/WebKit/mac/WebView/WebDocumentLoaderMac.h
new file mode 100644
index 0000000..9acba89
--- /dev/null
+++ b/WebKit/mac/WebView/WebDocumentLoaderMac.h
@@ -0,0 +1,63 @@
+/*
+ * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebCore/DocumentLoader.h>
+#import <wtf/RetainPtr.h>
+#import <wtf/HashSet.h>
+
+@class WebDataSource;
+@class WebView;
+
+namespace WebCore {
+ class ResourceRequest;
+}
+
+class WebDocumentLoaderMac : public WebCore::DocumentLoader {
+public:
+ WebDocumentLoaderMac(const WebCore::ResourceRequest&, const WebCore::SubstituteData&);
+
+ void setDataSource(WebDataSource *, WebView*);
+ void detachDataSource();
+ WebDataSource *dataSource() const;
+
+ virtual void attachToFrame();
+ virtual void detachFromFrame();
+
+ void increaseLoadCount(unsigned long identifier);
+ void decreaseLoadCount(unsigned long identifier);
+
+private:
+ void retainDataSource();
+ void releaseDataSource();
+
+ WebDataSource *m_dataSource;
+ bool m_isDataSourceRetained;
+ RetainPtr<id> m_resourceLoadDelegate;
+ RetainPtr<id> m_downloadDelegate;
+ HashSet<unsigned long> m_loadingResources;
+};
diff --git a/WebKit/mac/WebView/WebDocumentLoaderMac.mm b/WebKit/mac/WebView/WebDocumentLoaderMac.mm
new file mode 100644
index 0000000..d5812a4
--- /dev/null
+++ b/WebKit/mac/WebView/WebDocumentLoaderMac.mm
@@ -0,0 +1,156 @@
+/*
+ * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebDocumentLoaderMac.h"
+
+#import "WebKitVersionChecks.h"
+#import "WebView.h"
+
+using namespace WebCore;
+
+WebDocumentLoaderMac::WebDocumentLoaderMac(const ResourceRequest& request, const SubstituteData& substituteData)
+ : DocumentLoader(request, substituteData)
+ , m_dataSource(nil)
+ , m_isDataSourceRetained(false)
+{
+}
+
+static inline bool needsDataLoadWorkaround(WebView *webView)
+{
+#ifdef BUILDING_ON_TIGER
+ // Tiger has to be a little less efficient.
+ id frameLoadDelegate = [webView frameLoadDelegate];
+ if (!frameLoadDelegate)
+ return false;
+
+ NSString *bundleIdentifier = [[NSBundle bundleForClass:[frameLoadDelegate class]] bundleIdentifier];
+
+ if ([bundleIdentifier isEqualToString:@"com.apple.AppKit"])
+ return true;
+ if ([bundleIdentifier isEqualToString:@"com.adobe.Installers.Setup"])
+ return true;
+ return false;
+#else
+ static bool needsWorkaround = !WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITHOUT_ADOBE_INSTALLER_QUIRK)
+ && [[[NSBundle mainBundle] bundleIdentifier] isEqualToString:@"com.adobe.Installers.Setup"];
+ return needsWorkaround;
+#endif
+}
+
+void WebDocumentLoaderMac::setDataSource(WebDataSource *dataSource, WebView *webView)
+{
+ ASSERT(!m_dataSource);
+ ASSERT(!m_isDataSourceRetained);
+
+ m_dataSource = dataSource;
+ retainDataSource();
+
+ m_resourceLoadDelegate = [webView resourceLoadDelegate];
+ m_downloadDelegate = [webView downloadDelegate];
+
+ // Some clients run the run loop in a way that prevents the data load timer
+ // from firing. We work around that issue here. See <rdar://problem/5266289>
+ // and <rdar://problem/5049509>.
+ if (needsDataLoadWorkaround(webView))
+ m_deferMainResourceDataLoad = false;
+}
+
+WebDataSource *WebDocumentLoaderMac::dataSource() const
+{
+ return m_dataSource;
+}
+
+void WebDocumentLoaderMac::attachToFrame()
+{
+ DocumentLoader::attachToFrame();
+
+ retainDataSource();
+}
+
+void WebDocumentLoaderMac::detachFromFrame()
+{
+ DocumentLoader::detachFromFrame();
+
+ if (m_loadingResources.isEmpty())
+ releaseDataSource();
+
+ // FIXME: What prevents the data source from getting deallocated while the
+ // frame is not attached?
+}
+
+void WebDocumentLoaderMac::increaseLoadCount(unsigned long identifier)
+{
+ ASSERT(m_dataSource);
+
+ if (m_loadingResources.contains(identifier))
+ return;
+ m_loadingResources.add(identifier);
+
+ retainDataSource();
+}
+
+void WebDocumentLoaderMac::decreaseLoadCount(unsigned long identifier)
+{
+ HashSet<unsigned long>::iterator it = m_loadingResources.find(identifier);
+
+ // It is valid for a load to be cancelled before it's started.
+ if (it == m_loadingResources.end())
+ return;
+
+ m_loadingResources.remove(it);
+
+ if (m_loadingResources.isEmpty()) {
+ m_resourceLoadDelegate = 0;
+ m_downloadDelegate = 0;
+ if (!frame())
+ releaseDataSource();
+ }
+}
+
+void WebDocumentLoaderMac::retainDataSource()
+{
+ if (m_isDataSourceRetained || !m_dataSource)
+ return;
+ m_isDataSourceRetained = true;
+ CFRetain(m_dataSource);
+}
+
+void WebDocumentLoaderMac::releaseDataSource()
+{
+ if (!m_isDataSourceRetained)
+ return;
+ ASSERT(m_dataSource);
+ m_isDataSourceRetained = false;
+ CFRelease(m_dataSource);
+}
+
+void WebDocumentLoaderMac::detachDataSource()
+{
+ ASSERT(!m_isDataSourceRetained);
+ m_dataSource = nil;
+}
diff --git a/WebKit/mac/WebView/WebDocumentPrivate.h b/WebKit/mac/WebView/WebDocumentPrivate.h
new file mode 100644
index 0000000..f09d3bd
--- /dev/null
+++ b/WebKit/mac/WebView/WebDocumentPrivate.h
@@ -0,0 +1,82 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebDocument.h>
+#import <WebKit/WebHTMLView.h>
+
+@class DOMDocument;
+
+@protocol WebDocumentImage <NSObject>
+- (NSImage *)image;
+@end
+
+// This method is deprecated as it now lives on WebFrame.
+@protocol WebDocumentDOM <NSObject>
+- (DOMDocument *)DOMDocument;
+- (BOOL)canSaveAsWebArchive;
+@end
+
+@protocol WebDocumentSelection <WebDocumentText>
+- (NSArray *)pasteboardTypesForSelection;
+- (void)writeSelectionWithPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard;
+
+// Array of rects that tightly enclose the selected text, in coordinates of selectinView.
+- (NSArray *)selectionTextRects;
+
+// Rect tightly enclosing the entire selected area, in coordinates of selectionView.
+- (NSRect)selectionRect;
+
+// NSImage of the portion of the selection that's in view. This does not draw backgrounds.
+// The text is all black according to the parameter.
+- (NSImage *)selectionImageForcingBlackText:(BOOL)forceBlackText;
+
+// Rect tightly enclosing the entire selected area, in coordinates of selectionView.
+// NOTE: This method is equivalent to selectionRect and shouldn't be used; use selectionRect instead.
+- (NSRect)selectionImageRect;
+
+// View that draws the selection and can be made first responder. Often this is self but it could be
+// a nested view, as for example in the case of WebPDFView.
+- (NSView *)selectionView;
+@end
+
+@protocol WebDocumentIncrementalSearching
+/*!
+@method searchFor:direction:caseSensitive:wrap:startInSelection:
+ @abstract Searches a document view for a string and highlights the string if it is found.
+ @param string The string to search for.
+ @param forward YES to search forward, NO to seach backwards.
+ @param caseFlag YES to for case-sensitive search, NO for case-insensitive search.
+ @param wrapFlag YES to wrap around, NO to avoid wrapping.
+ @param startInSelection YES to begin search in the selected text (useful for incremental searching), NO to begin search after the selected text.
+ @result YES if found, NO if not found.
+ */
+- (BOOL)searchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag startInSelection:(BOOL)startInSelection;
+@end
+
+@interface WebHTMLView (WebDocumentPrivateProtocols) <WebDocumentSelection, WebDocumentIncrementalSearching>
+@end
diff --git a/WebKit/mac/WebView/WebDynamicScrollBarsView.h b/WebKit/mac/WebView/WebDynamicScrollBarsView.h
new file mode 100644
index 0000000..255deb8
--- /dev/null
+++ b/WebKit/mac/WebView/WebDynamicScrollBarsView.h
@@ -0,0 +1,71 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <AppKit/NSScrollView.h>
+
+#import <WebCore/WebCoreFrameView.h>
+
+// FIXME 2980779: This has grown to be more than just a dynamic scroll bar view,
+// and it is no longer completely appropriate for use outside of WebKit.
+
+@interface WebDynamicScrollBarsView : NSScrollView <WebCoreFrameView>
+{
+ WebCoreScrollbarMode hScroll;
+ WebCoreScrollbarMode vScroll;
+ BOOL hScrollModeLocked;
+ BOOL vScrollModeLocked;
+ BOOL suppressLayout;
+ BOOL suppressScrollers;
+ BOOL inUpdateScrollers;
+}
+
+- (void)setAllowsHorizontalScrolling:(BOOL)flag;
+- (BOOL)allowsHorizontalScrolling;
+- (void)setAllowsVerticalScrolling:(BOOL)flag;
+- (BOOL)allowsVerticalScrolling;
+
+- (void)setHorizontalScrollingMode:(WebCoreScrollbarMode)mode andLock:(BOOL)lock;
+- (void)setVerticalScrollingMode:(WebCoreScrollbarMode)mode andLock:(BOOL)lock;
+- (void)setScrollingMode:(WebCoreScrollbarMode)mode andLock:(BOOL)lock;
+
+- (void)setHorizontalScrollingModeLocked:(BOOL)locked;
+- (void)setVerticalScrollingModeLocked:(BOOL)locked;
+- (void)setScrollingModesLocked:(BOOL)mode;
+
+- (BOOL)horizontalScrollingModeLocked;
+- (BOOL)verticalScrollingModeLocked;
+
+// Convenience method to affect both scrolling directions at once.
+- (void)setAllowsScrolling:(BOOL)flag;
+
+// Returns YES if either horizontal or vertical scrolling is allowed.
+- (BOOL)allowsScrolling;
+
+- (void)updateScrollers;
+- (void)setSuppressLayout: (BOOL)flag;
+@end
diff --git a/WebKit/mac/WebView/WebDynamicScrollBarsView.m b/WebKit/mac/WebView/WebDynamicScrollBarsView.m
new file mode 100644
index 0000000..8374725
--- /dev/null
+++ b/WebKit/mac/WebView/WebDynamicScrollBarsView.m
@@ -0,0 +1,350 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebDynamicScrollBarsView.h>
+
+#import <WebKit/WebDocument.h>
+#import <WebKitSystemInterface.h>
+
+@implementation WebDynamicScrollBarsView
+
+- (void)setSuppressLayout: (BOOL)flag;
+{
+ suppressLayout = flag;
+}
+
+- (void)setScrollBarsSuppressed:(BOOL)suppressed repaintOnUnsuppress:(BOOL)repaint
+{
+ suppressScrollers = suppressed;
+
+ // This code was originally changes for a Leopard performance imporvement. We decided to
+ // ifdef it to fix correctness issues on Tiger documented in <rdar://problem/5441823>.
+#ifndef BUILDING_ON_TIGER
+ if (suppressed) {
+ [[self verticalScroller] setNeedsDisplay:NO];
+ [[self horizontalScroller] setNeedsDisplay:NO];
+ }
+
+ if (!suppressed && repaint)
+ [super reflectScrolledClipView:[self contentView]];
+#else
+ if (suppressed || repaint) {
+ [[self verticalScroller] setNeedsDisplay: !suppressed];
+ [[self horizontalScroller] setNeedsDisplay: !suppressed];
+ }
+#endif
+}
+
+- (void)updateScrollers
+{
+ // We need to do the work below twice in the case where a scroll bar disappears,
+ // making the second layout have a wider width than the first. Doing it more than
+ // twice would indicate some kind of infinite loop, so we do it at most twice.
+ // It's quite efficient to do this work twice in the normal case, so we don't bother
+ // trying to figure out of the second pass is needed or not.
+ if (inUpdateScrollers)
+ return;
+
+ inUpdateScrollers = true;
+
+ int pass;
+ BOOL hasVerticalScroller = [self hasVerticalScroller];
+ BOOL hasHorizontalScroller = [self hasHorizontalScroller];
+ BOOL oldHasVertical = hasVerticalScroller;
+ BOOL oldHasHorizontal = hasHorizontalScroller;
+
+ for (pass = 0; pass < 2; pass++) {
+ BOOL scrollsVertically;
+ BOOL scrollsHorizontally;
+
+ if (!suppressLayout && !suppressScrollers && (hScroll == WebCoreScrollbarAuto || vScroll == WebCoreScrollbarAuto)) {
+ // Do a layout if pending, before checking if scrollbars are needed.
+ // This fixes 2969367, although may introduce a slowdown in live resize performance.
+ NSView *documentView = [self documentView];
+ if (!documentView) {
+ scrollsHorizontally = NO;
+ scrollsVertically = NO;
+ } else {
+ if ((hasVerticalScroller != oldHasVertical ||
+ hasHorizontalScroller != oldHasHorizontal || [documentView inLiveResize]) && [documentView conformsToProtocol:@protocol(WebDocumentView)]) {
+ [(id <WebDocumentView>)documentView setNeedsLayout: YES];
+ [(id <WebDocumentView>)documentView layout];
+ }
+
+ NSSize documentSize = [documentView frame].size;
+ NSSize frameSize = [self frame].size;
+
+ scrollsVertically = (vScroll == WebCoreScrollbarAlwaysOn) ||
+ (vScroll == WebCoreScrollbarAuto && documentSize.height > frameSize.height);
+ if (scrollsVertically)
+ scrollsHorizontally = (hScroll == WebCoreScrollbarAlwaysOn) ||
+ (hScroll == WebCoreScrollbarAuto && documentSize.width + [NSScroller scrollerWidth] > frameSize.width);
+ else {
+ scrollsHorizontally = (hScroll == WebCoreScrollbarAlwaysOn) ||
+ (hScroll == WebCoreScrollbarAuto && documentSize.width > frameSize.width);
+ if (scrollsHorizontally)
+ scrollsVertically = (vScroll == WebCoreScrollbarAlwaysOn) ||
+ (vScroll == WebCoreScrollbarAuto && documentSize.height + [NSScroller scrollerWidth] > frameSize.height);
+ }
+ }
+ } else {
+ scrollsHorizontally = (hScroll == WebCoreScrollbarAuto) ? hasHorizontalScroller : (hScroll == WebCoreScrollbarAlwaysOn);
+ scrollsVertically = (vScroll == WebCoreScrollbarAuto) ? hasVerticalScroller : (vScroll == WebCoreScrollbarAlwaysOn);
+ }
+
+ if (hasVerticalScroller != scrollsVertically) {
+ [self setHasVerticalScroller:scrollsVertically];
+ hasVerticalScroller = scrollsVertically;
+ }
+
+ if (hasHorizontalScroller != scrollsHorizontally) {
+ [self setHasHorizontalScroller:scrollsHorizontally];
+ hasHorizontalScroller = scrollsHorizontally;
+ }
+ }
+
+ if (suppressScrollers) {
+ [[self verticalScroller] setNeedsDisplay: NO];
+ [[self horizontalScroller] setNeedsDisplay: NO];
+ }
+
+ inUpdateScrollers = false;
+}
+
+// Make the horizontal and vertical scroll bars come and go as needed.
+- (void)reflectScrolledClipView:(NSClipView *)clipView
+{
+ if (clipView == [self contentView]) {
+ // FIXME: This hack here prevents infinite recursion that takes place when we
+ // gyrate between having a vertical scroller and not having one. A reproducible
+ // case is clicking on the "the Policy Routing text" link at
+ // http://www.linuxpowered.com/archive/howto/Net-HOWTO-8.html.
+ // The underlying cause is some problem in the NSText machinery, but I was not
+ // able to pin it down.
+ if (!inUpdateScrollers && [[NSGraphicsContext currentContext] isDrawingToScreen])
+ [self updateScrollers];
+ }
+
+ // This code was originally changed for a Leopard performance imporvement. We decided to
+ // ifdef it to fix correctness issues on Tiger documented in <rdar://problem/5441823>.
+#ifndef BUILDING_ON_TIGER
+ // Update the scrollers if they're not being suppressed.
+ if (!suppressScrollers)
+ [super reflectScrolledClipView:clipView];
+#else
+ [super reflectScrolledClipView:clipView];
+
+ // Validate the scrollers if they're being suppressed.
+ if (suppressScrollers) {
+ [[self verticalScroller] setNeedsDisplay: NO];
+ [[self horizontalScroller] setNeedsDisplay: NO];
+ }
+#endif
+}
+
+- (void)setAllowsScrolling:(BOOL)flag
+{
+ if (hScrollModeLocked && vScrollModeLocked)
+ return;
+
+ if (flag && vScroll == WebCoreScrollbarAlwaysOff)
+ vScroll = WebCoreScrollbarAuto;
+ else if (!flag && vScroll != WebCoreScrollbarAlwaysOff)
+ vScroll = WebCoreScrollbarAlwaysOff;
+
+ if (flag && hScroll == WebCoreScrollbarAlwaysOff)
+ hScroll = WebCoreScrollbarAuto;
+ else if (!flag && hScroll != WebCoreScrollbarAlwaysOff)
+ hScroll = WebCoreScrollbarAlwaysOff;
+
+ [self updateScrollers];
+}
+
+- (BOOL)allowsScrolling
+{
+ // Returns YES if either horizontal or vertical scrolling is allowed.
+ return hScroll != WebCoreScrollbarAlwaysOff || vScroll != WebCoreScrollbarAlwaysOff;
+}
+
+- (void)setAllowsHorizontalScrolling:(BOOL)flag
+{
+ if (hScrollModeLocked)
+ return;
+ if (flag && hScroll == WebCoreScrollbarAlwaysOff)
+ hScroll = WebCoreScrollbarAuto;
+ else if (!flag && hScroll != WebCoreScrollbarAlwaysOff)
+ hScroll = WebCoreScrollbarAlwaysOff;
+ [self updateScrollers];
+}
+
+- (void)setAllowsVerticalScrolling:(BOOL)flag
+{
+ if (vScrollModeLocked)
+ return;
+ if (flag && vScroll == WebCoreScrollbarAlwaysOff)
+ vScroll = WebCoreScrollbarAuto;
+ else if (!flag && vScroll != WebCoreScrollbarAlwaysOff)
+ vScroll = WebCoreScrollbarAlwaysOff;
+ [self updateScrollers];
+}
+
+- (BOOL)allowsHorizontalScrolling
+{
+ return hScroll != WebCoreScrollbarAlwaysOff;
+}
+
+- (BOOL)allowsVerticalScrolling
+{
+ return vScroll != WebCoreScrollbarAlwaysOff;
+}
+
+-(WebCoreScrollbarMode)horizontalScrollingMode
+{
+ return hScroll;
+}
+
+-(WebCoreScrollbarMode)verticalScrollingMode
+{
+ return vScroll;
+}
+
+- (void)setHorizontalScrollingMode:(WebCoreScrollbarMode)mode
+{
+ [self setHorizontalScrollingMode:mode andLock:NO];
+}
+
+- (void)setHorizontalScrollingMode:(WebCoreScrollbarMode)mode andLock:(BOOL)lock
+{
+ if (mode == hScroll || hScrollModeLocked)
+ return;
+
+ hScroll = mode;
+
+ if (lock)
+ [self setHorizontalScrollingModeLocked:YES];
+
+ [self updateScrollers];
+}
+
+- (void)setVerticalScrollingMode:(WebCoreScrollbarMode)mode
+{
+ [self setVerticalScrollingMode:mode andLock:NO];
+}
+
+- (void)setVerticalScrollingMode:(WebCoreScrollbarMode)mode andLock:(BOOL)lock
+{
+ if (mode == vScroll || vScrollModeLocked)
+ return;
+
+ vScroll = mode;
+
+ if (lock)
+ [self setVerticalScrollingModeLocked:YES];
+
+ [self updateScrollers];
+}
+
+- (void)setScrollingMode:(WebCoreScrollbarMode)mode
+{
+ [self setScrollingMode:mode andLock:NO];
+}
+
+- (void)setScrollingMode:(WebCoreScrollbarMode)mode andLock:(BOOL)lock
+{
+ if ((mode == vScroll && mode == hScroll) || (vScrollModeLocked && hScrollModeLocked))
+ return;
+
+ BOOL update = NO;
+ if (mode != vScroll && !vScrollModeLocked) {
+ vScroll = mode;
+ update = YES;
+ }
+
+ if (mode != hScroll && !hScrollModeLocked) {
+ hScroll = mode;
+ update = YES;
+ }
+
+ if (lock)
+ [self setScrollingModesLocked:YES];
+
+ if (update)
+ [self updateScrollers];
+}
+
+- (void)setHorizontalScrollingModeLocked:(BOOL)locked
+{
+ hScrollModeLocked = locked;
+}
+
+- (void)setVerticalScrollingModeLocked:(BOOL)locked
+{
+ vScrollModeLocked = locked;
+}
+
+- (void)setScrollingModesLocked:(BOOL)locked
+{
+ hScrollModeLocked = vScrollModeLocked = locked;
+}
+
+- (BOOL)horizontalScrollingModeLocked
+{
+ return hScrollModeLocked;
+}
+
+- (BOOL)verticalScrollingModeLocked
+{
+ return vScrollModeLocked;
+}
+
+- (BOOL)autoforwardsScrollWheelEvents
+{
+ return YES;
+}
+
+- (void)scrollWheel:(NSEvent *)event
+{
+ float deltaX;
+ float deltaY;
+ BOOL isContinuous;
+ WKGetWheelEventDeltas(event, &deltaX, &deltaY, &isContinuous);
+
+ if (fabsf(deltaY) > fabsf(deltaX)) {
+ if (![self allowsVerticalScrolling]) {
+ [[self nextResponder] scrollWheel:event];
+ return;
+ }
+ } else if (![self allowsHorizontalScrolling]) {
+ [[self nextResponder] scrollWheel:event];
+ return;
+ }
+
+ [super scrollWheel:event];
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebEditingDelegate.h b/WebKit/mac/WebView/WebEditingDelegate.h
new file mode 100644
index 0000000..5de9ef0
--- /dev/null
+++ b/WebKit/mac/WebView/WebEditingDelegate.h
@@ -0,0 +1,57 @@
+/*
+ * Copyright (C) 2004, 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@class DOMCSSStyleDeclaration;
+@class DOMRange;
+@class WebView;
+
+typedef enum {
+ WebViewInsertActionTyped,
+ WebViewInsertActionPasted,
+ WebViewInsertActionDropped,
+} WebViewInsertAction;
+
+@interface NSObject (WebViewEditingDelegate)
+- (BOOL)webView:(WebView *)webView shouldBeginEditingInDOMRange:(DOMRange *)range;
+- (BOOL)webView:(WebView *)webView shouldEndEditingInDOMRange:(DOMRange *)range;
+- (BOOL)webView:(WebView *)webView shouldInsertNode:(DOMNode *)node replacingDOMRange:(DOMRange *)range givenAction:(WebViewInsertAction)action;
+- (BOOL)webView:(WebView *)webView shouldInsertText:(NSString *)text replacingDOMRange:(DOMRange *)range givenAction:(WebViewInsertAction)action;
+- (BOOL)webView:(WebView *)webView shouldDeleteDOMRange:(DOMRange *)range;
+- (BOOL)webView:(WebView *)webView shouldChangeSelectedDOMRange:(DOMRange *)currentRange toDOMRange:(DOMRange *)proposedRange affinity:(NSSelectionAffinity)selectionAffinity stillSelecting:(BOOL)flag;
+- (BOOL)webView:(WebView *)webView shouldApplyStyle:(DOMCSSStyleDeclaration *)style toElementsInDOMRange:(DOMRange *)range;
+- (BOOL)webView:(WebView *)webView shouldChangeTypingStyle:(DOMCSSStyleDeclaration *)currentStyle toStyle:(DOMCSSStyleDeclaration *)proposedStyle;
+- (BOOL)webView:(WebView *)webView doCommandBySelector:(SEL)selector;
+- (void)webViewDidBeginEditing:(NSNotification *)notification;
+- (void)webViewDidChange:(NSNotification *)notification;
+- (void)webViewDidEndEditing:(NSNotification *)notification;
+- (void)webViewDidChangeTypingStyle:(NSNotification *)notification;
+- (void)webViewDidChangeSelection:(NSNotification *)notification;
+- (NSUndoManager *)undoManagerForWebView:(WebView *)webView;
+@end
diff --git a/WebKit/mac/WebView/WebEditingDelegatePrivate.h b/WebKit/mac/WebView/WebEditingDelegatePrivate.h
new file mode 100644
index 0000000..1116de3
--- /dev/null
+++ b/WebKit/mac/WebView/WebEditingDelegatePrivate.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebEditingDelegate.h>
+
+@class DOMHTMLElement;
+
+@interface NSObject (WebViewEditingDelegatePrivate)
+- (BOOL)webView:(WebView *)webView shouldShowDeleteInterfaceForElement:(DOMHTMLElement *)element;
+- (void)webView:(WebView *)webView didWriteSelectionToPasteboard:(NSPasteboard *)pasteboard;
+- (void)webView:(WebView *)webView didSetSelectionTypesForPasteboard:(NSPasteboard *)pasteboard;
+- (BOOL)webView:(WebView *)webView shouldMoveRangeAfterDelete:(DOMRange *)range replacingRange:(DOMRange *)rangeToBeReplaced;
+@end
diff --git a/WebKit/mac/WebView/WebFormDelegate.h b/WebKit/mac/WebView/WebFormDelegate.h
new file mode 100644
index 0000000..1f4bee0
--- /dev/null
+++ b/WebKit/mac/WebView/WebFormDelegate.h
@@ -0,0 +1,74 @@
+/*
+ * Copyright (C) 2003, 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <AppKit/AppKit.h>
+
+@class DOMElement;
+@class DOMHTMLInputElement;
+@class DOMHTMLTextAreaElement;
+@class WebFrame;
+
+/*!
+ @protocol WebFormSubmissionListener
+*/
+@protocol WebFormSubmissionListener <NSObject>
+- (void)continue;
+@end
+
+/*!
+ @protocol WebFormDelegate
+*/
+@protocol WebFormDelegate <NSObject>
+
+// Various methods send by controls that edit text to their delegates, which are all
+// analogous to similar methods in AppKit/NSControl.h.
+// These methods are forwarded from widgets used in forms to the WebFormDelegate.
+
+- (void)textFieldDidBeginEditing:(DOMHTMLInputElement *)element inFrame:(WebFrame *)frame;
+- (void)textFieldDidEndEditing:(DOMHTMLInputElement *)element inFrame:(WebFrame *)frame;
+- (void)textDidChangeInTextField:(DOMHTMLInputElement *)element inFrame:(WebFrame *)frame;
+- (void)textDidChangeInTextArea:(DOMHTMLTextAreaElement *)element inFrame:(WebFrame *)frame;
+
+- (BOOL)textField:(DOMHTMLInputElement *)element doCommandBySelector:(SEL)commandSelector inFrame:(WebFrame *)frame;
+- (BOOL)textField:(DOMHTMLInputElement *)element shouldHandleEvent:(NSEvent *)event inFrame:(WebFrame *)frame;
+
+// Sent when a form is just about to be submitted (before the load is started)
+// listener must be sent continue when the delegate is done.
+- (void)frame:(WebFrame *)frame sourceFrame:(WebFrame *)sourceFrame willSubmitForm:(DOMElement *)form
+ withValues:(NSDictionary *)values submissionListener:(id <WebFormSubmissionListener>)listener;
+
+@end
+
+/*!
+ @class WebFormDelegate
+ @discussion The WebFormDelegate class responds to all WebFormDelegate protocol
+ methods by doing nothing. It's provided for the convenience of clients who only want
+ to implement some of the above methods and ignore others.
+*/
+@interface WebFormDelegate : NSObject <WebFormDelegate>
+@end
diff --git a/WebKit/mac/WebView/WebFormDelegate.m b/WebKit/mac/WebView/WebFormDelegate.m
new file mode 100644
index 0000000..df25f20
--- /dev/null
+++ b/WebKit/mac/WebView/WebFormDelegate.m
@@ -0,0 +1,79 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebFormDelegatePrivate.h"
+
+// FIXME: This could become an informal protocol; we switched all the API
+// delegates to be informal.
+
+@implementation WebFormDelegate
+
+static WebFormDelegate *sharedDelegate = nil;
+
+// Return a object with NOP implementations of the protocol's methods
+// Note this feature relies on our default delegate being stateless
++ (WebFormDelegate *)_sharedWebFormDelegate
+{
+ if (!sharedDelegate)
+ sharedDelegate = [[WebFormDelegate alloc] init];
+ return sharedDelegate;
+}
+
+- (void)textFieldDidBeginEditing:(DOMHTMLInputElement *)element inFrame:(WebFrame *)frame
+{
+}
+
+- (void)textFieldDidEndEditing:(DOMHTMLInputElement *)element inFrame:(WebFrame *)frame
+{
+}
+
+- (void)textDidChangeInTextField:(DOMHTMLInputElement *)element inFrame:(WebFrame *)frame
+{
+}
+
+- (void)textDidChangeInTextArea:(DOMHTMLTextAreaElement *)element inFrame:(WebFrame *)frame
+{
+}
+
+- (BOOL)textField:(DOMHTMLInputElement *)element doCommandBySelector:(SEL)commandSelector inFrame:(WebFrame *)frame
+{
+ return NO;
+}
+
+- (BOOL)textField:(DOMHTMLInputElement *)element shouldHandleEvent:(NSEvent *)event inFrame:(WebFrame *)frame
+{
+ return NO;
+}
+
+- (void)frame:(WebFrame *)frame sourceFrame:(WebFrame *)sourceFrame willSubmitForm:(DOMElement *)form
+ withValues:(NSDictionary *)values submissionListener:(id <WebFormSubmissionListener>)listener
+{
+ [listener continue];
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebFormDelegatePrivate.h b/WebKit/mac/WebView/WebFormDelegatePrivate.h
new file mode 100644
index 0000000..d566e89
--- /dev/null
+++ b/WebKit/mac/WebView/WebFormDelegatePrivate.h
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebFormDelegate.h"
+
+@interface WebFormDelegate (WebPrivate)
++ (WebFormDelegate *)_sharedWebFormDelegate;
+@end
diff --git a/WebKit/mac/WebView/WebFrame.h b/WebKit/mac/WebView/WebFrame.h
new file mode 100644
index 0000000..e435087
--- /dev/null
+++ b/WebKit/mac/WebView/WebFrame.h
@@ -0,0 +1,210 @@
+/*
+ * Copyright (C) 2003, 2004, 2005, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+#import <JavaScriptCore/JSBase.h>
+
+@class DOMDocument;
+@class DOMHTMLElement;
+@class NSURLRequest;
+@class WebArchive;
+@class WebDataSource;
+@class WebFramePrivate;
+@class WebFrameView;
+@class WebScriptObject;
+@class WebView;
+
+/*!
+ @class WebFrame
+ @discussion Every web page is represented by at least one WebFrame. A WebFrame
+ has a WebFrameView and a WebDataSource.
+*/
+@interface WebFrame : NSObject
+{
+@private
+ WebFramePrivate *_private;
+}
+
+/*!
+ @method initWithName:webFrameView:webView:
+ @abstract The designated initializer of WebFrame.
+ @discussion WebFrames are normally created for you by the WebView. You should
+ not need to invoke this method directly.
+ @param name The name of the frame.
+ @param view The WebFrameView for the frame.
+ @param webView The WebView that manages the frame.
+ @result Returns an initialized WebFrame.
+*/
+- (id)initWithName:(NSString *)name webFrameView:(WebFrameView *)view webView:(WebView *)webView;
+
+/*!
+ @method name
+ @result The frame name.
+*/
+- (NSString *)name;
+
+/*!
+ @method webView
+ @result Returns the WebView for the document that includes this frame.
+*/
+- (WebView *)webView;
+
+/*!
+ @method frameView
+ @result The WebFrameView for this frame.
+*/
+- (WebFrameView *)frameView;
+
+/*!
+ @method DOMDocument
+ @abstract Returns the DOM document of the frame.
+ @description Returns nil if the frame does not contain a DOM document such as a standalone image.
+*/
+- (DOMDocument *)DOMDocument;
+
+/*!
+ @method frameElement
+ @abstract Returns the frame element of the frame.
+ @description The class of the result is either DOMHTMLFrameElement, DOMHTMLIFrameElement or DOMHTMLObjectElement.
+ Returns nil if the frame is the main frame since there is no frame element for the frame in this case.
+*/
+- (DOMHTMLElement *)frameElement;
+
+/*!
+ @method loadRequest:
+ @param request The web request to load.
+*/
+- (void)loadRequest:(NSURLRequest *)request;
+
+/*!
+ @method loadData:MIMEType:textEncodingName:baseURL:
+ @param data The data to use for the main page of the document.
+ @param MIMEType The MIME type of the data.
+ @param encodingName The encoding of the data.
+ @param URL The base URL to apply to relative URLs within the document.
+*/
+- (void)loadData:(NSData *)data MIMEType:(NSString *)MIMEType textEncodingName:(NSString *)encodingName baseURL:(NSURL *)URL;
+
+/*!
+ @method loadHTMLString:baseURL:
+ @param string The string to use for the main page of the document.
+ @param URL The base URL to apply to relative URLs within the document.
+*/
+- (void)loadHTMLString:(NSString *)string baseURL:(NSURL *)URL;
+
+/*!
+ @method loadAlternateHTMLString:baseURL:forUnreachableURL:
+ @abstract Loads a page to display as a substitute for a URL that could not be reached.
+ @discussion This allows clients to display page-loading errors in the webview itself.
+ This is typically called while processing the WebFrameLoadDelegate method
+ -webView:didFailProvisionalLoadWithError:forFrame: or one of the the WebPolicyDelegate methods
+ -webView:decidePolicyForMIMEType:request:frame:decisionListener: or
+ -webView:unableToImplementPolicyWithError:frame:. If it is called from within one of those
+ three delegate methods then the back/forward list will be maintained appropriately.
+ @param string The string to use for the main page of the document.
+ @param baseURL The baseURL to apply to relative URLs within the document.
+ @param unreachableURL The URL for which this page will serve as alternate content.
+*/
+- (void)loadAlternateHTMLString:(NSString *)string baseURL:(NSURL *)baseURL forUnreachableURL:(NSURL *)unreachableURL;
+
+/*!
+ @method loadArchive:
+ @abstract Causes WebFrame to load a WebArchive.
+ @param archive The archive to be loaded.
+*/
+- (void)loadArchive:(WebArchive *)archive;
+
+/*!
+ @method dataSource
+ @discussion Returns the committed data source. Will return nil if the
+ provisional data source hasn't yet been loaded.
+ @result The datasource for this frame.
+*/
+- (WebDataSource *)dataSource;
+
+/*!
+ @method provisionalDataSource
+ @discussion Will return the provisional data source. The provisional data source will
+ be nil if no data source has been set on the frame, or the data source
+ has successfully transitioned to the committed data source.
+ @result The provisional datasource of this frame.
+*/
+- (WebDataSource *)provisionalDataSource;
+
+/*!
+ @method stopLoading
+ @discussion Stop any pending loads on the frame's data source,
+ and its children.
+*/
+- (void)stopLoading;
+
+/*!
+ @method reload
+*/
+- (void)reload;
+
+/*!
+ @method findFrameNamed:
+ @discussion This method returns a frame with the given name. findFrameNamed returns self
+ for _self and _current, the parent frame for _parent and the main frame for _top.
+ findFrameNamed returns self for _parent and _top if the receiver is the mainFrame.
+ findFrameNamed first searches from the current frame to all descending frames then the
+ rest of the frames in the WebView. If still not found, findFrameNamed searches the
+ frames of the other WebViews.
+ @param name The name of the frame to find.
+ @result The frame matching the provided name. nil if the frame is not found.
+*/
+- (WebFrame *)findFrameNamed:(NSString *)name;
+
+/*!
+ @method parentFrame
+ @result The frame containing this frame, or nil if this is a top level frame.
+*/
+- (WebFrame *)parentFrame;
+
+/*!
+ @method childFrames
+ @discussion The frames in the array are associated with a frame set or iframe.
+ @result Returns an array of WebFrame.
+*/
+- (NSArray *)childFrames;
+
+/*!
+ @method windowObject
+ @result The WebScriptObject representing the frame's JavaScript window object.
+*/
+- (WebScriptObject *)windowObject;
+
+/*!
+ @method globalContext
+ @result The frame's global JavaScript execution context. Use this method to
+ bridge between the WebKit and JavaScriptCore APIs.
+*/
+- (JSGlobalContextRef)globalContext;
+
+@end
diff --git a/WebKit/mac/WebView/WebFrame.mm b/WebKit/mac/WebView/WebFrame.mm
new file mode 100644
index 0000000..25c6246
--- /dev/null
+++ b/WebKit/mac/WebView/WebFrame.mm
@@ -0,0 +1,883 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebFrameInternal.h"
+
+#import "DOMCSSStyleDeclarationInternal.h"
+#import "DOMDocumentInternal.h"
+#import "DOMElementInternal.h"
+#import "DOMHTMLElementInternal.h"
+#import "DOMNodeInternal.h"
+#import "DOMRangeInternal.h"
+#import "WebBackForwardList.h"
+#import "WebChromeClient.h"
+#import "WebDataSourceInternal.h"
+#import "WebDocumentInternal.h"
+#import "WebDocumentLoaderMac.h"
+#import "WebFrameBridge.h"
+#import "WebFrameLoadDelegate.h"
+#import "WebFrameLoaderClient.h"
+#import "WebFrameViewInternal.h"
+#import "WebHTMLViewInternal.h"
+#import "WebHistoryItem.h"
+#import "WebHistoryItemInternal.h"
+#import "WebHistoryItemPrivate.h"
+#import "WebKitLogging.h"
+#import "WebKitStatisticsPrivate.h"
+#import "WebNSURLExtras.h"
+#import "WebNSURLRequestExtras.h"
+#import "WebNetscapePluginEmbeddedView.h"
+#import "WebNullPluginView.h"
+#import "WebPlugin.h"
+#import "WebPluginController.h"
+#import "WebPreferencesPrivate.h"
+#import "WebScriptDebugDelegatePrivate.h"
+#import "WebViewInternal.h"
+#import <WebCore/Chrome.h>
+#import <WebCore/ColorMac.h>
+#import <WebCore/Document.h>
+#import <WebCore/Event.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameTree.h>
+#import <WebCore/HistoryItem.h>
+#import <WebCore/HTMLFormElement.h>
+#import <WebCore/HTMLFrameOwnerElement.h>
+#import <WebCore/Page.h>
+#import <WebCore/SelectionController.h>
+#import <WebCore/SharedBuffer.h>
+#import <WebCore/FormState.h>
+#import <WebCore/ResourceRequest.h>
+#import <WebCore/kjs_binding.h>
+#import <WebCore/kjs_proxy.h>
+#import <WebKit/DOMDocument.h>
+#import <WebKit/DOMElement.h>
+#import <WebKit/DOMHTMLElement.h>
+#import <WebKit/DOMNode.h>
+#import <WebKit/DOMRange.h>
+#import <JavaScriptCore/APICast.h>
+
+using namespace WebCore;
+
+/*
+Here is the current behavior matrix for four types of navigations:
+
+Standard Nav:
+
+ Restore form state: YES
+ Restore scroll and focus state: YES
+ Cache policy: NSURLRequestUseProtocolCachePolicy
+ Add to back/forward list: YES
+
+Back/Forward:
+
+ Restore form state: YES
+ Restore scroll and focus state: YES
+ Cache policy: NSURLRequestReturnCacheDataElseLoad
+ Add to back/forward list: NO
+
+Reload (meaning only the reload button):
+
+ Restore form state: NO
+ Restore scroll and focus state: YES
+ Cache policy: NSURLRequestReloadIgnoringCacheData
+ Add to back/forward list: NO
+
+Repeat load of the same URL (by any other means of navigation other than the reload button, including hitting return in the location field):
+
+ Restore form state: NO
+ Restore scroll and focus state: NO, reset to initial conditions
+ Cache policy: NSURLRequestReloadIgnoringCacheData
+ Add to back/forward list: NO
+*/
+
+using namespace WebCore;
+
+NSString *WebPageCacheEntryDateKey = @"WebPageCacheEntryDateKey";
+NSString *WebPageCacheDataSourceKey = @"WebPageCacheDataSourceKey";
+NSString *WebPageCacheDocumentViewKey = @"WebPageCacheDocumentViewKey";
+
+@interface WebFrame (ForwardDecls)
+- (void)_loadHTMLString:(NSString *)string baseURL:(NSURL *)baseURL unreachableURL:(NSURL *)unreachableURL;
+- (WebHistoryItem *)_createItem:(BOOL)useOriginal;
+- (WebHistoryItem *)_createItemTreeWithTargetFrame:(WebFrame *)targetFrame clippedAtTarget:(BOOL)doClip;
+@end
+
+@interface NSView (WebFramePluginHosting)
+- (void)setWebFrame:(WebFrame *)webFrame;
+@end
+
+@implementation WebFramePrivate
+
+- (void)dealloc
+{
+ [webFrameView release];
+
+ [scriptDebugger release];
+
+ [super dealloc];
+}
+
+- (void)setWebFrameView:(WebFrameView *)v
+{
+ [v retain];
+ [webFrameView release];
+ webFrameView = v;
+}
+
+@end
+
+CSSStyleDeclaration* core(DOMCSSStyleDeclaration *declaration)
+{
+ return [declaration _CSSStyleDeclaration];
+}
+
+DOMCSSStyleDeclaration *kit(WebCore::CSSStyleDeclaration* declaration)
+{
+ return [DOMCSSStyleDeclaration _wrapCSSStyleDeclaration:declaration];
+}
+
+Element* core(DOMElement *element)
+{
+ return [element _element];
+}
+
+DOMElement *kit(Element* element)
+{
+ return [DOMElement _wrapElement:element];
+}
+
+Node* core(DOMNode *node)
+{
+ return [node _node];
+}
+
+DOMNode *kit(Node* node)
+{
+ return [DOMNode _wrapNode:node];
+}
+
+DOMNode *kit(PassRefPtr<Node> node)
+{
+ return [DOMNode _wrapNode:node.get()];
+}
+
+Document* core(DOMDocument *document)
+{
+ return [document _document];
+}
+
+DOMDocument *kit(Document* document)
+{
+ return [DOMDocument _wrapDocument:document];
+}
+
+HTMLElement* core(DOMHTMLElement *element)
+{
+ return [element _HTMLElement];
+}
+
+DOMHTMLElement *kit(HTMLElement *element)
+{
+ return [DOMHTMLElement _wrapHTMLElement:element];
+}
+
+Range* core(DOMRange *range)
+{
+ return [range _range];
+}
+
+DOMRange *kit(Range* range)
+{
+ return [DOMRange _wrapRange:range];
+}
+
+WebCore::EditableLinkBehavior core(WebKitEditableLinkBehavior editableLinkBehavior)
+{
+ return static_cast<WebCore::EditableLinkBehavior>(editableLinkBehavior);
+}
+
+WebKitEditableLinkBehavior kit(WebCore::EditableLinkBehavior editableLinkBehavior)
+{
+ return static_cast<WebKitEditableLinkBehavior>(editableLinkBehavior);
+}
+
+@implementation WebFrame (WebInternal)
+
+
+static inline WebFrame *frame(WebCoreFrameBridge *bridge)
+{
+ return ((WebFrameBridge *)bridge)->_frame;
+}
+
+Frame* core(WebFrame *frame)
+{
+ if (!frame)
+ return 0;
+
+ if (!frame->_private->bridge)
+ return 0;
+
+ return frame->_private->bridge->m_frame;
+}
+
+WebFrame *kit(Frame* frame)
+{
+ return frame ? ((WebFrameBridge *)frame->bridge())->_frame : nil;
+}
+
+Page* core(WebView *webView)
+{
+ return [webView page];
+}
+
+WebView *kit(Page* page)
+{
+ return page ? static_cast<WebChromeClient*>(page->chrome()->client())->webView() : nil;
+}
+
+WebView *getWebView(WebFrame *webFrame)
+{
+ Frame* coreFrame = core(webFrame);
+ if (!coreFrame)
+ return nil;
+ return kit(coreFrame->page());
+}
+
+/*
+ In the case of saving state about a page with frames, we store a tree of items that mirrors the frame tree.
+ The item that was the target of the user's navigation is designated as the "targetItem".
+ When this method is called with doClip=YES we're able to create the whole tree except for the target's children,
+ which will be loaded in the future. That part of the tree will be filled out as the child loads are committed.
+*/
+
++ (CFAbsoluteTime)_timeOfLastCompletedLoad
+{
+ return FrameLoader::timeOfLastCompletedLoad() - kCFAbsoluteTimeIntervalSince1970;
+}
+
+- (WebFrameBridge *)_bridge
+{
+ return _private->bridge;
+}
+
+- (void)_loadURL:(NSURL *)URL referrer:(NSString *)referrer intoChild:(WebFrame *)childFrame
+{
+ ASSERT(childFrame);
+ HistoryItem* parentItem = core(self)->loader()->currentHistoryItem();
+ FrameLoadType loadType = [self _frameLoader]->loadType();
+ FrameLoadType childLoadType = FrameLoadTypeRedirectWithLockedHistory;
+
+ // If we're moving in the backforward list, we might want to replace the content
+ // of this child frame with whatever was there at that point.
+ // Reload will maintain the frame contents, LoadSame will not.
+ if (parentItem && parentItem->children().size() &&
+ (isBackForwardLoadType(loadType)
+ || loadType == FrameLoadTypeReload
+ || loadType == FrameLoadTypeReloadAllowingStaleData))
+ {
+ HistoryItem* childItem = parentItem->childItemWithName([childFrame name]);
+ if (childItem) {
+ // Use the original URL to ensure we get all the side-effects, such as
+ // onLoad handlers, of any redirects that happened. An example of where
+ // this is needed is Radar 3213556.
+ URL = [NSURL _web_URLWithDataAsString:childItem->originalURLString()];
+ // These behaviors implied by these loadTypes should apply to the child frames
+ childLoadType = loadType;
+
+ if (isBackForwardLoadType(loadType))
+ // For back/forward, remember this item so we can traverse any child items as child frames load
+ core(childFrame)->loader()->setProvisionalHistoryItem(childItem);
+ else
+ // For reload, just reinstall the current item, since a new child frame was created but we won't be creating a new BF item
+ core(childFrame)->loader()->setCurrentHistoryItem(childItem);
+ }
+ }
+
+ WebArchive *archive = [[self _dataSource] _popSubframeArchiveWithName:[childFrame name]];
+ if (archive)
+ [childFrame loadArchive:archive];
+ else
+ [childFrame _frameLoader]->load([URL absoluteURL], referrer, childLoadType,
+ String(), 0, 0);
+}
+
+
+- (void)_viewWillMoveToHostWindow:(NSWindow *)hostWindow
+{
+ Frame* coreFrame = core(self);
+ for (Frame* frame = coreFrame; frame; frame = frame->tree()->traverseNext(coreFrame))
+ [[[kit(frame) frameView] documentView] viewWillMoveToHostWindow:hostWindow];
+}
+
+- (void)_viewDidMoveToHostWindow
+{
+ Frame* coreFrame = core(self);
+ for (Frame* frame = coreFrame; frame; frame = frame->tree()->traverseNext(coreFrame))
+ [[[kit(frame) frameView] documentView] viewDidMoveToHostWindow];
+}
+
+- (void)_addChild:(WebFrame *)child
+{
+ core(self)->tree()->appendChild(adoptRef(core(child)));
+ if ([child _dataSource])
+ [[child _dataSource] _documentLoader]->setOverrideEncoding([[self _dataSource] _documentLoader]->overrideEncoding());
+}
+
+- (int)_numPendingOrLoadingRequests:(BOOL)recurse
+{
+ return core(self)->loader()->numPendingOrLoadingRequests(recurse);
+}
+
+- (void)_reloadForPluginChanges
+{
+ Frame* coreFrame = core(self);
+ for (Frame* frame = coreFrame; frame; frame = frame->tree()->traverseNext(coreFrame)) {
+ NSView <WebDocumentView> *documentView = [[kit(frame) frameView] documentView];
+ if (([documentView isKindOfClass:[WebHTMLView class]] && coreFrame->loader()->containsPlugins()))
+ [kit(frame) reload];
+ }
+}
+
+- (void)_attachScriptDebugger
+{
+ if (!_private->scriptDebugger && core(self)->scriptProxy()->haveGlobalObject())
+ _private->scriptDebugger = [[WebScriptDebugger alloc] initWithWebFrame:self];
+}
+
+- (void)_detachScriptDebugger
+{
+ if (_private->scriptDebugger) {
+ id old = _private->scriptDebugger;
+ _private->scriptDebugger = nil;
+ [old release];
+ }
+}
+
+- (id)_initWithWebFrameView:(WebFrameView *)fv webView:(WebView *)v bridge:(WebFrameBridge *)bridge
+{
+ self = [super init];
+ if (!self)
+ return nil;
+
+ _private = [[WebFramePrivate alloc] init];
+ _private->bridge = bridge;
+
+ if (fv) {
+ [_private setWebFrameView:fv];
+ [fv _setWebFrame:self];
+ }
+
+ ++WebFrameCount;
+
+ return self;
+}
+
+- (NSArray *)_documentViews
+{
+ NSMutableArray *result = [NSMutableArray array];
+ Frame* coreFrame = core(self);
+ for (Frame* frame = coreFrame; frame; frame = frame->tree()->traverseNext(coreFrame)) {
+ id docView = [[kit(frame) frameView] documentView];
+ if (docView)
+ [result addObject:docView];
+ }
+ return result;
+}
+
+- (void)_updateBackground
+{
+ BOOL drawsBackground = [getWebView(self) drawsBackground];
+ NSColor *backgroundColor = [getWebView(self) backgroundColor];
+
+ Frame* coreFrame = core(self);
+ for (Frame* frame = coreFrame; frame; frame = frame->tree()->traverseNext(coreFrame)) {
+ WebFrameBridge *bridge = (WebFrameBridge *)frame->bridge();
+ WebFrame *webFrame = [bridge webFrame];
+ // Never call setDrawsBackground:YES here on the scroll view or the background color will
+ // flash between pages loads. setDrawsBackground:YES will be called in _frameLoadCompleted.
+ if (!drawsBackground)
+ [[[webFrame frameView] _scrollView] setDrawsBackground:NO];
+ [[[webFrame frameView] _scrollView] setBackgroundColor:backgroundColor];
+ id documentView = [[webFrame frameView] documentView];
+ if ([documentView respondsToSelector:@selector(setDrawsBackground:)])
+ [documentView setDrawsBackground:drawsBackground];
+ if ([documentView respondsToSelector:@selector(setBackgroundColor:)])
+ [documentView setBackgroundColor:backgroundColor];
+ [bridge setDrawsBackground:drawsBackground];
+ [bridge setBaseBackgroundColor:backgroundColor];
+ }
+}
+
+- (void)_setInternalLoadDelegate:(id)internalLoadDelegate
+{
+ _private->internalLoadDelegate = internalLoadDelegate;
+}
+
+- (id)_internalLoadDelegate
+{
+ return _private->internalLoadDelegate;
+}
+
+#ifndef BUILDING_ON_TIGER
+- (void)_unmarkAllBadGrammar
+{
+ Frame* coreFrame = core(self);
+ for (Frame* frame = coreFrame; frame; frame = frame->tree()->traverseNext(coreFrame)) {
+ Document *doc = frame->document();
+ if (!doc)
+ return;
+
+ doc->removeMarkers(DocumentMarker::Grammar);
+ }
+}
+#endif
+
+- (void)_unmarkAllMisspellings
+{
+ Frame* coreFrame = core(self);
+ for (Frame* frame = coreFrame; frame; frame = frame->tree()->traverseNext(coreFrame)) {
+ Document *doc = frame->document();
+ if (!doc)
+ return;
+
+ doc->removeMarkers(DocumentMarker::Spelling);
+ }
+}
+
+- (BOOL)_hasSelection
+{
+ id documentView = [_private->webFrameView documentView];
+
+ // optimization for common case to avoid creating potentially large selection string
+ if ([documentView isKindOfClass:[WebHTMLView class]])
+ if (Frame* coreFrame = core(self))
+ return coreFrame->selectionController()->isRange();
+
+ if ([documentView conformsToProtocol:@protocol(WebDocumentText)])
+ return [[documentView selectedString] length] > 0;
+
+ return NO;
+}
+
+- (void)_clearSelection
+{
+ id documentView = [_private->webFrameView documentView];
+ if ([documentView conformsToProtocol:@protocol(WebDocumentText)])
+ [documentView deselectAll];
+}
+
+#if !ASSERT_DISABLED
+- (BOOL)_atMostOneFrameHasSelection
+{
+ // FIXME: 4186050 is one known case that makes this debug check fail.
+ BOOL found = NO;
+ Frame* coreFrame = core(self);
+ for (Frame* frame = coreFrame; frame; frame = frame->tree()->traverseNext(coreFrame))
+ if ([kit(frame) _hasSelection]) {
+ if (found)
+ return NO;
+ found = YES;
+ }
+ return YES;
+}
+#endif
+
+- (WebFrame *)_findFrameWithSelection
+{
+ Frame* coreFrame = core(self);
+ for (Frame* frame = coreFrame; frame; frame = frame->tree()->traverseNext(coreFrame))
+ if ([kit(frame) _hasSelection])
+ return kit(frame);
+ return nil;
+}
+
+- (void)_clearSelectionInOtherFrames
+{
+ // We rely on WebDocumentSelection protocol implementors to call this method when they become first
+ // responder. It would be nicer to just notice first responder changes here instead, but there's no
+ // notification sent when the first responder changes in general (Radar 2573089).
+ WebFrame *frameWithSelection = [[getWebView(self) mainFrame] _findFrameWithSelection];
+ if (frameWithSelection != self)
+ [frameWithSelection _clearSelection];
+
+ // While we're in the general area of selection and frames, check that there is only one now.
+ ASSERT([[getWebView(self) mainFrame] _atMostOneFrameHasSelection]);
+}
+
+- (BOOL)_isMainFrame
+{
+ Frame* coreFrame = core(self);
+ if (!coreFrame)
+ return NO;
+ return coreFrame == coreFrame->page()->mainFrame() ;
+}
+
+- (FrameLoader*)_frameLoader
+{
+ Frame* frame = core(self);
+ return frame ? frame->loader() : 0;
+}
+
+static inline WebDataSource *dataSource(DocumentLoader* loader)
+{
+ return loader ? static_cast<WebDocumentLoaderMac*>(loader)->dataSource() : nil;
+}
+
+- (WebDataSource *)_dataSourceForDocumentLoader:(DocumentLoader*)loader
+{
+ return dataSource(loader);
+}
+
+- (void)_addDocumentLoader:(DocumentLoader*)loader toUnarchiveState:(WebArchive *)archive
+{
+ [dataSource(loader) _addToUnarchiveState:archive];
+}
+
+- (WebDataSource *)_dataSource
+{
+ FrameLoader* frameLoader = [self _frameLoader];
+
+ if (!frameLoader)
+ return nil;
+
+ return dataSource(frameLoader->documentLoader());
+}
+
+@end
+
+@implementation WebFrame (WebPrivate)
+
+// FIXME: Yhis exists only as a convenience for Safari, consider moving there.
+- (BOOL)_isDescendantOfFrame:(WebFrame *)ancestor
+{
+ Frame* coreFrame = core(self);
+ return coreFrame && coreFrame->tree()->isDescendantOf(core(ancestor));
+}
+
+- (void)_setShouldCreateRenderers:(BOOL)frame
+{
+ [_private->bridge setShouldCreateRenderers:frame];
+}
+
+- (NSColor *)_bodyBackgroundColor
+{
+ Document* document = core(self)->document();
+ if (!document)
+ return nil;
+ HTMLElement* body = document->body();
+ if (!body)
+ return nil;
+ RenderObject* bodyRenderer = body->renderer();
+ if (!bodyRenderer)
+ return nil;
+ Color color = bodyRenderer->style()->backgroundColor();
+ if (!color.isValid())
+ return nil;
+ return nsColor(color);
+}
+
+- (BOOL)_isFrameSet
+{
+ return core(self)->isFrameSet();
+}
+
+- (BOOL)_firstLayoutDone
+{
+ return [self _frameLoader]->firstLayoutDone();
+}
+
+- (WebFrameLoadType)_loadType
+{
+ return (WebFrameLoadType)[self _frameLoader]->loadType();
+}
+
+#ifndef __LP64__
+- (void)_recursive_resumeNullEventsForAllNetscapePlugins
+{
+ Frame* coreFrame = core(self);
+ for (Frame* frame = coreFrame; frame; frame = frame->tree()->traverseNext(coreFrame)) {
+ NSView <WebDocumentView> *documentView = [[kit(frame) frameView] documentView];
+ if ([documentView isKindOfClass:[WebHTMLView class]])
+ [(WebHTMLView *)documentView _resumeNullEventsForAllNetscapePlugins];
+ }
+}
+#endif
+
+#ifndef __LP64__
+- (void)_recursive_pauseNullEventsForAllNetscapePlugins
+{
+ Frame* coreFrame = core(self);
+ for (Frame* frame = coreFrame; frame; frame = frame->tree()->traverseNext(coreFrame)) {
+ NSView <WebDocumentView> *documentView = [[kit(frame) frameView] documentView];
+ if ([documentView isKindOfClass:[WebHTMLView class]])
+ [(WebHTMLView *)documentView _pauseNullEventsForAllNetscapePlugins];
+ }
+}
+#endif
+
+- (NSRange)_selectedNSRange
+{
+ return [_private->bridge selectedNSRange];
+}
+
+- (void)_selectNSRange:(NSRange)range
+{
+ [_private->bridge selectNSRange:range];
+}
+
+- (BOOL)_isDisplayingStandaloneImage
+{
+ Document* document = core(self)->document();
+ return document && document->isImageDocument();
+}
+
+@end
+
+@implementation WebFrame
+
+- (id)init
+{
+ return nil;
+}
+
+// Should be deprecated.
+- (id)initWithName:(NSString *)name webFrameView:(WebFrameView *)view webView:(WebView *)webView
+{
+ return nil;
+}
+
+- (void)dealloc
+{
+ ASSERT(_private->bridge == nil);
+ [_private release];
+ --WebFrameCount;
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT(_private->bridge == nil);
+ --WebFrameCount;
+ [super finalize];
+}
+
+- (NSString *)name
+{
+ Frame* coreFrame = core(self);
+ if (!coreFrame)
+ return nil;
+ return coreFrame->tree()->name();
+}
+
+- (WebFrameView *)frameView
+{
+ return _private->webFrameView;
+}
+
+- (WebView *)webView
+{
+ return getWebView(self);
+}
+
+- (DOMDocument *)DOMDocument
+{
+ Frame* coreFrame = core(self);
+ if (!coreFrame)
+ return nil;
+
+ // FIXME: <rdar://problem/5145841> When loading a custom view/representation
+ // into a web frame, the old document can still be around. This makes sure that
+ // we'll return nil in those cases.
+ if (![[self _dataSource] _isDocumentHTML])
+ return nil;
+
+ Document* document = coreFrame->document();
+
+ // According to the documentation, we should return nil if the frame doesn't have a document.
+ // While full-frame images and plugins do have an underlying HTML document, we return nil here to be
+ // backwards compatible.
+ if (document && (document->isPluginDocument() || document->isImageDocument()))
+ return nil;
+
+ return kit(coreFrame->document());
+}
+
+- (DOMHTMLElement *)frameElement
+{
+ Frame* coreFrame = core(self);
+ if (!coreFrame)
+ return nil;
+ return kit(coreFrame->ownerElement());
+}
+
+- (WebDataSource *)provisionalDataSource
+{
+ FrameLoader* frameLoader = [self _frameLoader];
+ return frameLoader ? dataSource(frameLoader->provisionalDocumentLoader()) : nil;
+}
+
+- (WebDataSource *)dataSource
+{
+ FrameLoader* loader = [self _frameLoader];
+ if (!loader || !loader->frameHasLoaded())
+ return nil;
+
+ return [self _dataSource];
+}
+
+- (void)loadRequest:(NSURLRequest *)request
+{
+ [self _frameLoader]->load(request);
+}
+
+static NSURL *createUniqueWebDataURL()
+{
+ CFUUIDRef UUIDRef = CFUUIDCreate(kCFAllocatorDefault);
+ NSString *UUIDString = (NSString *)CFUUIDCreateString(kCFAllocatorDefault, UUIDRef);
+ CFRelease(UUIDRef);
+ NSURL *URL = [NSURL URLWithString:[NSString stringWithFormat:@"applewebdata://%@", UUIDString]];
+ CFRelease(UUIDString);
+ return URL;
+}
+
+- (void)_loadData:(NSData *)data MIMEType:(NSString *)MIMEType textEncodingName:(NSString *)encodingName baseURL:(NSURL *)baseURL unreachableURL:(NSURL *)unreachableURL
+{
+ KURL responseURL;
+ if (!baseURL) {
+ baseURL = blankURL();
+ responseURL = createUniqueWebDataURL();
+ }
+
+ ResourceRequest request([baseURL absoluteURL]);
+
+ // hack because Mail checks for this property to detect data / archive loads
+ [NSURLProtocol setProperty:@"" forKey:@"WebDataRequest" inRequest:(NSMutableURLRequest *)request.nsURLRequest()];
+
+ SubstituteData substituteData(WebCore::SharedBuffer::wrapNSData(data), MIMEType, encodingName, [unreachableURL absoluteURL], responseURL);
+
+ [self _frameLoader]->load(request, substituteData);
+}
+
+
+- (void)loadData:(NSData *)data MIMEType:(NSString *)MIMEType textEncodingName:(NSString *)encodingName baseURL:(NSURL *)baseURL
+{
+ if (!MIMEType)
+ MIMEType = @"text/html";
+ [self _loadData:data MIMEType:MIMEType textEncodingName:encodingName baseURL:baseURL unreachableURL:nil];
+}
+
+- (void)_loadHTMLString:(NSString *)string baseURL:(NSURL *)baseURL unreachableURL:(NSURL *)unreachableURL
+{
+ NSData *data = [string dataUsingEncoding:NSUTF8StringEncoding];
+ [self _loadData:data MIMEType:@"text/html" textEncodingName:@"UTF-8" baseURL:baseURL unreachableURL:unreachableURL];
+}
+
+- (void)loadHTMLString:(NSString *)string baseURL:(NSURL *)baseURL
+{
+ [self _loadHTMLString:string baseURL:baseURL unreachableURL:nil];
+}
+
+- (void)loadAlternateHTMLString:(NSString *)string baseURL:(NSURL *)baseURL forUnreachableURL:(NSURL *)unreachableURL
+{
+ [self _loadHTMLString:string baseURL:baseURL unreachableURL:unreachableURL];
+}
+
+- (void)loadArchive:(WebArchive *)archive
+{
+ WebResource *mainResource = [archive mainResource];
+ if (mainResource) {
+ SubstituteData substituteData(WebCore::SharedBuffer::wrapNSData([mainResource data]), [mainResource MIMEType], [mainResource textEncodingName], KURL());
+ ResourceRequest request([mainResource URL]);
+
+ // hack because Mail checks for this property to detect data / archive loads
+ [NSURLProtocol setProperty:@"" forKey:@"WebDataRequest" inRequest:(NSMutableURLRequest *)request.nsURLRequest()];
+
+ RefPtr<DocumentLoader> documentLoader = core(self)->loader()->client()->createDocumentLoader(request, substituteData);
+
+ [dataSource(documentLoader.get()) _addToUnarchiveState:archive];
+
+ [self _frameLoader]->load(documentLoader.get());
+ }
+}
+
+- (void)stopLoading
+{
+ if (FrameLoader* frameLoader = [self _frameLoader])
+ frameLoader->stopForUserCancel();
+}
+
+- (void)reload
+{
+ [self _frameLoader]->reload();
+}
+
+- (WebFrame *)findFrameNamed:(NSString *)name
+{
+ Frame* coreFrame = core(self);
+ if (!coreFrame)
+ return nil;
+ return kit(coreFrame->tree()->find(name));
+}
+
+- (WebFrame *)parentFrame
+{
+ Frame* coreFrame = core(self);
+ if (!coreFrame)
+ return nil;
+ return [[kit(coreFrame->tree()->parent()) retain] autorelease];
+}
+
+- (NSArray *)childFrames
+{
+ Frame* coreFrame = core(self);
+ if (!coreFrame)
+ return [NSArray array];
+ NSMutableArray *children = [NSMutableArray arrayWithCapacity:coreFrame->tree()->childCount()];
+ for (Frame* child = coreFrame->tree()->firstChild(); child; child = child->tree()->nextSibling())
+ [children addObject:kit(child)];
+ return children;
+}
+
+- (WebScriptObject *)windowObject
+{
+ Frame* coreFrame = core(self);
+ if (!coreFrame)
+ return 0;
+ return coreFrame->windowScriptObject();
+}
+
+- (JSGlobalContextRef)globalContext
+{
+ Frame* coreFrame = core(self);
+ if (!coreFrame)
+ return 0;
+ return toGlobalRef(coreFrame->scriptProxy()->globalObject()->globalExec());
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebFrameInternal.h b/WebKit/mac/WebView/WebFrameInternal.h
new file mode 100644
index 0000000..89b5b1d
--- /dev/null
+++ b/WebKit/mac/WebView/WebFrameInternal.h
@@ -0,0 +1,171 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// This header contains WebFrame declarations that can be used anywhere in WebKit, but are neither SPI nor API.
+
+#import "WebFramePrivate.h"
+#import "WebPreferencesPrivate.h"
+
+#ifdef __cplusplus
+#import <WebCore/FrameLoaderTypes.h>
+#import <WebCore/Settings.h>
+#endif
+
+@class DOMCSSStyleDeclaration;
+@class DOMElement;
+@class DOMNode;
+@class DOMRange;
+@class WebFrameView;
+@class WebFrameBridge;
+@class WebHistoryItem;
+@class WebScriptDebugger;
+
+#ifdef __cplusplus
+
+namespace WebCore {
+ class CSSStyleDeclaration;
+ class Document;
+ class DocumentLoader;
+ class Element;
+ class Frame;
+ class Frame;
+ class FrameLoader;
+ class HistoryItem;
+ class HTMLElement;
+ class Node;
+ class Page;
+ class Range;
+}
+
+typedef WebCore::HistoryItem WebCoreHistoryItem;
+
+WebCore::CSSStyleDeclaration* core(DOMCSSStyleDeclaration *);
+DOMCSSStyleDeclaration *kit(WebCore::CSSStyleDeclaration*);
+
+WebCore::Frame* core(WebFrame *);
+WebFrame *kit(WebCore::Frame *);
+
+WebCore::Element* core(DOMElement *);
+DOMElement *kit(WebCore::Element*);
+
+WebCore::Node* core(DOMNode *);
+DOMNode *kit(WebCore::Node*);
+
+WebCore::Document* core(DOMDocument *);
+DOMDocument *kit(WebCore::Document*);
+
+WebCore::HTMLElement* core(DOMHTMLElement *);
+DOMHTMLElement *kit(WebCore::HTMLElement*);
+
+WebCore::Range* core(DOMRange *);
+DOMRange *kit(WebCore::Range*);
+
+WebCore::Page* core(WebView *);
+WebView *kit(WebCore::Page*);
+
+WebCore::EditableLinkBehavior core(WebKitEditableLinkBehavior);
+WebKitEditableLinkBehavior kit(WebCore::EditableLinkBehavior);
+
+WebView *getWebView(WebFrame *webFrame);
+
+@interface WebFramePrivate : NSObject
+{
+@public
+ WebFrameView *webFrameView;
+
+ WebFrameBridge *bridge;
+
+ WebScriptDebugger *scriptDebugger;
+ id internalLoadDelegate;
+}
+@end
+
+#else
+struct WebCoreHistoryItem;
+#endif
+
+@interface WebFrame (WebInternal)
+
+- (void)_updateBackground;
+- (void)_setInternalLoadDelegate:(id)internalLoadDelegate;
+- (id)_internalLoadDelegate;
+#ifndef BUILDING_ON_TIGER
+- (void)_unmarkAllBadGrammar;
+#endif
+- (void)_unmarkAllMisspellings;
+// Note that callers should not perform any ops on these views that could change the set of frames
+- (NSArray *)_documentViews;
+
+- (BOOL)_hasSelection;
+- (void)_clearSelection;
+- (WebFrame *)_findFrameWithSelection;
+- (void)_clearSelectionInOtherFrames;
+#ifdef __cplusplus
+- (id)_initWithWebFrameView:(WebFrameView *)fv webView:(WebView *)v bridge:(WebFrameBridge *)bridge;
+#endif
+
+- (BOOL)_isMainFrame;
+
+#ifdef __cplusplus
+
+- (WebCore::FrameLoader*)_frameLoader;
+- (WebDataSource *)_dataSourceForDocumentLoader:(WebCore::DocumentLoader*)loader;
+
+- (void)_addDocumentLoader:(WebCore::DocumentLoader*)loader toUnarchiveState:(WebArchive *)archive;
+
+#endif
+
+- (WebFrameBridge *)_bridge;
+
+- (void)_loadURL:(NSURL *)URL referrer:(NSString *)referrer intoChild:(WebFrame *)childFrame;
+
+- (void)_viewWillMoveToHostWindow:(NSWindow *)hostWindow;
+- (void)_viewDidMoveToHostWindow;
+
+- (void)_addChild:(WebFrame *)child;
+
++ (CFAbsoluteTime)_timeOfLastCompletedLoad;
+
+- (int)_numPendingOrLoadingRequests:(BOOL)recurse;
+
+- (void)_reloadForPluginChanges;
+
+- (void)_attachScriptDebugger;
+- (void)_detachScriptDebugger;
+
+// dataSource reports null for the initial empty document's data source; this is needed
+// to preserve compatibility with Mail and Safari among others. But internal to WebKit,
+// we need to be able to get the initial data source as well, so the _dataSource method
+// should be used instead.
+- (WebDataSource *)_dataSource;
+
+@end
+
+@interface NSObject (WebInternalFrameLoadDelegate)
+- (void)webFrame:(WebFrame *)webFrame didFinishLoadWithError:(NSError *)error;
+@end
diff --git a/WebKit/mac/WebView/WebFrameLoadDelegate.h b/WebKit/mac/WebView/WebFrameLoadDelegate.h
new file mode 100644
index 0000000..b463988
--- /dev/null
+++ b/WebKit/mac/WebView/WebFrameLoadDelegate.h
@@ -0,0 +1,196 @@
+/*
+ * Copyright (C) 2003, 2004, 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@class NSError;
+@class WebFrame;
+@class WebScriptObject;
+@class WebView;
+
+/*!
+ @category WebFrameLoadDelegate
+ @discussion A WebView's WebFrameLoadDelegate tracks the loading progress of its frames.
+ When a data source of a frame starts to load, the data source is considered "provisional".
+ Once at least one byte is received, the data source is considered "committed". This is done
+ so the contents of the frame will not be lost if the new data source fails to successfully load.
+*/
+@interface NSObject (WebFrameLoadDelegate)
+
+/*!
+ @method webView:didStartProvisionalLoadForFrame:
+ @abstract Notifies the delegate that the provisional load of a frame has started
+ @param webView The WebView sending the message
+ @param frame The frame for which the provisional load has started
+ @discussion This method is called after the provisional data source of a frame
+ has started to load.
+*/
+- (void)webView:(WebView *)sender didStartProvisionalLoadForFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:didReceiveServerRedirectForProvisionalLoadForFrame:
+ @abstract Notifies the delegate that a server redirect occurred during the provisional load
+ @param webView The WebView sending the message
+ @param frame The frame for which the redirect occurred
+*/
+- (void)webView:(WebView *)sender didReceiveServerRedirectForProvisionalLoadForFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:didFailProvisionalLoadWithError:forFrame:
+ @abstract Notifies the delegate that the provisional load has failed
+ @param webView The WebView sending the message
+ @param error The error that occurred
+ @param frame The frame for which the error occurred
+ @discussion This method is called after the provisional data source has failed to load.
+ The frame will continue to display the contents of the committed data source if there is one.
+*/
+- (void)webView:(WebView *)sender didFailProvisionalLoadWithError:(NSError *)error forFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:didCommitLoadForFrame:
+ @abstract Notifies the delegate that the load has changed from provisional to committed
+ @param webView The WebView sending the message
+ @param frame The frame for which the load has committed
+ @discussion This method is called after the provisional data source has become the
+ committed data source.
+
+ In some cases, a single load may be committed more than once. This happens
+ in the case of multipart/x-mixed-replace, also known as "server push". In this case,
+ a single location change leads to multiple documents that are loaded in sequence. When
+ this happens, a new commit will be sent for each document.
+*/
+- (void)webView:(WebView *)sender didCommitLoadForFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:didReceiveTitle:forFrame:
+ @abstract Notifies the delegate that the page title for a frame has been received
+ @param webView The WebView sending the message
+ @param title The new page title
+ @param frame The frame for which the title has been received
+ @discussion The title may update during loading; clients should be prepared for this.
+*/
+- (void)webView:(WebView *)sender didReceiveTitle:(NSString *)title forFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:didReceiveIcon:forFrame:
+ @abstract Notifies the delegate that a page icon image for a frame has been received
+ @param webView The WebView sending the message
+ @param image The icon image. Also known as a "favicon".
+ @param frame The frame for which a page icon has been received
+*/
+- (void)webView:(WebView *)sender didReceiveIcon:(NSImage *)image forFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:didFinishLoadForFrame:
+ @abstract Notifies the delegate that the committed load of a frame has completed
+ @param webView The WebView sending the message
+ @param frame The frame that finished loading
+ @discussion This method is called after the committed data source of a frame has successfully loaded
+ and will only be called when all subresources such as images and stylesheets are done loading.
+ Plug-In content and JavaScript-requested loads may occur after this method is called.
+*/
+- (void)webView:(WebView *)sender didFinishLoadForFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:didFailLoadWithError:forFrame:
+ @abstract Notifies the delegate that the committed load of a frame has failed
+ @param webView The WebView sending the message
+ @param error The error that occurred
+ @param frame The frame that failed to load
+ @discussion This method is called after a data source has committed but failed to completely load.
+*/
+- (void)webView:(WebView *)sender didFailLoadWithError:(NSError *)error forFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:didChangeLocationWithinPageForFrame:
+ @abstract Notifies the delegate that the scroll position in a frame has changed
+ @param webView The WebView sending the message
+ @param frame The frame that scrolled
+ @discussion This method is called when anchors within a page have been clicked.
+*/
+- (void)webView:(WebView *)sender didChangeLocationWithinPageForFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:willPerformClientRedirectToURL:delay:fireDate:forFrame:
+ @abstract Notifies the delegate that a frame will perform a client-side redirect
+ @param webView The WebView sending the message
+ @param URL The URL to be redirected to
+ @param seconds Seconds in which the redirect will happen
+ @param date The fire date
+ @param frame The frame on which the redirect will occur
+ @discussion This method can be used to continue progress feedback while a client-side
+ redirect is pending.
+*/
+- (void)webView:(WebView *)sender willPerformClientRedirectToURL:(NSURL *)URL delay:(NSTimeInterval)seconds fireDate:(NSDate *)date forFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:didCancelClientRedirectForFrame:
+ @abstract Notifies the delegate that a pending client-side redirect has been cancelled
+ @param webView The WebView sending the message
+ @param frame The frame for which the pending redirect was cancelled
+ @discussion A client-side redirect can be cancelled if a frame changes location before the timeout.
+*/
+- (void)webView:(WebView *)sender didCancelClientRedirectForFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:willCloseFrame:
+ @abstract Notifies the delegate that a frame will be closed
+ @param webView The WebView sending the message
+ @param frame The frame that will be closed
+ @discussion This method is called right before WebKit is done with the frame
+ and the objects that it contains.
+*/
+- (void)webView:(WebView *)sender willCloseFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:didClearWindowObject:forFrame:
+ @abstract Notifies the delegate that the JavaScript window object in a frame has
+ been cleared in preparation for a new load. This is the preferred place to set custom
+ properties on the window object using the WebScriptObject and JavaScriptCore APIs.
+ @param webView The webView sending the message.
+ @param windowObject The WebScriptObject representing the frame's JavaScript window object.
+ @param frame The WebFrame to which windowObject belongs.
+ @discussion If a delegate implements both webView:didClearWindowObject:forFrame:
+ and webView:windowScriptObjectAvailable:, only webView:didClearWindowObject:forFrame:
+ will be invoked. This enables a delegate to implement both methods for backwards
+ compatibility with older versions of WebKit.
+*/
+- (void)webView:(WebView *)webView didClearWindowObject:(WebScriptObject *)windowObject forFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:windowScriptObjectAvailable:
+ @abstract Notifies the delegate that the scripting object for a page is available. This is called
+ before the page is loaded. It may be useful to allow delegates to bind native objects to the window.
+ @param webView The webView sending the message.
+ @param windowScriptObject The WebScriptObject for the window in the scripting environment.
+ @discussion This method is deprecated. Consider using webView:didClearWindowObject:forFrame:
+ instead.
+*/
+- (void)webView:(WebView *)webView windowScriptObjectAvailable:(WebScriptObject *)windowScriptObject;
+
+@end
diff --git a/WebKit/mac/WebView/WebFramePrivate.h b/WebKit/mac/WebView/WebFramePrivate.h
new file mode 100644
index 0000000..4595572
--- /dev/null
+++ b/WebKit/mac/WebView/WebFramePrivate.h
@@ -0,0 +1,73 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// This header contains the WebFrame SPI.
+
+#import <WebKit/WebFrame.h>
+#import <JavaScriptCore/JSBase.h>
+
+@class WebScriptObject;
+
+// Keys for accessing the values in the page cache dictionary.
+extern NSString *WebPageCacheEntryDateKey;
+extern NSString *WebPageCacheDataSourceKey;
+extern NSString *WebPageCacheDocumentViewKey;
+
+typedef enum {
+ WebFrameLoadTypeStandard,
+ WebFrameLoadTypeBack,
+ WebFrameLoadTypeForward,
+ WebFrameLoadTypeIndexedBackForward, // a multi-item hop in the backforward list
+ WebFrameLoadTypeReload,
+ WebFrameLoadTypeReloadAllowingStaleData,
+ WebFrameLoadTypeSame, // user loads same URL again (but not reload button)
+ WebFrameLoadTypeInternal, // maps to WebCore::FrameLoadTypeRedirectWithLockedHistory
+ WebFrameLoadTypeReplace
+} WebFrameLoadType;
+
+@interface WebFrame (WebPrivate)
+- (BOOL)_isDescendantOfFrame:(WebFrame *)frame;
+- (void)_setShouldCreateRenderers:(BOOL)f;
+- (NSColor *)_bodyBackgroundColor;
+- (BOOL)_isFrameSet;
+- (BOOL)_firstLayoutDone;
+- (WebFrameLoadType)_loadType;
+#ifndef __LP64__
+- (void)_recursive_resumeNullEventsForAllNetscapePlugins;
+- (void)_recursive_pauseNullEventsForAllNetscapePlugins;
+#endif
+
+// These methods take and return NSRanges based on the root editable element as the positional base.
+// This fits with AppKit's idea of an input context. These methods are slow compared to their DOMRange equivalents.
+// You should use WebView's selectedDOMRange and setSelectedDOMRange whenever possible.
+- (NSRange)_selectedNSRange;
+- (void)_selectNSRange:(NSRange)range;
+
+- (BOOL)_isDisplayingStandaloneImage;
+
+@end
diff --git a/WebKit/mac/WebView/WebFrameView.h b/WebKit/mac/WebView/WebFrameView.h
new file mode 100644
index 0000000..e170403
--- /dev/null
+++ b/WebKit/mac/WebView/WebFrameView.h
@@ -0,0 +1,103 @@
+/*
+ * Copyright (C) 2003, 2004, 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@class WebDataSource;
+@class WebFrame;
+@class WebFrameViewPrivate;
+
+@protocol WebDocumentView;
+
+/*!
+ @class WebFrameView
+*/
+@interface WebFrameView : NSView
+{
+@private
+ WebFrameViewPrivate *_private;
+}
+
+/*!
+ @method webFrame
+ @abstract Returns the WebFrame associated with this WebFrameView
+ @result The WebFrameView's frame.
+*/
+- (WebFrame *)webFrame;
+
+/*!
+ @method documentView
+ @abstract Returns the WebFrameView's document subview
+ @result The subview that renders the WebFrameView's contents
+*/
+- (NSView <WebDocumentView> *)documentView;
+
+/*!
+ @method setAllowsScrolling:
+ @abstract Sets whether the WebFrameView allows its document to be scrolled
+ @param flag YES to allow the document to be scrolled, NO to disallow scrolling
+*/
+- (void)setAllowsScrolling:(BOOL)flag;
+
+/*!
+ @method allowsScrolling
+ @abstract Returns whether the WebFrameView allows its document to be scrolled
+ @result YES if the document is allowed to scroll, otherwise NO
+*/
+- (BOOL)allowsScrolling;
+
+/*!
+ @method canPrintHeadersAndFooters
+ @abstract Tells whether this frame can print headers and footers
+ @result YES if the frame can, no otherwise
+*/
+- (BOOL)canPrintHeadersAndFooters;
+
+/*!
+ @method printOperationWithPrintInfo
+ @abstract Creates a print operation set up to print this frame
+ @result A newly created print operation object
+*/
+- (NSPrintOperation *)printOperationWithPrintInfo:(NSPrintInfo *)printInfo;
+
+/*!
+ @method documentViewShouldHandlePrint
+ @abstract Called by the host application before it initializes and runs a print operation.
+ @result If NO is returned, the host application will abort its print operation and call -printDocumentView on the
+ WebFrameView. The document view is then expected to run its own print operation. If YES is returned, the host
+ application's print operation will continue as normal.
+*/
+- (BOOL)documentViewShouldHandlePrint;
+
+/*!
+ @method printDocumentView
+ @abstract Called by the host application when the WebFrameView returns YES from -documentViewShouldHandlePrint.
+*/
+- (void)printDocumentView;
+
+@end
diff --git a/WebKit/mac/WebView/WebFrameView.mm b/WebKit/mac/WebView/WebFrameView.mm
new file mode 100644
index 0000000..ef1a4bd
--- /dev/null
+++ b/WebKit/mac/WebView/WebFrameView.mm
@@ -0,0 +1,960 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebFrameView.h"
+
+#import "WebClipView.h"
+#import "WebDataSourcePrivate.h"
+#import "WebDocument.h"
+#import "WebDynamicScrollBarsView.h"
+#import "WebFrame.h"
+#import "WebFrameInternal.h"
+#import "WebFrameBridge.h"
+#import "WebFrameViewInternal.h"
+#import "WebFrameViewPrivate.h"
+#import "WebHistoryItemInternal.h"
+#import "WebHTMLViewPrivate.h"
+#import "WebKeyGenerator.h"
+#import "WebKitErrorsPrivate.h"
+#import "WebKitStatisticsPrivate.h"
+#import "WebKitVersionChecks.h"
+#import "WebNSDictionaryExtras.h"
+#import "WebNSObjectExtras.h"
+#import "WebNSPasteboardExtras.h"
+#import "WebNSViewExtras.h"
+#import "WebNSWindowExtras.h"
+#import "WebPDFView.h"
+#import "WebPreferenceKeysPrivate.h"
+#import "WebSystemInterface.h"
+#import "WebViewFactory.h"
+#import "WebViewInternal.h"
+#import "WebViewPrivate.h"
+#import <Foundation/NSURLRequest.h>
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/DragController.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameView.h>
+#import <WebCore/HistoryItem.h>
+#import <WebCore/Page.h>
+#import <WebCore/ThreadCheck.h>
+#import <WebCore/WebCoreFrameView.h>
+#import <WebCore/WebCoreView.h>
+#import <WebKitSystemInterface.h>
+
+using namespace WebCore;
+
+@interface NSWindow (WindowPrivate)
+- (BOOL)_needsToResetDragMargins;
+- (void)_setNeedsToResetDragMargins:(BOOL)s;
+@end
+
+@interface NSClipView (AppKitSecretsIKnow)
+- (BOOL)_scrollTo:(const NSPoint *)newOrigin animate:(BOOL)animate; // need the boolean result from this method
+@end
+
+enum {
+ SpaceKey = 0x0020
+};
+
+@interface WebFrameView (WebFrameViewFileInternal) <WebCoreBridgeHolder>
+- (float)_verticalKeyboardScrollDistance;
+- (WebCoreFrameBridge *) webCoreBridge;
+@end
+
+@interface WebFrameViewPrivate : NSObject {
+@public
+ WebFrame *webFrame;
+ WebDynamicScrollBarsView *frameScrollView;
+
+ // These margin values are used to temporarily hold the margins of a frame until
+ // we have the appropriate document view type.
+ int marginWidth;
+ int marginHeight;
+}
+@end
+
+@implementation WebFrameViewPrivate
+
+- init
+{
+ [super init];
+
+ marginWidth = -1;
+ marginHeight = -1;
+
+ return self;
+}
+
+- (void)dealloc
+{
+ [frameScrollView release];
+ [super dealloc];
+}
+
+@end
+
+@implementation WebFrameView (WebFrameViewFileInternal)
+
+- (float)_verticalKeyboardScrollDistance
+{
+ // Arrow keys scroll the same distance that clicking the scroll arrow does.
+ return [[self _scrollView] verticalLineScroll];
+}
+
+- (WebCoreFrameBridge *) webCoreBridge
+{
+ return [_private->webFrame _bridge];
+}
+
+@end
+
+@implementation WebFrameView (WebInternal)
+
+// Note that the WebVew is not retained.
+- (WebView *)_webView
+{
+ return [_private->webFrame webView];
+}
+
+- (void)_setMarginWidth:(int)w
+{
+ _private->marginWidth = w;
+}
+
+- (int)_marginWidth
+{
+ return _private->marginWidth;
+}
+
+- (void)_setMarginHeight:(int)h
+{
+ _private->marginHeight = h;
+}
+
+- (int)_marginHeight
+{
+ return _private->marginHeight;
+}
+
+- (void)_setDocumentView:(NSView <WebDocumentView> *)view
+{
+ WebDynamicScrollBarsView *sv = [self _scrollView];
+ core([self _webView])->dragController()->setDidInitiateDrag(false);
+
+ [sv setSuppressLayout:YES];
+
+ // If the old view is the first responder, transfer first responder status to the new view as
+ // a convenience and so that we don't leave the window pointing to a view that's no longer in it.
+ NSWindow *window = [sv window];
+ NSResponder *firstResponder = [window firstResponder];
+ bool makeNewViewFirstResponder = [firstResponder isKindOfClass:[NSView class]] && [(NSView *)firstResponder isDescendantOf:[sv documentView]];
+
+ // Suppress the resetting of drag margins since we know we can't affect them.
+ BOOL resetDragMargins = [window _needsToResetDragMargins];
+ [window _setNeedsToResetDragMargins:NO];
+ [sv setDocumentView:view];
+ [window _setNeedsToResetDragMargins:resetDragMargins];
+
+ if (makeNewViewFirstResponder)
+ [window makeFirstResponder:view];
+ [sv setSuppressLayout:NO];
+}
+
+-(NSView <WebDocumentView> *)_makeDocumentViewForDataSource:(WebDataSource *)dataSource
+{
+ NSString* MIMEType = [dataSource _responseMIMEType];
+ if (!MIMEType)
+ MIMEType = @"text/html";
+ Class viewClass = [[self class] _viewClassForMIMEType:MIMEType];
+ NSView <WebDocumentView> *documentView;
+ if (viewClass) {
+ // If the dataSource's representation has already been created, and it is also the
+ // same class as the desired documentView, then use it as the documentView instead
+ // of creating another one (Radar 4340787).
+ id <WebDocumentRepresentation> dataSourceRepresentation = [dataSource representation];
+ if (dataSourceRepresentation && [dataSourceRepresentation class] == viewClass)
+ documentView = (NSView <WebDocumentView> *)[dataSourceRepresentation retain];
+ else
+ documentView = [[viewClass alloc] initWithFrame:[self bounds]];
+ } else
+ documentView = nil;
+
+ [self _setDocumentView:documentView];
+ [documentView release];
+
+ return documentView;
+}
+
+- (void)_setWebFrame:(WebFrame *)webFrame
+{
+ if (!webFrame) {
+ NSView *docV = [self documentView];
+ if ([docV respondsToSelector:@selector(close)])
+ [docV performSelector:@selector(close)];
+ }
+
+ // Not retained because the WebView owns the WebFrame, which owns the WebFrameView.
+ _private->webFrame = webFrame;
+}
+
+- (WebDynamicScrollBarsView *)_scrollView
+{
+ // this can be called by [super dealloc] when cleaning up the keyview loop,
+ // after _private has been nilled out.
+ if (_private == nil) {
+ return nil;
+ }
+ return _private->frameScrollView;
+}
+
+- (float)_verticalPageScrollDistance
+{
+ float overlap = [self _verticalKeyboardScrollDistance];
+ float height = [[self _contentView] bounds].size.height;
+ return (height < overlap) ? height / 2 : height - overlap;
+}
+
+static inline void addTypesFromClass(NSMutableDictionary *allTypes, Class objCClass, NSArray *supportTypes)
+{
+ NSEnumerator *enumerator = [supportTypes objectEnumerator];
+ ASSERT(enumerator != nil);
+ NSString *mime = nil;
+ while ((mime = [enumerator nextObject]) != nil) {
+ // Don't clobber previously-registered classes.
+ if ([allTypes objectForKey:mime] == nil)
+ [allTypes setObject:objCClass forKey:mime];
+ }
+}
+
++ (NSMutableDictionary *)_viewTypesAllowImageTypeOmission:(BOOL)allowImageTypeOmission
+{
+ static NSMutableDictionary *viewTypes = nil;
+ static BOOL addedImageTypes = NO;
+
+ if (!viewTypes) {
+ viewTypes = [[NSMutableDictionary alloc] init];
+ addTypesFromClass(viewTypes, [WebHTMLView class], [WebHTMLView supportedNonImageMIMETypes]);
+
+ // Since this is a "secret default" we don't bother registering it.
+ BOOL omitPDFSupport = [[NSUserDefaults standardUserDefaults] boolForKey:@"WebKitOmitPDFSupport"];
+ if (!omitPDFSupport)
+ addTypesFromClass(viewTypes, [WebPDFView class], [WebPDFView supportedMIMETypes]);
+ }
+
+ if (!addedImageTypes && !allowImageTypeOmission) {
+ addTypesFromClass(viewTypes, [WebHTMLView class], [WebHTMLView supportedImageMIMETypes]);
+ addedImageTypes = YES;
+ }
+
+ return viewTypes;
+}
+
++ (BOOL)_canShowMIMETypeAsHTML:(NSString *)MIMEType
+{
+ return [[[self _viewTypesAllowImageTypeOmission:YES] _webkit_objectForMIMEType:MIMEType] isSubclassOfClass:[WebHTMLView class]];
+}
+
++ (Class)_viewClassForMIMEType:(NSString *)MIMEType
+{
+ Class viewClass;
+ return [WebView _viewClass:&viewClass andRepresentationClass:nil forMIMEType:MIMEType] ? viewClass : nil;
+}
+
+@end
+
+@implementation WebFrameView
+
+- initWithCoder:(NSCoder *)decoder
+{
+ // Older nibs containing WebViews will also contain WebFrameViews. We need to keep track of
+ // their count also to match the decrement in -dealloc.
+ ++WebFrameViewCount;
+ return [super initWithCoder:decoder];
+}
+
+- initWithFrame:(NSRect)frame
+{
+ self = [super initWithFrame:frame];
+ if (!self)
+ return nil;
+
+ static bool didFirstTimeInitialization;
+ if (!didFirstTimeInitialization) {
+ didFirstTimeInitialization = true;
+ InitWebCoreSystemInterface();
+
+ // Need to tell WebCore what function to call for the
+ // "History Item has Changed" notification
+ // Note: We also do this in WebHistoryItem's init method
+ WebCore::notifyHistoryItemChanged = WKNotifyHistoryItemChanged;
+
+ [WebViewFactory createSharedFactory];
+ [WebKeyGenerator createSharedGenerator];
+
+ NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
+
+ // CoreGraphics deferred updates are disabled if WebKitEnableCoalescedUpdatesPreferenceKey is set
+ // to NO, or has no value. For compatibility with Mac OS X 10.4.6, deferred updates are OFF by
+ // default.
+ if (![defaults boolForKey:WebKitEnableDeferredUpdatesPreferenceKey])
+ WKDisableCGDeferredUpdates();
+
+ if (!WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITH_MAIN_THREAD_EXCEPTIONS))
+ setDefaultThreadViolationBehavior(LogOnFirstThreadViolation);
+ }
+
+ _private = [[WebFrameViewPrivate alloc] init];
+
+ WebDynamicScrollBarsView *scrollView = [[WebDynamicScrollBarsView alloc] initWithFrame:NSMakeRect(0.0f, 0.0f, frame.size.width, frame.size.height)];
+ _private->frameScrollView = scrollView;
+ [scrollView setContentView:[[[WebClipView alloc] initWithFrame:[scrollView bounds]] autorelease]];
+ [scrollView setDrawsBackground:NO];
+ [scrollView setHasVerticalScroller:NO];
+ [scrollView setHasHorizontalScroller:NO];
+ [scrollView setAutoresizingMask:NSViewWidthSizable | NSViewHeightSizable];
+ [scrollView setLineScroll:40.0f];
+ [self addSubview:scrollView];
+ // don't call our overridden version here; we need to make the standard NSView link between us
+ // and our subview so that previousKeyView and previousValidKeyView work as expected. This works
+ // together with our becomeFirstResponder and setNextKeyView overrides.
+ [super setNextKeyView:scrollView];
+
+ ++WebFrameViewCount;
+
+ return self;
+}
+
+- (void)dealloc
+{
+ --WebFrameViewCount;
+
+ [_private release];
+ _private = nil;
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ --WebFrameViewCount;
+
+ [super finalize];
+}
+
+- (WebFrame *)webFrame
+{
+ return _private->webFrame;
+}
+
+- (void)setAllowsScrolling:(BOOL)flag
+{
+ WebDynamicScrollBarsView *scrollView = [self _scrollView];
+ [scrollView setAllowsScrolling:flag];
+ WebCore::Frame *frame = core([self webFrame]);
+ if (WebCore::FrameView *view = frame? frame->view() : 0) {
+ view->setHScrollbarMode((WebCore::ScrollbarMode)[scrollView horizontalScrollingMode]);
+ view->setVScrollbarMode((WebCore::ScrollbarMode)[scrollView verticalScrollingMode]);
+ }
+}
+
+- (BOOL)allowsScrolling
+{
+ return [[self _scrollView] allowsScrolling];
+}
+
+- (NSView <WebDocumentView> *)documentView
+{
+ return [[self _scrollView] documentView];
+}
+
+- (BOOL)acceptsFirstResponder
+{
+ // We always accept first responder; this matches OS X 10.2 WebKit
+ // behavior (see 3469791).
+ return YES;
+}
+
+- (BOOL)becomeFirstResponder
+{
+ // This works together with setNextKeyView to splice the WebFrameView into
+ // the key loop similar to the way NSScrollView does this. Note that
+ // WebView has similar code.
+
+ // If the scrollView won't accept first-responderness now, then we just become
+ // the first responder ourself like a normal view. This lets us be the first
+ // responder in cases where no page has yet been loaded (see 3469791).
+ if ([[self _scrollView] acceptsFirstResponder]) {
+ NSWindow *window = [self window];
+ if ([window keyViewSelectionDirection] == NSSelectingPrevious) {
+ NSView *previousValidKeyView = [self previousValidKeyView];
+ // If we couldn't find a previous valid key view, ask the webview. This handles frameset
+ // cases like 3748628. Note that previousValidKeyView should never be self but can be
+ // due to AppKit oddness (mentioned in 3748628).
+ if (previousValidKeyView == nil || previousValidKeyView == self) {
+ previousValidKeyView = [[[self webFrame] webView] previousValidKeyView];
+ }
+ // I don't know if the following cases ever occur anymore, but I'm leaving in the old test for
+ // now to avoid causing trouble just before shipping Tiger.
+ ASSERT((previousValidKeyView != self) && (previousValidKeyView != [self _scrollView]));
+ if ((previousValidKeyView != self) && (previousValidKeyView != [self _scrollView])) {
+ [window makeFirstResponder:previousValidKeyView];
+ }
+ } else {
+ [window makeFirstResponder:[self _scrollView]];
+ }
+ }
+
+ return YES;
+}
+
+- (void)setNextKeyView:(NSView *)aView
+{
+ // This works together with becomeFirstResponder to splice the WebFrameView into
+ // the key loop similar to the way NSScrollView does this. Note that
+ // WebView has very similar code.
+ if ([self _scrollView] != nil) {
+ [[self _scrollView] setNextKeyView:aView];
+ } else {
+ [super setNextKeyView:aView];
+ }
+}
+
+- (BOOL)isOpaque
+{
+ return [[self _webView] drawsBackground];
+}
+
+- (void)drawRect:(NSRect)rect
+{
+ if ([self documentView] == nil) {
+ // Need to paint ourselves if there's no documentView to do it instead.
+ if ([[self _webView] drawsBackground]) {
+ [[[self _webView] backgroundColor] set];
+ NSRectFill(rect);
+ }
+ } else {
+#ifndef NDEBUG
+ if ([[self _scrollView] drawsBackground]) {
+ [[NSColor cyanColor] set];
+ NSRectFill(rect);
+ }
+#endif
+ }
+}
+
+- (void)setFrameSize:(NSSize)size
+{
+ if (!NSEqualSizes(size, [self frame].size) && [[[self webFrame] webView] drawsBackground]) {
+ [[self _scrollView] setDrawsBackground:YES];
+ }
+ [super setFrameSize:size];
+}
+
+- (WebFrameBridge *)_bridge
+{
+ return [[self webFrame] _bridge];
+}
+
+- (BOOL)_scrollOverflowInDirection:(WebScrollDirection)direction granularity:(WebScrollGranularity)granularity
+{
+ // scrolling overflows is only applicable if we're dealing with an WebHTMLView
+ return ([[self documentView] isKindOfClass:[WebHTMLView class]] && [[self _bridge] scrollOverflowInDirection:direction granularity:granularity]);
+}
+
+- (void)scrollToBeginningOfDocument:(id)sender
+{
+ if (![self _scrollOverflowInDirection:WebScrollUp granularity:WebScrollDocument]) {
+
+ if (![self _hasScrollBars]) {
+ [[self _largestChildWithScrollBars] scrollToBeginningOfDocument:sender];
+ return;
+ }
+
+ [[self _contentView] scrollPoint:[[[self _scrollView] documentView] frame].origin];
+ }
+}
+
+- (void)scrollToEndOfDocument:(id)sender
+{
+ if (![self _scrollOverflowInDirection:WebScrollDown granularity:WebScrollDocument]) {
+
+ if (![self _hasScrollBars]) {
+ [[self _largestChildWithScrollBars] scrollToEndOfDocument:sender];
+ return;
+ }
+
+ NSRect frame = [[[self _scrollView] documentView] frame];
+ [[self _contentView] scrollPoint:NSMakePoint(frame.origin.x, NSMaxY(frame))];
+ }
+}
+
+- (void)_goBack
+{
+ [[self _webView] goBack];
+}
+
+- (void)_goForward
+{
+ [[self _webView] goForward];
+}
+
+- (BOOL)_scrollVerticallyBy:(float)delta
+{
+ // This method uses the secret method _scrollTo on NSClipView.
+ // It does that because it needs to know definitively whether scrolling was
+ // done or not to help implement the "scroll parent if we are at the limit" feature.
+ // In the presence of smooth scrolling, there's no easy way to tell if the method
+ // did any scrolling or not with the public API.
+ NSPoint point = [[self _contentView] bounds].origin;
+ point.y += delta;
+ return [[self _contentView] _scrollTo:&point animate:YES];
+}
+
+- (BOOL)_scrollHorizontallyBy:(float)delta
+{
+ NSPoint point = [[self _contentView] bounds].origin;
+ point.x += delta;
+ return [[self _contentView] _scrollTo:&point animate:YES];
+}
+
+- (float)_horizontalKeyboardScrollDistance
+{
+ // Arrow keys scroll the same distance that clicking the scroll arrow does.
+ return [[self _scrollView] horizontalLineScroll];
+}
+
+- (float)_horizontalPageScrollDistance
+{
+ float overlap = [self _horizontalKeyboardScrollDistance];
+ float width = [[self _contentView] bounds].size.width;
+ return (width < overlap) ? width / 2 : width - overlap;
+}
+
+- (BOOL)_pageVertically:(BOOL)up
+{
+ if ([self _scrollOverflowInDirection:up ? WebScrollUp : WebScrollDown granularity:WebScrollPage])
+ return YES;
+
+ if (![self _hasScrollBars])
+ return [[self _largestChildWithScrollBars] _pageVertically:up];
+
+ float delta = [self _verticalPageScrollDistance];
+ return [self _scrollVerticallyBy:up ? -delta : delta];
+}
+
+- (BOOL)_pageHorizontally:(BOOL)left
+{
+ if ([self _scrollOverflowInDirection:left ? WebScrollLeft : WebScrollRight granularity:WebScrollPage])
+ return YES;
+
+ if (![self _hasScrollBars])
+ return [[self _largestChildWithScrollBars] _pageHorizontally:left];
+
+ float delta = [self _horizontalPageScrollDistance];
+ return [self _scrollHorizontallyBy:left ? -delta : delta];
+}
+
+- (BOOL)_scrollLineVertically:(BOOL)up
+{
+ if ([self _scrollOverflowInDirection:up ? WebScrollUp : WebScrollDown granularity:WebScrollLine])
+ return YES;
+
+ if (![self _hasScrollBars])
+ return [[self _largestChildWithScrollBars] _scrollLineVertically:up];
+
+ float delta = [self _verticalKeyboardScrollDistance];
+ return [self _scrollVerticallyBy:up ? -delta : delta];
+}
+
+- (BOOL)_scrollLineHorizontally:(BOOL)left
+{
+ if ([self _scrollOverflowInDirection:left ? WebScrollLeft : WebScrollRight granularity:WebScrollLine])
+ return YES;
+
+ if (![self _hasScrollBars])
+ return [[self _largestChildWithScrollBars] _scrollLineHorizontally:left];
+
+ float delta = [self _horizontalKeyboardScrollDistance];
+ return [self _scrollHorizontallyBy:left ? -delta : delta];
+}
+
+- (void)scrollPageUp:(id)sender
+{
+ if (![self _pageVertically:YES]) {
+ // If we were already at the top, tell the next responder to scroll if it can.
+ [[self nextResponder] tryToPerform:@selector(scrollPageUp:) with:sender];
+ }
+}
+
+- (void)scrollPageDown:(id)sender
+{
+ if (![self _pageVertically:NO]) {
+ // If we were already at the bottom, tell the next responder to scroll if it can.
+ [[self nextResponder] tryToPerform:@selector(scrollPageDown:) with:sender];
+ }
+}
+
+- (void)scrollLineUp:(id)sender
+{
+ [self _scrollLineVertically:YES];
+}
+
+- (void)scrollLineDown:(id)sender
+{
+ [self _scrollLineVertically:NO];
+}
+
+- (BOOL)_firstResponderIsFormControl
+{
+ NSResponder *firstResponder = [[self window] firstResponder];
+
+ // WebHTMLView is an NSControl subclass these days, but it's not a form control
+ if ([firstResponder isKindOfClass:[WebHTMLView class]]) {
+ return NO;
+ }
+ return [firstResponder isKindOfClass:[NSControl class]];
+}
+
+- (void)keyDown:(NSEvent *)event
+{
+ NSString *characters = [event characters];
+ int index, count;
+ BOOL callSuper = YES;
+ BOOL maintainsBackForwardList = core([self webFrame])->page()->backForwardList()->enabled() ? YES : NO;
+
+ count = [characters length];
+ for (index = 0; index < count; ++index) {
+ switch ([characters characterAtIndex:index]) {
+ case NSDeleteCharacter:
+ if (!maintainsBackForwardList) {
+ callSuper = YES;
+ break;
+ }
+ // This odd behavior matches some existing browsers,
+ // including Windows IE
+ if ([event modifierFlags] & NSShiftKeyMask) {
+ [self _goForward];
+ } else {
+ [self _goBack];
+ }
+ callSuper = NO;
+ break;
+ case SpaceKey:
+ // Checking for a control will allow events to percolate
+ // correctly when the focus is on a form control and we
+ // are in full keyboard access mode.
+ if ((![self allowsScrolling] && ![self _largestChildWithScrollBars]) || [self _firstResponderIsFormControl]) {
+ callSuper = YES;
+ break;
+ }
+ if ([event modifierFlags] & NSShiftKeyMask) {
+ [self scrollPageUp:nil];
+ } else {
+ [self scrollPageDown:nil];
+ }
+ callSuper = NO;
+ break;
+ case NSPageUpFunctionKey:
+ if (![self allowsScrolling] && ![self _largestChildWithScrollBars]) {
+ callSuper = YES;
+ break;
+ }
+ [self scrollPageUp:nil];
+ callSuper = NO;
+ break;
+ case NSPageDownFunctionKey:
+ if (![self allowsScrolling] && ![self _largestChildWithScrollBars]) {
+ callSuper = YES;
+ break;
+ }
+ [self scrollPageDown:nil];
+ callSuper = NO;
+ break;
+ case NSHomeFunctionKey:
+ if (![self allowsScrolling] && ![self _largestChildWithScrollBars]) {
+ callSuper = YES;
+ break;
+ }
+ [self scrollToBeginningOfDocument:nil];
+ callSuper = NO;
+ break;
+ case NSEndFunctionKey:
+ if (![self allowsScrolling] && ![self _largestChildWithScrollBars]) {
+ callSuper = YES;
+ break;
+ }
+ [self scrollToEndOfDocument:nil];
+ callSuper = NO;
+ break;
+ case NSUpArrowFunctionKey:
+ // We don't handle shifted or control-arrow keys here, so let super have a chance.
+ if ([event modifierFlags] & (NSShiftKeyMask | NSControlKeyMask)) {
+ callSuper = YES;
+ break;
+ }
+ if ((![self allowsScrolling] && ![self _largestChildWithScrollBars]) ||
+ [[[self window] firstResponder] isKindOfClass:[NSPopUpButton class]]) {
+ // Let arrow keys go through to pop up buttons
+ // <rdar://problem/3455910>: hitting up or down arrows when focus is on a
+ // pop-up menu should pop the menu
+ callSuper = YES;
+ break;
+ }
+ if ([event modifierFlags] & NSCommandKeyMask) {
+ [self scrollToBeginningOfDocument:nil];
+ } else if ([event modifierFlags] & NSAlternateKeyMask) {
+ [self scrollPageUp:nil];
+ } else {
+ [self scrollLineUp:nil];
+ }
+ callSuper = NO;
+ break;
+ case NSDownArrowFunctionKey:
+ // We don't handle shifted or control-arrow keys here, so let super have a chance.
+ if ([event modifierFlags] & (NSShiftKeyMask | NSControlKeyMask)) {
+ callSuper = YES;
+ break;
+ }
+ if ((![self allowsScrolling] && ![self _largestChildWithScrollBars]) ||
+ [[[self window] firstResponder] isKindOfClass:[NSPopUpButton class]]) {
+ // Let arrow keys go through to pop up buttons
+ // <rdar://problem/3455910>: hitting up or down arrows when focus is on a
+ // pop-up menu should pop the menu
+ callSuper = YES;
+ break;
+ }
+ if ([event modifierFlags] & NSCommandKeyMask) {
+ [self scrollToEndOfDocument:nil];
+ } else if ([event modifierFlags] & NSAlternateKeyMask) {
+ [self scrollPageDown:nil];
+ } else {
+ [self scrollLineDown:nil];
+ }
+ callSuper = NO;
+ break;
+ case NSLeftArrowFunctionKey:
+ // We don't handle shifted or control-arrow keys here, so let super have a chance.
+ if ([event modifierFlags] & (NSShiftKeyMask | NSControlKeyMask)) {
+ callSuper = YES;
+ break;
+ }
+ // Check back/forward related keys.
+ if ([event modifierFlags] & NSCommandKeyMask) {
+ if (!maintainsBackForwardList) {
+ callSuper = YES;
+ break;
+ }
+ [self _goBack];
+ } else {
+ // Now check scrolling related keys.
+ if ((![self allowsScrolling] && ![self _largestChildWithScrollBars])) {
+ callSuper = YES;
+ break;
+ }
+
+ if ([event modifierFlags] & NSAlternateKeyMask) {
+ [self _pageHorizontally:YES];
+ } else {
+ [self _scrollLineHorizontally:YES];
+ }
+ }
+ callSuper = NO;
+ break;
+ case NSRightArrowFunctionKey:
+ // We don't handle shifted or control-arrow keys here, so let super have a chance.
+ if ([event modifierFlags] & (NSShiftKeyMask | NSControlKeyMask)) {
+ callSuper = YES;
+ break;
+ }
+ // Check back/forward related keys.
+ if ([event modifierFlags] & NSCommandKeyMask) {
+ if (!maintainsBackForwardList) {
+ callSuper = YES;
+ break;
+ }
+ [self _goForward];
+ } else {
+ // Now check scrolling related keys.
+ if ((![self allowsScrolling] && ![self _largestChildWithScrollBars])) {
+ callSuper = YES;
+ break;
+ }
+
+ if ([event modifierFlags] & NSAlternateKeyMask) {
+ [self _pageHorizontally:NO];
+ } else {
+ [self _scrollLineHorizontally:NO];
+ }
+ }
+ callSuper = NO;
+ break;
+ }
+ }
+
+ if (callSuper) {
+ [super keyDown:event];
+ } else {
+ // if we did something useful, get the cursor out of the way
+ [NSCursor setHiddenUntilMouseMoves:YES];
+ }
+}
+
+- (NSView *)_webcore_effectiveFirstResponder
+{
+ NSView *view = [self documentView];
+ return view ? [view _webcore_effectiveFirstResponder] : [super _webcore_effectiveFirstResponder];
+}
+
+- (BOOL)canPrintHeadersAndFooters
+{
+ NSView *documentView = [[self _scrollView] documentView];
+ if ([documentView respondsToSelector:@selector(canPrintHeadersAndFooters)]) {
+ return [(id)documentView canPrintHeadersAndFooters];
+ }
+ return NO;
+}
+
+- (NSPrintOperation *)printOperationWithPrintInfo:(NSPrintInfo *)printInfo
+{
+ NSView *documentView = [[self _scrollView] documentView];
+ if (!documentView) {
+ return nil;
+ }
+ if ([documentView respondsToSelector:@selector(printOperationWithPrintInfo:)]) {
+ return [(id)documentView printOperationWithPrintInfo:printInfo];
+ }
+ return [NSPrintOperation printOperationWithView:documentView printInfo:printInfo];
+}
+
+- (BOOL)documentViewShouldHandlePrint
+{
+ NSView *documentView = [[self _scrollView] documentView];
+ if (documentView && [documentView respondsToSelector:@selector(documentViewShouldHandlePrint)])
+ return [(id)documentView documentViewShouldHandlePrint];
+
+ return NO;
+}
+
+- (void)printDocumentView
+{
+ NSView *documentView = [[self _scrollView] documentView];
+ if (documentView && [documentView respondsToSelector:@selector(printDocumentView)])
+ [(id)documentView printDocumentView];
+}
+
+@end
+
+@implementation WebFrameView (WebPrivate)
+
+- (float)_area
+{
+ NSRect frame = [self frame];
+ return frame.size.height * frame.size.width;
+}
+
+- (BOOL)_hasScrollBars
+{
+ NSScrollView *scrollView = [self _scrollView];
+ return [scrollView hasHorizontalScroller] || [scrollView hasVerticalScroller];
+}
+
+- (WebFrameView *)_largestChildWithScrollBars
+{
+ WebFrameView *largest = nil;
+ NSArray *frameChildren = [[self webFrame] childFrames];
+
+ unsigned i;
+ for (i=0; i < [frameChildren count]; i++) {
+ WebFrameView *childFrameView = [[frameChildren objectAtIndex:i] frameView];
+ WebFrameView *scrollableFrameView = [childFrameView _hasScrollBars] ? childFrameView : [childFrameView _largestChildWithScrollBars];
+ if (!scrollableFrameView)
+ continue;
+
+ // Some ads lurk in child frames of zero width and height, see radar 4406994. These don't count as scrollable.
+ // Maybe someday we'll discover that this minimum area check should be larger, but this covers the known cases.
+ float area = [scrollableFrameView _area];
+ if (area < 1.0)
+ continue;
+
+ if (!largest || (area > [largest _area])) {
+ largest = scrollableFrameView;
+ }
+ }
+
+ return largest;
+}
+
+- (NSClipView *)_contentView
+{
+ return [[self _scrollView] contentView];
+}
+
+- (Class)_customScrollViewClass
+{
+ if ([_private->frameScrollView class] == [WebDynamicScrollBarsView class])
+ return nil;
+ return [_private->frameScrollView class];
+}
+
+- (void)_setCustomScrollViewClass:(Class)customClass
+{
+ if (!customClass)
+ customClass = [WebDynamicScrollBarsView class];
+ ASSERT([customClass isSubclassOfClass:[WebDynamicScrollBarsView class]]);
+ if (customClass == [_private->frameScrollView class])
+ return;
+ if ([customClass isSubclassOfClass:[WebDynamicScrollBarsView class]]) {
+ WebDynamicScrollBarsView *oldScrollView = _private->frameScrollView; // already retained
+ NSView <WebDocumentView> *documentView = [[self documentView] retain];
+
+ WebDynamicScrollBarsView *scrollView = [[customClass alloc] initWithFrame:[oldScrollView frame]];
+ [scrollView setContentView:[[[WebClipView alloc] initWithFrame:[scrollView bounds]] autorelease]];
+ [scrollView setDrawsBackground:[oldScrollView drawsBackground]];
+ [scrollView setHasVerticalScroller:[oldScrollView hasVerticalScroller]];
+ [scrollView setHasHorizontalScroller:[oldScrollView hasHorizontalScroller]];
+ [scrollView setAutoresizingMask:[oldScrollView autoresizingMask]];
+ [scrollView setLineScroll:[oldScrollView lineScroll]];
+ [self addSubview:scrollView];
+
+ // don't call our overridden version here; we need to make the standard NSView link between us
+ // and our subview so that previousKeyView and previousValidKeyView work as expected. This works
+ // together with our becomeFirstResponder and setNextKeyView overrides.
+ [super setNextKeyView:scrollView];
+
+ _private->frameScrollView = scrollView;
+
+ [self _setDocumentView:documentView];
+ [[self _bridge] installInFrame:scrollView];
+
+ [oldScrollView removeFromSuperview];
+ [oldScrollView release];
+ [documentView release];
+ }
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebFrameViewInternal.h b/WebKit/mac/WebView/WebFrameViewInternal.h
new file mode 100644
index 0000000..0304617
--- /dev/null
+++ b/WebKit/mac/WebView/WebFrameViewInternal.h
@@ -0,0 +1,50 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebFrameView.h>
+
+@class WebDynamicScrollBarsView;
+@class WebView;
+
+@interface WebFrameView (WebInternal)
+
+- (WebView *)_webView;
+- (void)_setDocumentView:(NSView <WebDocumentView> *)view;
+- (NSView <WebDocumentView> *)_makeDocumentViewForDataSource:(WebDataSource *)dataSource;
+- (void)_setWebFrame:(WebFrame *)webFrame;
+- (int)_marginWidth;
+- (int)_marginHeight;
+- (void)_setMarginWidth:(int)w;
+- (void)_setMarginHeight:(int)h;
+- (float)_verticalPageScrollDistance;
++ (NSMutableDictionary *)_viewTypesAllowImageTypeOmission:(BOOL)allowImageTypeOmission;
++ (Class)_viewClassForMIMEType:(NSString *)MIMEType;
++ (BOOL)_canShowMIMETypeAsHTML:(NSString *)MIMEType;
+- (WebDynamicScrollBarsView *)_scrollView;
+
+@end
diff --git a/WebKit/mac/WebView/WebFrameViewPrivate.h b/WebKit/mac/WebView/WebFrameViewPrivate.h
new file mode 100644
index 0000000..47c053e
--- /dev/null
+++ b/WebKit/mac/WebView/WebFrameViewPrivate.h
@@ -0,0 +1,65 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebFrameView.h>
+
+@interface WebFrameView (WebPrivate)
+
+/*!
+ @method _largestChildWithScrollBars
+ @abstract Of the child WebFrameViews that are displaying scroll bars, determines which has the largest area.
+ @result A child WebFrameView that is displaying scroll bars, or nil if none.
+*/
+- (WebFrameView *)_largestChildWithScrollBars;
+
+/*!
+ @method _hasScrollBars
+ @result YES if at least one scroll bar is currently displayed
+ */
+- (BOOL)_hasScrollBars;
+
+/*!
+ @method _contentView
+ @result The content view (NSClipView) of the WebFrameView's scroll view.
+ */
+- (NSClipView *)_contentView;
+
+/*!
+ @method _customScrollViewClass
+ @result The custom scroll view class that is installed, nil if the default scroll view is being used.
+ */
+- (Class)_customScrollViewClass;
+
+/*!
+ @method _setCustomScrollViewClass:
+ @result Switches the WebFrameView's scroll view class, this class needs to be a subclass of WebDynamicScrollBarsView.
+ Passing nil will switch back to the default WebDynamicScrollBarsView class.
+ */
+- (void)_setCustomScrollViewClass:(Class)scrollViewClass;
+
+@end
diff --git a/WebKit/mac/WebView/WebHTMLRepresentation.h b/WebKit/mac/WebView/WebHTMLRepresentation.h
new file mode 100644
index 0000000..2098c47
--- /dev/null
+++ b/WebKit/mac/WebView/WebHTMLRepresentation.h
@@ -0,0 +1,66 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+#import <WebKit/WebDocumentPrivate.h>
+
+@class WebHTMLRepresentationPrivate;
+@class NSView;
+
+@class DOMNode;
+@class DOMElement;
+
+@protocol WebDocumentMarkup;
+@protocol WebDocumentRepresentation;
+@protocol WebDocumentSourceRepresentation;
+
+/*!
+ @class WebHTMLRepresentation
+*/
+@interface WebHTMLRepresentation : NSObject <WebDocumentRepresentation, WebDocumentDOM>
+{
+ WebHTMLRepresentationPrivate *_private;
+}
+
++ (NSArray *)supportedMIMETypes;
++ (NSArray *)supportedNonImageMIMETypes;
++ (NSArray *)supportedImageMIMETypes;
+
+- (NSAttributedString *)attributedStringFrom:(DOMNode *)startNode startOffset:(int)startOffset to:(DOMNode *)endNode endOffset:(int)endOffset;
+
+- (DOMElement *)elementWithName:(NSString *)name inForm:(DOMElement *)form;
+- (BOOL)elementDoesAutoComplete:(DOMElement *)element;
+- (BOOL)elementIsPassword:(DOMElement *)element;
+- (DOMElement *)formForElement:(DOMElement *)element;
+- (DOMElement *)currentForm;
+- (NSArray *)controlsInForm:(DOMElement *)form;
+- (NSString *)searchForLabels:(NSArray *)labels beforeElement:(DOMElement *)element;
+- (NSString *)matchLabels:(NSArray *)labels againstElement:(DOMElement *)element;
+
+@end
diff --git a/WebKit/mac/WebView/WebHTMLRepresentation.mm b/WebKit/mac/WebView/WebHTMLRepresentation.mm
new file mode 100644
index 0000000..1a25ade
--- /dev/null
+++ b/WebKit/mac/WebView/WebHTMLRepresentation.mm
@@ -0,0 +1,322 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebHTMLRepresentation.h"
+
+#import "DOMNodeInternal.h"
+#import "DOMRangeInternal.h"
+#import "WebArchive.h"
+#import "WebBasePluginPackage.h"
+#import "WebDataSourceInternal.h"
+#import "WebDocumentPrivate.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebKitNSStringExtras.h"
+#import "WebKitStatisticsPrivate.h"
+#import "WebNSAttributedStringExtras.h"
+#import "WebNSObjectExtras.h"
+#import "WebResourcePrivate.h"
+#import "WebView.h"
+#import <Foundation/NSURLResponse.h>
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/Document.h>
+#import <WebCore/DocumentLoader.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/MIMETypeRegistry.h>
+#import <WebCore/Range.h>
+
+using namespace WebCore;
+
+@interface WebHTMLRepresentationPrivate : NSObject
+{
+@public
+ WebDataSource *dataSource;
+ WebFrameBridge *bridge;
+ NSData *parsedArchiveData;
+
+ BOOL hasSentResponseToPlugin;
+ id <WebPluginManualLoader> manualLoader;
+ NSView *pluginView;
+}
+@end
+
+@implementation WebHTMLRepresentationPrivate
+
+- (void)dealloc
+{
+ [parsedArchiveData release];
+ [super dealloc];
+}
+
+@end
+
+@implementation WebHTMLRepresentation
+
+static NSArray *stringArray(const HashSet<String>& set)
+{
+ NSMutableArray *array = [NSMutableArray arrayWithCapacity:set.size()];
+ HashSet<String>::const_iterator end = set.end();
+ for (HashSet<String>::const_iterator it = set.begin(); it != end; ++it)
+ [array addObject:(NSString *)(*it)];
+ return array;
+}
+
+static NSArray *concatenateArrays(NSArray *first, NSArray *second)
+{
+ NSMutableArray *result = [[first mutableCopy] autorelease];
+ [result addObjectsFromArray:second];
+ return result;
+}
+
++ (NSArray *)supportedMIMETypes
+{
+ static RetainPtr<NSArray> staticSupportedMIMETypes =
+ concatenateArrays([self supportedNonImageMIMETypes], [self supportedImageMIMETypes]);
+ return staticSupportedMIMETypes.get();
+}
+
++ (NSArray *)supportedNonImageMIMETypes
+{
+ static RetainPtr<NSArray> staticSupportedNonImageMIMETypes =
+ stringArray(MIMETypeRegistry::getSupportedNonImageMIMETypes());
+ return staticSupportedNonImageMIMETypes.get();
+}
+
++ (NSArray *)supportedImageMIMETypes
+{
+ static RetainPtr<NSArray> staticSupportedImageMIMETypes =
+ stringArray(MIMETypeRegistry::getSupportedImageMIMETypes());
+ return staticSupportedImageMIMETypes.get();
+}
+
+- init
+{
+ self = [super init];
+ if (!self)
+ return nil;
+
+ _private = [[WebHTMLRepresentationPrivate alloc] init];
+
+ ++WebHTMLRepresentationCount;
+
+ return self;
+}
+
+- (void)dealloc
+{
+ --WebHTMLRepresentationCount;
+
+ [_private release];
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ --WebHTMLRepresentationCount;
+
+ [super finalize];
+}
+
+- (WebFrameBridge *)_bridge
+{
+ return _private->bridge;
+}
+
+- (void)_redirectDataToManualLoader:(id<WebPluginManualLoader>)manualLoader forPluginView:(NSView *)pluginView;
+{
+ _private->manualLoader = manualLoader;
+ _private->pluginView = pluginView;
+}
+
+- (void)setDataSource:(WebDataSource *)dataSource
+{
+ _private->dataSource = dataSource;
+ _private->bridge = [[dataSource webFrame] _bridge];
+}
+
+- (BOOL)_isDisplayingWebArchive
+{
+ return [[[_private->dataSource response] MIMEType] _webkit_isCaseInsensitiveEqualToString:@"application/x-webarchive"];
+}
+
+- (void)receivedData:(NSData *)data withDataSource:(WebDataSource *)dataSource
+{
+ if ([dataSource webFrame] && ![self _isDisplayingWebArchive]) {
+ if (!_private->pluginView)
+ [_private->bridge receivedData:data textEncodingName:[[_private->dataSource response] textEncodingName]];
+
+ if (_private->pluginView) {
+ if (!_private->hasSentResponseToPlugin) {
+ [_private->manualLoader pluginView:_private->pluginView receivedResponse:[dataSource response]];
+ _private->hasSentResponseToPlugin = YES;
+ }
+
+ [_private->manualLoader pluginView:_private->pluginView receivedData:data];
+ }
+ }
+}
+
+- (void)receivedError:(NSError *)error withDataSource:(WebDataSource *)dataSource
+{
+ if (_private->pluginView) {
+ [_private->manualLoader pluginView:_private->pluginView receivedError:error];
+ }
+}
+
+- (void)_loadDataSourceAsWebArchive
+{
+ WebArchive *archive = [[WebArchive alloc] initWithData:[_private->dataSource data]];
+ WebResource *mainResource = [archive mainResource];
+ if (!mainResource) {
+ [archive release];
+ return;
+ }
+
+ NSData *data = [mainResource data];
+ [data retain];
+ [_private->parsedArchiveData release];
+ _private->parsedArchiveData = data;
+
+ [_private->dataSource _addToUnarchiveState:archive];
+ [archive release];
+
+ WebFrame *webFrame = [_private->dataSource webFrame];
+
+ if (!webFrame)
+ return;
+
+ core(webFrame)->loader()->continueLoadWithData(SharedBuffer::wrapNSData(data).get(), [mainResource MIMEType], [mainResource textEncodingName], [mainResource URL]);
+}
+
+- (void)finishedLoadingWithDataSource:(WebDataSource *)dataSource
+{
+ WebFrame *frame = [dataSource webFrame];
+
+ if (_private->pluginView) {
+ [_private->manualLoader pluginViewFinishedLoading:_private->pluginView];
+ return;
+ }
+
+ if (frame) {
+ if ([self _isDisplayingWebArchive])
+ [self _loadDataSourceAsWebArchive];
+ else
+ // Telling the bridge we received some data and passing nil as the data is our
+ // way to get work done that is normally done when the first bit of data is
+ // received, even for the case of a document with no data (like about:blank).
+ [_private->bridge receivedData:nil textEncodingName:[[_private->dataSource response] textEncodingName]];
+
+ WebView *webView = [frame webView];
+ if ([webView isEditable])
+ core(frame)->applyEditingStyleToBodyElement();
+ }
+}
+
+- (BOOL)canProvideDocumentSource
+{
+ return [_private->bridge canProvideDocumentSource];
+}
+
+- (BOOL)canSaveAsWebArchive
+{
+ return [_private->bridge canSaveAsWebArchive];
+}
+
+- (NSString *)documentSource
+{
+ if ([self _isDisplayingWebArchive])
+ return [[[NSString alloc] initWithData:_private->parsedArchiveData encoding:NSUTF8StringEncoding] autorelease];
+
+ return [_private->bridge stringWithData:[_private->dataSource data]];
+}
+
+- (NSString *)title
+{
+ return nsStringNilIfEmpty([_private->dataSource _documentLoader]->title());
+}
+
+- (DOMDocument *)DOMDocument
+{
+ return [[_private->bridge webFrame] DOMDocument];
+}
+
+- (NSAttributedString *)attributedText
+{
+ // FIXME: Implement
+ return nil;
+}
+
+- (NSAttributedString *)attributedStringFrom:(DOMNode *)startNode startOffset:(int)startOffset to:(DOMNode *)endNode endOffset:(int)endOffset
+{
+ Range range([startNode _node]->document(), [startNode _node], startOffset, [endNode _node], endOffset);
+ return [NSAttributedString _web_attributedStringFromRange:&range];
+}
+
+- (DOMElement *)elementWithName:(NSString *)name inForm:(DOMElement *)form
+{
+ return [_private->bridge elementWithName:name inForm:form];
+}
+
+- (BOOL)elementDoesAutoComplete:(DOMElement *)element
+{
+ return [_private->bridge elementDoesAutoComplete:element];
+}
+
+- (BOOL)elementIsPassword:(DOMElement *)element
+{
+ return [_private->bridge elementIsPassword:element];
+}
+
+- (DOMElement *)formForElement:(DOMElement *)element
+{
+ return [_private->bridge formForElement:element];
+}
+
+- (DOMElement *)currentForm
+{
+ return [_private->bridge currentForm];
+}
+
+- (NSArray *)controlsInForm:(DOMElement *)form
+{
+ return [_private->bridge controlsInForm:form];
+}
+
+- (NSString *)searchForLabels:(NSArray *)labels beforeElement:(DOMElement *)element
+{
+ return [_private->bridge searchForLabels:labels beforeElement:element];
+}
+
+- (NSString *)matchLabels:(NSArray *)labels againstElement:(DOMElement *)element
+{
+ return [_private->bridge matchLabels:labels againstElement:element];
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebHTMLRepresentationPrivate.h b/WebKit/mac/WebView/WebHTMLRepresentationPrivate.h
new file mode 100644
index 0000000..3737bb2
--- /dev/null
+++ b/WebKit/mac/WebView/WebHTMLRepresentationPrivate.h
@@ -0,0 +1,38 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebHTMLRepresentation.h>
+
+@class WebFrameBridge;
+@protocol WebPluginManualLoader;
+
+@interface WebHTMLRepresentation (WebPrivate)
+- (WebFrameBridge *)_bridge;
+- (void)_redirectDataToManualLoader:(id<WebPluginManualLoader>)manualLoader forPluginView:(NSView *)pluginView;
+- (void)printDOMTree;
+@end
diff --git a/WebKit/mac/WebView/WebHTMLView.h b/WebKit/mac/WebView/WebHTMLView.h
new file mode 100644
index 0000000..a191cef
--- /dev/null
+++ b/WebKit/mac/WebView/WebHTMLView.h
@@ -0,0 +1,63 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebDocument.h>
+
+@class WebDataSource;
+@class WebHTMLViewPrivate;
+
+/*!
+ @class WebHTMLView
+ @discussion A document view of WebFrameView that displays HTML content.
+ WebHTMLView is a NSControl because it hosts NSCells that are painted by WebCore's Aqua theme
+ renderer (and those cells must be hosted by an enclosing NSControl in order to paint properly).
+*/
+@interface WebHTMLView : NSControl <WebDocumentView, WebDocumentSearching>
+{
+@private
+ WebHTMLViewPrivate *_private;
+}
+
+/*!
+ @method setNeedsToApplyStyles:
+ @abstract Sets flag to cause reapplication of style information.
+ @param flag YES to apply style information, NO to not apply style information.
+*/
+- (void)setNeedsToApplyStyles:(BOOL)flag;
+
+/*!
+ @method reapplyStyles
+ @discussion Immediately causes reapplication of style information to the view. This should not be called directly,
+ instead call setNeedsToApplyStyles:.
+*/
+- (void)reapplyStyles;
+
+- (void)outdent:(id)sender;
+
+@end
+
diff --git a/WebKit/mac/WebView/WebHTMLView.mm b/WebKit/mac/WebView/WebHTMLView.mm
new file mode 100644
index 0000000..485b850
--- /dev/null
+++ b/WebKit/mac/WebView/WebHTMLView.mm
@@ -0,0 +1,5711 @@
+/*
+ * Copyright (C) 2005, 2006, 2007, 2008 Apple Inc. All rights reserved.
+ * (C) 2006, 2007 Graham Dennis (graham.dennis@gmail.com)
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebHTMLView.h"
+
+#import "DOMNodeInternal.h"
+#import "DOMRangeInternal.h"
+#import "WebArchive.h"
+#import "WebArchiver.h"
+#import "WebBaseNetscapePluginViewInternal.h"
+#import "WebClipView.h"
+#import "WebDOMOperationsPrivate.h"
+#import "WebDataSourceInternal.h"
+#import "WebDefaultUIDelegate.h"
+#import "WebDocumentInternal.h"
+#import "WebDynamicScrollBarsView.h"
+#import "WebEditingDelegate.h"
+#import "WebElementDictionary.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebFramePrivate.h"
+#import "WebFrameViewInternal.h"
+#import "WebHTMLRepresentationPrivate.h"
+#import "WebHTMLViewInternal.h"
+#import "WebKitLogging.h"
+#import "WebKitNSStringExtras.h"
+#import "WebKitPluginContainerView.h"
+#import "WebKitVersionChecks.h"
+#import "WebLocalizableStrings.h"
+#import "WebNSAttributedStringExtras.h"
+#import "WebNSEventExtras.h"
+#import "WebNSFileManagerExtras.h"
+#import "WebNSImageExtras.h"
+#import "WebNSObjectExtras.h"
+#import "WebNSPasteboardExtras.h"
+#import "WebNSPrintOperationExtras.h"
+#import "WebNSURLExtras.h"
+#import "WebNSViewExtras.h"
+#import "WebNetscapePluginEmbeddedView.h"
+#import "WebPluginController.h"
+#import "WebPreferences.h"
+#import "WebPreferencesPrivate.h"
+#import "WebResourcePrivate.h"
+#import "WebStringTruncator.h"
+#import "WebUIDelegatePrivate.h"
+#import "WebViewInternal.h"
+#import <AppKit/NSAccessibility.h>
+#import <ApplicationServices/ApplicationServices.h>
+#import <dlfcn.h>
+#import <WebCore/CachedImage.h>
+#import <WebCore/CachedResourceClient.h>
+#import <WebCore/ColorMac.h>
+#import <WebCore/ContextMenu.h>
+#import <WebCore/ContextMenuController.h>
+#import <WebCore/Document.h>
+#import <WebCore/Editor.h>
+#import <WebCore/EditorDeleteAction.h>
+#import <WebCore/Element.h>
+#import <WebCore/EventHandler.h>
+#import <WebCore/EventNames.h>
+#import <WebCore/ExceptionHandlers.h>
+#import <WebCore/DragController.h>
+#import <WebCore/FloatRect.h>
+#import <WebCore/FocusController.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/FrameView.h>
+#import <WebCore/HitTestResult.h>
+#import <WebCore/HTMLNames.h>
+#import <WebCore/Image.h>
+#import <WebCore/KeyboardEvent.h>
+#import <WebCore/MIMETypeRegistry.h>
+#import <WebCore/Page.h>
+#import <WebCore/PlatformKeyboardEvent.h>
+#import <WebCore/PlatformMouseEvent.h>
+#import <WebCore/Range.h>
+#import <WebCore/SelectionController.h>
+#import <WebCore/SharedBuffer.h>
+#import <WebCore/Text.h>
+#import <WebCore/WebCoreObjCExtras.h>
+#import <WebCore/WebCoreTextRenderer.h>
+#import <WebKit/DOM.h>
+#import <WebKit/DOMExtensions.h>
+#import <WebKit/DOMPrivate.h>
+#import <WebKitSystemInterface.h>
+
+using namespace WebCore;
+using namespace HTMLNames;
+using namespace WTF;
+
+@interface NSWindow (BorderViewAccess)
+- (NSView*)_web_borderView;
+@end
+
+@implementation NSWindow (BorderViewAccess)
+- (NSView*)_web_borderView
+{
+ return _borderView;
+}
+@end
+
+static IMP oldSetCursorIMP = NULL;
+
+#ifdef BUILDING_ON_TIGER
+static IMP oldResetCursorRectsIMP = NULL;
+static BOOL canSetCursor = YES;
+
+static void resetCursorRects(NSWindow* self, SEL cmd)
+{
+ NSPoint point = [self mouseLocationOutsideOfEventStream];
+ NSView* view = [[self _web_borderView] hitTest:point];
+ if ([view isKindOfClass:[WebHTMLView class]]) {
+ WebHTMLView *htmlView = (WebHTMLView*)view;
+ NSPoint localPoint = [htmlView convertPoint:point fromView:nil];
+ NSDictionary *dict = [htmlView elementAtPoint:point allowShadowContent:NO];
+ DOMElement *element = [dict objectForKey:WebElementDOMNodeKey];
+ if (![element isKindOfClass:[DOMHTMLAppletElement class]] && ![element isKindOfClass:[DOMHTMLObjectElement class]] &&
+ ![element isKindOfClass:[DOMHTMLEmbedElement class]])
+ canSetCursor = NO;
+ }
+ oldResetCursorRectsIMP(self, cmd);
+ canSetCursor = YES;
+}
+
+static void setCursor(NSCursor* self, SEL cmd)
+{
+ if (canSetCursor)
+ oldSetCursorIMP(self, cmd);
+}
+#else
+static void setCursor(NSWindow* self, SEL cmd, NSPoint point)
+{
+ NSView* view = [[self _web_borderView] hitTest:point];
+ if ([view isKindOfClass:[WebHTMLView class]]) {
+ WebHTMLView *htmlView = (WebHTMLView*)view;
+ NSPoint localPoint = [htmlView convertPoint:point fromView:nil];
+ NSDictionary *dict = [htmlView elementAtPoint:point allowShadowContent:NO];
+ DOMElement *element = [dict objectForKey:WebElementDOMNodeKey];
+ if (![element isKindOfClass:[DOMHTMLAppletElement class]] && ![element isKindOfClass:[DOMHTMLObjectElement class]] &&
+ ![element isKindOfClass:[DOMHTMLEmbedElement class]])
+ return;
+ }
+ oldSetCursorIMP(self, cmd, point);
+}
+#endif
+
+extern "C" {
+
+// Need to declare these attribute names because AppKit exports them but does not make them available in API or SPI headers.
+
+extern NSString *NSMarkedClauseSegmentAttributeName;
+extern NSString *NSTextInputReplacementRangeAttributeName;
+
+}
+
+@interface NSView (AppKitSecretsIKnowAbout)
+- (void)_recursiveDisplayRectIfNeededIgnoringOpacity:(NSRect)rect isVisibleRect:(BOOL)isVisibleRect rectIsVisibleRectForView:(NSView *)visibleView topView:(BOOL)topView;
+- (void)_recursiveDisplayAllDirtyWithLockFocus:(BOOL)needsLockFocus visRect:(NSRect)visRect;
+- (NSRect)_dirtyRect;
+- (void)_setDrawsOwnDescendants:(BOOL)drawsOwnDescendants;
+- (void)_propagateDirtyRectsToOpaqueAncestors;
+- (void)_windowChangedKeyState;
+@end
+
+@interface NSApplication (AppKitSecretsIKnowAbout)
+- (void)speakString:(NSString *)string;
+@end
+
+@interface NSWindow (AppKitSecretsIKnowAbout)
+- (id)_newFirstResponderAfterResigning;
+- (void)_setForceActiveControls:(BOOL)flag;
+@end
+
+@interface NSAttributedString (AppKitSecretsIKnowAbout)
+- (id)_initWithDOMRange:(DOMRange *)domRange;
+- (DOMDocumentFragment *)_documentFromRange:(NSRange)range document:(DOMDocument *)document documentAttributes:(NSDictionary *)dict subresources:(NSArray **)subresources;
+@end
+
+@interface NSSpellChecker (CurrentlyPrivateForTextView)
+- (void)learnWord:(NSString *)word;
+@end
+
+// By imaging to a width a little wider than the available pixels,
+// thin pages will be scaled down a little, matching the way they
+// print in IE and Camino. This lets them use fewer sheets than they
+// would otherwise, which is presumably why other browsers do this.
+// Wide pages will be scaled down more than this.
+#define PrintingMinimumShrinkFactor 1.25f
+
+// This number determines how small we are willing to reduce the page content
+// in order to accommodate the widest line. If the page would have to be
+// reduced smaller to make the widest line fit, we just clip instead (this
+// behavior matches MacIE and Mozilla, at least)
+#define PrintingMaximumShrinkFactor 2.0f
+
+// This number determines how short the last printed page of a multi-page print session
+// can be before we try to shrink the scale in order to reduce the number of pages, and
+// thus eliminate the orphan.
+#define LastPrintedPageOrphanRatio 0.1f
+
+// This number determines the amount the scale factor is adjusted to try to eliminate orphans.
+// It has no direct mathematical relationship to LastPrintedPageOrphanRatio, due to variable
+// numbers of pages, logic to avoid breaking elements, and CSS-supplied hard page breaks.
+#define PrintingOrphanShrinkAdjustment 1.1f
+
+#define AUTOSCROLL_INTERVAL 0.1f
+
+#define DRAG_LABEL_BORDER_X 4.0f
+//Keep border_y in synch with DragController::LinkDragBorderInset
+#define DRAG_LABEL_BORDER_Y 2.0f
+#define DRAG_LABEL_RADIUS 5.0f
+#define DRAG_LABEL_BORDER_Y_OFFSET 2.0f
+
+#define MIN_DRAG_LABEL_WIDTH_BEFORE_CLIP 120.0f
+#define MAX_DRAG_LABEL_WIDTH 320.0f
+
+#define DRAG_LINK_LABEL_FONT_SIZE 11.0f
+#define DRAG_LINK_URL_FONT_SIZE 10.0f
+
+// Any non-zero value will do, but using something recognizable might help us debug some day.
+#define TRACKING_RECT_TAG 0xBADFACE
+
+// FIXME: This constant is copied from AppKit's _NXSmartPaste constant.
+#define WebSmartPastePboardType @"NeXT smart paste pasteboard type"
+
+#define STANDARD_WEIGHT 5
+#define MIN_BOLD_WEIGHT 9
+#define STANDARD_BOLD_WEIGHT 10
+
+// Fake URL scheme.
+#define WebDataProtocolScheme @"webkit-fake-url"
+
+// <rdar://problem/4985524> References to WebCoreScrollView as a subview of a WebHTMLView may be present
+// in some NIB files, so NSUnarchiver must be still able to look up this now-unused class.
+@interface WebCoreScrollView : NSScrollView
+@end
+
+@implementation WebCoreScrollView
+@end
+
+// if YES, do the standard NSView hit test (which can't give the right result when HTML overlaps a view)
+static BOOL forceNSViewHitTest;
+
+// if YES, do the "top WebHTMLView" hit test (which we'd like to do all the time but can't because of Java requirements [see bug 4349721])
+static BOOL forceWebHTMLViewHitTest;
+
+static WebHTMLView *lastHitView;
+
+// We need this to be able to safely reference the CachedImage for the promised drag data
+static CachedResourceClient* promisedDataClient()
+{
+ static CachedResourceClient* staticCachedResourceClient = new CachedResourceClient;
+ return staticCachedResourceClient;
+}
+
+@interface WebHTMLView (WebTextSizing) <_WebDocumentTextSizing>
+@end
+
+@interface WebHTMLView (WebHTMLViewFileInternal)
+- (BOOL)_imageExistsAtPaths:(NSArray *)paths;
+- (DOMDocumentFragment *)_documentFragmentFromPasteboard:(NSPasteboard *)pasteboard inContext:(DOMRange *)context allowPlainText:(BOOL)allowPlainText;
+- (NSString *)_plainTextFromPasteboard:(NSPasteboard *)pasteboard;
+- (void)_pasteWithPasteboard:(NSPasteboard *)pasteboard allowPlainText:(BOOL)allowPlainText;
+- (void)_pasteAsPlainTextWithPasteboard:(NSPasteboard *)pasteboard;
+- (BOOL)_shouldInsertFragment:(DOMDocumentFragment *)fragment replacingDOMRange:(DOMRange *)range givenAction:(WebViewInsertAction)action;
+- (BOOL)_shouldInsertText:(NSString *)text replacingDOMRange:(DOMRange *)range givenAction:(WebViewInsertAction)action;
+- (BOOL)_shouldReplaceSelectionWithText:(NSString *)text givenAction:(WebViewInsertAction)action;
+- (float)_calculatePrintHeight;
+- (void)_updateTextSizeMultiplier;
+- (DOMRange *)_selectedRange;
+- (BOOL)_shouldDeleteRange:(DOMRange *)range;
+- (NSView *)_hitViewForEvent:(NSEvent *)event;
+- (void)_writeSelectionWithPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard cachedAttributedString:(NSAttributedString *)attributedString;
+- (DOMRange *)_documentRange;
+- (WebFrameBridge *)_bridge;
+- (void)_setMouseDownEvent:(NSEvent *)event;
+- (WebHTMLView *)_topHTMLView;
+- (BOOL)_isTopHTMLView;
+- (void)_web_setPrintingModeRecursive;
+- (void)_web_setPrintingModeRecursiveAndAdjustViewSize;
+- (void)_web_clearPrintingModeRecursive;
+@end
+
+@interface WebHTMLView (WebForwardDeclaration) // FIXME: Put this in a normal category and stop doing the forward declaration trick.
+- (void)_setPrinting:(BOOL)printing minimumPageWidth:(float)minPageWidth maximumPageWidth:(float)maxPageWidth adjustViewSize:(BOOL)adjustViewSize;
+@end
+
+@class NSInputContext;
+@interface NSResponder (IMSecretsIKnowAbout)
+- (NSInputContext *)inputContext;
+@end
+
+@interface WebHTMLView (WebNSTextInputSupport) <NSTextInput>
+- (void)_updateSelectionForInputManager;
+@end
+
+@interface WebHTMLView (WebEditingStyleSupport)
+- (DOMCSSStyleDeclaration *)_emptyStyle;
+- (NSString *)_colorAsString:(NSColor *)color;
+@end
+
+@interface NSView (WebHTMLViewFileInternal)
+- (void)_web_addDescendantWebHTMLViewsToArray:(NSMutableArray *) array;
+@end
+
+@interface NSMutableDictionary (WebHTMLViewFileInternal)
+- (void)_web_setObjectIfNotNil:(id)object forKey:(id)key;
+@end
+
+// Handles the complete: text command
+@interface WebTextCompleteController : NSObject {
+@private
+ WebHTMLView *_view;
+ NSWindow *_popupWindow;
+ NSTableView *_tableView;
+ NSArray *_completions;
+ NSString *_originalString;
+ int prefixLength;
+}
+- (id)initWithHTMLView:(WebHTMLView *)view;
+- (void)doCompletion;
+- (void)endRevertingChange:(BOOL)revertChange moveLeft:(BOOL)goLeft;
+- (BOOL)popupWindowIsOpen;
+- (BOOL)filterKeyDown:(NSEvent *)event;
+- (void)_reflectSelection;
+@end
+
+struct WebHTMLViewInterpretKeyEventsParameters {
+ KeyboardEvent* event;
+ BOOL eventWasHandled;
+ BOOL shouldSaveCommand;
+ // The Input Method may consume an event and not tell us, in
+ // which case we should not bubble the event up the DOM
+ BOOL consumedByIM;
+};
+
+static NSCellStateValue kit(TriState state)
+{
+ switch (state) {
+ case FalseTriState:
+ return NSOffState;
+ case TrueTriState:
+ return NSOnState;
+ case MixedTriState:
+ return NSMixedState;
+ }
+ ASSERT_NOT_REACHED();
+ return NSOffState;
+}
+
+@implementation WebHTMLViewPrivate
+
++ (void)initialize
+{
+#ifndef BUILDING_ON_TIGER
+ WebCoreObjCFinalizeOnMainThread(self);
+#endif
+
+ if (!oldSetCursorIMP) {
+#ifdef BUILDING_ON_TIGER
+ Method setCursorMethod = class_getInstanceMethod([NSCursor class], @selector(set));
+#else
+ Method setCursorMethod = class_getInstanceMethod([NSWindow class], @selector(_setCursorForMouseLocation:));
+#endif
+ ASSERT(setCursorMethod);
+
+ oldSetCursorIMP = method_setImplementation(setCursorMethod, (IMP)setCursor);
+ ASSERT(oldSetCursorIMP);
+ }
+
+#ifdef BUILDING_ON_TIGER
+ if (!oldResetCursorRectsIMP) {
+ Method resetCursorRectsMethod = class_getInstanceMethod([NSWindow class], @selector(resetCursorRects));
+ ASSERT(resetCursorRectsMethod);
+ oldResetCursorRectsIMP = method_setImplementation(resetCursorRectsMethod, (IMP)resetCursorRects);
+ ASSERT(oldResetCursorRectsIMP);
+ }
+#endif
+
+}
+
+- (void)dealloc
+{
+ ASSERT(!autoscrollTimer);
+ ASSERT(!autoscrollTriggerEvent);
+ ASSERT(!updateFocusedAndActiveStateTimer);
+ ASSERT(!updateMouseoverTimer);
+
+ [mouseDownEvent release];
+ [keyDownEvent release];
+ [pluginController release];
+ [toolTip release];
+ [compController release];
+ [dataSource release];
+ [highlighters release];
+ if (promisedDragTIFFDataSource)
+ promisedDragTIFFDataSource->deref(promisedDataClient());
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+
+ if (promisedDragTIFFDataSource)
+ promisedDragTIFFDataSource->deref(promisedDataClient());
+
+ [super finalize];
+}
+
+- (void)clear
+{
+ [mouseDownEvent release];
+ [keyDownEvent release];
+ [pluginController release];
+ [toolTip release];
+ [compController release];
+ [dataSource release];
+ [highlighters release];
+ if (promisedDragTIFFDataSource)
+ promisedDragTIFFDataSource->deref(promisedDataClient());
+
+ mouseDownEvent = nil;
+ keyDownEvent = nil;
+ pluginController = nil;
+ toolTip = nil;
+ compController = nil;
+ dataSource = nil;
+ highlighters = nil;
+ promisedDragTIFFDataSource = 0;
+}
+
+@end
+
+@implementation WebHTMLView (WebHTMLViewFileInternal)
+
+- (DOMRange *)_documentRange
+{
+ return [[[self _frame] DOMDocument] _documentRange];
+}
+
+- (BOOL)_imageExistsAtPaths:(NSArray *)paths
+{
+ NSEnumerator *enumerator = [paths objectEnumerator];
+ NSString *path;
+
+ while ((path = [enumerator nextObject]) != nil) {
+ NSString *MIMEType = WKGetMIMETypeForExtension([path pathExtension]);
+ if (MIMETypeRegistry::isSupportedImageResourceMIMEType(MIMEType))
+ return YES;
+ }
+
+ return NO;
+}
+
+- (WebDataSource *)_dataSource
+{
+ return _private->dataSource;
+}
+
+- (WebFrameBridge *)_bridge
+{
+ return [_private->dataSource _bridge];
+}
+
+- (WebView *)_webView
+{
+ return [_private->dataSource _webView];
+}
+
+- (WebFrameView *)_frameView
+{
+ return [[_private->dataSource webFrame] frameView];
+}
+
+- (DOMDocumentFragment *)_documentFragmentWithPaths:(NSArray *)paths
+{
+ DOMDocumentFragment *fragment;
+ NSEnumerator *enumerator = [paths objectEnumerator];
+ NSMutableArray *domNodes = [[NSMutableArray alloc] init];
+ NSString *path;
+
+ while ((path = [enumerator nextObject]) != nil) {
+ // Non-image file types; _web_userVisibleString is appropriate here because this will
+ // be pasted as visible text.
+ NSString *url = [[[NSURL fileURLWithPath:path] _webkit_canonicalize] _web_userVisibleString];
+ [domNodes addObject:[[[self _frame] DOMDocument] createTextNode: url]];
+ }
+
+ fragment = [[self _bridge] documentFragmentWithNodesAsParagraphs:domNodes];
+
+ [domNodes release];
+
+ return [fragment firstChild] != nil ? fragment : nil;
+}
+
++ (NSArray *)_excludedElementsForAttributedStringConversion
+{
+ static NSArray *elements = nil;
+ if (elements == nil) {
+ elements = [[NSArray alloc] initWithObjects:
+ // Omit style since we want style to be inline so the fragment can be easily inserted.
+ @"style",
+ // Omit xml so the result is not XHTML.
+ @"xml",
+ // Omit tags that will get stripped when converted to a fragment anyway.
+ @"doctype", @"html", @"head", @"body",
+ // Omit deprecated tags.
+ @"applet", @"basefont", @"center", @"dir", @"font", @"isindex", @"menu", @"s", @"strike", @"u",
+ // Omit object so no file attachments are part of the fragment.
+ @"object", nil];
+ CFRetain(elements);
+ }
+ return elements;
+}
+
+static NSURL* uniqueURLWithRelativePart(NSString *relativePart)
+{
+ CFUUIDRef UUIDRef = CFUUIDCreate(kCFAllocatorDefault);
+ NSString *UUIDString = (NSString *)CFUUIDCreateString(kCFAllocatorDefault, UUIDRef);
+ CFRelease(UUIDRef);
+ NSURL *URL = [NSURL URLWithString:[NSString stringWithFormat:@"%@://%@/%@", WebDataProtocolScheme, UUIDString, relativePart]];
+ CFRelease(UUIDString);
+
+ return URL;
+}
+
+- (DOMDocumentFragment *)_documentFragmentFromPasteboard:(NSPasteboard *)pasteboard
+ inContext:(DOMRange *)context
+ allowPlainText:(BOOL)allowPlainText
+{
+ NSArray *types = [pasteboard types];
+ DOMDocumentFragment *fragment = nil;
+
+ if ([types containsObject:WebArchivePboardType] &&
+ (fragment = [self _documentFragmentFromPasteboard:pasteboard
+ forType:WebArchivePboardType
+ inContext:context
+ subresources:0]))
+ return fragment;
+
+ if ([types containsObject:NSFilenamesPboardType] &&
+ (fragment = [self _documentFragmentFromPasteboard:pasteboard
+ forType:NSFilenamesPboardType
+ inContext:context
+ subresources:0]))
+ return fragment;
+
+ if ([types containsObject:NSHTMLPboardType] &&
+ (fragment = [self _documentFragmentFromPasteboard:pasteboard
+ forType:NSHTMLPboardType
+ inContext:context
+ subresources:0]))
+ return fragment;
+
+ if ([types containsObject:NSRTFPboardType] &&
+ (fragment = [self _documentFragmentFromPasteboard:pasteboard
+ forType:NSRTFPboardType
+ inContext:context
+ subresources:0]))
+ return fragment;
+
+ if ([types containsObject:NSRTFDPboardType] &&
+ (fragment = [self _documentFragmentFromPasteboard:pasteboard
+ forType:NSRTFDPboardType
+ inContext:context
+ subresources:0]))
+ return fragment;
+
+ if ([types containsObject:NSTIFFPboardType] &&
+ (fragment = [self _documentFragmentFromPasteboard:pasteboard
+ forType:NSTIFFPboardType
+ inContext:context
+ subresources:0]))
+ return fragment;
+
+ if ([types containsObject:NSPICTPboardType] &&
+ (fragment = [self _documentFragmentFromPasteboard:pasteboard
+ forType:NSPICTPboardType
+ inContext:context
+ subresources:0]))
+ return fragment;
+
+ if ([types containsObject:NSURLPboardType] &&
+ (fragment = [self _documentFragmentFromPasteboard:pasteboard
+ forType:NSURLPboardType
+ inContext:context
+ subresources:0]))
+ return fragment;
+
+ if (allowPlainText && [types containsObject:NSStringPboardType] &&
+ (fragment = [self _documentFragmentFromPasteboard:pasteboard
+ forType:NSStringPboardType
+ inContext:context
+ subresources:0])) {
+ return fragment;
+ }
+
+ return nil;
+}
+
+- (NSString *)_plainTextFromPasteboard:(NSPasteboard *)pasteboard
+{
+ NSArray *types = [pasteboard types];
+
+ if ([types containsObject:NSStringPboardType])
+ return [pasteboard stringForType:NSStringPboardType];
+
+ NSAttributedString *attributedString = nil;
+ NSString *string;
+
+ if ([types containsObject:NSRTFDPboardType])
+ attributedString = [[NSAttributedString alloc] initWithRTFD:[pasteboard dataForType:NSRTFDPboardType] documentAttributes:NULL];
+ if (attributedString == nil && [types containsObject:NSRTFPboardType])
+ attributedString = [[NSAttributedString alloc] initWithRTF:[pasteboard dataForType:NSRTFPboardType] documentAttributes:NULL];
+ if (attributedString != nil) {
+ string = [[attributedString string] copy];
+ [attributedString release];
+ return [string autorelease];
+ }
+
+ if ([types containsObject:NSFilenamesPboardType]) {
+ string = [[pasteboard propertyListForType:NSFilenamesPboardType] componentsJoinedByString:@"\n"];
+ if (string != nil)
+ return string;
+ }
+
+ NSURL *URL;
+
+ if ((URL = [NSURL URLFromPasteboard:pasteboard])) {
+ string = [URL _web_userVisibleString];
+ if ([string length] > 0)
+ return string;
+ }
+
+ return nil;
+}
+
+- (void)_pasteWithPasteboard:(NSPasteboard *)pasteboard allowPlainText:(BOOL)allowPlainText
+{
+ DOMRange *range = [self _selectedRange];
+ DOMDocumentFragment *fragment = [self _documentFragmentFromPasteboard:pasteboard
+ inContext:range allowPlainText:allowPlainText];
+ WebFrameBridge *bridge = [self _bridge];
+ if (fragment && [self _shouldInsertFragment:fragment replacingDOMRange:[self _selectedRange] givenAction:WebViewInsertActionPasted]) {
+ [bridge replaceSelectionWithFragment:fragment selectReplacement:NO smartReplace:[self _canSmartReplaceWithPasteboard:pasteboard] matchStyle:NO];
+ }
+}
+
+- (void)_pasteAsPlainTextWithPasteboard:(NSPasteboard *)pasteboard
+{
+ NSString *text = [self _plainTextFromPasteboard:pasteboard];
+ if ([self _shouldReplaceSelectionWithText:text givenAction:WebViewInsertActionPasted])
+ [[self _bridge] replaceSelectionWithText:text selectReplacement:NO smartReplace:[self _canSmartReplaceWithPasteboard:pasteboard]];
+}
+
+- (BOOL)_shouldInsertFragment:(DOMDocumentFragment *)fragment replacingDOMRange:(DOMRange *)range givenAction:(WebViewInsertAction)action
+{
+ WebView *webView = [self _webView];
+ DOMNode *child = [fragment firstChild];
+ if ([fragment lastChild] == child && [child isKindOfClass:[DOMCharacterData class]])
+ return [[webView _editingDelegateForwarder] webView:webView shouldInsertText:[(DOMCharacterData *)child data] replacingDOMRange:range givenAction:action];
+ return [[webView _editingDelegateForwarder] webView:webView shouldInsertNode:fragment replacingDOMRange:range givenAction:action];
+}
+
+- (BOOL)_shouldInsertText:(NSString *)text replacingDOMRange:(DOMRange *)range givenAction:(WebViewInsertAction)action
+{
+ WebView *webView = [self _webView];
+ return [[webView _editingDelegateForwarder] webView:webView shouldInsertText:text replacingDOMRange:range givenAction:action];
+}
+
+- (BOOL)_shouldReplaceSelectionWithText:(NSString *)text givenAction:(WebViewInsertAction)action
+{
+ return [self _shouldInsertText:text replacingDOMRange:[self _selectedRange] givenAction:action];
+}
+
+// Calculate the vertical size of the view that fits on a single page
+- (float)_calculatePrintHeight
+{
+ // Obtain the print info object for the current operation
+ NSPrintInfo *pi = [[NSPrintOperation currentOperation] printInfo];
+
+ // Calculate the page height in points
+ NSSize paperSize = [pi paperSize];
+ return paperSize.height - [pi topMargin] - [pi bottomMargin];
+}
+
+- (void)_updateTextSizeMultiplier
+{
+ [[self _bridge] setTextSizeMultiplier:[[self _webView] textSizeMultiplier]];
+}
+
+- (DOMRange *)_selectedRange
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame ? kit(coreFrame->selectionController()->toRange().get()) : nil;
+}
+
+- (BOOL)_shouldDeleteRange:(DOMRange *)range
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame && coreFrame->editor()->shouldDeleteRange(core(range));
+}
+
+- (NSView *)_hitViewForEvent:(NSEvent *)event
+{
+ // Usually, we hack AK's hitTest method to catch all events at the topmost WebHTMLView.
+ // Callers of this method, however, want to query the deepest view instead.
+ forceNSViewHitTest = YES;
+ NSView *hitView = [[[self window] contentView] hitTest:[event locationInWindow]];
+ forceNSViewHitTest = NO;
+ return hitView;
+}
+
+- (void)_writeSelectionWithPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard cachedAttributedString:(NSAttributedString *)attributedString
+{
+ // Put HTML on the pasteboard.
+ if ([types containsObject:WebArchivePboardType]) {
+ WebArchive *archive = [WebArchiver archiveSelectionInFrame:[self _frame]];
+ [pasteboard setData:[archive data] forType:WebArchivePboardType];
+ }
+
+ // Put the attributed string on the pasteboard (RTF/RTFD format).
+ if ([types containsObject:NSRTFDPboardType]) {
+ if (attributedString == nil) {
+ attributedString = [self selectedAttributedString];
+ }
+ NSData *RTFDData = [attributedString RTFDFromRange:NSMakeRange(0, [attributedString length]) documentAttributes:nil];
+ [pasteboard setData:RTFDData forType:NSRTFDPboardType];
+ }
+ if ([types containsObject:NSRTFPboardType]) {
+ if (attributedString == nil) {
+ attributedString = [self selectedAttributedString];
+ }
+ if ([attributedString containsAttachments]) {
+ attributedString = [attributedString _web_attributedStringByStrippingAttachmentCharacters];
+ }
+ NSData *RTFData = [attributedString RTFFromRange:NSMakeRange(0, [attributedString length]) documentAttributes:nil];
+ [pasteboard setData:RTFData forType:NSRTFPboardType];
+ }
+
+ // Put plain string on the pasteboard.
+ if ([types containsObject:NSStringPboardType]) {
+ // Map &nbsp; to a plain old space because this is better for source code, other browsers do it,
+ // and because HTML forces you to do this any time you want two spaces in a row.
+ NSMutableString *s = [[self selectedString] mutableCopy];
+ const unichar NonBreakingSpaceCharacter = 0xA0;
+ NSString *NonBreakingSpaceString = [NSString stringWithCharacters:&NonBreakingSpaceCharacter length:1];
+ [s replaceOccurrencesOfString:NonBreakingSpaceString withString:@" " options:0 range:NSMakeRange(0, [s length])];
+ [pasteboard setString:s forType:NSStringPboardType];
+ [s release];
+ }
+
+ if ([self _canSmartCopyOrDelete] && [types containsObject:WebSmartPastePboardType]) {
+ [pasteboard setData:nil forType:WebSmartPastePboardType];
+ }
+}
+
+- (void)_setMouseDownEvent:(NSEvent *)event
+{
+ ASSERT(!event || [event type] == NSLeftMouseDown || [event type] == NSRightMouseDown || [event type] == NSOtherMouseDown);
+
+ if (event == _private->mouseDownEvent)
+ return;
+
+ [event retain];
+ [_private->mouseDownEvent release];
+ _private->mouseDownEvent = event;
+}
+
+- (void)_cancelUpdateFocusedAndActiveStateTimer
+{
+ if (_private->updateFocusedAndActiveStateTimer) {
+ CFRunLoopTimerInvalidate(_private->updateFocusedAndActiveStateTimer);
+ CFRelease(_private->updateFocusedAndActiveStateTimer);
+ _private->updateFocusedAndActiveStateTimer = NULL;
+ }
+}
+
+- (void)_cancelUpdateMouseoverTimer
+{
+ if (_private->updateMouseoverTimer) {
+ CFRunLoopTimerInvalidate(_private->updateMouseoverTimer);
+ CFRelease(_private->updateMouseoverTimer);
+ _private->updateMouseoverTimer = NULL;
+ }
+}
+
+- (WebHTMLView *)_topHTMLView
+{
+ // FIXME: this can fail if the dataSource is nil, which happens when the WebView is tearing down from the window closing.
+ WebHTMLView *view = (WebHTMLView *)[[[[_private->dataSource _webView] mainFrame] frameView] documentView];
+ ASSERT(view);
+ ASSERT([view isKindOfClass:[WebHTMLView class]]);
+ return view;
+}
+
+- (BOOL)_isTopHTMLView
+{
+ // FIXME: this should be a cached boolean that doesn't rely on _topHTMLView since that can fail (see _topHTMLView).
+ return self == [self _topHTMLView];
+}
+
+- (void)_web_setPrintingModeRecursive
+{
+ [self _setPrinting:YES minimumPageWidth:0.0f maximumPageWidth:0.0f adjustViewSize:NO];
+
+#ifndef NDEBUG
+ _private->enumeratingSubviews = YES;
+#endif
+
+ NSMutableArray *descendantWebHTMLViews = [[NSMutableArray alloc] init];
+
+ [self _web_addDescendantWebHTMLViewsToArray:descendantWebHTMLViews];
+
+ unsigned count = [descendantWebHTMLViews count];
+ for (unsigned i = 0; i < count; ++i)
+ [[descendantWebHTMLViews objectAtIndex:i] _setPrinting:YES minimumPageWidth:0.0f maximumPageWidth:0.0f adjustViewSize:NO];
+
+ [descendantWebHTMLViews release];
+
+#ifndef NDEBUG
+ _private->enumeratingSubviews = NO;
+#endif
+}
+
+- (void)_web_clearPrintingModeRecursive
+{
+ [self _setPrinting:NO minimumPageWidth:0.0f maximumPageWidth:0.0f adjustViewSize:NO];
+
+#ifndef NDEBUG
+ _private->enumeratingSubviews = YES;
+#endif
+
+ NSMutableArray *descendantWebHTMLViews = [[NSMutableArray alloc] init];
+
+ [self _web_addDescendantWebHTMLViewsToArray:descendantWebHTMLViews];
+
+ unsigned count = [descendantWebHTMLViews count];
+ for (unsigned i = 0; i < count; ++i)
+ [[descendantWebHTMLViews objectAtIndex:i] _setPrinting:NO minimumPageWidth:0.0f maximumPageWidth:0.0f adjustViewSize:NO];
+
+ [descendantWebHTMLViews release];
+
+#ifndef NDEBUG
+ _private->enumeratingSubviews = NO;
+#endif
+}
+
+- (void)_web_setPrintingModeRecursiveAndAdjustViewSize
+{
+ [self _setPrinting:YES minimumPageWidth:0.0f maximumPageWidth:0.0f adjustViewSize:YES];
+
+#ifndef NDEBUG
+ _private->enumeratingSubviews = YES;
+#endif
+
+ NSMutableArray *descendantWebHTMLViews = [[NSMutableArray alloc] init];
+
+ [self _web_addDescendantWebHTMLViewsToArray:descendantWebHTMLViews];
+
+ unsigned count = [descendantWebHTMLViews count];
+ for (unsigned i = 0; i < count; ++i)
+ [[descendantWebHTMLViews objectAtIndex:i] _setPrinting:YES minimumPageWidth:0.0f maximumPageWidth:0.0f adjustViewSize:YES];
+
+ [descendantWebHTMLViews release];
+
+#ifndef NDEBUG
+ _private->enumeratingSubviews = NO;
+#endif
+}
+
+@end
+
+@implementation WebHTMLView (WebPrivate)
+
++ (NSArray *)supportedMIMETypes
+{
+ return [WebHTMLRepresentation supportedMIMETypes];
+}
+
++ (NSArray *)supportedImageMIMETypes
+{
+ return [WebHTMLRepresentation supportedImageMIMETypes];
+}
+
++ (NSArray *)supportedNonImageMIMETypes
+{
+ return [WebHTMLRepresentation supportedNonImageMIMETypes];
+}
+
++ (NSArray *)unsupportedTextMIMETypes
+{
+ return [NSArray arrayWithObjects:
+ @"text/calendar", // iCal
+ @"text/x-calendar",
+ @"text/x-vcalendar",
+ @"text/vcalendar",
+ @"text/vcard", // vCard
+ @"text/x-vcard",
+ @"text/directory",
+ @"text/ldif", // Netscape Address Book
+ @"text/qif", // Quicken
+ @"text/x-qif",
+ @"text/x-csv", // CSV (for Address Book and Microsoft Outlook)
+ @"text/x-vcf", // vCard type used in Sun affinity app
+ @"text/rtf", // Rich Text Format
+ nil];
+}
+
++ (void)_postFlagsChangedEvent:(NSEvent *)flagsChangedEvent
+{
+ // This is a workaround for: <rdar://problem/2981619> NSResponder_Private should include notification for FlagsChanged
+ NSEvent *fakeEvent = [NSEvent mouseEventWithType:NSMouseMoved
+ location:[[flagsChangedEvent window] convertScreenToBase:[NSEvent mouseLocation]]
+ modifierFlags:[flagsChangedEvent modifierFlags]
+ timestamp:[flagsChangedEvent timestamp]
+ windowNumber:[flagsChangedEvent windowNumber]
+ context:[flagsChangedEvent context]
+ eventNumber:0 clickCount:0 pressure:0];
+
+ // Pretend it's a mouse move.
+ [[NSNotificationCenter defaultCenter]
+ postNotificationName:WKMouseMovedNotification() object:self
+ userInfo:[NSDictionary dictionaryWithObject:fakeEvent forKey:@"NSEvent"]];
+}
+
+- (void)_updateMouseoverWithFakeEvent
+{
+ [self _cancelUpdateMouseoverTimer];
+
+ NSEvent *fakeEvent = [NSEvent mouseEventWithType:NSMouseMoved
+ location:[[self window] convertScreenToBase:[NSEvent mouseLocation]]
+ modifierFlags:[[NSApp currentEvent] modifierFlags]
+ timestamp:[NSDate timeIntervalSinceReferenceDate]
+ windowNumber:[[self window] windowNumber]
+ context:[[NSApp currentEvent] context]
+ eventNumber:0 clickCount:0 pressure:0];
+
+ [self _updateMouseoverWithEvent:fakeEvent];
+}
+
+static void _updateMouseoverTimerCallback(CFRunLoopTimerRef timer, void *info)
+{
+ WebHTMLView *view = (WebHTMLView *)info;
+
+ [view _updateMouseoverWithFakeEvent];
+}
+
+- (void)_frameOrBoundsChanged
+{
+ if (!NSEqualSizes(_private->lastLayoutSize, [(NSClipView *)[self superview] documentVisibleRect].size)) {
+ [self setNeedsLayout:YES];
+ [self setNeedsDisplay:YES];
+ [_private->compController endRevertingChange:NO moveLeft:NO];
+ }
+
+ NSPoint origin = [[self superview] bounds].origin;
+ if (!NSEqualPoints(_private->lastScrollPosition, origin)) {
+ [[self _bridge] sendScrollEvent];
+ [_private->compController endRevertingChange:NO moveLeft:NO];
+
+ WebView *webView = [self _webView];
+ [[webView _UIDelegateForwarder] webView:webView didScrollDocumentInFrameView:[self _frameView]];
+ }
+ _private->lastScrollPosition = origin;
+
+ if ([self window] && !_private->closed && !_private->updateMouseoverTimer) {
+ CFRunLoopTimerContext context = { 0, self, NULL, NULL, NULL };
+
+ // Use a 100ms delay so that the synthetic mouse over update doesn't cause cursor thrashing when pages are loading
+ // and scrolling rapidly back to back.
+ _private->updateMouseoverTimer = CFRunLoopTimerCreate(NULL, CFAbsoluteTimeGetCurrent() + 0.1, 0, 0, 0,
+ _updateMouseoverTimerCallback, &context);
+ CFRunLoopAddTimer(CFRunLoopGetCurrent(), _private->updateMouseoverTimer, kCFRunLoopDefaultMode);
+ }
+}
+
+- (void)_setAsideSubviews
+{
+ ASSERT(!_private->subviewsSetAside);
+ ASSERT(_private->savedSubviews == nil);
+ _private->savedSubviews = _subviews;
+ _subviews = nil;
+ _private->subviewsSetAside = YES;
+ }
+
+ - (void)_restoreSubviews
+ {
+ ASSERT(_private->subviewsSetAside);
+ ASSERT(_subviews == nil);
+ _subviews = _private->savedSubviews;
+ _private->savedSubviews = nil;
+ _private->subviewsSetAside = NO;
+}
+
+#ifndef NDEBUG
+
+- (void)didAddSubview:(NSView *)subview
+{
+ if (_private->enumeratingSubviews)
+ LOG(View, "A view of class %s was added during subview enumeration for layout or printing mode change. This view might paint without first receiving layout.", object_getClassName([subview class]));
+}
+
+- (void)willRemoveSubview:(NSView *)subview
+{
+ if (_private->enumeratingSubviews)
+ LOG(View, "A view of class %s was removed during subview enumeration for layout or printing mode change. We will still do layout or the printing mode change even though this view is no longer in the view hierarchy.", object_getClassName([subview class]));
+}
+
+#endif
+
+#ifdef BUILDING_ON_TIGER
+
+// This is called when we are about to draw, but before our dirty rect is propagated to our ancestors.
+// That's the perfect time to do a layout, except that ideally we'd want to be sure that we're dirty
+// before doing it. As a compromise, when we're opaque we do the layout only when actually asked to
+// draw, but when we're transparent we do the layout at this stage so views behind us know that they
+// need to be redrawn (in case the layout causes some things to get dirtied).
+- (void)_propagateDirtyRectsToOpaqueAncestors
+{
+ if (![[self _webView] drawsBackground])
+ [self _web_layoutIfNeededRecursive];
+ [super _propagateDirtyRectsToOpaqueAncestors];
+}
+
+#else
+
+- (void)viewWillDraw
+{
+ // On window close we will be called when the datasource is nil, then hit an assert in _topHTMLView
+ // So check if the dataSource is nil before calling [self _isTopHTMLView], this can be removed
+ // once the FIXME in _isTopHTMLView is fixed.
+ if (_private->dataSource && [self _isTopHTMLView])
+ [self _web_layoutIfNeededRecursive];
+ [super viewWillDraw];
+}
+
+#endif
+
+// Don't let AppKit even draw subviews. We take care of that.
+- (void)_recursiveDisplayRectIfNeededIgnoringOpacity:(NSRect)rect isVisibleRect:(BOOL)isVisibleRect rectIsVisibleRectForView:(NSView *)visibleView topView:(BOOL)topView
+{
+ // This helps when we print as part of a larger print process.
+ // If the WebHTMLView itself is what we're printing, then we will never have to do this.
+ BOOL wasInPrintingMode = _private->printing;
+ BOOL isPrinting = ![NSGraphicsContext currentContextDrawingToScreen];
+ if (wasInPrintingMode != isPrinting) {
+ if (isPrinting)
+ [self _web_setPrintingModeRecursive];
+ else
+ [self _web_clearPrintingModeRecursive];
+ }
+
+#ifdef BUILDING_ON_TIGER
+
+ // Because Tiger does not have viewWillDraw we need to do layout here.
+ [self _web_layoutIfNeededRecursive];
+ [_subviews makeObjectsPerformSelector:@selector(_propagateDirtyRectsToOpaqueAncestors)];
+
+#endif
+
+ [self _setAsideSubviews];
+ [super _recursiveDisplayRectIfNeededIgnoringOpacity:rect isVisibleRect:isVisibleRect rectIsVisibleRectForView:visibleView topView:topView];
+ [self _restoreSubviews];
+
+ if (wasInPrintingMode != isPrinting) {
+ if (wasInPrintingMode)
+ [self _web_setPrintingModeRecursive];
+ else
+ [self _web_clearPrintingModeRecursive];
+ }
+}
+
+// Don't let AppKit even draw subviews. We take care of that.
+- (void)_recursiveDisplayAllDirtyWithLockFocus:(BOOL)needsLockFocus visRect:(NSRect)visRect
+{
+ BOOL needToSetAsideSubviews = !_private->subviewsSetAside;
+
+ BOOL wasInPrintingMode = _private->printing;
+ BOOL isPrinting = ![NSGraphicsContext currentContextDrawingToScreen];
+
+ if (needToSetAsideSubviews) {
+ // This helps when we print as part of a larger print process.
+ // If the WebHTMLView itself is what we're printing, then we will never have to do this.
+ if (wasInPrintingMode != isPrinting) {
+ if (isPrinting)
+ [self _web_setPrintingModeRecursive];
+ else
+ [self _web_clearPrintingModeRecursive];
+ }
+
+#ifdef BUILDING_ON_TIGER
+
+ // Because Tiger does not have viewWillDraw we need to do layout here.
+ NSRect boundsBeforeLayout = [self bounds];
+ if (!NSIsEmptyRect(visRect))
+ [self _web_layoutIfNeededRecursive];
+
+ // If layout changes the view's bounds, then we need to recompute the visRect.
+ // That's because the visRect passed to us was based on the bounds at the time
+ // we were called. This method is only displayed to draw "all", so it's safe
+ // to just call visibleRect to compute the entire rectangle.
+ if (!NSEqualRects(boundsBeforeLayout, [self bounds]))
+ visRect = [self visibleRect];
+
+#endif
+
+ [self _setAsideSubviews];
+ }
+
+ [super _recursiveDisplayAllDirtyWithLockFocus:needsLockFocus visRect:visRect];
+
+ if (needToSetAsideSubviews) {
+ if (wasInPrintingMode != isPrinting) {
+ if (wasInPrintingMode)
+ [self _web_setPrintingModeRecursive];
+ else
+ [self _web_clearPrintingModeRecursive];
+ }
+
+ [self _restoreSubviews];
+ }
+}
+
+- (BOOL)_insideAnotherHTMLView
+{
+ return self != [self _topHTMLView];
+}
+
+- (NSView *)hitTest:(NSPoint)point
+{
+ // WebHTMLView objects handle all events for objects inside them.
+ // To get those events, we prevent hit testing from AppKit.
+
+ // But there are three exceptions to this:
+ // 1) For right mouse clicks and control clicks we don't yet have an implementation
+ // that works for nested views, so we let the hit testing go through the
+ // standard NSView code path (needs to be fixed, see bug 4361618).
+ // 2) Java depends on doing a hit test inside it's mouse moved handling,
+ // so we let the hit testing go through the standard NSView code path
+ // when the current event is a mouse move (except when we are calling
+ // from _updateMouseoverWithEvent, so we have to use a global,
+ // forceWebHTMLViewHitTest, for that)
+ // 3) The acceptsFirstMouse: and shouldDelayWindowOrderingForEvent: methods
+ // both need to figure out which view to check with inside the WebHTMLView.
+ // They use a global to change the behavior of hitTest: so they can get the
+ // right view. The global is forceNSViewHitTest and the method they use to
+ // do the hit testing is _hitViewForEvent:. (But this does not work correctly
+ // when there is HTML overlapping the view, see bug 4361626)
+ // 4) NSAccessibilityHitTest relies on this for checking the cursor position.
+ // Our check for that is whether the event is NSFlagsChanged. This works
+ // for VoiceOver's cntl-opt-f5 command (move focus to item under cursor)
+ // and Dictionary's cmd-cntl-D (open dictionary popup for item under cursor).
+ // This is of course a hack.
+
+ BOOL captureHitsOnSubviews;
+ if (forceNSViewHitTest)
+ captureHitsOnSubviews = NO;
+ else if (forceWebHTMLViewHitTest)
+ captureHitsOnSubviews = YES;
+ else {
+ NSEvent *event = [[self window] currentEvent];
+ captureHitsOnSubviews = !([event type] == NSMouseMoved
+ || [event type] == NSRightMouseDown
+ || ([event type] == NSLeftMouseDown && ([event modifierFlags] & NSControlKeyMask) != 0)
+ || [event type] == NSFlagsChanged);
+ }
+
+ if (!captureHitsOnSubviews)
+ return [super hitTest:point];
+ if ([[self superview] mouse:point inRect:[self frame]])
+ return self;
+ return nil;
+}
+
+- (void)_clearLastHitViewIfSelf
+{
+ if (lastHitView == self)
+ lastHitView = nil;
+}
+
+- (NSTrackingRectTag)addTrackingRect:(NSRect)rect owner:(id)owner userData:(void *)data assumeInside:(BOOL)assumeInside
+{
+ ASSERT(_private->trackingRectOwner == nil);
+ _private->trackingRectOwner = owner;
+ _private->trackingRectUserData = data;
+ return TRACKING_RECT_TAG;
+}
+
+- (NSTrackingRectTag)_addTrackingRect:(NSRect)rect owner:(id)owner userData:(void *)data assumeInside:(BOOL)assumeInside useTrackingNum:(int)tag
+{
+ ASSERT(tag == 0 || tag == TRACKING_RECT_TAG);
+ ASSERT(_private->trackingRectOwner == nil);
+ _private->trackingRectOwner = owner;
+ _private->trackingRectUserData = data;
+ return TRACKING_RECT_TAG;
+}
+
+- (void)_addTrackingRects:(NSRect *)rects owner:(id)owner userDataList:(void **)userDataList assumeInsideList:(BOOL *)assumeInsideList trackingNums:(NSTrackingRectTag *)trackingNums count:(int)count
+{
+ ASSERT(count == 1);
+ ASSERT(trackingNums[0] == 0 || trackingNums[0] == TRACKING_RECT_TAG);
+ ASSERT(_private->trackingRectOwner == nil);
+ _private->trackingRectOwner = owner;
+ _private->trackingRectUserData = userDataList[0];
+ trackingNums[0] = TRACKING_RECT_TAG;
+}
+
+- (void)removeTrackingRect:(NSTrackingRectTag)tag
+{
+ if (tag == 0)
+ return;
+
+ if (_private && (tag == TRACKING_RECT_TAG)) {
+ _private->trackingRectOwner = nil;
+ return;
+ }
+
+ if (_private && (tag == _private->lastToolTipTag)) {
+ [super removeTrackingRect:tag];
+ _private->lastToolTipTag = 0;
+ return;
+ }
+
+ // If any other tracking rect is being removed, we don't know how it was created
+ // and it's possible there's a leak involved (see 3500217)
+ ASSERT_NOT_REACHED();
+}
+
+- (void)_removeTrackingRects:(NSTrackingRectTag *)tags count:(int)count
+{
+ int i;
+ for (i = 0; i < count; ++i) {
+ int tag = tags[i];
+ if (tag == 0)
+ continue;
+ ASSERT(tag == TRACKING_RECT_TAG);
+ if (_private != nil) {
+ _private->trackingRectOwner = nil;
+ }
+ }
+}
+
+- (void)_sendToolTipMouseExited
+{
+ // Nothing matters except window, trackingNumber, and userData.
+ NSEvent *fakeEvent = [NSEvent enterExitEventWithType:NSMouseExited
+ location:NSMakePoint(0, 0)
+ modifierFlags:0
+ timestamp:0
+ windowNumber:[[self window] windowNumber]
+ context:NULL
+ eventNumber:0
+ trackingNumber:TRACKING_RECT_TAG
+ userData:_private->trackingRectUserData];
+ [_private->trackingRectOwner mouseExited:fakeEvent];
+}
+
+- (void)_sendToolTipMouseEntered
+{
+ // Nothing matters except window, trackingNumber, and userData.
+ NSEvent *fakeEvent = [NSEvent enterExitEventWithType:NSMouseEntered
+ location:NSMakePoint(0, 0)
+ modifierFlags:0
+ timestamp:0
+ windowNumber:[[self window] windowNumber]
+ context:NULL
+ eventNumber:0
+ trackingNumber:TRACKING_RECT_TAG
+ userData:_private->trackingRectUserData];
+ [_private->trackingRectOwner mouseEntered:fakeEvent];
+}
+
+- (void)_setToolTip:(NSString *)string
+{
+ NSString *toolTip = [string length] == 0 ? nil : string;
+ NSString *oldToolTip = _private->toolTip;
+ if ((toolTip == nil || oldToolTip == nil) ? toolTip == oldToolTip : [toolTip isEqualToString:oldToolTip]) {
+ return;
+ }
+ if (oldToolTip) {
+ [self _sendToolTipMouseExited];
+ [oldToolTip release];
+ }
+ _private->toolTip = [toolTip copy];
+ if (toolTip) {
+ // See radar 3500217 for why we remove all tooltips rather than just the single one we created.
+ [self removeAllToolTips];
+ NSRect wideOpenRect = NSMakeRect(-100000, -100000, 200000, 200000);
+ _private->lastToolTipTag = [self addToolTipRect:wideOpenRect owner:self userData:NULL];
+ [self _sendToolTipMouseEntered];
+ }
+}
+
+- (NSString *)view:(NSView *)view stringForToolTip:(NSToolTipTag)tag point:(NSPoint)point userData:(void *)data
+{
+ return [[_private->toolTip copy] autorelease];
+}
+
+- (void)_updateMouseoverWithEvent:(NSEvent *)event
+{
+ if (_private->closed)
+ return;
+
+ NSView *contentView = [[event window] contentView];
+ NSPoint locationForHitTest = [[contentView superview] convertPoint:[event locationInWindow] fromView:nil];
+
+ forceWebHTMLViewHitTest = YES;
+ NSView *hitView = [contentView hitTest:locationForHitTest];
+ forceWebHTMLViewHitTest = NO;
+
+ WebHTMLView *view = nil;
+ if ([hitView isKindOfClass:[WebHTMLView class]] && ![[(WebHTMLView *)hitView _webView] isHoverFeedbackSuspended])
+ view = (WebHTMLView *)hitView;
+
+ if (view)
+ [view retain];
+
+ if (lastHitView != view && lastHitView && [lastHitView _frame]) {
+ // If we are moving out of a view (or frame), let's pretend the mouse moved
+ // all the way out of that view. But we have to account for scrolling, because
+ // khtml doesn't understand our clipping.
+ NSRect visibleRect = [[[[lastHitView _frame] frameView] _scrollView] documentVisibleRect];
+ float yScroll = visibleRect.origin.y;
+ float xScroll = visibleRect.origin.x;
+
+ event = [NSEvent mouseEventWithType:NSMouseMoved
+ location:NSMakePoint(-1 - xScroll, -1 - yScroll )
+ modifierFlags:[[NSApp currentEvent] modifierFlags]
+ timestamp:[NSDate timeIntervalSinceReferenceDate]
+ windowNumber:[[view window] windowNumber]
+ context:[[NSApp currentEvent] context]
+ eventNumber:0 clickCount:0 pressure:0];
+ if (Frame* lastHitCoreFrame = core([lastHitView _frame]))
+ lastHitCoreFrame->eventHandler()->mouseMoved(event);
+ }
+
+ lastHitView = view;
+
+ if (view) {
+ if (Frame* coreFrame = core([view _frame]))
+ coreFrame->eventHandler()->mouseMoved(event);
+
+ [view release];
+ }
+}
+
+// keep in sync with WebPasteboardHelper::insertablePasteboardTypes
++ (NSArray *)_insertablePasteboardTypes
+{
+ static NSArray *types = nil;
+ if (!types) {
+ types = [[NSArray alloc] initWithObjects:WebArchivePboardType, NSHTMLPboardType,
+ NSFilenamesPboardType, NSTIFFPboardType, NSPICTPboardType, NSURLPboardType,
+ NSRTFDPboardType, NSRTFPboardType, NSStringPboardType, NSColorPboardType, nil];
+ CFRetain(types);
+ }
+ return types;
+}
+
++ (NSArray *)_selectionPasteboardTypes
+{
+ // FIXME: We should put data for NSHTMLPboardType on the pasteboard but Microsoft Excel doesn't like our format of HTML (3640423).
+ return [NSArray arrayWithObjects:WebArchivePboardType, NSRTFDPboardType, NSRTFPboardType, NSStringPboardType, nil];
+}
+
+- (NSImage *)_dragImageForURL:(NSString*)urlString withLabel:(NSString*)label
+{
+ BOOL drawURLString = YES;
+ BOOL clipURLString = NO, clipLabelString = NO;
+
+ if (!label) {
+ drawURLString = NO;
+ label = urlString;
+ }
+
+ NSFont *labelFont = [[NSFontManager sharedFontManager] convertFont:[NSFont systemFontOfSize:DRAG_LINK_LABEL_FONT_SIZE]
+ toHaveTrait:NSBoldFontMask];
+ NSFont *urlFont = [NSFont systemFontOfSize: DRAG_LINK_URL_FONT_SIZE];
+ NSSize labelSize;
+ labelSize.width = [label _web_widthWithFont: labelFont];
+ labelSize.height = [labelFont ascender] - [labelFont descender];
+ if (labelSize.width > MAX_DRAG_LABEL_WIDTH){
+ labelSize.width = MAX_DRAG_LABEL_WIDTH;
+ clipLabelString = YES;
+ }
+
+ NSSize imageSize, urlStringSize;
+ imageSize.width = labelSize.width + DRAG_LABEL_BORDER_X * 2.0f;
+ imageSize.height = labelSize.height + DRAG_LABEL_BORDER_Y * 2.0f;
+ if (drawURLString) {
+ urlStringSize.width = [urlString _web_widthWithFont: urlFont];
+ urlStringSize.height = [urlFont ascender] - [urlFont descender];
+ imageSize.height += urlStringSize.height;
+ if (urlStringSize.width > MAX_DRAG_LABEL_WIDTH) {
+ imageSize.width = MAX(MAX_DRAG_LABEL_WIDTH + DRAG_LABEL_BORDER_X * 2.0f, MIN_DRAG_LABEL_WIDTH_BEFORE_CLIP);
+ clipURLString = YES;
+ } else {
+ imageSize.width = MAX(labelSize.width + DRAG_LABEL_BORDER_X * 2.0f, urlStringSize.width + DRAG_LABEL_BORDER_X * 2.0f);
+ }
+ }
+ NSImage *dragImage = [[[NSImage alloc] initWithSize: imageSize] autorelease];
+ [dragImage lockFocus];
+
+ [[NSColor colorWithCalibratedRed: 0.7f green: 0.7f blue: 0.7f alpha: 0.8f] set];
+
+ // Drag a rectangle with rounded corners/
+ NSBezierPath *path = [NSBezierPath bezierPath];
+ [path appendBezierPathWithOvalInRect: NSMakeRect(0.0f, 0.0f, DRAG_LABEL_RADIUS * 2.0f, DRAG_LABEL_RADIUS * 2.0f)];
+ [path appendBezierPathWithOvalInRect: NSMakeRect(0, imageSize.height - DRAG_LABEL_RADIUS * 2.0f, DRAG_LABEL_RADIUS * 2.0f, DRAG_LABEL_RADIUS * 2.0f)];
+ [path appendBezierPathWithOvalInRect: NSMakeRect(imageSize.width - DRAG_LABEL_RADIUS * 2.0f, imageSize.height - DRAG_LABEL_RADIUS * 2.0f, DRAG_LABEL_RADIUS * 2.0f, DRAG_LABEL_RADIUS * 2.0f)];
+ [path appendBezierPathWithOvalInRect: NSMakeRect(imageSize.width - DRAG_LABEL_RADIUS * 2.0f, 0.0f, DRAG_LABEL_RADIUS * 2.0f, DRAG_LABEL_RADIUS * 2.0f)];
+
+ [path appendBezierPathWithRect: NSMakeRect(DRAG_LABEL_RADIUS, 0.0f, imageSize.width - DRAG_LABEL_RADIUS * 2.0f, imageSize.height)];
+ [path appendBezierPathWithRect: NSMakeRect(0.0f, DRAG_LABEL_RADIUS, DRAG_LABEL_RADIUS + 10.0f, imageSize.height - 2.0f * DRAG_LABEL_RADIUS)];
+ [path appendBezierPathWithRect: NSMakeRect(imageSize.width - DRAG_LABEL_RADIUS - 20.0f, DRAG_LABEL_RADIUS, DRAG_LABEL_RADIUS + 20.0f, imageSize.height - 2.0f * DRAG_LABEL_RADIUS)];
+ [path fill];
+
+ NSColor *topColor = [NSColor colorWithCalibratedWhite:0.0f alpha:0.75f];
+ NSColor *bottomColor = [NSColor colorWithCalibratedWhite:1.0f alpha:0.5f];
+ if (drawURLString) {
+ if (clipURLString)
+ urlString = [WebStringTruncator centerTruncateString: urlString toWidth:imageSize.width - (DRAG_LABEL_BORDER_X * 2.0f) withFont:urlFont];
+
+ [urlString _web_drawDoubledAtPoint:NSMakePoint(DRAG_LABEL_BORDER_X, DRAG_LABEL_BORDER_Y - [urlFont descender])
+ withTopColor:topColor bottomColor:bottomColor font:urlFont];
+ }
+
+ if (clipLabelString)
+ label = [WebStringTruncator rightTruncateString: label toWidth:imageSize.width - (DRAG_LABEL_BORDER_X * 2.0f) withFont:labelFont];
+ [label _web_drawDoubledAtPoint:NSMakePoint (DRAG_LABEL_BORDER_X, imageSize.height - DRAG_LABEL_BORDER_Y_OFFSET - [labelFont pointSize])
+ withTopColor:topColor bottomColor:bottomColor font:labelFont];
+
+ [dragImage unlockFocus];
+
+ return dragImage;
+}
+
+- (NSImage *)_dragImageForLinkElement:(NSDictionary *)element
+{
+ NSURL *linkURL = [element objectForKey: WebElementLinkURLKey];
+
+ NSString *label = [element objectForKey: WebElementLinkLabelKey];
+ NSString *urlString = [linkURL _web_userVisibleString];
+ return [self _dragImageForURL:urlString withLabel:label];
+}
+
+- (void)pasteboardChangedOwner:(NSPasteboard *)pasteboard
+{
+ [self setPromisedDragTIFFDataSource:0];
+}
+
+- (void)pasteboard:(NSPasteboard *)pasteboard provideDataForType:(NSString *)type
+{
+ if ([type isEqual:NSRTFDPboardType] && [[pasteboard types] containsObject:WebArchivePboardType]) {
+ WebArchive *archive = [[WebArchive alloc] initWithData:[pasteboard dataForType:WebArchivePboardType]];
+ [pasteboard _web_writePromisedRTFDFromArchive:archive containsImage:[[pasteboard types] containsObject:NSTIFFPboardType]];
+ [archive release];
+ } else if ([type isEqual:NSTIFFPboardType] && [self promisedDragTIFFDataSource]) {
+ if (Image* image = [self promisedDragTIFFDataSource]->image())
+ [pasteboard setData:(NSData *)image->getTIFFRepresentation() forType:NSTIFFPboardType];
+ [self setPromisedDragTIFFDataSource:0];
+ }
+}
+
+- (void)_handleAutoscrollForMouseDragged:(NSEvent *)event
+{
+ [self autoscroll:event];
+ [self _startAutoscrollTimer:event];
+}
+
+- (WebPluginController *)_pluginController
+{
+ return _private->pluginController;
+}
+
+- (void)_layoutForPrinting
+{
+ // Set printing mode temporarily so we can adjust the size of the view. This will allow
+ // AppKit's pagination code to use the correct height for the page content. Leaving printing
+ // mode on indefinitely would interfere with Mail's printing mechanism (at least), so we just
+ // turn it off again after adjusting the size.
+ [self _web_setPrintingModeRecursiveAndAdjustViewSize];
+ [self _web_clearPrintingModeRecursive];
+}
+
+- (void)_smartInsertForString:(NSString *)pasteString replacingRange:(DOMRange *)rangeToReplace beforeString:(NSString **)beforeString afterString:(NSString **)afterString
+{
+ if (!pasteString || !rangeToReplace || ![[self _webView] smartInsertDeleteEnabled]) {
+ if (beforeString)
+ *beforeString = nil;
+ if (afterString)
+ *afterString = nil;
+ return;
+ }
+
+ [[self _bridge] smartInsertForString:pasteString replacingRange:rangeToReplace beforeString:beforeString afterString:afterString];
+}
+
+- (BOOL)_canSmartReplaceWithPasteboard:(NSPasteboard *)pasteboard
+{
+ return [[self _webView] smartInsertDeleteEnabled] && [[pasteboard types] containsObject:WebSmartPastePboardType];
+}
+
+- (void)_startAutoscrollTimer: (NSEvent *)triggerEvent
+{
+ if (_private->autoscrollTimer == nil) {
+ _private->autoscrollTimer = [[NSTimer scheduledTimerWithTimeInterval:AUTOSCROLL_INTERVAL
+ target:self selector:@selector(_autoscroll) userInfo:nil repeats:YES] retain];
+ _private->autoscrollTriggerEvent = [triggerEvent retain];
+ }
+}
+
+// FIXME: _selectionRect is deprecated in favor of selectionRect, which is in protocol WebDocumentSelection.
+// We can't remove this yet because it's still in use by Mail.
+- (NSRect)_selectionRect
+{
+ return [self selectionRect];
+}
+
+- (void)_stopAutoscrollTimer
+{
+ NSTimer *timer = _private->autoscrollTimer;
+ _private->autoscrollTimer = nil;
+ [_private->autoscrollTriggerEvent release];
+ _private->autoscrollTriggerEvent = nil;
+ [timer invalidate];
+ [timer release];
+}
+
+- (void)_autoscroll
+{
+ // Guarantee that the autoscroll timer is invalidated, even if we don't receive
+ // a mouse up event.
+ BOOL isStillDown = CGEventSourceButtonState(kCGEventSourceStateCombinedSessionState, kCGMouseButtonLeft);
+ if (!isStillDown){
+ [self _stopAutoscrollTimer];
+ return;
+ }
+
+ NSEvent *fakeEvent = [NSEvent mouseEventWithType:NSLeftMouseDragged
+ location:[[self window] convertScreenToBase:[NSEvent mouseLocation]]
+ modifierFlags:[[NSApp currentEvent] modifierFlags]
+ timestamp:[NSDate timeIntervalSinceReferenceDate]
+ windowNumber:[[self window] windowNumber]
+ context:[[NSApp currentEvent] context]
+ eventNumber:0 clickCount:0 pressure:0];
+ [self mouseDragged:fakeEvent];
+}
+
+- (BOOL)_canEdit
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame && coreFrame->editor()->canEdit();
+}
+
+- (BOOL)_canEditRichly
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame && coreFrame->editor()->canEditRichly();
+}
+
+- (BOOL)_canAlterCurrentSelection
+{
+ return [self _hasSelectionOrInsertionPoint] && [self _isEditable];
+}
+
+- (BOOL)_hasSelection
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame && coreFrame->selectionController()->isRange();
+}
+
+- (BOOL)_hasSelectionOrInsertionPoint
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame && coreFrame->selectionController()->isCaretOrRange();
+}
+
+- (BOOL)_hasInsertionPoint
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame && coreFrame->selectionController()->isCaret();
+}
+
+- (BOOL)_isEditable
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame && coreFrame->selectionController()->isContentEditable();
+}
+
+- (BOOL)_transparentBackground
+{
+ return _private->transparentBackground;
+}
+
+- (void)_setTransparentBackground:(BOOL)f
+{
+ _private->transparentBackground = f;
+}
+
+- (NSImage *)_selectionDraggingImage
+{
+ if ([self _hasSelection]) {
+ NSImage *dragImage = core([self _frame])->selectionImage();
+ [dragImage _web_dissolveToFraction:WebDragImageAlpha];
+ return dragImage;
+ }
+ return nil;
+}
+
+- (NSRect)_selectionDraggingRect
+{
+ // Mail currently calls this method. We can eliminate it when Mail no longer calls it.
+ return [self selectionRect];
+}
+
+- (DOMNode *)_insertOrderedList
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame ? kit(coreFrame->editor()->insertOrderedList().get()) : nil;
+}
+
+- (DOMNode *)_insertUnorderedList
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame ? kit(coreFrame->editor()->insertUnorderedList().get()) : nil;
+}
+
+- (BOOL)_canIncreaseSelectionListLevel
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame && coreFrame->editor()->canIncreaseSelectionListLevel();
+}
+
+- (BOOL)_canDecreaseSelectionListLevel
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame && coreFrame->editor()->canDecreaseSelectionListLevel();
+}
+
+- (DOMNode *)_increaseSelectionListLevel
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame ? kit(coreFrame->editor()->increaseSelectionListLevel().get()) : nil;
+}
+
+- (DOMNode *)_increaseSelectionListLevelOrdered
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame ? kit(coreFrame->editor()->increaseSelectionListLevelOrdered().get()) : nil;
+}
+
+- (DOMNode *)_increaseSelectionListLevelUnordered
+{
+ Frame* coreFrame = core([self _frame]);
+ return coreFrame ? kit(coreFrame->editor()->increaseSelectionListLevelUnordered().get()) : nil;
+}
+
+- (void)_decreaseSelectionListLevel
+{
+ Frame* coreFrame = core([self _frame]);
+ if (coreFrame)
+ coreFrame->editor()->decreaseSelectionListLevel();
+}
+
+- (void)_setHighlighter:(id<WebHTMLHighlighter>)highlighter ofType:(NSString*)type
+{
+ if (!_private->highlighters)
+ _private->highlighters = [[NSMutableDictionary alloc] init];
+ [_private->highlighters setObject:highlighter forKey:type];
+}
+
+- (void)_removeHighlighterOfType:(NSString*)type
+{
+ [_private->highlighters removeObjectForKey:type];
+}
+
+- (void)_updateFocusedAndActiveState
+{
+ [self _cancelUpdateFocusedAndActiveStateTimer];
+
+ // This method does the job of updating the view based on the view's firstResponder-ness and
+ // the window key-ness of the window containing this view. This involves four kinds of
+ // drawing updates right now.
+ //
+ // The four display attributes are as follows:
+ //
+ // 1. The background color used to draw behind selected content (active | inactive color)
+ // 2. Caret blinking (blinks | does not blink)
+ // 3. The drawing of a focus ring around links in web pages.
+ //
+ // Also, this is responsible for letting the bridge know if the window has gained or lost focus
+ // so we can send focus and blur events.
+
+ Frame* frame = core([self _frame]);
+ if (!frame)
+ return;
+
+ Page* page = frame->page();
+ if (!page)
+ return;
+
+ NSWindow *window = [self window];
+ BOOL windowIsKey = [window isKeyWindow];
+ BOOL windowOrSheetIsKey = windowIsKey || [[window attachedSheet] isKeyWindow];
+
+ // FIXME: this can move to WebView since active state is Page level, not Frame level.
+ NSResponder *firstResponder = [window firstResponder];
+ if (firstResponder == self || firstResponder == [self _frameView])
+ page->focusController()->setActive(!_private->resigningFirstResponder && windowIsKey);
+
+ Frame* focusedFrame = page->focusController()->focusedOrMainFrame();
+ frame->selectionController()->setFocused(frame == focusedFrame && windowOrSheetIsKey);
+}
+
+- (void)_writeSelectionToPasteboard:(NSPasteboard *)pasteboard
+{
+ ASSERT([self _hasSelection]);
+ NSArray *types = [self pasteboardTypesForSelection];
+
+ // Don't write RTFD to the pasteboard when the copied attributed string has no attachments.
+ NSAttributedString *attributedString = [self selectedAttributedString];
+ NSMutableArray *mutableTypes = nil;
+ if (![attributedString containsAttachments]) {
+ mutableTypes = [types mutableCopy];
+ [mutableTypes removeObject:NSRTFDPboardType];
+ types = mutableTypes;
+ }
+
+ [pasteboard declareTypes:types owner:[self _topHTMLView]];
+ [self _writeSelectionWithPasteboardTypes:types toPasteboard:pasteboard cachedAttributedString:attributedString];
+ [mutableTypes release];
+}
+
+- (void)close
+{
+ // Check for a nil _private here incase we were created with initWithCoder. In that case, the WebView is just throwing
+ // out the archived WebHTMLView and recreating a new one if needed. So close doesn't need to do anything in that case.
+ if (!_private || _private->closed)
+ return;
+ [self _cancelUpdateMouseoverTimer];
+ [self _cancelUpdateFocusedAndActiveStateTimer];
+ [self _clearLastHitViewIfSelf];
+ // FIXME: This is slow; should remove individual observers instead.
+ [[NSNotificationCenter defaultCenter] removeObserver:self];
+ [_private->pluginController destroyAllPlugins];
+ [_private->pluginController setDataSource:nil];
+ // remove tooltips before clearing _private so removeTrackingRect: will work correctly
+ [self removeAllToolTips];
+ [_private clear];
+ _private->closed = YES;
+ Page* page = core([self _webView]);
+ if (page)
+ page->dragController()->setDraggingImageURL(KURL());
+}
+
+- (BOOL)_hasHTMLDocument
+{
+ Frame* coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return NO;
+ Document* document = coreFrame->document();
+ return document && document->isHTMLDocument();
+}
+
+- (DOMDocumentFragment *)_documentFragmentFromPasteboard:(NSPasteboard *)pasteboard
+ forType:(NSString *)pboardType
+ inContext:(DOMRange *)context
+ subresources:(NSArray **)subresources
+{
+ if (pboardType == WebArchivePboardType) {
+ WebArchive *archive = [[WebArchive alloc] initWithData:[pasteboard dataForType:WebArchivePboardType]];
+ if (subresources)
+ *subresources = [archive subresources];
+ DOMDocumentFragment *fragment = [[self _dataSource] _documentFragmentWithArchive:archive];
+ [archive release];
+ return fragment;
+ }
+ if (pboardType == NSFilenamesPboardType)
+ return [self _documentFragmentWithPaths:[pasteboard propertyListForType:NSFilenamesPboardType]];
+
+ if (pboardType == NSHTMLPboardType) {
+ NSString *HTMLString = [pasteboard stringForType:NSHTMLPboardType];
+ // This is a hack to make Microsoft's HTML pasteboard data work. See 3778785.
+ if ([HTMLString hasPrefix:@"Version:"]) {
+ NSRange range = [HTMLString rangeOfString:@"<html" options:NSCaseInsensitiveSearch];
+ if (range.location != NSNotFound)
+ HTMLString = [HTMLString substringFromIndex:range.location];
+ }
+ if ([HTMLString length] == 0)
+ return nil;
+
+ return [[self _bridge] documentFragmentWithMarkupString:HTMLString baseURLString:nil];
+ }
+
+ // The _hasHTMLDocument clause here is a workaround for a bug in NSAttributedString: Radar 5052369.
+ // If we call _documentFromRange on an XML document we'll get "setInnerHTML: method not found".
+ // FIXME: Remove this once bug 5052369 is fixed.
+ if ([self _hasHTMLDocument] && pboardType == NSRTFPboardType || pboardType == NSRTFDPboardType) {
+ NSAttributedString *string = nil;
+ if (pboardType == NSRTFDPboardType)
+ string = [[NSAttributedString alloc] initWithRTFD:[pasteboard dataForType:NSRTFDPboardType] documentAttributes:NULL];
+ if (string == nil)
+ string = [[NSAttributedString alloc] initWithRTF:[pasteboard dataForType:NSRTFPboardType] documentAttributes:NULL];
+ if (string == nil)
+ return nil;
+
+ NSDictionary *documentAttributes = [[NSDictionary alloc] initWithObjectsAndKeys:
+ [[self class] _excludedElementsForAttributedStringConversion], NSExcludedElementsDocumentAttribute,
+ self, @"WebResourceHandler", nil];
+ NSArray *s;
+
+ BOOL wasDeferringCallbacks = [[self _webView] defersCallbacks];
+ if (!wasDeferringCallbacks)
+ [[self _webView] setDefersCallbacks:YES];
+
+ DOMDocumentFragment *fragment = [string _documentFromRange:NSMakeRange(0, [string length])
+ document:[[self _frame] DOMDocument]
+ documentAttributes:documentAttributes
+ subresources:&s];
+ if (subresources)
+ *subresources = s;
+
+ NSEnumerator *e = [s objectEnumerator];
+ WebResource *r;
+ while ((r = [e nextObject]))
+ [[self _dataSource] addSubresource:r];
+
+ if (!wasDeferringCallbacks)
+ [[self _webView] setDefersCallbacks:NO];
+
+ [documentAttributes release];
+ [string release];
+ return fragment;
+ }
+ if (pboardType == NSTIFFPboardType) {
+ WebResource *resource = [[WebResource alloc] initWithData:[pasteboard dataForType:NSTIFFPboardType]
+ URL:uniqueURLWithRelativePart(@"image.tiff")
+ MIMEType:@"image/tiff"
+ textEncodingName:nil
+ frameName:nil];
+ DOMDocumentFragment *fragment = [[self _dataSource] _documentFragmentWithImageResource:resource];
+ [resource release];
+ return fragment;
+ }
+ if (pboardType == NSPICTPboardType) {
+ WebResource *resource = [[WebResource alloc] initWithData:[pasteboard dataForType:NSPICTPboardType]
+ URL:uniqueURLWithRelativePart(@"image.pict")
+ MIMEType:@"image/pict"
+ textEncodingName:nil
+ frameName:nil];
+ DOMDocumentFragment *fragment = [[self _dataSource] _documentFragmentWithImageResource:resource];
+ [resource release];
+ return fragment;
+ }
+ if (pboardType == NSURLPboardType) {
+ NSURL *URL = [NSURL URLFromPasteboard:pasteboard];
+ DOMDocument* document = [[self _frame] DOMDocument];
+ ASSERT(document);
+ if (!document)
+ return nil;
+ DOMHTMLAnchorElement *anchor = (DOMHTMLAnchorElement *)[document createElement:@"a"];
+ NSString *URLString = [URL _web_originalDataAsString];
+ if ([URLString length] == 0)
+ return nil;
+ NSString *URLTitleString = [pasteboard stringForType:WebURLNamePboardType];
+ DOMText *text = [document createTextNode:URLTitleString];
+ [anchor setHref:URLString];
+ [anchor appendChild:text];
+ DOMDocumentFragment *fragment = [document createDocumentFragment];
+ [fragment appendChild:anchor];
+ return fragment;
+ }
+ if (pboardType == NSStringPboardType)
+ return [[self _bridge] documentFragmentWithText:[pasteboard stringForType:NSStringPboardType]
+ inContext:context];
+
+ return nil;
+}
+
+@end
+
+@implementation NSView (WebHTMLViewFileInternal)
+
+- (void)_web_addDescendantWebHTMLViewsToArray:(NSMutableArray *)array
+{
+ unsigned count = [_subviews count];
+ for (unsigned i = 0; i < count; ++i) {
+ NSView *child = [_subviews objectAtIndex:i];
+ if ([child isKindOfClass:[WebHTMLView class]])
+ [array addObject:child];
+ [child _web_addDescendantWebHTMLViewsToArray:array];
+ }
+}
+
+@end
+
+@implementation NSMutableDictionary (WebHTMLViewFileInternal)
+
+- (void)_web_setObjectIfNotNil:(id)object forKey:(id)key
+{
+ if (object == nil) {
+ [self removeObjectForKey:key];
+ } else {
+ [self setObject:object forKey:key];
+ }
+}
+
+@end
+
+#ifdef BUILDING_ON_TIGER
+
+// The following is a workaround for
+// <rdar://problem/3429631> window stops getting mouse moved events after first tooltip appears
+// The trick is to define a category on NSToolTipPanel that implements setAcceptsMouseMovedEvents:.
+// Since the category will be searched before the real class, we'll prevent the flag from being
+// set on the tool tip panel.
+
+@interface NSToolTipPanel : NSPanel
+@end
+
+@interface NSToolTipPanel (WebHTMLViewFileInternal)
+@end
+
+@implementation NSToolTipPanel (WebHTMLViewFileInternal)
+
+- (void)setAcceptsMouseMovedEvents:(BOOL)flag
+{
+ // Do nothing, preventing the tool tip panel from trying to accept mouse-moved events.
+}
+
+@end
+
+#endif
+
+@interface NSArray (WebHTMLView)
+- (void)_web_makePluginViewsPerformSelector:(SEL)selector withObject:(id)object;
+@end
+
+@implementation WebHTMLView
+
++ (void)initialize
+{
+ [NSApp registerServicesMenuSendTypes:[[self class] _selectionPasteboardTypes]
+ returnTypes:[[self class] _insertablePasteboardTypes]];
+#ifndef BUILDING_ON_TIGER
+ WebCoreObjCFinalizeOnMainThread(self);
+#endif
+}
+
+- (id)initWithFrame:(NSRect)frame
+{
+ self = [super initWithFrame:frame];
+ if (!self)
+ return nil;
+
+ [self setFocusRingType:NSFocusRingTypeNone];
+
+ // Make all drawing go through us instead of subviews.
+ [self _setDrawsOwnDescendants:YES];
+
+ _private = [[WebHTMLViewPrivate alloc] init];
+
+ _private->pluginController = [[WebPluginController alloc] initWithDocumentView:self];
+ _private->needsLayout = YES;
+
+ return self;
+}
+
+- (void)dealloc
+{
+ // We can't assert that close has already been called because
+ // this view can be removed from it's superview, even though
+ // it could be needed later, so close if needed.
+ [self close];
+ [_private release];
+ _private = nil;
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+ // We can't assert that close has already been called because
+ // this view can be removed from it's superview, even though
+ // it could be needed later, so close if needed.
+ [self close];
+ [super finalize];
+}
+
+// Returns YES if the delegate returns YES (so we should do no more work).
+- (BOOL)callDelegateDoCommandBySelectorIfNeeded:(SEL)selector
+{
+ BOOL callerAlreadyCalledDelegate = _private->selectorForDoCommandBySelector == selector;
+ _private->selectorForDoCommandBySelector = 0;
+ if (callerAlreadyCalledDelegate)
+ return NO;
+ WebView *webView = [self _webView];
+ return [[webView _editingDelegateForwarder] webView:webView doCommandBySelector:selector];
+}
+
+static String commandNameForSelector(SEL selector)
+{
+ // Change a few command names into ones supported by WebCore::Editor.
+ // If this list gets too long we might decide we need to use a hash table.
+ if (selector == @selector(insertParagraphSeparator:) || selector == @selector(insertNewlineIgnoringFieldEditor:))
+ return "InsertNewline";
+ if (selector == @selector(insertTabIgnoringFieldEditor:))
+ return "InsertTab";
+ if (selector == @selector(pageDown:))
+ return "MovePageDown";
+ if (selector == @selector(pageDownAndModifySelection:))
+ return "MovePageDownAndModifySelection";
+ if (selector == @selector(pageUp:))
+ return "MovePageUp";
+ if (selector == @selector(pageUpAndModifySelection:))
+ return "MovePageUpAndModifySelection";
+
+ // Remove the trailing colon.
+ const char* selectorName = sel_getName(selector);
+ size_t selectorNameLength = strlen(selectorName);
+ ASSERT(selectorNameLength >= 2);
+ ASSERT(selectorName[selectorNameLength - 1] == ':');
+ return String(selectorName, selectorNameLength - 1);
+}
+
+- (Editor::Command)coreCommandBySelector:(SEL)selector
+{
+ Frame* coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return Editor::Command();
+ return coreFrame->editor()->command(commandNameForSelector(selector));
+}
+
+- (Editor::Command)coreCommandByName:(const char*)name
+{
+ Frame* coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return Editor::Command();
+ return coreFrame->editor()->command(name);
+}
+
+- (void)executeCoreCommandBySelector:(SEL)selector
+{
+ if ([self callDelegateDoCommandBySelectorIfNeeded:selector])
+ return;
+ [self coreCommandBySelector:selector].execute();
+}
+
+- (void)executeCoreCommandByName:(const char*)name
+{
+ [self coreCommandByName:name].execute();
+}
+
+// These commands are forwarded to the Editor object in WebCore.
+// Ideally we'd do this for all editing commands; more of the code
+// should be moved from here to there, and more commands should be
+// added to this list.
+
+// FIXME: Maybe we should set things up so that all these share a single method implementation function.
+// The functions are identical.
+
+#define WEBCORE_COMMAND(command) - (void)command:(id)sender { [self executeCoreCommandBySelector:_cmd]; }
+
+WEBCORE_COMMAND(alignCenter)
+WEBCORE_COMMAND(alignJustified)
+WEBCORE_COMMAND(alignLeft)
+WEBCORE_COMMAND(alignRight)
+WEBCORE_COMMAND(copy)
+WEBCORE_COMMAND(cut)
+WEBCORE_COMMAND(delete)
+WEBCORE_COMMAND(deleteBackward)
+WEBCORE_COMMAND(deleteBackwardByDecomposingPreviousCharacter)
+WEBCORE_COMMAND(deleteForward)
+WEBCORE_COMMAND(deleteToBeginningOfLine)
+WEBCORE_COMMAND(deleteToBeginningOfParagraph)
+WEBCORE_COMMAND(deleteToEndOfLine)
+WEBCORE_COMMAND(deleteToEndOfParagraph)
+WEBCORE_COMMAND(deleteToMark)
+WEBCORE_COMMAND(deleteWordBackward)
+WEBCORE_COMMAND(deleteWordForward)
+WEBCORE_COMMAND(indent)
+WEBCORE_COMMAND(insertBacktab)
+WEBCORE_COMMAND(insertLineBreak)
+WEBCORE_COMMAND(insertNewline)
+WEBCORE_COMMAND(insertNewlineIgnoringFieldEditor)
+WEBCORE_COMMAND(insertParagraphSeparator)
+WEBCORE_COMMAND(insertTab)
+WEBCORE_COMMAND(insertTabIgnoringFieldEditor)
+WEBCORE_COMMAND(moveBackward)
+WEBCORE_COMMAND(moveBackwardAndModifySelection)
+WEBCORE_COMMAND(moveDown)
+WEBCORE_COMMAND(moveDownAndModifySelection)
+WEBCORE_COMMAND(moveForward)
+WEBCORE_COMMAND(moveForwardAndModifySelection)
+WEBCORE_COMMAND(moveLeft)
+WEBCORE_COMMAND(moveLeftAndModifySelection)
+WEBCORE_COMMAND(moveParagraphBackwardAndModifySelection)
+WEBCORE_COMMAND(moveParagraphForwardAndModifySelection)
+WEBCORE_COMMAND(moveRight)
+WEBCORE_COMMAND(moveRightAndModifySelection)
+WEBCORE_COMMAND(moveToBeginningOfDocument)
+WEBCORE_COMMAND(moveToBeginningOfDocumentAndModifySelection)
+WEBCORE_COMMAND(moveToBeginningOfLine)
+WEBCORE_COMMAND(moveToBeginningOfLineAndModifySelection)
+WEBCORE_COMMAND(moveToBeginningOfParagraph)
+WEBCORE_COMMAND(moveToBeginningOfParagraphAndModifySelection)
+WEBCORE_COMMAND(moveToBeginningOfSentence)
+WEBCORE_COMMAND(moveToBeginningOfSentenceAndModifySelection)
+WEBCORE_COMMAND(moveToEndOfDocument)
+WEBCORE_COMMAND(moveToEndOfDocumentAndModifySelection)
+WEBCORE_COMMAND(moveToEndOfLine)
+WEBCORE_COMMAND(moveToEndOfLineAndModifySelection)
+WEBCORE_COMMAND(moveToEndOfParagraph)
+WEBCORE_COMMAND(moveToEndOfParagraphAndModifySelection)
+WEBCORE_COMMAND(moveToEndOfSentence)
+WEBCORE_COMMAND(moveToEndOfSentenceAndModifySelection)
+WEBCORE_COMMAND(moveUp)
+WEBCORE_COMMAND(moveUpAndModifySelection)
+WEBCORE_COMMAND(moveWordBackward)
+WEBCORE_COMMAND(moveWordBackwardAndModifySelection)
+WEBCORE_COMMAND(moveWordForward)
+WEBCORE_COMMAND(moveWordForwardAndModifySelection)
+WEBCORE_COMMAND(moveWordLeft)
+WEBCORE_COMMAND(moveWordLeftAndModifySelection)
+WEBCORE_COMMAND(moveWordRight)
+WEBCORE_COMMAND(moveWordRightAndModifySelection)
+WEBCORE_COMMAND(outdent)
+WEBCORE_COMMAND(pageDown)
+WEBCORE_COMMAND(pageDownAndModifySelection)
+WEBCORE_COMMAND(pageUp)
+WEBCORE_COMMAND(pageUpAndModifySelection)
+WEBCORE_COMMAND(selectAll)
+WEBCORE_COMMAND(selectLine)
+WEBCORE_COMMAND(selectParagraph)
+WEBCORE_COMMAND(selectSentence)
+WEBCORE_COMMAND(selectToMark)
+WEBCORE_COMMAND(selectWord)
+WEBCORE_COMMAND(setMark)
+WEBCORE_COMMAND(subscript)
+WEBCORE_COMMAND(superscript)
+WEBCORE_COMMAND(swapWithMark)
+WEBCORE_COMMAND(transpose)
+WEBCORE_COMMAND(underline)
+WEBCORE_COMMAND(unscript)
+WEBCORE_COMMAND(yank)
+WEBCORE_COMMAND(yankAndSelect)
+
+#undef WEBCORE_COMMAND
+
+#define COMMAND_PROLOGUE if ([self callDelegateDoCommandBySelectorIfNeeded:_cmd]) return;
+
+- (IBAction)takeFindStringFromSelection:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ if (![self _hasSelection]) {
+ NSBeep();
+ return;
+ }
+
+ [NSPasteboard _web_setFindPasteboardString:[self selectedString] withOwner:self];
+}
+
+- (BOOL)writeSelectionToPasteboard:(NSPasteboard *)pasteboard types:(NSArray *)types
+{
+ [pasteboard declareTypes:types owner:[self _topHTMLView]];
+ [self writeSelectionWithPasteboardTypes:types toPasteboard:pasteboard];
+ return YES;
+}
+
+- (BOOL)readSelectionFromPasteboard:(NSPasteboard *)pasteboard
+{
+ Frame* coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return NO;
+ if (coreFrame->selectionController()->isContentRichlyEditable())
+ [self _pasteWithPasteboard:pasteboard allowPlainText:YES];
+ else
+ [self _pasteAsPlainTextWithPasteboard:pasteboard];
+ return YES;
+}
+
+- (id)validRequestorForSendType:(NSString *)sendType returnType:(NSString *)returnType
+{
+ if (sendType != nil && [[self pasteboardTypesForSelection] containsObject:sendType] && [self _hasSelection]) {
+ return self;
+ } else if (returnType != nil && [[[self class] _insertablePasteboardTypes] containsObject:returnType] && [self _isEditable]) {
+ return self;
+ }
+ return [[self nextResponder] validRequestorForSendType:sendType returnType:returnType];
+}
+
+// jumpToSelection is the old name for what AppKit now calls centerSelectionInVisibleArea. Safari
+// was using the old jumpToSelection selector in its menu. Newer versions of Safari will use the
+// selector centerSelectionInVisibleArea. We'll leave the old selector in place for two reasons:
+// (1) Compatibility between older Safari and newer WebKit; (2) other WebKit-based applications
+// might be using the selector, and we don't want to break them.
+- (void)jumpToSelection:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->revealSelection(RenderLayer::gAlignCenterAlways);
+}
+
+- (NSCellStateValue)selectionHasStyle:(CSSStyleDeclaration*)style
+{
+ Frame* coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return NSOffState;
+ return kit(coreFrame->editor()->selectionHasStyle(style));
+}
+
+- (BOOL)validateUserInterfaceItemWithoutDelegate:(id <NSValidatedUserInterfaceItem>)item
+{
+ SEL action = [item action];
+ RefPtr<Frame> frame = core([self _frame]);
+
+ if (!frame)
+ return NO;
+
+ if (Document* doc = frame->document()) {
+ if (doc->isPluginDocument())
+ return NO;
+ if (doc->isImageDocument()) {
+ if (action == @selector(copy:))
+ return frame->loader()->isComplete();
+ return NO;
+ }
+ }
+
+ if (action == @selector(changeSpelling:)
+ || action == @selector(_changeSpellingFromMenu:)
+ || action == @selector(checkSpelling:)
+ || action == @selector(complete:)
+ || action == @selector(pasteFont:))
+ return [self _canEdit];
+
+ if (action == @selector(showGuessPanel:)) {
+#ifndef BUILDING_ON_TIGER
+ // Match OS X AppKit behavior for post-Tiger. Don't change Tiger behavior.
+ NSMenuItem *menuItem = (NSMenuItem *)item;
+ if ([menuItem isKindOfClass:[NSMenuItem class]]) {
+ BOOL panelShowing = [[[NSSpellChecker sharedSpellChecker] spellingPanel] isVisible];
+ [menuItem setTitle:panelShowing ? UI_STRING("Hide Spelling and Grammar", "menu item title") : UI_STRING("Show Spelling and Grammar", "menu item title")];
+ }
+#endif
+ return [self _canEdit];
+ }
+
+ if (action == @selector(changeBaseWritingDirection:)) {
+ NSWritingDirection writingDirection = static_cast<NSWritingDirection>([item tag]);
+ if (writingDirection == NSWritingDirectionNatural)
+ return NO;
+ NSMenuItem *menuItem = (NSMenuItem *)item;
+ if ([menuItem isKindOfClass:[NSMenuItem class]]) {
+ RefPtr<CSSStyleDeclaration> style = new CSSMutableStyleDeclaration;
+ ExceptionCode ec;
+ style->setProperty("direction", writingDirection == NSWritingDirectionLeftToRight ? "LTR" : "RTL", ec);
+ [menuItem setState:frame->editor()->selectionHasStyle(style.get())];
+ }
+ return [self _canEdit];
+ }
+
+ if (action == @selector(toggleBaseWritingDirection:)) {
+ NSMenuItem *menuItem = (NSMenuItem *)item;
+ if ([menuItem isKindOfClass:[NSMenuItem class]]) {
+ RefPtr<CSSStyleDeclaration> style = new CSSMutableStyleDeclaration;
+ ExceptionCode ec;
+ style->setProperty("direction", "RTL", ec);
+ // Take control of the title of the menu item, instead of just checking/unchecking it because otherwise
+ // we don't know what the check would mean.
+ [menuItem setTitle:frame->editor()->selectionHasStyle(style.get())
+ ? UI_STRING("Left to Right", "Left to Right context menu item")
+ : UI_STRING("Right to Left", "Right to Left context menu item")];
+ }
+ return [self _canEdit];
+ }
+
+ if (action == @selector(changeAttributes:)
+ || action == @selector(changeColor:)
+ || action == @selector(changeFont:))
+ return [self _canEditRichly];
+
+ if (action == @selector(capitalizeWord:)
+ || action == @selector(lowercaseWord:)
+ || action == @selector(uppercaseWord:))
+ return [self _hasSelection] && [self _isEditable];
+
+ if (action == @selector(centerSelectionInVisibleArea:)
+ || action == @selector(jumpToSelection:)
+ || action == @selector(copyFont:))
+ return [self _hasSelection] || ([self _isEditable] && [self _hasInsertionPoint]);
+
+ if (action == @selector(changeDocumentBackgroundColor:))
+ return [[self _webView] isEditable] && [self _canEditRichly];
+
+ if (action == @selector(_ignoreSpellingFromMenu:)
+ || action == @selector(_learnSpellingFromMenu:)
+ || action == @selector(takeFindStringFromSelection:))
+ return [self _hasSelection];
+
+ if (action == @selector(paste:) || action == @selector(pasteAsPlainText:))
+ return frame && (frame->editor()->canDHTMLPaste() || frame->editor()->canPaste());
+
+ if (action == @selector(pasteAsRichText:))
+ return frame && (frame->editor()->canDHTMLPaste()
+ || (frame->editor()->canPaste() && frame->selectionController()->isContentRichlyEditable()));
+
+ if (action == @selector(performFindPanelAction:))
+ return NO;
+
+ if (action == @selector(_lookUpInDictionaryFromMenu:))
+ return [self _hasSelection];
+
+#ifndef BUILDING_ON_TIGER
+ if (action == @selector(toggleGrammarChecking:)) {
+ // FIXME 4799134: WebView is the bottleneck for this grammar-checking logic, but we must validate
+ // the selector here because we implement it here, and we must implement it here because the AppKit
+ // code checks the first responder.
+ NSMenuItem *menuItem = (NSMenuItem *)item;
+ if ([menuItem isKindOfClass:[NSMenuItem class]])
+ [menuItem setState:[self isGrammarCheckingEnabled] ? NSOnState : NSOffState];
+ return YES;
+ }
+#endif
+
+ Editor::Command command = [self coreCommandBySelector:action];
+ if (command.isSupported()) {
+ NSMenuItem *menuItem = (NSMenuItem *)item;
+ if ([menuItem isKindOfClass:[NSMenuItem class]])
+ [menuItem setState:kit(command.state())];
+ return command.isEnabled();
+ }
+
+ return YES;
+}
+
+- (BOOL)validateUserInterfaceItem:(id <NSValidatedUserInterfaceItem>)item
+{
+ BOOL result = [self validateUserInterfaceItemWithoutDelegate:item];
+ return CallUIDelegateReturningBoolean(result, [self _webView], @selector(webView:validateUserInterfaceItem:defaultValidation:), item, result);
+}
+
+- (BOOL)acceptsFirstResponder
+{
+ // Don't accept first responder when we first click on this view.
+ // We have to pass the event down through WebCore first to be sure we don't hit a subview.
+ // Do accept first responder at any other time, for example from keyboard events,
+ // or from calls back from WebCore once we begin mouse-down event handling.
+ NSEvent *event = [NSApp currentEvent];
+ if ([event type] == NSLeftMouseDown
+ && !_private->handlingMouseDownEvent
+ && NSPointInRect([event locationInWindow], [self convertRect:[self visibleRect] toView:nil])) {
+ return NO;
+ }
+ return YES;
+}
+
+- (BOOL)maintainsInactiveSelection
+{
+ // This method helps to determine whether the WebHTMLView should maintain
+ // an inactive selection when it's not first responder.
+ // Traditionally, these views have not maintained such selections,
+ // clearing them when the view was not first responder. However,
+ // to fix bugs like this one:
+ // <rdar://problem/3672088>: "Editable WebViews should maintain a selection even
+ // when they're not firstResponder"
+ // it was decided to add a switch to act more like an NSTextView.
+
+ if ([[self _webView] maintainsInactiveSelection])
+ return YES;
+
+ // Predict the case where we are losing first responder status only to
+ // gain it back again. Want to keep the selection in that case.
+ id nextResponder = [[self window] _newFirstResponderAfterResigning];
+ if ([nextResponder isKindOfClass:[NSScrollView class]]) {
+ id contentView = [nextResponder contentView];
+ if (contentView)
+ nextResponder = contentView;
+ }
+ if ([nextResponder isKindOfClass:[NSClipView class]]) {
+ id documentView = [nextResponder documentView];
+ if (documentView)
+ nextResponder = documentView;
+ }
+ if (nextResponder == self)
+ return YES;
+
+ Frame* coreFrame = core([self _frame]);
+ bool selectionIsEditable = coreFrame && coreFrame->selectionController()->isContentEditable();
+ bool nextResponderIsInWebView = [nextResponder isKindOfClass:[NSView class]]
+ && [nextResponder isDescendantOf:[[[self _webView] mainFrame] frameView]];
+
+ return selectionIsEditable && nextResponderIsInWebView;
+}
+
+- (void)addMouseMovedObserver
+{
+ if (!_private->dataSource || ![self _isTopHTMLView])
+ return;
+
+ // Unless the Dashboard asks us to do this for all windows, keep an observer going only for the key window.
+ if (!([[self window] isKeyWindow] || [[self _webView] _dashboardBehavior:WebDashboardBehaviorAlwaysSendMouseEventsToAllWindows]))
+ return;
+
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(mouseMovedNotification:)
+ name:WKMouseMovedNotification() object:nil];
+ [self _frameOrBoundsChanged];
+}
+
+- (void)removeMouseMovedObserverUnconditionally
+{
+ [[NSNotificationCenter defaultCenter] removeObserver:self
+ name:WKMouseMovedNotification() object:nil];
+}
+
+- (void)removeMouseMovedObserver
+{
+ // Don't remove the observer if we're running the Dashboard.
+ if ([[self _webView] _dashboardBehavior:WebDashboardBehaviorAlwaysSendMouseEventsToAllWindows])
+ return;
+
+ [[self _webView] _mouseDidMoveOverElement:nil modifierFlags:0];
+ [self removeMouseMovedObserverUnconditionally];
+}
+
+- (void)addSuperviewObservers
+{
+ // We watch the bounds of our superview, so that we can do a layout when the size
+ // of the superview changes. This is different from other scrollable things that don't
+ // need this kind of thing because their layout doesn't change.
+
+ // We need to pay attention to both height and width because our "layout" has to change
+ // to extend the background the full height of the space and because some elements have
+ // sizes that are based on the total size of the view.
+
+ NSView *superview = [self superview];
+ if (superview && [self window]) {
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(_frameOrBoundsChanged)
+ name:NSViewFrameDidChangeNotification object:superview];
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(_frameOrBoundsChanged)
+ name:NSViewBoundsDidChangeNotification object:superview];
+
+ // In addition to registering for frame/bounds change notifications, call -_frameOrBoundsChanged.
+ // It will check the current size/scroll against the previous layout's size/scroll. We need to
+ // do this here to catch the case where the WebView is laid out at one size, removed from its
+ // window, resized, and inserted into another window. Our frame/bounds changed notifications
+ // will not be sent in that situation, since we only watch for changes while in the view hierarchy.
+ [self _frameOrBoundsChanged];
+ }
+}
+
+- (void)removeSuperviewObservers
+{
+ NSView *superview = [self superview];
+ if (superview && [self window]) {
+ [[NSNotificationCenter defaultCenter] removeObserver:self
+ name:NSViewFrameDidChangeNotification object:superview];
+ [[NSNotificationCenter defaultCenter] removeObserver:self
+ name:NSViewBoundsDidChangeNotification object:superview];
+ }
+}
+
+- (void)addWindowObservers
+{
+ NSWindow *window = [self window];
+ if (window) {
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(windowDidBecomeKey:)
+ name:NSWindowDidBecomeKeyNotification object:nil];
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(windowDidResignKey:)
+ name:NSWindowDidResignKeyNotification object:nil];
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(windowWillClose:)
+ name:NSWindowWillCloseNotification object:window];
+ }
+}
+
+- (void)removeWindowObservers
+{
+ NSWindow *window = [self window];
+ if (window) {
+ [[NSNotificationCenter defaultCenter] removeObserver:self
+ name:NSWindowDidBecomeKeyNotification object:nil];
+ [[NSNotificationCenter defaultCenter] removeObserver:self
+ name:NSWindowDidResignKeyNotification object:nil];
+ [[NSNotificationCenter defaultCenter] removeObserver:self
+ name:NSWindowWillCloseNotification object:window];
+ }
+}
+
+- (void)viewWillMoveToSuperview:(NSView *)newSuperview
+{
+ [self removeSuperviewObservers];
+}
+
+- (void)viewDidMoveToSuperview
+{
+ // Do this here in case the text size multiplier changed when a non-HTML
+ // view was installed.
+ if ([self superview] != nil) {
+ [self _updateTextSizeMultiplier];
+ [self addSuperviewObservers];
+ }
+}
+
+static void _updateFocusedAndActiveStateTimerCallback(CFRunLoopTimerRef timer, void *info)
+{
+ WebHTMLView *view = (WebHTMLView *)info;
+ [view _updateFocusedAndActiveState];
+}
+
+- (void)viewWillMoveToWindow:(NSWindow *)window
+{
+ // Don't do anything if we aren't initialized. This happens
+ // when decoding a WebView. When WebViews are decoded their subviews
+ // are created by initWithCoder: and so won't be normally
+ // initialized. The stub views are discarded by WebView.
+ if (!_private)
+ return;
+
+ // FIXME: Some of these calls may not work because this view may be already removed from it's superview.
+ [self removeMouseMovedObserverUnconditionally];
+ [self removeWindowObservers];
+ [self removeSuperviewObservers];
+ [self _cancelUpdateMouseoverTimer];
+ [self _cancelUpdateFocusedAndActiveStateTimer];
+
+ [[self _pluginController] stopAllPlugins];
+}
+
+- (void)viewDidMoveToWindow
+{
+ // Don't do anything if we aren't initialized. This happens
+ // when decoding a WebView. When WebViews are decoded their subviews
+ // are created by initWithCoder: and so won't be normally
+ // initialized. The stub views are discarded by WebView.
+ if (!_private || _private->closed)
+ return;
+
+ [self _stopAutoscrollTimer];
+ if ([self window]) {
+ _private->lastScrollPosition = [[self superview] bounds].origin;
+ [self addWindowObservers];
+ [self addSuperviewObservers];
+ [self addMouseMovedObserver];
+
+ // Schedule this update, rather than making the call right now.
+ // The reason is that placing the caret in the just-installed view requires
+ // the HTML/XML document to be available on the WebCore side, but it is not
+ // at the time this code is running. However, it will be there on the next
+ // crank of the run loop. Doing this helps to make a blinking caret appear
+ // in a new, empty window "automatic".
+ if (!_private->updateFocusedAndActiveStateTimer) {
+ CFRunLoopTimerContext context = { 0, self, NULL, NULL, NULL };
+ _private->updateFocusedAndActiveStateTimer = CFRunLoopTimerCreate(NULL, CFAbsoluteTimeGetCurrent(), 0, 0, 0,
+ _updateFocusedAndActiveStateTimerCallback, &context);
+ CFRunLoopAddTimer(CFRunLoopGetCurrent(), _private->updateFocusedAndActiveStateTimer, kCFRunLoopDefaultMode);
+ }
+
+ [[self _pluginController] startAllPlugins];
+
+ _private->lastScrollPosition = NSZeroPoint;
+ }
+}
+
+- (void)viewWillMoveToHostWindow:(NSWindow *)hostWindow
+{
+ [[self subviews] _web_makePluginViewsPerformSelector:@selector(viewWillMoveToHostWindow:) withObject:hostWindow];
+}
+
+- (void)viewDidMoveToHostWindow
+{
+ [[self subviews] _web_makePluginViewsPerformSelector:@selector(viewDidMoveToHostWindow) withObject:nil];
+}
+
+
+- (void)addSubview:(NSView *)view
+{
+ [super addSubview:view];
+
+ if ([WebPluginController isPlugInView:view])
+ [[self _pluginController] addPlugin:view];
+}
+
+- (void)willRemoveSubview:(NSView *)subview
+{
+ if ([WebPluginController isPlugInView:subview])
+ [[self _pluginController] destroyPlugin:subview];
+
+ [super willRemoveSubview:subview];
+}
+
+- (void)reapplyStyles
+{
+ if (!_private->needsToApplyStyles) {
+ return;
+ }
+
+#ifdef _KWQ_TIMING
+ double start = CFAbsoluteTimeGetCurrent();
+#endif
+
+ [[self _bridge] reapplyStylesForDeviceType:
+ _private->printing ? WebCoreDevicePrinter : WebCoreDeviceScreen];
+
+#ifdef _KWQ_TIMING
+ double thisTime = CFAbsoluteTimeGetCurrent() - start;
+ LOG(Timing, "%s apply style seconds = %f", [self URL], thisTime);
+#endif
+
+ _private->needsToApplyStyles = NO;
+}
+
+// Do a layout, but set up a new fixed width for the purposes of doing printing layout.
+// minPageWidth==0 implies a non-printing layout
+- (void)layoutToMinimumPageWidth:(float)minPageWidth maximumPageWidth:(float)maxPageWidth adjustingViewSize:(BOOL)adjustViewSize
+{
+ [self reapplyStyles];
+
+ if (!_private->needsLayout && ![[self _bridge] needsLayout])
+ return;
+
+#ifdef _KWQ_TIMING
+ double start = CFAbsoluteTimeGetCurrent();
+#endif
+
+ LOG(View, "%@ doing layout", self);
+
+ if (minPageWidth > 0.0) {
+ [[self _bridge] forceLayoutWithMinimumPageWidth:minPageWidth maximumPageWidth:maxPageWidth adjustingViewSize:adjustViewSize];
+ } else {
+ [[self _bridge] forceLayoutAdjustingViewSize:adjustViewSize];
+ }
+ _private->needsLayout = NO;
+
+ if (!_private->printing)
+ _private->lastLayoutSize = [(NSClipView *)[self superview] documentVisibleRect].size;
+
+#ifdef _KWQ_TIMING
+ double thisTime = CFAbsoluteTimeGetCurrent() - start;
+ LOG(Timing, "%s layout seconds = %f", [self URL], thisTime);
+#endif
+}
+
+- (void)layout
+{
+ [self layoutToMinimumPageWidth:0.0f maximumPageWidth:0.0f adjustingViewSize:NO];
+}
+
+- (NSMenu *)menuForEvent:(NSEvent *)event
+{
+ [_private->compController endRevertingChange:NO moveLeft:NO];
+
+ _private->handlingMouseDownEvent = YES;
+ BOOL handledEvent = NO;
+ Frame* coreFrame = core([self _frame]);
+
+ if (!coreFrame) {
+ _private->handlingMouseDownEvent = NO;
+ return nil;
+ }
+
+ Page* page = coreFrame->page();
+ if (!page)
+ return nil;
+
+ page->contextMenuController()->clearContextMenu();
+ // Match behavior of other browsers by sending an onmousedown event for right clicks.
+ coreFrame->eventHandler()->mouseDown(event);
+ handledEvent = coreFrame->eventHandler()->sendContextMenuEvent(PlatformMouseEvent(event));
+ _private->handlingMouseDownEvent = NO;
+
+ if (!handledEvent)
+ return nil;
+
+ ContextMenu* coreMenu = page->contextMenuController()->contextMenu();
+ if (!coreMenu)
+ return nil;
+
+ NSArray* menuItems = coreMenu->platformDescription();
+ NSMenu* menu = nil;
+ if (menuItems && [menuItems count] > 0) {
+ menu = [[[NSMenu alloc] init] autorelease];
+ for (unsigned i = 0; i < [menuItems count]; i++)
+ [menu addItem:[menuItems objectAtIndex:i]];
+ }
+
+ return menu;
+}
+
+- (BOOL)searchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag
+{
+ return [self searchFor:string direction:forward caseSensitive:caseFlag wrap:wrapFlag startInSelection:NO];
+}
+
+- (void)clearFocus
+{
+ Frame* coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return;
+ Document* document = coreFrame->document();
+ if (!document)
+ return;
+
+ document->setFocusedNode(0);
+}
+
+- (BOOL)isOpaque
+{
+ return [[self _webView] drawsBackground];
+}
+
+- (void)setNeedsDisplay:(BOOL)flag
+{
+ LOG(View, "%@ setNeedsDisplay:%@", self, flag ? @"YES" : @"NO");
+ [super setNeedsDisplay:flag];
+}
+
+- (void)setNeedsLayout: (BOOL)flag
+{
+ LOG(View, "%@ setNeedsLayout:%@", self, flag ? @"YES" : @"NO");
+ _private->needsLayout = flag;
+}
+
+- (void)setNeedsToApplyStyles: (BOOL)flag
+{
+ LOG(View, "%@ setNeedsToApplyStyles:%@", self, flag ? @"YES" : @"NO");
+ _private->needsToApplyStyles = flag;
+}
+
+- (void)drawSingleRect:(NSRect)rect
+{
+ [NSGraphicsContext saveGraphicsState];
+ NSRectClip(rect);
+
+ ASSERT([[self superview] isKindOfClass:[WebClipView class]]);
+
+ [(WebClipView *)[self superview] setAdditionalClip:rect];
+
+ @try {
+ if ([self _transparentBackground]) {
+ [[NSColor clearColor] set];
+ NSRectFill (rect);
+ }
+
+ [[self _bridge] drawRect:rect];
+
+ // This hack is needed for <rdar://problem/5023545>. We can hit a race condition where drawRect will be
+ // called after the WebView has closed. If the client did not properly close the WebView and set the
+ // UIDelegate to nil, then the UIDelegate will be stale and this code will crash.
+ static BOOL version3OrLaterClient = WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITHOUT_QUICKBOOKS_QUIRK);
+ if (version3OrLaterClient) {
+ WebView *webView = [self _webView];
+ [[webView _UIDelegateForwarder] webView:webView didDrawRect:[webView convertRect:rect fromView:self]];
+ }
+
+ [(WebClipView *)[self superview] resetAdditionalClip];
+
+ [NSGraphicsContext restoreGraphicsState];
+ } @catch (NSException *localException) {
+ [(WebClipView *)[self superview] resetAdditionalClip];
+ [NSGraphicsContext restoreGraphicsState];
+ LOG_ERROR("Exception caught while drawing: %@", localException);
+ [localException raise];
+ }
+}
+
+- (void)drawRect:(NSRect)rect
+{
+ ASSERT_MAIN_THREAD();
+ LOG(View, "%@ drawing", self);
+
+ const NSRect *rects;
+ NSInteger count;
+ [self getRectsBeingDrawn:&rects count:&count];
+
+ BOOL subviewsWereSetAside = _private->subviewsSetAside;
+ if (subviewsWereSetAside)
+ [self _restoreSubviews];
+
+#ifdef _KWQ_TIMING
+ double start = CFAbsoluteTimeGetCurrent();
+#endif
+
+ // If count == 0 here, use the rect passed in for drawing. This is a workaround for:
+ // <rdar://problem/3908282> REGRESSION (Mail): No drag image dragging selected text in Blot and Mail
+ // The reason for the workaround is that this method is called explicitly from the code
+ // to generate a drag image, and at that time, getRectsBeingDrawn:count: will return a zero count.
+ const int cRectThreshold = 10;
+ const float cWastedSpaceThreshold = 0.75f;
+ BOOL useUnionedRect = (count <= 1) || (count > cRectThreshold);
+ if (!useUnionedRect) {
+ // Attempt to guess whether or not we should use the unioned rect or the individual rects.
+ // We do this by computing the percentage of "wasted space" in the union. If that wasted space
+ // is too large, then we will do individual rect painting instead.
+ float unionPixels = (rect.size.width * rect.size.height);
+ float singlePixels = 0;
+ for (int i = 0; i < count; ++i)
+ singlePixels += rects[i].size.width * rects[i].size.height;
+ float wastedSpace = 1 - (singlePixels / unionPixels);
+ if (wastedSpace <= cWastedSpaceThreshold)
+ useUnionedRect = YES;
+ }
+
+ if (useUnionedRect)
+ [self drawSingleRect:rect];
+ else
+ for (int i = 0; i < count; ++i)
+ [self drawSingleRect:rects[i]];
+
+#ifdef _KWQ_TIMING
+ double thisTime = CFAbsoluteTimeGetCurrent() - start;
+ LOG(Timing, "%s draw seconds = %f", widget->part()->baseURL().URL().latin1(), thisTime);
+#endif
+
+ if (subviewsWereSetAside)
+ [self _setAsideSubviews];
+}
+
+// Turn off the additional clip while computing our visibleRect.
+- (NSRect)visibleRect
+{
+ if (!([[self superview] isKindOfClass:[WebClipView class]]))
+ return [super visibleRect];
+
+ WebClipView *clipView = (WebClipView *)[self superview];
+
+ BOOL hasAdditionalClip = [clipView hasAdditionalClip];
+ if (!hasAdditionalClip) {
+ return [super visibleRect];
+ }
+
+ NSRect additionalClip = [clipView additionalClip];
+ [clipView resetAdditionalClip];
+ NSRect visibleRect = [super visibleRect];
+ [clipView setAdditionalClip:additionalClip];
+ return visibleRect;
+}
+
+- (BOOL)isFlipped
+{
+ return YES;
+}
+
+- (void)windowDidBecomeKey:(NSNotification *)notification
+{
+ NSWindow *keyWindow = [notification object];
+
+ if (keyWindow == [self window])
+ [self addMouseMovedObserver];
+
+ if (keyWindow == [self window] || keyWindow == [[self window] attachedSheet])
+ [self _updateFocusedAndActiveState];
+}
+
+- (void)windowDidResignKey:(NSNotification *)notification
+{
+ NSWindow *formerKeyWindow = [notification object];
+
+ if (formerKeyWindow == [self window])
+ [self removeMouseMovedObserver];
+
+ if (formerKeyWindow == [self window] || formerKeyWindow == [[self window] attachedSheet]) {
+ [self _updateFocusedAndActiveState];
+ [_private->compController endRevertingChange:NO moveLeft:NO];
+ }
+}
+
+- (void)windowWillClose:(NSNotification *)notification
+{
+ [_private->compController endRevertingChange:NO moveLeft:NO];
+ [[self _pluginController] destroyAllPlugins];
+}
+
+- (void)scrollWheel:(NSEvent *)event
+{
+ [self retain];
+ Frame* frame = core([self _frame]);
+ if (!frame || !frame->eventHandler()->wheelEvent(event))
+ [super scrollWheel:event];
+ [self release];
+}
+
+- (BOOL)_isSelectionEvent:(NSEvent *)event
+{
+ NSPoint point = [self convertPoint:[event locationInWindow] fromView:nil];
+ return [[[self elementAtPoint:point allowShadowContent:YES] objectForKey:WebElementIsSelectedKey] boolValue];
+}
+
+- (BOOL)acceptsFirstMouse:(NSEvent *)event
+{
+ NSView *hitView = [self _hitViewForEvent:event];
+ WebHTMLView *hitHTMLView = [hitView isKindOfClass:[self class]] ? (WebHTMLView *)hitView : nil;
+
+ if ([[self _webView] _dashboardBehavior:WebDashboardBehaviorAlwaysAcceptsFirstMouse])
+ return YES;
+
+ if (hitHTMLView) {
+ bool result = false;
+ if (Frame* coreFrame = core([hitHTMLView _frame])) {
+ coreFrame->eventHandler()->setActivationEventNumber([event eventNumber]);
+ [hitHTMLView _setMouseDownEvent:event];
+ if ([hitHTMLView _isSelectionEvent:event])
+ result = coreFrame->eventHandler()->eventMayStartDrag(event);
+ [hitHTMLView _setMouseDownEvent:nil];
+ }
+ return result;
+ }
+ return [hitView acceptsFirstMouse:event];
+}
+
+- (BOOL)shouldDelayWindowOrderingForEvent:(NSEvent *)event
+{
+ NSView *hitView = [self _hitViewForEvent:event];
+ WebHTMLView *hitHTMLView = [hitView isKindOfClass:[self class]] ? (WebHTMLView *)hitView : nil;
+ if (hitHTMLView) {
+ bool result = false;
+ if ([hitHTMLView _isSelectionEvent:event])
+ if (Frame* coreFrame = core([hitHTMLView _frame])) {
+ [hitHTMLView _setMouseDownEvent:event];
+ result = coreFrame->eventHandler()->eventMayStartDrag(event);
+ [hitHTMLView _setMouseDownEvent:nil];
+ }
+ return result;
+ }
+ return [hitView shouldDelayWindowOrderingForEvent:event];
+}
+
+- (void)mouseDown:(NSEvent *)event
+{
+ RetainPtr<WebHTMLView> protector = self;
+ if ([[self inputContext] wantsToHandleMouseEvents] && [[self inputContext] handleMouseEvent:event])
+ return;
+
+ _private->handlingMouseDownEvent = YES;
+
+ // Record the mouse down position so we can determine drag hysteresis.
+ [self _setMouseDownEvent:event];
+
+ NSInputManager *currentInputManager = [NSInputManager currentInputManager];
+ if ([currentInputManager wantsToHandleMouseEvents] && [currentInputManager handleMouseEvent:event])
+ goto done;
+
+ [_private->compController endRevertingChange:NO moveLeft:NO];
+
+ // If the web page handles the context menu event and menuForEvent: returns nil, we'll get control click events here.
+ // We don't want to pass them along to KHTML a second time.
+ if (!([event modifierFlags] & NSControlKeyMask)) {
+ _private->ignoringMouseDraggedEvents = NO;
+
+ // Don't do any mouseover while the mouse is down.
+ [self _cancelUpdateMouseoverTimer];
+
+ // Let WebCore get a chance to deal with the event. This will call back to us
+ // to start the autoscroll timer if appropriate.
+ if (Frame* coreframe = core([self _frame]))
+ coreframe->eventHandler()->mouseDown(event);
+ }
+
+done:
+ _private->handlingMouseDownEvent = NO;
+}
+
+- (void)dragImage:(NSImage *)dragImage
+ at:(NSPoint)at
+ offset:(NSSize)offset
+ event:(NSEvent *)event
+ pasteboard:(NSPasteboard *)pasteboard
+ source:(id)source
+ slideBack:(BOOL)slideBack
+{
+ ASSERT(self == [self _topHTMLView]);
+ [super dragImage:dragImage at:at offset:offset event:event pasteboard:pasteboard source:source slideBack:slideBack];
+}
+
+- (void)mouseDragged:(NSEvent *)event
+{
+ NSInputManager *currentInputManager = [NSInputManager currentInputManager];
+ if ([currentInputManager wantsToHandleMouseEvents] && [currentInputManager handleMouseEvent:event])
+ return;
+
+ [self retain];
+
+ if (!_private->ignoringMouseDraggedEvents)
+ if (Frame* coreframe = core([self _frame]))
+ coreframe->eventHandler()->mouseDragged(event);
+
+ [self release];
+}
+
+- (NSDragOperation)draggingSourceOperationMaskForLocal:(BOOL)isLocal
+{
+ ASSERT(![self _webView] || [self _isTopHTMLView]);
+
+ Page *page = core([self _webView]);
+
+ if (!page)
+ return NSDragOperationNone;
+
+ if (page->dragController()->dragOperation() == DragOperationNone)
+ return NSDragOperationGeneric | NSDragOperationCopy;
+
+ return (NSDragOperation)page->dragController()->dragOperation();
+}
+
+- (void)draggedImage:(NSImage *)image movedTo:(NSPoint)screenLoc
+{
+ ASSERT(![self _webView] || [self _isTopHTMLView]);
+
+ NSPoint windowImageLoc = [[self window] convertScreenToBase:screenLoc];
+ NSPoint windowMouseLoc = windowImageLoc;
+
+ if (Page* page = core([self _webView])) {
+ DragController* dragController = page->dragController();
+ NSPoint windowMouseLoc = NSMakePoint(windowImageLoc.x + dragController->dragOffset().x(), windowImageLoc.y + dragController->dragOffset().y());
+ }
+
+ [[self _bridge] dragSourceMovedTo:windowMouseLoc];
+}
+
+- (void)draggedImage:(NSImage *)anImage endedAt:(NSPoint)aPoint operation:(NSDragOperation)operation
+{
+ ASSERT(![self _webView] || [self _isTopHTMLView]);
+
+ NSPoint windowImageLoc = [[self window] convertScreenToBase:aPoint];
+ NSPoint windowMouseLoc = windowImageLoc;
+
+ if (Page* page = core([self _webView])) {
+ DragController* dragController = page->dragController();
+ windowMouseLoc = NSMakePoint(windowImageLoc.x + dragController->dragOffset().x(), windowImageLoc.y + dragController->dragOffset().y());
+ dragController->dragEnded();
+ }
+
+ [[self _bridge] dragSourceEndedAt:windowMouseLoc operation:operation];
+
+ // Prevent queued mouseDragged events from coming after the drag and fake mouseUp event.
+ _private->ignoringMouseDraggedEvents = YES;
+
+ // Once the dragging machinery kicks in, we no longer get mouse drags or the up event.
+ // WebCore expects to get balanced down/up's, so we must fake up a mouseup.
+ NSEvent *fakeEvent = [NSEvent mouseEventWithType:NSLeftMouseUp
+ location:windowMouseLoc
+ modifierFlags:[[NSApp currentEvent] modifierFlags]
+ timestamp:[NSDate timeIntervalSinceReferenceDate]
+ windowNumber:[[self window] windowNumber]
+ context:[[NSApp currentEvent] context]
+ eventNumber:0 clickCount:0 pressure:0];
+ [self mouseUp:fakeEvent]; // This will also update the mouseover state.
+}
+
+- (NSArray *)namesOfPromisedFilesDroppedAtDestination:(NSURL *)dropDestination
+{
+ NSFileWrapper *wrapper = nil;
+ NSURL *draggingImageURL = nil;
+
+ if (WebCore::CachedResource* tiffResource = [self promisedDragTIFFDataSource]) {
+
+ SharedBuffer *buffer = tiffResource->data();
+ if (!buffer)
+ goto noPromisedData;
+
+ NSData *data = buffer->createNSData();
+ NSURLResponse *response = tiffResource->response().nsURLResponse();
+ draggingImageURL = [response URL];
+ wrapper = [[[NSFileWrapper alloc] initRegularFileWithContents:data] autorelease];
+ [wrapper setPreferredFilename:[response suggestedFilename]];
+ }
+
+noPromisedData:
+
+ if (!wrapper) {
+ ASSERT(![self _webView] || [self _isTopHTMLView]);
+ Page* page = core([self _webView]);
+
+ //If a load occurs midway through a drag, the view may be detached, which gives
+ //us no ability to get to the original Page, so we cannot access any drag state
+ //FIXME: is there a way to recover?
+ if (!page)
+ return nil;
+
+ KURL imageURL = page->dragController()->draggingImageURL();
+ ASSERT(!imageURL.isEmpty());
+ draggingImageURL = imageURL;
+
+ wrapper = [[self _dataSource] _fileWrapperForURL:draggingImageURL];
+ }
+
+ if (wrapper == nil) {
+ LOG_ERROR("Failed to create image file.");
+ return nil;
+ }
+
+ // FIXME: Report an error if we fail to create a file.
+ NSString *path = [[dropDestination path] stringByAppendingPathComponent:[wrapper preferredFilename]];
+ path = [[NSFileManager defaultManager] _webkit_pathWithUniqueFilenameForPath:path];
+ if (![wrapper writeToFile:path atomically:NO updateFilenames:YES])
+ LOG_ERROR("Failed to create image file via -[NSFileWrapper writeToFile:atomically:updateFilenames:]");
+
+ if (draggingImageURL)
+ [[NSFileManager defaultManager] _webkit_setMetadataURL:[draggingImageURL absoluteString] referrer:nil atPath:path];
+
+ return [NSArray arrayWithObject:[path lastPathComponent]];
+}
+
+- (void)mouseUp:(NSEvent *)event
+{
+ [self _setMouseDownEvent:nil];
+
+ NSInputManager *currentInputManager = [NSInputManager currentInputManager];
+ if ([currentInputManager wantsToHandleMouseEvents] && [currentInputManager handleMouseEvent:event])
+ return;
+
+ [self retain];
+
+ [self _stopAutoscrollTimer];
+ if (Frame* coreframe = core([self _frame]))
+ coreframe->eventHandler()->mouseUp(event);
+ [self _updateMouseoverWithFakeEvent];
+
+ [self release];
+}
+
+- (void)mouseMovedNotification:(NSNotification *)notification
+{
+ [self _updateMouseoverWithEvent:[[notification userInfo] objectForKey:@"NSEvent"]];
+}
+
+// returning YES from this method is the way we tell AppKit that it is ok for this view
+// to be in the key loop even when "tab to all controls" is not on.
+- (BOOL)needsPanelToBecomeKey
+{
+ return YES;
+}
+
+- (BOOL)becomeFirstResponder
+{
+ NSSelectionDirection direction = NSDirectSelection;
+ if (![[self _webView] _isPerformingProgrammaticFocus])
+ direction = [[self window] keyViewSelectionDirection];
+
+ [self _updateFocusedAndActiveState];
+ [self _updateFontPanel];
+
+ Frame* frame = core([self _frame]);
+ if (!frame)
+ return YES;
+
+ frame->editor()->setStartNewKillRingSequence(true);
+
+ if (direction == NSDirectSelection)
+ return YES;
+
+ Page* page = frame->page();
+ if (!page)
+ return YES;
+
+ page->focusController()->setFocusedFrame(frame);
+ if (Document* document = frame->document())
+ document->setFocusedNode(0);
+ page->focusController()->setInitialFocus(direction == NSSelectingNext ? FocusDirectionForward : FocusDirectionBackward,
+ frame->eventHandler()->currentKeyboardEvent().get());
+ return YES;
+}
+
+- (BOOL)resignFirstResponder
+{
+ BOOL resign = [super resignFirstResponder];
+ if (resign) {
+ [_private->compController endRevertingChange:NO moveLeft:NO];
+ _private->resigningFirstResponder = YES;
+ if (![self maintainsInactiveSelection]) {
+ [self deselectAll];
+ if (![[self _webView] _isPerformingProgrammaticFocus])
+ [self clearFocus];
+ }
+ [self _updateFocusedAndActiveState];
+ _private->resigningFirstResponder = NO;
+ }
+ return resign;
+}
+
+- (void)setDataSource:(WebDataSource *)dataSource
+{
+ ASSERT(dataSource);
+ if (_private->dataSource != dataSource) {
+ ASSERT(!_private->closed);
+ BOOL hadDataSource = _private->dataSource != nil;
+
+ [dataSource retain];
+ [_private->dataSource release];
+ _private->dataSource = dataSource;
+ [_private->pluginController setDataSource:dataSource];
+
+ if (!hadDataSource)
+ [self addMouseMovedObserver];
+ }
+}
+
+- (void)dataSourceUpdated:(WebDataSource *)dataSource
+{
+}
+
+// This is an override of an NSControl method that wants to repaint the entire view when the window resigns/becomes
+// key. WebHTMLView is an NSControl only because it hosts NSCells that are painted by WebCore's Aqua theme
+// renderer (and those cells must be hosted by an enclosing NSControl in order to paint properly).
+- (void)updateCell:(NSCell*)cell
+{
+}
+
+// Does setNeedsDisplay:NO as a side effect when printing is ending.
+// pageWidth != 0 implies we will relayout to a new width
+- (void)_setPrinting:(BOOL)printing minimumPageWidth:(float)minPageWidth maximumPageWidth:(float)maxPageWidth adjustViewSize:(BOOL)adjustViewSize
+{
+ WebFrame *frame = [self _frame];
+ NSArray *subframes = [frame childFrames];
+ unsigned n = [subframes count];
+ unsigned i;
+ for (i = 0; i != n; ++i) {
+ WebFrame *subframe = [subframes objectAtIndex:i];
+ WebFrameView *frameView = [subframe frameView];
+ if ([[subframe _dataSource] _isDocumentHTML]) {
+ [(WebHTMLView *)[frameView documentView] _setPrinting:printing minimumPageWidth:0.0f maximumPageWidth:0.0f adjustViewSize:adjustViewSize];
+ }
+ }
+
+ if (printing != _private->printing) {
+ [_private->pageRects release];
+ _private->pageRects = nil;
+ _private->printing = printing;
+ if (!printing)
+ _private->avoidingPrintOrphan = NO;
+ [self setNeedsToApplyStyles:YES];
+ [self setNeedsLayout:YES];
+ [self layoutToMinimumPageWidth:minPageWidth maximumPageWidth:maxPageWidth adjustingViewSize:adjustViewSize];
+ if (!printing) {
+ // Can't do this when starting printing or nested printing won't work, see 3491427.
+ [self setNeedsDisplay:NO];
+ }
+ }
+}
+
+- (BOOL)canPrintHeadersAndFooters
+{
+ return YES;
+}
+
+// This is needed for the case where the webview is embedded in the view that's being printed.
+// It shouldn't be called when the webview is being printed directly.
+- (void)adjustPageHeightNew:(float *)newBottom top:(float)oldTop bottom:(float)oldBottom limit:(float)bottomLimit
+{
+ // This helps when we print as part of a larger print process.
+ // If the WebHTMLView itself is what we're printing, then we will never have to do this.
+ BOOL wasInPrintingMode = _private->printing;
+ if (!wasInPrintingMode)
+ [self _setPrinting:YES minimumPageWidth:0.0f maximumPageWidth:0.0f adjustViewSize:NO];
+
+ [[self _bridge] adjustPageHeightNew:newBottom top:oldTop bottom:oldBottom limit:bottomLimit];
+
+ if (!wasInPrintingMode) {
+ NSPrintOperation *currenPrintOperation = [NSPrintOperation currentOperation];
+ if (currenPrintOperation)
+ // delay _setPrinting:NO until back to main loop as this method may get called repeatedly
+ [self performSelector:@selector(_delayedEndPrintMode:) withObject:currenPrintOperation afterDelay:0];
+ else
+ // not sure if this is actually ever invoked, it probably shouldn't be
+ [self _setPrinting:NO minimumPageWidth:0.0f maximumPageWidth:0.0f adjustViewSize:NO];
+ }
+}
+
+- (float)_availablePaperWidthForPrintOperation:(NSPrintOperation *)printOperation
+{
+ NSPrintInfo *printInfo = [printOperation printInfo];
+ return [printInfo paperSize].width - [printInfo leftMargin] - [printInfo rightMargin];
+}
+
+- (float)_scaleFactorForPrintOperation:(NSPrintOperation *)printOperation
+{
+ float viewWidth = NSWidth([self bounds]);
+ if (viewWidth < 1) {
+ LOG_ERROR("%@ has no width when printing", self);
+ return 1.0f;
+ }
+
+ float userScaleFactor = [printOperation _web_pageSetupScaleFactor];
+ float maxShrinkToFitScaleFactor = 1.0f / PrintingMaximumShrinkFactor;
+ float shrinkToFitScaleFactor = [self _availablePaperWidthForPrintOperation:printOperation]/viewWidth;
+ float shrinkToAvoidOrphan = _private->avoidingPrintOrphan ? (1.0f / PrintingOrphanShrinkAdjustment) : 1.0f;
+ return userScaleFactor * MAX(maxShrinkToFitScaleFactor, shrinkToFitScaleFactor) * shrinkToAvoidOrphan;
+}
+
+// FIXME 3491344: This is a secret AppKit-internal method that we need to override in order
+// to get our shrink-to-fit to work with a custom pagination scheme. We can do this better
+// if AppKit makes it SPI/API.
+- (float)_provideTotalScaleFactorForPrintOperation:(NSPrintOperation *)printOperation
+{
+ return [self _scaleFactorForPrintOperation:printOperation];
+}
+
+// This is used for Carbon printing. At some point we might want to make this public API.
+- (void)setPageWidthForPrinting:(float)pageWidth
+{
+ [self _setPrinting:NO minimumPageWidth:0.0f maximumPageWidth:0.0f adjustViewSize:NO];
+ [self _setPrinting:YES minimumPageWidth:pageWidth maximumPageWidth:pageWidth adjustViewSize:YES];
+}
+
+- (void)_endPrintMode
+{
+ [self _setPrinting:NO minimumPageWidth:0.0f maximumPageWidth:0.0f adjustViewSize:YES];
+ [[self window] setAutodisplay:YES];
+}
+
+- (void)_delayedEndPrintMode:(NSPrintOperation *)initiatingOperation
+{
+ ASSERT_ARG(initiatingOperation, initiatingOperation != nil);
+ NSPrintOperation *currentOperation = [NSPrintOperation currentOperation];
+ if (initiatingOperation == currentOperation) {
+ // The print operation is still underway. We don't expect this to ever happen, hence the assert, but we're
+ // being extra paranoid here since the printing code is so fragile. Delay the cleanup
+ // further.
+ ASSERT_NOT_REACHED();
+ [self performSelector:@selector(_delayedEndPrintMode:) withObject:initiatingOperation afterDelay:0];
+ } else if ([currentOperation view] == self) {
+ // A new print job has started, but it is printing the same WebHTMLView again. We don't expect
+ // this to ever happen, hence the assert, but we're being extra paranoid here since the printing code is so
+ // fragile. Do nothing, because we don't want to break the print job currently in progress, and
+ // the print job currently in progress is responsible for its own cleanup.
+ ASSERT_NOT_REACHED();
+ } else {
+ // The print job that kicked off this delayed call has finished, and this view is not being
+ // printed again. We expect that no other print job has started. Since this delayed call wasn't
+ // cancelled, beginDocument and endDocument must not have been called, and we need to clean up
+ // the print mode here.
+ ASSERT(currentOperation == nil);
+ [self _endPrintMode];
+ }
+}
+
+// Return the number of pages available for printing
+- (BOOL)knowsPageRange:(NSRangePointer)range
+{
+ // Must do this explicit display here, because otherwise the view might redisplay while the print
+ // sheet was up, using printer fonts (and looking different).
+ [self displayIfNeeded];
+ [[self window] setAutodisplay:NO];
+
+ // If we are a frameset just print with the layout we have onscreen, otherwise relayout
+ // according to the paper size
+ float minLayoutWidth = 0.0f;
+ float maxLayoutWidth = 0.0f;
+ Frame* frame = core([self _frame]);
+ if (!frame)
+ return NO;
+ if (!frame->isFrameSet()) {
+ float paperWidth = [self _availablePaperWidthForPrintOperation:[NSPrintOperation currentOperation]];
+ minLayoutWidth = paperWidth * PrintingMinimumShrinkFactor;
+ maxLayoutWidth = paperWidth * PrintingMaximumShrinkFactor;
+ }
+ [self _setPrinting:YES minimumPageWidth:minLayoutWidth maximumPageWidth:maxLayoutWidth adjustViewSize:YES]; // will relayout
+ NSPrintOperation *printOperation = [NSPrintOperation currentOperation];
+ // Certain types of errors, including invalid page ranges, can cause beginDocument and
+ // endDocument to be skipped after we've put ourselves in print mode (see 4145905). In those cases
+ // we need to get out of print mode without relying on any more callbacks from the printing mechanism.
+ // If we get as far as beginDocument without trouble, then this delayed request will be cancelled.
+ // If not cancelled, this delayed call will be invoked in the next pass through the main event loop,
+ // which is after beginDocument and endDocument would be called.
+ [self performSelector:@selector(_delayedEndPrintMode:) withObject:printOperation afterDelay:0];
+ [[self _webView] _adjustPrintingMarginsForHeaderAndFooter];
+
+ // There is a theoretical chance that someone could do some drawing between here and endDocument,
+ // if something caused setNeedsDisplay after this point. If so, it's not a big tragedy, because
+ // you'd simply see the printer fonts on screen. As of this writing, this does not happen with Safari.
+
+ range->location = 1;
+ float totalScaleFactor = [self _scaleFactorForPrintOperation:printOperation];
+ float userScaleFactor = [printOperation _web_pageSetupScaleFactor];
+ [_private->pageRects release];
+ float fullPageHeight = floorf([self _calculatePrintHeight]/totalScaleFactor);
+ NSArray *newPageRects = [[self _bridge] computePageRectsWithPrintWidthScaleFactor:userScaleFactor
+ printHeight:fullPageHeight];
+
+ // AppKit gets all messed up if you give it a zero-length page count (see 3576334), so if we
+ // hit that case we'll pass along a degenerate 1 pixel square to print. This will print
+ // a blank page (with correct-looking header and footer if that option is on), which matches
+ // the behavior of IE and Camino at least.
+ if ([newPageRects count] == 0)
+ newPageRects = [NSArray arrayWithObject:[NSValue valueWithRect:NSMakeRect(0, 0, 1, 1)]];
+ else if ([newPageRects count] > 1) {
+ // If the last page is a short orphan, try adjusting the print height slightly to see if this will squeeze the
+ // content onto one fewer page. If it does, use the adjusted scale. If not, use the original scale.
+ float lastPageHeight = NSHeight([[newPageRects lastObject] rectValue]);
+ if (lastPageHeight/fullPageHeight < LastPrintedPageOrphanRatio) {
+ NSArray *adjustedPageRects = [[self _bridge] computePageRectsWithPrintWidthScaleFactor:userScaleFactor
+ printHeight:fullPageHeight*PrintingOrphanShrinkAdjustment];
+ // Use the adjusted rects only if the page count went down
+ if ([adjustedPageRects count] < [newPageRects count]) {
+ newPageRects = adjustedPageRects;
+ _private->avoidingPrintOrphan = YES;
+ }
+ }
+ }
+
+ _private->pageRects = [newPageRects retain];
+
+ range->length = [_private->pageRects count];
+
+ return YES;
+}
+
+// Return the drawing rectangle for a particular page number
+- (NSRect)rectForPage:(int)page
+{
+ return [[_private->pageRects objectAtIndex:page - 1] rectValue];
+}
+
+- (void)drawPageBorderWithSize:(NSSize)borderSize
+{
+ ASSERT(NSEqualSizes(borderSize, [[[NSPrintOperation currentOperation] printInfo] paperSize]));
+ [[self _webView] _drawHeaderAndFooter];
+}
+
+- (void)beginDocument
+{
+ @try {
+ // From now on we'll get a chance to call _endPrintMode in either beginDocument or
+ // endDocument, so we can cancel the "just in case" pending call.
+ [NSObject cancelPreviousPerformRequestsWithTarget:self
+ selector:@selector(_delayedEndPrintMode:)
+ object:[NSPrintOperation currentOperation]];
+ [super beginDocument];
+ } @catch (NSException *localException) {
+ // Exception during [super beginDocument] means that endDocument will not get called,
+ // so we need to clean up our "print mode" here.
+ [self _endPrintMode];
+ }
+}
+
+- (void)endDocument
+{
+ [super endDocument];
+ // Note sadly at this point [NSGraphicsContext currentContextDrawingToScreen] is still NO
+ [self _endPrintMode];
+}
+
+- (void)keyDown:(NSEvent *)event
+{
+ RetainPtr<WebHTMLView> selfProtector = self;
+ BOOL eventWasSentToWebCore = (_private->keyDownEvent == event);
+
+ BOOL callSuper = NO;
+
+ [_private->keyDownEvent release];
+ _private->keyDownEvent = [event retain];
+
+ BOOL completionPopupWasOpen = _private->compController && [_private->compController popupWindowIsOpen];
+ Frame* coreFrame = core([self _frame]);
+ if (!eventWasSentToWebCore && coreFrame && coreFrame->eventHandler()->keyEvent(event)) {
+ // WebCore processed a key event, bail on any preexisting complete: UI
+ if (completionPopupWasOpen)
+ [_private->compController endRevertingChange:YES moveLeft:NO];
+ } else if (!_private->compController || ![_private->compController filterKeyDown:event]) {
+ // Not consumed by complete: popup window
+ [_private->compController endRevertingChange:YES moveLeft:NO];
+ callSuper = YES;
+ }
+ if (callSuper)
+ [super keyDown:event];
+ else
+ [NSCursor setHiddenUntilMouseMoves:YES];
+}
+
+- (void)keyUp:(NSEvent *)event
+{
+ BOOL eventWasSentToWebCore = (_private->keyDownEvent == event);
+
+ [self retain];
+ Frame* coreFrame = core([self _frame]);
+ if (eventWasSentToWebCore || !coreFrame || !coreFrame->eventHandler()->keyEvent(event))
+ [super keyUp:event];
+ [self release];
+}
+
+- (void)flagsChanged:(NSEvent *)event
+{
+ Frame* coreFrame = core([self _frame]);
+ if (coreFrame)
+ coreFrame->eventHandler()->capsLockStateMayHaveChanged();
+
+ RetainPtr<WebHTMLView> selfProtector = self;
+
+ unsigned short keyCode = [event keyCode];
+ //Don't make an event from the num lock and function keys
+ if (coreFrame && keyCode != 0 && keyCode != 10 && keyCode != 63)
+ coreFrame->eventHandler()->keyEvent(PlatformKeyboardEvent(event));
+
+ [super flagsChanged:event];
+}
+
+- (id)accessibilityAttributeValue:(NSString*)attributeName
+{
+ if ([attributeName isEqualToString: NSAccessibilityChildrenAttribute]) {
+ id accTree = [[self _bridge] accessibilityTree];
+ if (accTree)
+ return [NSArray arrayWithObject:accTree];
+ return nil;
+ }
+ return [super accessibilityAttributeValue:attributeName];
+}
+
+- (id)accessibilityFocusedUIElement
+{
+ id accTree = [[self _bridge] accessibilityTree];
+ if (accTree)
+ return [accTree accessibilityFocusedUIElement];
+ return self;
+}
+
+- (id)accessibilityHitTest:(NSPoint)point
+{
+ id accTree = [[self _bridge] accessibilityTree];
+ if (accTree) {
+ NSPoint windowCoord = [[self window] convertScreenToBase:point];
+ return [accTree accessibilityHitTest:[self convertPoint:windowCoord fromView:nil]];
+ }
+ return self;
+}
+
+- (id)_accessibilityParentForSubview:(NSView *)subview
+{
+ id accTree = [[self _bridge] accessibilityTree];
+ if (!accTree)
+ return self;
+ id parent = [accTree _accessibilityParentForSubview:subview];
+ if (!parent)
+ return self;
+ return parent;
+}
+
+- (void)centerSelectionInVisibleArea:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->revealSelection(RenderLayer::gAlignCenterAlways);
+}
+
+- (NSData *)_selectionStartFontAttributesAsRTF
+{
+ Frame* coreFrame = core([self _frame]);
+ NSAttributedString *string = [[NSAttributedString alloc] initWithString:@"x"
+ attributes:coreFrame ? coreFrame->fontAttributesForSelectionStart() : nil];
+ NSData *data = [string RTFFromRange:NSMakeRange(0, [string length]) documentAttributes:nil];
+ [string release];
+ return data;
+}
+
+- (NSDictionary *)_fontAttributesFromFontPasteboard
+{
+ NSPasteboard *fontPasteboard = [NSPasteboard pasteboardWithName:NSFontPboard];
+ if (fontPasteboard == nil)
+ return nil;
+ NSData *data = [fontPasteboard dataForType:NSFontPboardType];
+ if (data == nil || [data length] == 0)
+ return nil;
+ // NSTextView does something more efficient by parsing the attributes only, but that's not available in API.
+ NSAttributedString *string = [[[NSAttributedString alloc] initWithRTF:data documentAttributes:NULL] autorelease];
+ if (string == nil || [string length] == 0)
+ return nil;
+ return [string fontAttributesInRange:NSMakeRange(0, 1)];
+}
+
+- (DOMCSSStyleDeclaration *)_emptyStyle
+{
+ return [[[self _frame] DOMDocument] createCSSStyleDeclaration];
+}
+
+- (NSString *)_colorAsString:(NSColor *)color
+{
+ NSColor *rgbColor = [color colorUsingColorSpaceName:NSCalibratedRGBColorSpace];
+ // FIXME: If color is non-nil and rgbColor is nil, that means we got some kind
+ // of fancy color that can't be converted to RGB. Changing that to "transparent"
+ // might not be great, but it's probably OK.
+ if (rgbColor == nil)
+ return @"transparent";
+ float r = [rgbColor redComponent];
+ float g = [rgbColor greenComponent];
+ float b = [rgbColor blueComponent];
+ float a = [rgbColor alphaComponent];
+ if (a == 0)
+ return @"transparent";
+ if (r == 0 && g == 0 && b == 0 && a == 1)
+ return @"black";
+ if (r == 1 && g == 1 && b == 1 && a == 1)
+ return @"white";
+ // FIXME: Lots more named colors. Maybe we could use the table in WebCore?
+ if (a == 1)
+ return [NSString stringWithFormat:@"rgb(%.0f,%.0f,%.0f)", r * 255, g * 255, b * 255];
+ return [NSString stringWithFormat:@"rgba(%.0f,%.0f,%.0f,%f)", r * 255, g * 255, b * 255, a];
+}
+
+- (NSString *)_shadowAsString:(NSShadow *)shadow
+{
+ if (shadow == nil)
+ return @"none";
+ NSSize offset = [shadow shadowOffset];
+ float blurRadius = [shadow shadowBlurRadius];
+ if (offset.width == 0 && offset.height == 0 && blurRadius == 0)
+ return @"none";
+ NSColor *color = [shadow shadowColor];
+ if (color == nil)
+ return @"none";
+ // FIXME: Handle non-integral values here?
+ if (blurRadius == 0)
+ return [NSString stringWithFormat:@"%@ %.0fpx %.0fpx", [self _colorAsString:color], offset.width, offset.height];
+ return [NSString stringWithFormat:@"%@ %.0fpx %.0fpx %.0fpx", [self _colorAsString:color], offset.width, offset.height, blurRadius];
+}
+
+- (DOMCSSStyleDeclaration *)_styleFromFontAttributes:(NSDictionary *)dictionary
+{
+ DOMCSSStyleDeclaration *style = [self _emptyStyle];
+
+ NSColor *color = [dictionary objectForKey:NSBackgroundColorAttributeName];
+ [style setBackgroundColor:[self _colorAsString:color]];
+
+ NSFont *font = [dictionary objectForKey:NSFontAttributeName];
+ if (font == nil) {
+ [style setFontFamily:@"Helvetica"];
+ [style setFontSize:@"12px"];
+ [style setFontWeight:@"normal"];
+ [style setFontStyle:@"normal"];
+ } else {
+ NSFontManager *fm = [NSFontManager sharedFontManager];
+ // FIXME: Need more sophisticated escaping code if we want to handle family names
+ // with characters like single quote or backslash in their names.
+ [style setFontFamily:[NSString stringWithFormat:@"'%@'", [font familyName]]];
+ [style setFontSize:[NSString stringWithFormat:@"%0.fpx", [font pointSize]]];
+ if ([fm weightOfFont:font] >= MIN_BOLD_WEIGHT)
+ [style setFontWeight:@"bold"];
+ else
+ [style setFontWeight:@"normal"];
+ if (([fm traitsOfFont:font] & NSItalicFontMask) != 0)
+ [style setFontStyle:@"italic"];
+ else
+ [style setFontStyle:@"normal"];
+ }
+
+ color = [dictionary objectForKey:NSForegroundColorAttributeName];
+ [style setColor:color ? [self _colorAsString:color] : (NSString *)@"black"];
+
+ NSShadow *shadow = [dictionary objectForKey:NSShadowAttributeName];
+ [style setTextShadow:[self _shadowAsString:shadow]];
+
+ int strikethroughInt = [[dictionary objectForKey:NSStrikethroughStyleAttributeName] intValue];
+
+ int superscriptInt = [[dictionary objectForKey:NSSuperscriptAttributeName] intValue];
+ if (superscriptInt > 0)
+ [style setVerticalAlign:@"super"];
+ else if (superscriptInt < 0)
+ [style setVerticalAlign:@"sub"];
+ else
+ [style setVerticalAlign:@"baseline"];
+ int underlineInt = [[dictionary objectForKey:NSUnderlineStyleAttributeName] intValue];
+ // FIXME: Underline wins here if we have both (see bug 3790443).
+ if (strikethroughInt == NSUnderlineStyleNone && underlineInt == NSUnderlineStyleNone)
+ [style setProperty:@"-khtml-text-decorations-in-effect" value:@"none" priority:@""];
+ else if (underlineInt == NSUnderlineStyleNone)
+ [style setProperty:@"-khtml-text-decorations-in-effect" value:@"line-through" priority:@""];
+ else
+ [style setProperty:@"-khtml-text-decorations-in-effect" value:@"underline" priority:@""];
+
+ return style;
+}
+
+- (void)_applyStyleToSelection:(DOMCSSStyleDeclaration *)style withUndoAction:(EditAction)undoAction
+{
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->editor()->applyStyleToSelection(core(style), undoAction);
+}
+
+- (void)_applyParagraphStyleToSelection:(DOMCSSStyleDeclaration *)style withUndoAction:(EditAction)undoAction
+{
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->editor()->applyParagraphStyleToSelection(core(style), undoAction);
+}
+
+- (BOOL)_handleStyleKeyEquivalent:(NSEvent *)event
+{
+ ASSERT([self _webView]);
+ if (![[[self _webView] preferences] respectStandardStyleKeyEquivalents])
+ return NO;
+
+ if (![self _canEdit])
+ return NO;
+
+ if (([event modifierFlags] & NSDeviceIndependentModifierFlagsMask) != NSCommandKeyMask)
+ return NO;
+
+ NSString *string = [event characters];
+ if ([string caseInsensitiveCompare:@"b"] == NSOrderedSame) {
+ [self executeCoreCommandByName:"ToggleBold"];
+ return YES;
+ }
+ if ([string caseInsensitiveCompare:@"i"] == NSOrderedSame) {
+ [self executeCoreCommandByName:"ToggleItalic"];
+ return YES;
+ }
+
+ return NO;
+}
+
+- (BOOL)performKeyEquivalent:(NSEvent *)event
+{
+ if ([self _handleStyleKeyEquivalent:event])
+ return YES;
+
+ BOOL eventWasSentToWebCore = (_private->keyDownEvent == event);
+ BOOL ret = NO;
+
+ [_private->keyDownEvent release];
+ _private->keyDownEvent = [event retain];
+
+ [self retain];
+
+ // Pass command-key combos through WebCore if there is a key binding available for
+ // this event. This lets web pages have a crack at intercepting command-modified keypresses.
+ // But don't do it if we have already handled the event.
+ // Pressing Esc results in a fake event being sent - don't pass it to WebCore.
+ if (!eventWasSentToWebCore && event == [NSApp currentEvent] && self == [[self window] firstResponder])
+ if (Frame* frame = core([self _frame]))
+ ret = frame->eventHandler()->keyEvent(event);
+
+ if (!ret)
+ ret = [super performKeyEquivalent:event];
+
+ [self release];
+
+ return ret;
+}
+
+- (void)copyFont:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ // Put RTF with font attributes on the pasteboard.
+ // Maybe later we should add a pasteboard type that contains CSS text for "native" copy and paste font.
+ NSPasteboard *fontPasteboard = [NSPasteboard pasteboardWithName:NSFontPboard];
+ [fontPasteboard declareTypes:[NSArray arrayWithObject:NSFontPboardType] owner:nil];
+ [fontPasteboard setData:[self _selectionStartFontAttributesAsRTF] forType:NSFontPboardType];
+}
+
+- (void)pasteFont:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ // Read RTF with font attributes from the pasteboard.
+ // Maybe later we should add a pasteboard type that contains CSS text for "native" copy and paste font.
+ [self _applyStyleToSelection:[self _styleFromFontAttributes:[self _fontAttributesFromFontPasteboard]] withUndoAction:EditActionPasteFont];
+}
+
+- (void)pasteAsRichText:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ // Since rich text always beats plain text when both are on the pasteboard, it's not
+ // clear how this is different from plain old paste.
+ [self _pasteWithPasteboard:[NSPasteboard generalPasteboard] allowPlainText:NO];
+}
+
+- (NSFont *)_originalFontA
+{
+ return [[NSFontManager sharedFontManager] fontWithFamily:@"Helvetica" traits:0 weight:STANDARD_WEIGHT size:10.0f];
+}
+
+- (NSFont *)_originalFontB
+{
+ return [[NSFontManager sharedFontManager] fontWithFamily:@"Times" traits:(NSBoldFontMask | NSItalicFontMask) weight:STANDARD_BOLD_WEIGHT size:12.0f];
+}
+
+- (void)_addToStyle:(DOMCSSStyleDeclaration *)style fontA:(NSFont *)a fontB:(NSFont *)b
+{
+ // Since there's no way to directly ask NSFontManager what style change it's going to do
+ // we instead pass two "specimen" fonts to it and let it change them. We then deduce what
+ // style change it was doing by looking at what happened to each of the two fonts.
+ // So if it was making the text bold, both fonts will be bold after the fact.
+
+ if (a == nil || b == nil)
+ return;
+
+ NSFontManager *fm = [NSFontManager sharedFontManager];
+
+ NSFont *oa = [self _originalFontA];
+
+ NSString *aFamilyName = [a familyName];
+ NSString *bFamilyName = [b familyName];
+
+ int aPointSize = (int)[a pointSize];
+ int bPointSize = (int)[b pointSize];
+
+ int aWeight = [fm weightOfFont:a];
+ int bWeight = [fm weightOfFont:b];
+
+ BOOL aIsBold = aWeight >= MIN_BOLD_WEIGHT;
+
+ BOOL aIsItalic = ([fm traitsOfFont:a] & NSItalicFontMask) != 0;
+ BOOL bIsItalic = ([fm traitsOfFont:b] & NSItalicFontMask) != 0;
+
+ if ([aFamilyName isEqualToString:bFamilyName]) {
+ NSString *familyNameForCSS = aFamilyName;
+
+ // The family name may not be specific enough to get us the font specified.
+ // In some cases, the only way to get exactly what we are looking for is to use
+ // the Postscript name.
+
+ // Find the font the same way the rendering code would later if it encountered this CSS.
+ NSFontTraitMask traits = 0;
+ if (aIsBold)
+ traits |= NSBoldFontMask;
+ if (aIsItalic)
+ traits |= NSItalicFontMask;
+ NSFont *foundFont = WebCoreFindFont(aFamilyName, traits, aPointSize);
+
+ // If we don't find a font with the same Postscript name, then we'll have to use the
+ // Postscript name to make the CSS specific enough.
+ if (![[foundFont fontName] isEqualToString:[a fontName]]) {
+ familyNameForCSS = [a fontName];
+ }
+
+ // FIXME: Need more sophisticated escaping code if we want to handle family names
+ // with characters like single quote or backslash in their names.
+ [style setFontFamily:[NSString stringWithFormat:@"'%@'", familyNameForCSS]];
+ }
+
+ int soa = (int)[oa pointSize];
+ if (aPointSize == bPointSize)
+ [style setFontSize:[NSString stringWithFormat:@"%dpx", aPointSize]];
+ else if (aPointSize < soa)
+ [style _setFontSizeDelta:@"-1px"];
+ else if (aPointSize > soa)
+ [style _setFontSizeDelta:@"1px"];
+
+ if (aWeight == bWeight)
+ [style setFontWeight:aIsBold ? @"bold" : @"normal"];
+
+ if (aIsItalic == bIsItalic)
+ [style setFontStyle:aIsItalic ? @"italic" : @"normal"];
+}
+
+- (DOMCSSStyleDeclaration *)_styleFromFontManagerOperation
+{
+ DOMCSSStyleDeclaration *style = [self _emptyStyle];
+
+ NSFontManager *fm = [NSFontManager sharedFontManager];
+
+ NSFont *oa = [self _originalFontA];
+ NSFont *ob = [self _originalFontB];
+ [self _addToStyle:style fontA:[fm convertFont:oa] fontB:[fm convertFont:ob]];
+
+ return style;
+}
+
+- (void)changeFont:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ [self _applyStyleToSelection:[self _styleFromFontManagerOperation] withUndoAction:EditActionSetFont];
+}
+
+- (DOMCSSStyleDeclaration *)_styleForAttributeChange:(id)sender
+{
+ DOMCSSStyleDeclaration *style = [self _emptyStyle];
+
+ NSShadow *shadow = [[NSShadow alloc] init];
+ [shadow setShadowOffset:NSMakeSize(1, 1)];
+
+ NSDictionary *oa = [NSDictionary dictionaryWithObjectsAndKeys:
+ [self _originalFontA], NSFontAttributeName,
+ nil];
+ NSDictionary *ob = [NSDictionary dictionaryWithObjectsAndKeys:
+ [NSColor blackColor], NSBackgroundColorAttributeName,
+ [self _originalFontB], NSFontAttributeName,
+ [NSColor whiteColor], NSForegroundColorAttributeName,
+ shadow, NSShadowAttributeName,
+ [NSNumber numberWithInt:NSUnderlineStyleSingle], NSStrikethroughStyleAttributeName,
+ [NSNumber numberWithInt:1], NSSuperscriptAttributeName,
+ [NSNumber numberWithInt:NSUnderlineStyleSingle], NSUnderlineStyleAttributeName,
+ nil];
+
+ [shadow release];
+
+#if 0
+
+NSObliquenessAttributeName /* float; skew to be applied to glyphs, default 0: no skew */
+ // font-style, but that is just an on-off switch
+
+NSExpansionAttributeName /* float; log of expansion factor to be applied to glyphs, default 0: no expansion */
+ // font-stretch?
+
+NSKernAttributeName /* float, amount to modify default kerning, if 0, kerning off */
+ // letter-spacing? probably not good enough
+
+NSUnderlineColorAttributeName /* NSColor, default nil: same as foreground color */
+NSStrikethroughColorAttributeName /* NSColor, default nil: same as foreground color */
+ // text-decoration-color?
+
+NSLigatureAttributeName /* int, default 1: default ligatures, 0: no ligatures, 2: all ligatures */
+NSBaselineOffsetAttributeName /* float, in points; offset from baseline, default 0 */
+NSStrokeWidthAttributeName /* float, in percent of font point size, default 0: no stroke; positive for stroke alone, negative for stroke and fill (a typical value for outlined text would be 3.0) */
+NSStrokeColorAttributeName /* NSColor, default nil: same as foreground color */
+ // need extensions?
+
+#endif
+
+ NSDictionary *a = [sender convertAttributes:oa];
+ NSDictionary *b = [sender convertAttributes:ob];
+
+ NSColor *ca = [a objectForKey:NSBackgroundColorAttributeName];
+ NSColor *cb = [b objectForKey:NSBackgroundColorAttributeName];
+ if (ca == cb) {
+ [style setBackgroundColor:[self _colorAsString:ca]];
+ }
+
+ [self _addToStyle:style fontA:[a objectForKey:NSFontAttributeName] fontB:[b objectForKey:NSFontAttributeName]];
+
+ ca = [a objectForKey:NSForegroundColorAttributeName];
+ cb = [b objectForKey:NSForegroundColorAttributeName];
+ if (ca == cb) {
+ [style setColor:[self _colorAsString:ca]];
+ }
+
+ NSShadow *sha = [a objectForKey:NSShadowAttributeName];
+ if (sha)
+ [style setTextShadow:[self _shadowAsString:sha]];
+ else if ([b objectForKey:NSShadowAttributeName] == nil)
+ [style setTextShadow:@"none"];
+
+ int sa = [[a objectForKey:NSStrikethroughStyleAttributeName] intValue];
+ int sb = [[b objectForKey:NSStrikethroughStyleAttributeName] intValue];
+ if (sa == sb) {
+ if (sa == NSUnderlineStyleNone)
+ [style setProperty:@"-khtml-text-decorations-in-effect" value:@"none" priority:@""];
+ // we really mean "no line-through" rather than "none"
+ else
+ [style setProperty:@"-khtml-text-decorations-in-effect" value:@"line-through" priority:@""];
+ // we really mean "add line-through" rather than "line-through"
+ }
+
+ sa = [[a objectForKey:NSSuperscriptAttributeName] intValue];
+ sb = [[b objectForKey:NSSuperscriptAttributeName] intValue];
+ if (sa == sb) {
+ if (sa > 0)
+ [style setVerticalAlign:@"super"];
+ else if (sa < 0)
+ [style setVerticalAlign:@"sub"];
+ else
+ [style setVerticalAlign:@"baseline"];
+ }
+
+ int ua = [[a objectForKey:NSUnderlineStyleAttributeName] intValue];
+ int ub = [[b objectForKey:NSUnderlineStyleAttributeName] intValue];
+ if (ua == ub) {
+ if (ua == NSUnderlineStyleNone)
+ [style setProperty:@"-khtml-text-decorations-in-effect" value:@"none" priority:@""];
+ // we really mean "no underline" rather than "none"
+ else
+ [style setProperty:@"-khtml-text-decorations-in-effect" value:@"underline" priority:@""];
+ // we really mean "add underline" rather than "underline"
+ }
+
+ return style;
+}
+
+- (void)changeAttributes:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ [self _applyStyleToSelection:[self _styleForAttributeChange:sender] withUndoAction:EditActionChangeAttributes];
+}
+
+- (DOMCSSStyleDeclaration *)_styleFromColorPanelWithSelector:(SEL)selector
+{
+ DOMCSSStyleDeclaration *style = [self _emptyStyle];
+
+ ASSERT([style respondsToSelector:selector]);
+ [style performSelector:selector withObject:[self _colorAsString:[[NSColorPanel sharedColorPanel] color]]];
+
+ return style;
+}
+
+- (EditAction)_undoActionFromColorPanelWithSelector:(SEL)selector
+{
+ if (selector == @selector(setBackgroundColor:))
+ return EditActionSetBackgroundColor;
+ return EditActionSetColor;
+}
+
+- (void)_changeCSSColorUsingSelector:(SEL)selector inRange:(DOMRange *)range
+{
+ DOMCSSStyleDeclaration *style = [self _styleFromColorPanelWithSelector:selector];
+ WebView *webView = [self _webView];
+ if ([[webView _editingDelegateForwarder] webView:webView shouldApplyStyle:style toElementsInDOMRange:range])
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->editor()->applyStyle(core(style), [self _undoActionFromColorPanelWithSelector:selector]);
+}
+
+- (void)changeDocumentBackgroundColor:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ // Mimicking NSTextView, this method sets the background color for the
+ // entire document. There is no NSTextView API for setting the background
+ // color on the selected range only. Note that this method is currently
+ // never called from the UI (see comment in changeColor:).
+ // FIXME: this actually has no effect when called, probably due to 3654850. _documentRange seems
+ // to do the right thing because it works in startSpeaking:, and I know setBackgroundColor: does the
+ // right thing because I tested it with [self _selectedRange].
+ // FIXME: This won't actually apply the style to the entire range here, because it ends up calling
+ // [bridge applyStyle:], which operates on the current selection. To make this work right, we'll
+ // need to save off the selection, temporarily set it to the entire range, make the change, then
+ // restore the old selection.
+ [self _changeCSSColorUsingSelector:@selector(setBackgroundColor:) inRange:[self _documentRange]];
+}
+
+- (void)changeColor:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ // FIXME: in NSTextView, this method calls changeDocumentBackgroundColor: when a
+ // private call has earlier been made by [NSFontFontEffectsBox changeColor:], see 3674493.
+ // AppKit will have to be revised to allow this to work with anything that isn't an
+ // NSTextView. However, this might not be required for Tiger, since the background-color
+ // changing box in the font panel doesn't work in Mail (3674481), though it does in TextEdit.
+ [self _applyStyleToSelection:[self _styleFromColorPanelWithSelector:@selector(setColor:)]
+ withUndoAction:EditActionSetColor];
+}
+
+- (void)_changeWordCaseWithSelector:(SEL)selector
+{
+ if (![self _canEdit])
+ return;
+
+ WebFrameBridge *bridge = [self _bridge];
+ [self selectWord:nil];
+ NSString *word = [[bridge selectedString] performSelector:selector];
+ // FIXME: Does this need a different action context other than "typed"?
+ if ([self _shouldReplaceSelectionWithText:word givenAction:WebViewInsertActionTyped])
+ [bridge replaceSelectionWithText:word selectReplacement:NO smartReplace:NO];
+}
+
+- (void)uppercaseWord:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ [self _changeWordCaseWithSelector:@selector(uppercaseString)];
+}
+
+- (void)lowercaseWord:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ [self _changeWordCaseWithSelector:@selector(lowercaseString)];
+}
+
+- (void)capitalizeWord:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ [self _changeWordCaseWithSelector:@selector(capitalizedString)];
+}
+
+- (void)complete:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ if (![self _canEdit])
+ return;
+ if (!_private->compController)
+ _private->compController = [[WebTextCompleteController alloc] initWithHTMLView:self];
+ [_private->compController doCompletion];
+}
+
+- (void)checkSpelling:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->editor()->advanceToNextMisspelling();
+}
+
+- (void)showGuessPanel:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ NSSpellChecker *checker = [NSSpellChecker sharedSpellChecker];
+ if (!checker) {
+ LOG_ERROR("No NSSpellChecker");
+ return;
+ }
+
+ NSPanel *spellingPanel = [checker spellingPanel];
+#ifndef BUILDING_ON_TIGER
+ // Post-Tiger, this menu item is a show/hide toggle, to match AppKit. Leave Tiger behavior alone
+ // to match rest of OS X.
+ if ([spellingPanel isVisible]) {
+ [spellingPanel orderOut:sender];
+ return;
+ }
+#endif
+
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->editor()->advanceToNextMisspelling(true);
+ [spellingPanel orderFront:sender];
+}
+
+- (void)_changeSpellingToWord:(NSString *)newWord
+{
+ if (![self _canEdit])
+ return;
+
+ // Don't correct to empty string. (AppKit checked this, we might as well too.)
+ if (![NSSpellChecker sharedSpellChecker]) {
+ LOG_ERROR("No NSSpellChecker");
+ return;
+ }
+
+ if ([newWord isEqualToString:@""])
+ return;
+
+ if ([self _shouldReplaceSelectionWithText:newWord givenAction:WebViewInsertActionPasted])
+ [[self _bridge] replaceSelectionWithText:newWord selectReplacement:YES smartReplace:NO];
+}
+
+- (void)changeSpelling:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ [self _changeSpellingToWord:[[sender selectedCell] stringValue]];
+}
+
+- (void)ignoreSpelling:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ NSSpellChecker *checker = [NSSpellChecker sharedSpellChecker];
+ if (!checker) {
+ LOG_ERROR("No NSSpellChecker");
+ return;
+ }
+
+ NSString *stringToIgnore = [sender stringValue];
+ unsigned int length = [stringToIgnore length];
+ if (stringToIgnore && length > 0) {
+ [checker ignoreWord:stringToIgnore inSpellDocumentWithTag:[[self _webView] spellCheckerDocumentTag]];
+ // FIXME: Need to clear misspelling marker if the currently selected word is the one we are to ignore?
+ }
+}
+
+- (void)performFindPanelAction:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ // Implementing this will probably require copying all of NSFindPanel.h and .m.
+ // We need *almost* the same thing as AppKit, but not quite.
+ LOG_ERROR("unimplemented");
+}
+
+- (void)startSpeaking:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ WebFrameBridge *bridge = [self _bridge];
+ DOMRange *range = [self _selectedRange];
+ if (!range || [range collapsed])
+ range = [self _documentRange];
+ [NSApp speakString:[bridge stringForRange:range]];
+}
+
+- (void)stopSpeaking:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ [NSApp stopSpeaking:sender];
+}
+
+- (void)toggleBaseWritingDirection:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ if (![self _canEdit])
+ return;
+
+ Frame* coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return;
+
+ const char* direction = "rtl";
+ switch (coreFrame->baseWritingDirectionForSelectionStart()) {
+ case NSWritingDirectionLeftToRight:
+ break;
+ case NSWritingDirectionRightToLeft:
+ direction = "ltr";
+ break;
+ // The writingDirectionForSelectionStart method will never return "natural". It
+ // will always return a concrete direction. So, keep the compiler happy, and assert not reached.
+ case NSWritingDirectionNatural:
+ ASSERT_NOT_REACHED();
+ break;
+ }
+
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->editor()->setBaseWritingDirection(direction);
+}
+
+- (void)changeBaseWritingDirection:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ if (![self _canEdit])
+ return;
+
+ NSWritingDirection writingDirection = static_cast<NSWritingDirection>([sender tag]);
+
+ // We disable the menu item that performs this action because we can't implement
+ // NSWritingDirectionNatural's behavior using CSS.
+ ASSERT(writingDirection != NSWritingDirectionNatural);
+
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->editor()->setBaseWritingDirection(writingDirection == NSWritingDirectionLeftToRight ? "ltr" : "rtl");
+}
+
+static BOOL writingDirectionKeyBindingsEnabled()
+{
+ NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
+ return [defaults boolForKey:@"NSAllowsBaseWritingDirectionKeyBindings"] || [defaults boolForKey:@"AppleTextDirection"];
+}
+
+- (void)_changeBaseWritingDirectionTo:(NSWritingDirection)direction
+{
+ if (![self _canEdit])
+ return;
+
+ static BOOL bindingsEnabled = writingDirectionKeyBindingsEnabled();
+
+ if (!bindingsEnabled) {
+ NSBeep();
+ return;
+ }
+
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->editor()->setBaseWritingDirection(direction == NSWritingDirectionLeftToRight ? "ltr" : "rtl");
+}
+
+- (void)changeBaseWritingDirectionToLTR:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ [self _changeBaseWritingDirectionTo:NSWritingDirectionLeftToRight];
+}
+
+- (void)changeBaseWritingDirectionToRTL:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ [self _changeBaseWritingDirectionTo:NSWritingDirectionRightToLeft];
+}
+
+#if 0
+
+// CSS does not have a way to specify an outline font, which may make this difficult to implement.
+// Maybe a special case of text-shadow?
+- (void)outline:(id)sender;
+
+// This is part of table support, which may be in NSTextView for Tiger.
+// It's probably simple to do the equivalent thing for WebKit.
+- (void)insertTable:(id)sender;
+
+// This could be important.
+- (void)toggleTraditionalCharacterShape:(id)sender;
+
+// I'm not sure what the equivalents of these in the web world are.
+- (void)insertLineSeparator:(id)sender;
+- (void)insertPageBreak:(id)sender;
+
+// These methods are not implemented in NSTextView yet at the time of this writing.
+- (void)changeCaseOfLetter:(id)sender;
+- (void)transposeWords:(id)sender;
+
+#endif
+
+// Super-hack alert.
+// Workaround for bug 3789278.
+
+// Returns a selector only if called while:
+// 1) first responder is self
+// 2) handling a key down event
+// 3) not yet inside keyDown: method
+// 4) key is an arrow key
+// The selector is the one that gets sent by -[NSWindow _processKeyboardUIKey] for this key.
+- (SEL)_arrowKeyDownEventSelectorIfPreprocessing
+{
+ NSWindow *w = [self window];
+ if ([w firstResponder] != self)
+ return NULL;
+ NSEvent *e = [w currentEvent];
+ if ([e type] != NSKeyDown)
+ return NULL;
+ if (e == _private->keyDownEvent)
+ return NULL;
+ NSString *s = [e charactersIgnoringModifiers];
+ if ([s length] == 0)
+ return NULL;
+ switch ([s characterAtIndex:0]) {
+ case NSDownArrowFunctionKey:
+ return @selector(moveDown:);
+ case NSLeftArrowFunctionKey:
+ return @selector(moveLeft:);
+ case NSRightArrowFunctionKey:
+ return @selector(moveRight:);
+ case NSUpArrowFunctionKey:
+ return @selector(moveUp:);
+ default:
+ return NULL;
+ }
+}
+
+// Returns NO instead of YES if called on the selector that the
+// _arrowKeyDownEventSelectorIfPreprocessing method returns.
+// This should only happen inside -[NSWindow _processKeyboardUIKey],
+// and together with the change below should cause that method
+// to return NO rather than handling the key.
+// Also set a 1-shot flag for the nextResponder check below.
+- (BOOL)respondsToSelector:(SEL)selector
+{
+ if (![super respondsToSelector:selector])
+ return NO;
+ SEL arrowKeySelector = [self _arrowKeyDownEventSelectorIfPreprocessing];
+ if (selector != arrowKeySelector)
+ return YES;
+ _private->nextResponderDisabledOnce = YES;
+ return NO;
+}
+
+// Returns nil instead of the next responder if called when the
+// one-shot flag is set, and _arrowKeyDownEventSelectorIfPreprocessing
+// returns something other than NULL. This should only happen inside
+// -[NSWindow _processKeyboardUIKey] and together with the change above
+// should cause that method to return NO rather than handling the key.
+- (NSResponder *)nextResponder
+{
+ BOOL disabled = _private->nextResponderDisabledOnce;
+ _private->nextResponderDisabledOnce = NO;
+ if (disabled && [self _arrowKeyDownEventSelectorIfPreprocessing] != NULL)
+ return nil;
+ return [super nextResponder];
+}
+
+// Despite its name, this is called at different times than windowDidBecomeKey is.
+// It takes into account all the other factors that determine when NSCell draws
+// with different tints, so it's the right call to use for control tints. We'd prefer
+// to do this with API. <rdar://problem/5136760>
+- (void)_windowChangedKeyState
+{
+ if (Frame* frame = core([self _frame]))
+ if (FrameView* view = frame->view())
+ view->updateControlTints();
+ [super _windowChangedKeyState];
+}
+
+- (void)otherMouseDown:(NSEvent *)event
+{
+ if ([event buttonNumber] == 2)
+ [self mouseDown:event];
+ else
+ [super otherMouseDown:event];
+}
+
+- (void)otherMouseDragged:(NSEvent *)event
+{
+ if ([event buttonNumber] == 2)
+ [self mouseDragged:event];
+ else
+ [super otherMouseDragged:event];
+}
+
+- (void)otherMouseUp:(NSEvent *)event
+{
+ if ([event buttonNumber] == 2)
+ [self mouseUp:event];
+ else
+ [super otherMouseUp:event];
+}
+
+@end
+
+@implementation WebHTMLView (WebTextSizing)
+
+- (IBAction)_makeTextSmaller:(id)sender
+{
+ [self _updateTextSizeMultiplier];
+}
+
+- (IBAction)_makeTextLarger:(id)sender
+{
+ [self _updateTextSizeMultiplier];
+}
+
+- (IBAction)_makeTextStandardSize:(id)sender
+{
+ [self _updateTextSizeMultiplier];
+}
+
+- (BOOL)_tracksCommonSizeFactor
+{
+ return YES;
+}
+
+- (void)_textSizeMultiplierChanged
+{
+ [self _updateTextSizeMultiplier];
+}
+
+// never sent because we track the common size factor
+- (BOOL)_canMakeTextSmaller
+{
+ ASSERT_NOT_REACHED();
+ return NO;
+}
+
+- (BOOL)_canMakeTextLarger
+{
+ ASSERT_NOT_REACHED();
+ return NO;
+}
+
+- (BOOL)_canMakeTextStandardSize
+{
+ ASSERT_NOT_REACHED();
+ return NO;
+}
+
+@end
+
+@implementation NSArray (WebHTMLView)
+
+- (void)_web_makePluginViewsPerformSelector:(SEL)selector withObject:(id)object
+{
+#ifndef __LP64__
+ NSEnumerator *enumerator = [self objectEnumerator];
+ WebNetscapePluginEmbeddedView *view;
+ while ((view = [enumerator nextObject]) != nil)
+ if ([view isKindOfClass:[WebNetscapePluginEmbeddedView class]])
+ [view performSelector:selector withObject:object];
+#endif
+}
+
+@end
+
+@implementation WebHTMLView (WebInternal)
+
+- (void)_selectionChanged
+{
+ [self _updateSelectionForInputManager];
+ [self _updateFontPanel];
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->editor()->setStartNewKillRingSequence(true);
+}
+
+- (void)_updateFontPanel
+{
+ // FIXME: NSTextView bails out if becoming or resigning first responder, for which it has ivar flags. Not
+ // sure if we need to do something similar.
+
+ if (![self _canEdit])
+ return;
+
+ NSWindow *window = [self window];
+ // FIXME: is this first-responder check correct? What happens if a subframe is editable and is first responder?
+ if ([NSApp keyWindow] != window || [window firstResponder] != self)
+ return;
+
+ BOOL multiple = NO;
+ NSFont *font = [[self _bridge] fontForSelection:&multiple];
+
+ // FIXME: for now, return a bogus font that distinguishes the empty selection from the non-empty
+ // selection. We should be able to remove this once the rest of this code works properly.
+ if (font == nil)
+ font = [self _hasSelection] ? [NSFont menuFontOfSize:23] : [NSFont toolTipsFontOfSize:17];
+ ASSERT(font != nil);
+
+ NSFontManager *fm = [NSFontManager sharedFontManager];
+ [fm setSelectedFont:font isMultiple:multiple];
+
+ // FIXME: we don't keep track of selected attributes, or set them on the font panel. This
+ // appears to have no effect on the UI. E.g., underlined text in Mail or TextEdit is
+ // not reflected in the font panel. Maybe someday this will change.
+}
+
+- (BOOL)_canSmartCopyOrDelete
+{
+ return [[self _webView] smartInsertDeleteEnabled] && [[self _bridge] selectionGranularity] == WordGranularity;
+}
+
+- (NSEvent *)_mouseDownEvent
+{
+ return _private->mouseDownEvent;
+}
+
+#ifndef __LP64__
+- (void)_pauseNullEventsForAllNetscapePlugins
+{
+ NSArray *subviews = [self subviews];
+ unsigned int subviewCount = [subviews count];
+ unsigned int subviewIndex;
+
+ for (subviewIndex = 0; subviewIndex < subviewCount; subviewIndex++) {
+ NSView *subview = [subviews objectAtIndex:subviewIndex];
+ if ([subview isKindOfClass:[WebBaseNetscapePluginView class]])
+ [(WebBaseNetscapePluginView *)subview stopNullEvents];
+ }
+}
+#endif
+
+#ifndef __LP64__
+- (void)_resumeNullEventsForAllNetscapePlugins
+{
+ NSArray *subviews = [self subviews];
+ unsigned int subviewCount = [subviews count];
+ unsigned int subviewIndex;
+
+ for (subviewIndex = 0; subviewIndex < subviewCount; subviewIndex++) {
+ NSView *subview = [subviews objectAtIndex:subviewIndex];
+ if ([subview isKindOfClass:[WebBaseNetscapePluginView class]])
+ [(WebBaseNetscapePluginView *)subview restartNullEvents];
+ }
+}
+#endif
+
+- (id<WebHTMLHighlighter>)_highlighterForType:(NSString*)type
+{
+ return [_private->highlighters objectForKey:type];
+}
+
+- (WebFrame *)_frame
+{
+ return [_private->dataSource webFrame];
+}
+
+- (void)paste:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ RetainPtr<WebHTMLView> selfProtector = self;
+ RefPtr<Frame> coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return;
+ if (coreFrame->editor()->tryDHTMLPaste())
+ return; // DHTML did the whole operation
+ if (!coreFrame->editor()->canPaste())
+ return;
+ if (coreFrame->selectionController()->isContentRichlyEditable())
+ [self _pasteWithPasteboard:[NSPasteboard generalPasteboard] allowPlainText:YES];
+ else
+ coreFrame->editor()->pasteAsPlainText();
+}
+
+- (void)pasteAsPlainText:(id)sender
+{
+ COMMAND_PROLOGUE
+
+ if (![self _canEdit])
+ return;
+ [self _pasteAsPlainTextWithPasteboard:[NSPasteboard generalPasteboard]];
+}
+
+- (void)closeIfNotCurrentView
+{
+ if ([[[self _frame] frameView] documentView] != self)
+ [self close];
+}
+
+- (DOMDocumentFragment*)_documentFragmentFromPasteboard:(NSPasteboard *)pasteboard
+{
+ return [self _documentFragmentFromPasteboard:pasteboard inContext:nil allowPlainText:NO];
+}
+
+#ifndef BUILDING_ON_TIGER
+
+- (BOOL)isGrammarCheckingEnabled
+{
+ // FIXME 4799134: WebView is the bottleneck for this grammar-checking logic, but we must implement the method here because
+ // the AppKit code checks the first responder.
+ return [[self _webView] isGrammarCheckingEnabled];
+}
+
+- (void)setGrammarCheckingEnabled:(BOOL)flag
+{
+ // FIXME 4799134: WebView is the bottleneck for this grammar-checking logic, but we must implement the method here because
+ // the AppKit code checks the first responder.
+ [[self _webView] setGrammarCheckingEnabled:flag];
+}
+
+- (void)toggleGrammarChecking:(id)sender
+{
+ // FIXME 4799134: WebView is the bottleneck for this grammar-checking logic, but we must implement the method here because
+ // the AppKit code checks the first responder.
+ [[self _webView] toggleGrammarChecking:sender];
+}
+
+
+static CGPoint coreGraphicsScreenPointForAppKitScreenPoint(NSPoint point)
+{
+ NSArray *screens = [NSScreen screens];
+
+ if ([screens count] == 0) {
+ // You could theoretically get here if running with no monitor, in which case it doesn't matter
+ // much where the "on-screen" point is.
+ return CGPointMake(point.x, point.y);
+ }
+
+ // Flip the y coordinate from the top of the menu bar screen -- see 4636390
+ return CGPointMake(point.x, NSMaxY([[screens objectAtIndex:0] frame]) - point.y);
+}
+
+#endif
+
+- (void)_lookUpInDictionaryFromMenu:(id)sender
+{
+ // Dictionary API will accept a whitespace-only string and display UI as if it were real text,
+ // so bail out early to avoid that.
+ if ([[[self selectedString] _webkit_stringByTrimmingWhitespace] length] == 0)
+ return;
+
+ // We soft link to get the function that displays the dictionary (either pop-up window or app) to avoid the performance
+ // penalty of linking to another framework. This function changed signature as well as framework between Tiger and Leopard,
+ // so the two cases are handled separately.
+
+#ifdef BUILDING_ON_TIGER
+ typedef OSStatus (*ServiceWindowShowFunction)(id inWordString, NSRect inWordBoundary, UInt16 inLineDirection);
+ const char *frameworkPath = "/System/Library/Frameworks/ApplicationServices.framework/Frameworks/LangAnalysis.framework/LangAnalysis";
+ const char *functionName = "DCMDictionaryServiceWindowShow";
+#else
+ typedef void (*ServiceWindowShowFunction)(id unusedDictionaryRef, id inWordString, CFRange selectionRange, id unusedFont, CGPoint textOrigin, Boolean verticalText, id unusedTransform);
+ const char *frameworkPath = "/System/Library/Frameworks/Carbon.framework/Frameworks/HIToolbox.framework/HIToolbox";
+ const char *functionName = "HIDictionaryWindowShow";
+#endif
+
+ static bool lookedForFunction = false;
+ static ServiceWindowShowFunction dictionaryServiceWindowShow = NULL;
+
+ if (!lookedForFunction) {
+ void* langAnalysisFramework = dlopen(frameworkPath, RTLD_LAZY);
+ ASSERT(langAnalysisFramework);
+ if (langAnalysisFramework)
+ dictionaryServiceWindowShow = (ServiceWindowShowFunction)dlsym(langAnalysisFramework, functionName);
+ lookedForFunction = true;
+ }
+
+ ASSERT(dictionaryServiceWindowShow);
+ if (!dictionaryServiceWindowShow) {
+ NSLog(@"Couldn't find the %s function in %s", functionName, frameworkPath);
+ return;
+ }
+
+ NSAttributedString *attrString = [self selectedAttributedString];
+
+ Frame* coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return;
+
+#ifdef BUILDING_ON_TIGER
+ // FIXME: must check for right-to-left here
+ NSWritingDirection writingDirection = NSWritingDirectionLeftToRight;
+
+ // FIXME: the dictionary API expects the rect for the first line of selection. Passing
+ // the rect for the entire selection, as we do here, positions the pop-up window near
+ // the bottom of the selection rather than at the selected word.
+ NSRect rect = [self convertRect:coreFrame->selectionRect() toView:nil];
+ rect.origin = [[self window] convertBaseToScreen:rect.origin];
+ NSData *data = [attrString RTFFromRange:NSMakeRange(0, [attrString length]) documentAttributes:nil];
+ dictionaryServiceWindowShow(data, rect, (writingDirection == NSWritingDirectionRightToLeft) ? 1 : 0);
+#else
+ // The HIDictionaryWindowShow function requires the origin, in CG screen coordinates, of the first character of text in the selection.
+ // FIXME 4945808: We approximate this in a way that works well when a single word is selected, and less well in some other cases
+ // (but no worse than we did in Tiger)
+ NSRect rect = coreFrame->selectionRect();
+
+ NSDictionary *attributes = [attrString fontAttributesInRange:NSMakeRange(0,1)];
+ NSFont *font = [attributes objectForKey:NSFontAttributeName];
+ if (font)
+ rect.origin.y += [font ascender];
+
+ NSPoint windowPoint = [self convertPoint:rect.origin toView:nil];
+ NSPoint screenPoint = [[self window] convertBaseToScreen:windowPoint];
+
+ dictionaryServiceWindowShow(nil, attrString, CFRangeMake(0, [attrString length]), nil,
+ coreGraphicsScreenPointForAppKitScreenPoint(screenPoint), false, nil);
+#endif
+}
+
+- (void)_hoverFeedbackSuspendedChanged
+{
+ [self _updateMouseoverWithFakeEvent];
+}
+
+- (BOOL)_interceptEditingKeyEvent:(KeyboardEvent*)event shouldSaveCommand:(BOOL)shouldSave
+{
+ // Ask AppKit to process the key event -- it will call back with either insertText or doCommandBySelector.
+ WebHTMLViewInterpretKeyEventsParameters parameters;
+ parameters.eventWasHandled = false;
+ parameters.shouldSaveCommand = shouldSave;
+ // If we're intercepting the initial IM call we assume that the IM has consumed the event,
+ // and only change this assumption if one of the NSTextInput/Responder callbacks is used.
+ // We assume the IM will *not* consume hotkey sequences
+ parameters.consumedByIM = !event->metaKey() && shouldSave;
+
+ if (const PlatformKeyboardEvent* platformEvent = event->keyEvent()) {
+ NSEvent *macEvent = platformEvent->macEvent();
+ if ([macEvent type] == NSKeyDown && [_private->compController filterKeyDown:macEvent])
+ return true;
+
+ if ([macEvent type] == NSFlagsChanged)
+ return false;
+
+ parameters.event = event;
+ _private->interpretKeyEventsParameters = &parameters;
+ _private->receivedNOOP = NO;
+ const Vector<KeypressCommand>& commands = event->keypressCommands();
+ bool hasKeypressCommand = !commands.isEmpty();
+
+ // FIXME: interpretKeyEvents doesn't match application key equivalents (such as Cmd+A),
+ // and sends noop: for those. As a result, we don't handle those from within WebCore,
+ // but send a full sequence of DOM events, including an unneeded keypress.
+ if (parameters.shouldSaveCommand || !hasKeypressCommand)
+ [self interpretKeyEvents:[NSArray arrayWithObject:macEvent]];
+ else {
+ size_t size = commands.size();
+ // Are there commands that would just cause text insertion if executed via Editor?
+ // WebKit doesn't have enough information about mode to decide how they should be treated, so we leave it upon WebCore
+ // to either handle them immediately (e.g. Tab that changes focus) or let a keypress event be generated
+ // (e.g. Tab that inserts a Tab character, or Enter).
+ bool haveTextInsertionCommands = false;
+ for (size_t i = 0; i < size; ++i) {
+ if ([self coreCommandBySelector:NSSelectorFromString(commands[i].commandName)].isTextInsertion())
+ haveTextInsertionCommands = true;
+ }
+ if (!haveTextInsertionCommands || platformEvent->type() == PlatformKeyboardEvent::Char)
+ for (size_t i = 0; i < size; ++i)
+ if (commands[i].commandName == "insertText:")
+ [self insertText:commands[i].text];
+ else
+ [self doCommandBySelector:NSSelectorFromString(commands[i].commandName)];
+ }
+ _private->interpretKeyEventsParameters = 0;
+ }
+ return (!_private->receivedNOOP && parameters.eventWasHandled) || parameters.consumedByIM;
+}
+
+- (WebCore::CachedImage*)promisedDragTIFFDataSource
+{
+ return _private->promisedDragTIFFDataSource;
+}
+
+- (void)setPromisedDragTIFFDataSource:(WebCore::CachedImage*)source
+{
+ if (source)
+ source->ref(promisedDataClient());
+
+ if (_private->promisedDragTIFFDataSource)
+ _private->promisedDragTIFFDataSource->deref(promisedDataClient());
+ _private->promisedDragTIFFDataSource = source;
+}
+
+#undef COMMAND_PROLOGUE
+
+- (void)_layoutIfNeeded
+{
+ ASSERT(!_private->subviewsSetAside);
+
+ if ([[self _bridge] needsLayout])
+ _private->needsLayout = YES;
+ if (_private->needsToApplyStyles || _private->needsLayout)
+ [self layout];
+}
+
+- (void)_web_layoutIfNeededRecursive
+{
+ [self _layoutIfNeeded];
+
+#ifndef NDEBUG
+ _private->enumeratingSubviews = YES;
+#endif
+
+ NSMutableArray *descendantWebHTMLViews = [[NSMutableArray alloc] init];
+
+ [self _web_addDescendantWebHTMLViewsToArray:descendantWebHTMLViews];
+
+ unsigned count = [descendantWebHTMLViews count];
+ for (unsigned i = 0; i < count; ++i)
+ [[descendantWebHTMLViews objectAtIndex:i] _layoutIfNeeded];
+
+ [descendantWebHTMLViews release];
+
+#ifndef NDEBUG
+ _private->enumeratingSubviews = NO;
+#endif
+}
+
+@end
+
+@implementation WebHTMLView (WebNSTextInputSupport)
+
+- (NSArray *)validAttributesForMarkedText
+{
+ static NSArray *validAttributes;
+ if (!validAttributes) {
+ validAttributes = [[NSArray alloc] initWithObjects:
+ NSUnderlineStyleAttributeName, NSUnderlineColorAttributeName,
+ NSMarkedClauseSegmentAttributeName, NSTextInputReplacementRangeAttributeName, nil];
+ // NSText also supports the following attributes, but it's
+ // hard to tell which are really required for text input to
+ // work well; I have not seen any input method make use of them yet.
+ // NSFontAttributeName, NSForegroundColorAttributeName,
+ // NSBackgroundColorAttributeName, NSLanguageAttributeName.
+ CFRetain(validAttributes);
+ }
+ LOG(TextInput, "validAttributesForMarkedText -> (...)");
+ return validAttributes;
+}
+
+// Utility function to make sure we don't return anything through the NSTextInput
+// API when an editable region is not currently focused.
+static BOOL isTextInput(Frame* coreFrame)
+{
+ return coreFrame && !coreFrame->selectionController()->isNone() && coreFrame->selectionController()->isContentEditable();
+}
+
+// Work around for <rdar://problem/5522011>
+// Some input methods do not properly behave when TSM is in secure input mode
+// which can allow the password to be made visible. We prevent this by overriding
+// the active context if a password field is focused.
+- (NSInputContext *)inputContext
+{
+ Frame* coreFrame = core([self _frame]);
+ if (coreFrame && coreFrame->selectionController()->isInPasswordField())
+ return nil;
+ return [super inputContext];
+}
+
+- (NSAttributedString *)textStorage
+{
+ if (!isTextInput(core([self _frame]))) {
+ LOG(TextInput, "textStorage -> nil");
+ return nil;
+ }
+ NSAttributedString *result = [self attributedSubstringFromRange:NSMakeRange(0, UINT_MAX)];
+
+ LOG(TextInput, "textStorage -> \"%@\"", result ? [result string] : @"");
+
+ // We have to return an empty string rather than null to prevent TSM from calling -string
+ return result ? result : [[[NSAttributedString alloc] initWithString:@""] autorelease];
+}
+
+- (NSUInteger)characterIndexForPoint:(NSPoint)thePoint
+{
+ NSWindow *window = [self window];
+ WebFrameBridge *bridge = [self _bridge];
+
+ if (window)
+ thePoint = [window convertScreenToBase:thePoint];
+ thePoint = [self convertPoint:thePoint fromView:nil];
+
+ DOMRange *range = [bridge characterRangeAtPoint:thePoint];
+ if (!range) {
+ LOG(TextInput, "characterIndexForPoint:(%f, %f) -> NSNotFound", thePoint.x, thePoint.y);
+ return NSNotFound;
+ }
+
+ unsigned result = [bridge convertDOMRangeToNSRange:range].location;
+ LOG(TextInput, "characterIndexForPoint:(%f, %f) -> %u", thePoint.x, thePoint.y, result);
+ return result;
+}
+
+- (NSRect)firstRectForCharacterRange:(NSRange)theRange
+{
+ WebFrameBridge *bridge = [self _bridge];
+
+ // Just to match NSTextView's behavior. Regression tests cannot detect this;
+ // to reproduce, use a test application from http://bugs.webkit.org/show_bug.cgi?id=4682
+ // (type something; try ranges (1, -1) and (2, -1).
+ if ((theRange.location + theRange.length < theRange.location) && (theRange.location + theRange.length != 0))
+ theRange.length = 0;
+
+ DOMRange *range = [bridge convertNSRangeToDOMRange:theRange];
+ if (!range) {
+ LOG(TextInput, "firstRectForCharacterRange:(%u, %u) -> (0, 0, 0, 0)", theRange.location, theRange.length);
+ return NSMakeRect(0, 0, 0, 0);
+ }
+
+ ASSERT([range startContainer]);
+ ASSERT([range endContainer]);
+
+ NSRect resultRect = [bridge firstRectForDOMRange:range];
+ resultRect = [self convertRect:resultRect toView:nil];
+
+ NSWindow *window = [self window];
+ if (window)
+ resultRect.origin = [window convertBaseToScreen:resultRect.origin];
+
+ LOG(TextInput, "firstRectForCharacterRange:(%u, %u) -> (%f, %f, %f, %f)", theRange.location, theRange.length, resultRect.origin.x, resultRect.origin.y, resultRect.size.width, resultRect.size.height);
+ return resultRect;
+}
+
+- (NSRange)selectedRange
+{
+ if (!isTextInput(core([self _frame]))) {
+ LOG(TextInput, "selectedRange -> (NSNotFound, 0)");
+ return NSMakeRange(NSNotFound, 0);
+ }
+ NSRange result = [[self _bridge] selectedNSRange];
+
+ LOG(TextInput, "selectedRange -> (%u, %u)", result.location, result.length);
+ return result;
+}
+
+- (NSRange)markedRange
+{
+ NSRange result = [[self _bridge] markedTextNSRange];
+ LOG(TextInput, "markedRange -> (%u, %u)", result.location, result.length);
+ return result;
+}
+
+- (NSAttributedString *)attributedSubstringFromRange:(NSRange)nsRange
+{
+ if (!isTextInput(core([self _frame]))) {
+ LOG(TextInput, "attributedSubstringFromRange:(%u, %u) -> nil", nsRange.location, nsRange.length);
+ return nil;
+ }
+ WebFrameBridge *bridge = [self _bridge];
+ DOMRange *domRange = [bridge convertNSRangeToDOMRange:nsRange];
+ if (!domRange) {
+ LOG(TextInput, "attributedSubstringFromRange:(%u, %u) -> nil", nsRange.location, nsRange.length);
+ return nil;
+ }
+
+ NSAttributedString *result = [NSAttributedString _web_attributedStringFromRange:core(domRange)];
+
+ // [NSAttributedString(WebKitExtras) _web_attributedStringFromRange:] insists on inserting a trailing
+ // whitespace at the end of the string which breaks the ATOK input method. <rdar://problem/5400551>
+ // To work around this we truncate the resultant string to the correct length.
+ if ([result length] > nsRange.length) {
+ ASSERT([result length] == nsRange.length + 1);
+ ASSERT([[result string] characterAtIndex:nsRange.length] == '\n' || [[result string] characterAtIndex:nsRange.length] == ' ');
+ result = [result attributedSubstringFromRange:NSMakeRange(0, nsRange.length)];
+ }
+ LOG(TextInput, "attributedSubstringFromRange:(%u, %u) -> \"%@\"", nsRange.location, nsRange.length, [result string]);
+ return result;
+}
+
+// test for 10.4 because of <rdar://problem/4243463>
+#ifdef BUILDING_ON_TIGER
+- (long)conversationIdentifier
+{
+ return (long)self;
+}
+#else
+- (NSInteger)conversationIdentifier
+{
+ return (NSInteger)self;
+}
+#endif
+
+- (BOOL)hasMarkedText
+{
+ Frame* coreFrame = core([self _frame]);
+ BOOL result = coreFrame && coreFrame->editor()->hasComposition();
+ LOG(TextInput, "hasMarkedText -> %u", result);
+ return result;
+}
+
+- (void)unmarkText
+{
+ LOG(TextInput, "unmarkText");
+
+ // Use pointer to get parameters passed to us by the caller of interpretKeyEvents.
+ WebHTMLViewInterpretKeyEventsParameters* parameters = _private->interpretKeyEventsParameters;
+ _private->interpretKeyEventsParameters = 0;
+
+ if (parameters) {
+ parameters->eventWasHandled = YES;
+ parameters->consumedByIM = NO;
+ }
+
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->editor()->confirmComposition();
+}
+
+static void extractUnderlines(NSAttributedString *string, Vector<CompositionUnderline>& result)
+{
+ int length = [[string string] length];
+
+ int i = 0;
+ while (i < length) {
+ NSRange range;
+ NSDictionary *attrs = [string attributesAtIndex:i longestEffectiveRange:&range inRange:NSMakeRange(i, length - i)];
+
+ if (NSNumber *style = [attrs objectForKey:NSUnderlineStyleAttributeName]) {
+ Color color = Color::black;
+ if (NSColor *colorAttr = [attrs objectForKey:NSUnderlineColorAttributeName])
+ color = colorFromNSColor([colorAttr colorUsingColorSpaceName:NSDeviceRGBColorSpace]);
+ result.append(CompositionUnderline(range.location, NSMaxRange(range), color, [style intValue] > 1));
+ }
+
+ i = range.location + range.length;
+ }
+}
+
+- (void)setMarkedText:(id)string selectedRange:(NSRange)newSelRange
+{
+ BOOL isAttributedString = [string isKindOfClass:[NSAttributedString class]]; // Otherwise, NSString
+
+ LOG(TextInput, "setMarkedText:\"%@\" selectedRange:(%u, %u)", isAttributedString ? [string string] : string, newSelRange.location, newSelRange.length);
+
+ // Use pointer to get parameters passed to us by the caller of interpretKeyEvents.
+ WebHTMLViewInterpretKeyEventsParameters* parameters = _private->interpretKeyEventsParameters;
+ _private->interpretKeyEventsParameters = 0;
+
+ if (parameters) {
+ parameters->eventWasHandled = YES;
+ parameters->consumedByIM = NO;
+ }
+
+ Frame* coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return;
+
+ if (![self _isEditable])
+ return;
+
+ Vector<CompositionUnderline> underlines;
+ NSString *text = string;
+
+ if (isAttributedString) {
+ unsigned markedTextLength = [(NSString *)string length];
+ NSString *rangeString = [string attribute:NSTextInputReplacementRangeAttributeName atIndex:0 longestEffectiveRange:NULL inRange:NSMakeRange(0, markedTextLength)];
+ LOG(TextInput, " ReplacementRange: %@", rangeString);
+ // The AppKit adds a 'secret' property to the string that contains the replacement range.
+ // The replacement range is the range of the the text that should be replaced with the new string.
+ if (rangeString)
+ [[self _bridge] selectNSRange:NSRangeFromString(rangeString)];
+
+ text = [string string];
+ extractUnderlines(string, underlines);
+ }
+
+ coreFrame->editor()->setComposition(text, underlines, newSelRange.location, NSMaxRange(newSelRange));
+}
+
+- (void)doCommandBySelector:(SEL)selector
+{
+ LOG(TextInput, "doCommandBySelector:\"%s\"", sel_getName(selector));
+
+ // Use pointer to get parameters passed to us by the caller of interpretKeyEvents.
+ // The same call to interpretKeyEvents can do more than one command.
+ WebHTMLViewInterpretKeyEventsParameters* parameters = _private->interpretKeyEventsParameters;
+ if (parameters)
+ parameters->consumedByIM = NO;
+
+ if (selector == @selector(noop:)) {
+ _private->receivedNOOP = YES;
+ return;
+ }
+
+ KeyboardEvent* event = parameters ? parameters->event : 0;
+ bool shouldSaveCommand = parameters && parameters->shouldSaveCommand;
+
+ if (event && shouldSaveCommand)
+ event->keypressCommands().append(KeypressCommand(NSStringFromSelector(selector)));
+ else {
+ // Make sure that only direct calls to doCommandBySelector: see the parameters by setting to 0.
+ _private->interpretKeyEventsParameters = 0;
+
+ bool eventWasHandled = true;
+
+ WebView *webView = [self _webView];
+ Frame* coreFrame = core([self _frame]);
+ if (![[webView _editingDelegateForwarder] webView:webView doCommandBySelector:selector] && coreFrame) {
+ Editor::Command command = [self coreCommandBySelector:selector];
+ if (command.isSupported())
+ eventWasHandled = command.execute(event);
+ else {
+ _private->selectorForDoCommandBySelector = selector;
+ [super doCommandBySelector:selector];
+ _private->selectorForDoCommandBySelector = 0;
+ }
+ }
+
+ if (parameters)
+ parameters->eventWasHandled = eventWasHandled;
+
+ // Restore the parameters so that other calls to doCommandBySelector: see them,
+ // and other commands can participate in setting the "eventWasHandled" flag.
+ _private->interpretKeyEventsParameters = parameters;
+ }
+}
+
+- (void)insertText:(id)string
+{
+ BOOL isAttributedString = [string isKindOfClass:[NSAttributedString class]]; // Otherwise, NSString
+
+ LOG(TextInput, "insertText:\"%@\"", isAttributedString ? [string string] : string);
+
+ WebHTMLViewInterpretKeyEventsParameters* parameters = _private->interpretKeyEventsParameters;
+ _private->interpretKeyEventsParameters = 0;
+ if (parameters)
+ parameters->consumedByIM = NO;
+
+ // We don't support inserting an attributed string but input methods don't appear to require this.
+ RefPtr<Frame> coreFrame = core([self _frame]);
+ NSString *text;
+ bool isFromInputMethod = coreFrame && coreFrame->editor()->hasComposition();
+ if (isAttributedString) {
+ text = [string string];
+ // We deal with the NSTextInputReplacementRangeAttributeName attribute from NSAttributedString here
+ // simply because it is used by at least one Input Method -- it corresonds to the kEventParamTextInputSendReplaceRange
+ // event in TSM. This behaviour matches that of -[WebHTMLView setMarkedText:selectedRange:] when it receives an
+ // NSAttributedString
+ NSString *rangeString = [string attribute:NSTextInputReplacementRangeAttributeName atIndex:0 longestEffectiveRange:NULL inRange:NSMakeRange(0, [text length])];
+ LOG(TextInput, " ReplacementRange: %@", rangeString);
+ if (rangeString) {
+ [[self _bridge] selectNSRange:NSRangeFromString(rangeString)];
+ isFromInputMethod = YES;
+ }
+ } else
+ text = string;
+
+ bool eventHandled = false;
+ if ([text length]) {
+ KeyboardEvent* event = parameters ? parameters->event : 0;
+
+ // insertText can be called from an input method or from normal key event processing
+ // If its from normal key event processing, we may need to save the action to perform it later.
+ // If its from an input method, then we should go ahead and insert the text now.
+ // We assume it's from the input method if we have marked text.
+ // FIXME: In theory, this could be wrong for some input methods, so we should try to find
+ // another way to determine if the call is from the input method
+ bool shouldSaveCommand = parameters && parameters->shouldSaveCommand;
+ if (event && shouldSaveCommand && !isFromInputMethod) {
+ event->keypressCommands().append(KeypressCommand("insertText:", text));
+ _private->interpretKeyEventsParameters = parameters;
+ return;
+ }
+
+ String eventText = text;
+ eventText.replace(NSBackTabCharacter, NSTabCharacter); // same thing is done in KeyEventMac.mm in WebCore
+ if (coreFrame) {
+ if (!coreFrame->editor()->hasComposition())
+ eventHandled = coreFrame->editor()->insertText(eventText, event);
+ else {
+ eventHandled = true;
+ coreFrame->editor()->confirmComposition(eventText);
+ }
+ }
+ }
+
+ if (!parameters)
+ return;
+
+ if (isFromInputMethod) {
+ // Allow doCommandBySelector: to be called after insertText: by resetting interpretKeyEventsParameters
+ _private->interpretKeyEventsParameters = parameters;
+ parameters->consumedByIM = YES;
+ return;
+ }
+
+ parameters->eventWasHandled = eventHandled;
+}
+
+- (void)_updateSelectionForInputManager
+{
+ Frame* coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return;
+
+ if (!coreFrame->editor()->hasComposition())
+ return;
+
+ if (coreFrame->editor()->ignoreCompositionSelectionChange())
+ return;
+
+ unsigned start;
+ unsigned end;
+ if (coreFrame->editor()->getCompositionSelection(start, end))
+ [[NSInputManager currentInputManager] markedTextSelectionChanged:NSMakeRange(start, end - start) client:self];
+ else {
+ coreFrame->editor()->confirmCompositionWithoutDisturbingSelection();
+ [[NSInputManager currentInputManager] markedTextAbandoned:self];
+ }
+}
+
+@end
+
+/*
+ This class runs the show for handing the complete: NSTextView operation. It counts on its HTML view
+ to call endRevertingChange: whenever the current completion needs to be aborted.
+
+ The class is in one of two modes: PopupWindow showing, or not. It is shown when a completion yields
+ more than one match. If a completion yields one or zero matches, it is not shown, and **there is no
+ state carried across to the next completion**.
+ */
+
+@implementation WebTextCompleteController
+
+- (id)initWithHTMLView:(WebHTMLView *)view
+{
+ self = [super init];
+ if (!self)
+ return nil;
+ _view = view;
+ return self;
+}
+
+- (void)dealloc
+{
+ [_popupWindow release];
+ [_completions release];
+ [_originalString release];
+
+ [super dealloc];
+}
+
+- (void)_insertMatch:(NSString *)match
+{
+ // FIXME: 3769654 - We should preserve case of string being inserted, even in prefix (but then also be
+ // able to revert that). Mimic NSText.
+ WebFrameBridge *bridge = [_view _bridge];
+ NSString *newText = [match substringFromIndex:prefixLength];
+ [bridge replaceSelectionWithText:newText selectReplacement:YES smartReplace:NO];
+}
+
+// mostly lifted from NSTextView_KeyBinding.m
+- (void)_buildUI
+{
+ NSRect scrollFrame = NSMakeRect(0, 0, 100, 100);
+ NSRect tableFrame = NSZeroRect;
+ tableFrame.size = [NSScrollView contentSizeForFrameSize:scrollFrame.size hasHorizontalScroller:NO hasVerticalScroller:YES borderType:NSNoBorder];
+ // Added cast to work around problem with multiple Foundation initWithIdentifier: methods with different parameter types.
+ NSTableColumn *column = [(NSTableColumn *)[NSTableColumn alloc] initWithIdentifier:[NSNumber numberWithInt:0]];
+ [column setWidth:tableFrame.size.width];
+ [column setEditable:NO];
+
+ _tableView = [[NSTableView alloc] initWithFrame:tableFrame];
+ [_tableView setAutoresizingMask:NSViewWidthSizable];
+ [_tableView addTableColumn:column];
+ [column release];
+ [_tableView setGridStyleMask:NSTableViewGridNone];
+ [_tableView setCornerView:nil];
+ [_tableView setHeaderView:nil];
+ [_tableView setColumnAutoresizingStyle:NSTableViewUniformColumnAutoresizingStyle];
+ [_tableView setDelegate:self];
+ [_tableView setDataSource:self];
+ [_tableView setTarget:self];
+ [_tableView setDoubleAction:@selector(tableAction:)];
+
+ NSScrollView *scrollView = [[NSScrollView alloc] initWithFrame:scrollFrame];
+ [scrollView setBorderType:NSNoBorder];
+ [scrollView setHasVerticalScroller:YES];
+ [scrollView setAutoresizingMask:NSViewWidthSizable | NSViewHeightSizable];
+ [scrollView setDocumentView:_tableView];
+ [_tableView release];
+
+ _popupWindow = [[NSWindow alloc] initWithContentRect:scrollFrame styleMask:NSBorderlessWindowMask backing:NSBackingStoreBuffered defer:NO];
+ [_popupWindow setAlphaValue:0.88f];
+ [_popupWindow setContentView:scrollView];
+ [scrollView release];
+ [_popupWindow setHasShadow:YES];
+ [_popupWindow setOneShot:YES];
+ [_popupWindow _setForceActiveControls:YES];
+ [_popupWindow setReleasedWhenClosed:NO];
+}
+
+// mostly lifted from NSTextView_KeyBinding.m
+- (void)_placePopupWindow:(NSPoint)topLeft
+{
+ int numberToShow = [_completions count];
+ if (numberToShow > 20) {
+ numberToShow = 20;
+ }
+
+ NSRect windowFrame;
+ NSPoint wordStart = topLeft;
+ windowFrame.origin = [[_view window] convertBaseToScreen:[_view convertPoint:wordStart toView:nil]];
+ windowFrame.size.height = numberToShow * [_tableView rowHeight] + (numberToShow + 1) * [_tableView intercellSpacing].height;
+ windowFrame.origin.y -= windowFrame.size.height;
+ NSDictionary *attributes = [NSDictionary dictionaryWithObjectsAndKeys:[NSFont systemFontOfSize:12.0f], NSFontAttributeName, nil];
+ float maxWidth = 0.0f;
+ int maxIndex = -1;
+ int i;
+ for (i = 0; i < numberToShow; i++) {
+ float width = ceilf([[_completions objectAtIndex:i] sizeWithAttributes:attributes].width);
+ if (width > maxWidth) {
+ maxWidth = width;
+ maxIndex = i;
+ }
+ }
+ windowFrame.size.width = 100;
+ if (maxIndex >= 0) {
+ maxWidth = ceilf([NSScrollView frameSizeForContentSize:NSMakeSize(maxWidth, 100.0f) hasHorizontalScroller:NO hasVerticalScroller:YES borderType:NSNoBorder].width);
+ maxWidth = ceilf([NSWindow frameRectForContentRect:NSMakeRect(0.0f, 0.0f, maxWidth, 100.0f) styleMask:NSBorderlessWindowMask].size.width);
+ maxWidth += 5.0f;
+ windowFrame.size.width = MAX(maxWidth, windowFrame.size.width);
+ maxWidth = MIN(400.0f, windowFrame.size.width);
+ }
+ [_popupWindow setFrame:windowFrame display:NO];
+
+ [_tableView reloadData];
+ [_tableView selectRowIndexes:[NSIndexSet indexSetWithIndex:0] byExtendingSelection:NO];
+ [_tableView scrollRowToVisible:0];
+ [self _reflectSelection];
+ [_popupWindow setLevel:NSPopUpMenuWindowLevel];
+ [_popupWindow orderFront:nil];
+ [[_view window] addChildWindow:_popupWindow ordered:NSWindowAbove];
+}
+
+- (void)doCompletion
+{
+ if (!_popupWindow) {
+ NSSpellChecker *checker = [NSSpellChecker sharedSpellChecker];
+ if (!checker) {
+ LOG_ERROR("No NSSpellChecker");
+ return;
+ }
+
+ // Get preceeding word stem
+ WebFrameBridge *bridge = [_view _bridge];
+ DOMRange *selection = kit(core([_view _frame])->selectionController()->toRange().get());
+ DOMRange *wholeWord = [bridge rangeByAlteringCurrentSelection:SelectionController::EXTEND
+ direction:SelectionController::BACKWARD granularity:WordGranularity];
+ DOMRange *prefix = [wholeWord cloneRange];
+ [prefix setEnd:[selection startContainer] offset:[selection startOffset]];
+
+ // Reject some NOP cases
+ if ([prefix collapsed]) {
+ NSBeep();
+ return;
+ }
+ NSString *prefixStr = [bridge stringForRange:prefix];
+ NSString *trimmedPrefix = [prefixStr stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceAndNewlineCharacterSet]];
+ if ([trimmedPrefix length] == 0) {
+ NSBeep();
+ return;
+ }
+ prefixLength = [prefixStr length];
+
+ // Lookup matches
+ [_completions release];
+ _completions = [checker completionsForPartialWordRange:NSMakeRange(0, [prefixStr length]) inString:prefixStr language:nil inSpellDocumentWithTag:[[_view _webView] spellCheckerDocumentTag]];
+ [_completions retain];
+
+ if (!_completions || [_completions count] == 0) {
+ NSBeep();
+ } else if ([_completions count] == 1) {
+ [self _insertMatch:[_completions objectAtIndex:0]];
+ } else {
+ ASSERT(!_originalString); // this should only be set IFF we have a popup window
+ _originalString = [[bridge stringForRange:selection] retain];
+ [self _buildUI];
+ NSRect wordRect = [bridge caretRectAtNode:[wholeWord startContainer] offset:[wholeWord startOffset] affinity:NSSelectionAffinityDownstream];
+ // +1 to be under the word, not the caret
+ // FIXME - 3769652 - Wrong positioning for right to left languages. We should line up the upper
+ // right corner with the caret instead of upper left, and the +1 would be a -1.
+ NSPoint wordLowerLeft = { NSMinX(wordRect)+1, NSMaxY(wordRect) };
+ [self _placePopupWindow:wordLowerLeft];
+ }
+ } else {
+ [self endRevertingChange:YES moveLeft:NO];
+ }
+}
+
+- (void)endRevertingChange:(BOOL)revertChange moveLeft:(BOOL)goLeft
+{
+ if (_popupWindow) {
+ // tear down UI
+ [[_view window] removeChildWindow:_popupWindow];
+ [_popupWindow orderOut:self];
+ // Must autorelease because event tracking code may be on the stack touching UI
+ [_popupWindow autorelease];
+ _popupWindow = nil;
+
+ if (revertChange) {
+ WebFrameBridge *bridge = [_view _bridge];
+ [bridge replaceSelectionWithText:_originalString selectReplacement:YES smartReplace:NO];
+ } else if ([_view _hasSelection]) {
+ if (goLeft)
+ [_view moveBackward:nil];
+ else
+ [_view moveForward:nil];
+ }
+ [_originalString release];
+ _originalString = nil;
+ }
+ // else there is no state to abort if the window was not up
+}
+
+- (BOOL)popupWindowIsOpen
+{
+ return _popupWindow != nil;
+}
+
+// WebHTMLView gives us a crack at key events it sees. Return whether we consumed the event.
+// The features for the various keys mimic NSTextView.
+- (BOOL)filterKeyDown:(NSEvent *)event
+{
+ if (!_popupWindow)
+ return NO;
+ NSString *string = [event charactersIgnoringModifiers];
+ if (![string length])
+ return NO;
+ unichar c = [string characterAtIndex:0];
+ if (c == NSUpArrowFunctionKey) {
+ int selectedRow = [_tableView selectedRow];
+ if (0 < selectedRow) {
+ [_tableView selectRowIndexes:[NSIndexSet indexSetWithIndex:selectedRow - 1] byExtendingSelection:NO];
+ [_tableView scrollRowToVisible:selectedRow - 1];
+ }
+ return YES;
+ }
+ if (c == NSDownArrowFunctionKey) {
+ int selectedRow = [_tableView selectedRow];
+ if (selectedRow < (int)[_completions count] - 1) {
+ [_tableView selectRowIndexes:[NSIndexSet indexSetWithIndex:selectedRow + 1] byExtendingSelection:NO];
+ [_tableView scrollRowToVisible:selectedRow + 1];
+ }
+ return YES;
+ }
+ if (c == NSRightArrowFunctionKey || c == '\n' || c == '\r' || c == '\t') {
+ // FIXME: What about backtab?
+ [self endRevertingChange:NO moveLeft:NO];
+ return YES;
+ }
+ if (c == NSLeftArrowFunctionKey) {
+ [self endRevertingChange:NO moveLeft:YES];
+ return YES;
+ }
+ if (c == 0x1B || c == NSF5FunctionKey) {
+ // FIXME: F5?
+ [self endRevertingChange:YES moveLeft:NO];
+ return YES;
+ }
+ if (c == ' ' || c >= 0x21 && c <= 0x2F || c >= 0x3A && c <= 0x40 || c >= 0x5B && c <= 0x60 || c >= 0x7B && c <= 0x7D) {
+ // FIXME: Is the above list of keys really definitive?
+ // Originally this code called ispunct; aren't there other punctuation keys on international keyboards?
+ [self endRevertingChange:NO moveLeft:NO];
+ return NO; // let the char get inserted
+ }
+ return NO;
+}
+
+- (void)_reflectSelection
+{
+ int selectedRow = [_tableView selectedRow];
+ ASSERT(selectedRow >= 0 && selectedRow < (int)[_completions count]);
+ [self _insertMatch:[_completions objectAtIndex:selectedRow]];
+}
+
+- (void)tableAction:(id)sender
+{
+ [self _reflectSelection];
+ [self endRevertingChange:NO moveLeft:NO];
+}
+
+- (int)numberOfRowsInTableView:(NSTableView *)tableView
+{
+ return [_completions count];
+}
+
+- (id)tableView:(NSTableView *)tableView objectValueForTableColumn:(NSTableColumn *)tableColumn row:(int)row
+{
+ return [_completions objectAtIndex:row];
+}
+
+- (void)tableViewSelectionDidChange:(NSNotification *)notification
+{
+ [self _reflectSelection];
+}
+
+@end
+
+@implementation WebHTMLView (WebDocumentPrivateProtocols)
+
+- (NSRect)selectionRect
+{
+ if ([self _hasSelection])
+ return core([self _frame])->selectionRect();
+ return NSZeroRect;
+}
+
+- (NSArray *)selectionTextRects
+{
+ if (![self _hasSelection])
+ return nil;
+
+ Vector<FloatRect> list;
+ if (Frame* coreFrame = core([self _frame]))
+ coreFrame->selectionTextRects(list);
+
+ unsigned size = list.size();
+ NSMutableArray *result = [[[NSMutableArray alloc] initWithCapacity:size] autorelease];
+ for (unsigned i = 0; i < size; ++i)
+ [result addObject:[NSValue valueWithRect:list[i]]];
+
+ return result;
+}
+
+- (NSView *)selectionView
+{
+ return self;
+}
+
+- (NSImage *)selectionImageForcingBlackText:(BOOL)forceBlackText
+{
+ if ([self _hasSelection])
+ return core([self _frame])->selectionImage(forceBlackText);
+ return nil;
+}
+
+- (NSRect)selectionImageRect
+{
+ if ([self _hasSelection])
+ return core([self _frame])->selectionRect();
+ return NSZeroRect;
+}
+
+- (NSArray *)pasteboardTypesForSelection
+{
+ if ([self _canSmartCopyOrDelete]) {
+ NSMutableArray *types = [[[[self class] _selectionPasteboardTypes] mutableCopy] autorelease];
+ [types addObject:WebSmartPastePboardType];
+ return types;
+ } else {
+ return [[self class] _selectionPasteboardTypes];
+ }
+}
+
+- (void)writeSelectionWithPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard
+{
+ [self _writeSelectionWithPasteboardTypes:types toPasteboard:pasteboard cachedAttributedString:nil];
+}
+
+- (void)selectAll
+{
+ Frame* coreFrame = core([self _frame]);
+ if (coreFrame)
+ coreFrame->selectionController()->selectAll();
+}
+
+- (void)deselectAll
+{
+ Frame* coreFrame = core([self _frame]);
+ if (!coreFrame)
+ return;
+ coreFrame->selectionController()->clear();
+}
+
+- (NSString *)string
+{
+ return [[self _bridge] stringForRange:[self _documentRange]];
+}
+
+- (NSAttributedString *)_attributeStringFromDOMRange:(DOMRange *)range
+{
+ NSAttributedString *attributedString;
+#if !LOG_DISABLED
+ double start = CFAbsoluteTimeGetCurrent();
+#endif
+ attributedString = [[[NSAttributedString alloc] _initWithDOMRange:range] autorelease];
+#if !LOG_DISABLED
+ double duration = CFAbsoluteTimeGetCurrent() - start;
+ LOG(Timing, "creating attributed string from selection took %f seconds.", duration);
+#endif
+ return attributedString;
+}
+
+- (NSAttributedString *)attributedString
+{
+ DOMDocument *document = [[self _frame] DOMDocument];
+ NSAttributedString *attributedString = [self _attributeStringFromDOMRange:[document _documentRange]];
+ if (!attributedString) {
+ Document* coreDocument = core(document);
+ Range range(coreDocument, coreDocument, 0, 0, 0);
+ attributedString = [NSAttributedString _web_attributedStringFromRange:&range];
+ }
+ return attributedString;
+}
+
+- (NSString *)selectedString
+{
+ return [[self _bridge] selectedString];
+}
+
+- (NSAttributedString *)selectedAttributedString
+{
+ NSAttributedString *attributedString = [self _attributeStringFromDOMRange:[self _selectedRange]];
+ if (!attributedString) {
+ Frame* coreFrame = core([self _frame]);
+ if (coreFrame) {
+ RefPtr<Range> range = coreFrame->selectionController()->selection().toRange();
+ attributedString = [NSAttributedString _web_attributedStringFromRange:range.get()];
+ }
+ }
+ return attributedString;
+}
+
+- (BOOL)supportsTextEncoding
+{
+ return YES;
+}
+
+- (BOOL)searchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag startInSelection:(BOOL)startInSelection
+{
+ if (![string length])
+ return NO;
+
+ return [[self _bridge] searchFor:string direction:forward caseSensitive:caseFlag wrap:wrapFlag startInSelection:startInSelection];
+}
+
+@end
+
+@implementation WebHTMLView (WebDocumentInternalProtocols)
+
+- (NSDictionary *)elementAtPoint:(NSPoint)point
+{
+ return [self elementAtPoint:point allowShadowContent:NO];
+}
+
+- (NSDictionary *)elementAtPoint:(NSPoint)point allowShadowContent:(BOOL)allow;
+{
+ Frame* coreframe = core([self _frame]);
+ if (coreframe)
+ return [[[WebElementDictionary alloc] initWithHitTestResult:coreframe->eventHandler()->hitTestResultAtPoint(IntPoint(point), allow)] autorelease];
+ return nil;
+}
+
+- (NSUInteger)markAllMatchesForText:(NSString *)string caseSensitive:(BOOL)caseFlag limit:(NSUInteger)limit
+{
+ return [[self _bridge] markAllMatchesForText:string caseSensitive:caseFlag limit:limit];
+}
+
+- (void)setMarkedTextMatchesAreHighlighted:(BOOL)newValue
+{
+ [[self _bridge] setMarkedTextMatchesAreHighlighted:newValue];
+}
+
+- (BOOL)markedTextMatchesAreHighlighted
+{
+ return [[self _bridge] markedTextMatchesAreHighlighted];
+}
+
+- (void)unmarkAllTextMatches
+{
+ return [[self _bridge] unmarkAllTextMatches];
+}
+
+- (NSArray *)rectsForTextMatches
+{
+ return [[self _bridge] rectsForTextMatches];
+}
+
+@end
+
+// This is used by AppKit and is included here so that WebDataProtocolScheme is only defined once.
+@implementation NSURL (WebDataURL)
+
++ (NSURL *)_web_uniqueWebDataURL
+{
+ CFUUIDRef UUIDRef = CFUUIDCreate(kCFAllocatorDefault);
+ NSString *UUIDString = (NSString *)CFUUIDCreateString(kCFAllocatorDefault, UUIDRef);
+ CFRelease(UUIDRef);
+ NSURL *URL = [NSURL URLWithString:[NSString stringWithFormat:@"%@://%@", WebDataProtocolScheme, UUIDString]];
+ CFRelease(UUIDString);
+ return URL;
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebHTMLViewInternal.h b/WebKit/mac/WebView/WebHTMLViewInternal.h
new file mode 100644
index 0000000..e54ab2d
--- /dev/null
+++ b/WebKit/mac/WebView/WebHTMLViewInternal.h
@@ -0,0 +1,129 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// Things internal to the WebKit framework; not SPI.
+
+#import <WebKit/WebHTMLViewPrivate.h>
+
+@class WebTextCompleteController;
+@class DOMDocumentFragment;
+@class DOMElement;
+
+namespace WebCore {
+ class KeyboardEvent;
+ class CachedImage;
+}
+
+struct WebHTMLViewInterpretKeyEventsParameters;
+
+@interface WebHTMLViewPrivate : NSObject
+{
+@public
+ BOOL closed;
+ BOOL needsLayout;
+ BOOL needsToApplyStyles;
+ BOOL ignoringMouseDraggedEvents;
+ BOOL printing;
+ BOOL avoidingPrintOrphan;
+
+ id savedSubviews;
+ BOOL subviewsSetAside;
+
+ NSEvent *mouseDownEvent; // Kept after handling the event.
+ BOOL handlingMouseDownEvent;
+ NSEvent *keyDownEvent; // Kept after handling the event.
+
+ NSSize lastLayoutSize;
+
+ NSPoint lastScrollPosition;
+
+ WebPluginController *pluginController;
+
+ NSString *toolTip;
+ NSToolTipTag lastToolTipTag;
+ id trackingRectOwner;
+ void *trackingRectUserData;
+
+ NSTimer *autoscrollTimer;
+ NSEvent *autoscrollTriggerEvent;
+
+ NSArray* pageRects;
+
+ NSMutableDictionary* highlighters;
+
+ BOOL resigningFirstResponder;
+ BOOL nextResponderDisabledOnce;
+
+ WebTextCompleteController *compController;
+
+ BOOL transparentBackground;
+
+ WebHTMLViewInterpretKeyEventsParameters *interpretKeyEventsParameters;
+ BOOL receivedNOOP;
+
+ WebDataSource *dataSource;
+ WebCore::CachedImage *promisedDragTIFFDataSource;
+
+ CFRunLoopTimerRef updateFocusedAndActiveStateTimer;
+ CFRunLoopTimerRef updateMouseoverTimer;
+
+ SEL selectorForDoCommandBySelector;
+
+#ifndef NDEBUG
+ BOOL enumeratingSubviews;
+#endif
+}
+- (void)clear;
+@end
+
+@interface WebHTMLView (WebInternal)
+- (void)_selectionChanged;
+- (void)_updateFontPanel;
+- (BOOL)_canSmartCopyOrDelete;
+#ifndef __LP64__
+- (void)_pauseNullEventsForAllNetscapePlugins;
+- (void)_resumeNullEventsForAllNetscapePlugins;
+#endif
+- (id<WebHTMLHighlighter>)_highlighterForType:(NSString*)type;
+- (WebFrame *)_frame;
+- (void)paste:(id)sender;
+- (void)closeIfNotCurrentView;
+- (void)_lookUpInDictionaryFromMenu:(id)sender;
+- (void)_hoverFeedbackSuspendedChanged;
+- (BOOL)_interceptEditingKeyEvent:(WebCore::KeyboardEvent *)event shouldSaveCommand:(BOOL)shouldSave;
+- (DOMDocumentFragment*)_documentFragmentFromPasteboard:(NSPasteboard *)pasteboard;
+- (NSEvent *)_mouseDownEvent;
+#ifndef BUILDING_ON_TIGER
+- (BOOL)isGrammarCheckingEnabled;
+- (void)setGrammarCheckingEnabled:(BOOL)flag;
+- (void)toggleGrammarChecking:(id)sender;
+#endif
+- (WebCore::CachedImage*)promisedDragTIFFDataSource;
+- (void)setPromisedDragTIFFDataSource:(WebCore::CachedImage*)source;
+- (void)_web_layoutIfNeededRecursive;
+@end
diff --git a/WebKit/mac/WebView/WebHTMLViewPrivate.h b/WebKit/mac/WebView/WebHTMLViewPrivate.h
new file mode 100644
index 0000000..a2773f4
--- /dev/null
+++ b/WebKit/mac/WebView/WebHTMLViewPrivate.h
@@ -0,0 +1,126 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebHTMLView.h>
+
+@class DOMDocumentFragment;
+@class DOMElement;
+@class DOMNode;
+@class DOMRange;
+@class WebArchive;
+@class WebFrameBridge;
+@class WebView;
+@class WebFrame;
+@class WebPluginController;
+
+@protocol WebHTMLHighlighter
+- (NSRect)highlightRectForLine:(NSRect)lineRect representedNode:(DOMNode *)node;
+- (void)paintHighlightForBox:(NSRect)boxRect onLine:(NSRect)lineRect behindText:(BOOL)text entireLine:(BOOL)line representedNode:(DOMNode *)node;
+
+// the following methods are deprecated and will be removed once Mail switches to the new methods <rdar://problem/5050528>
+- (NSRect)highlightRectForLine:(NSRect)lineRect;
+- (void)paintHighlightForBox:(NSRect)boxRect onLine:(NSRect)lineRect behindText:(BOOL)text entireLine:(BOOL)line;
+@end
+
+@interface WebHTMLView (WebPrivate)
+
++ (NSArray *)supportedMIMETypes;
++ (NSArray *)supportedImageMIMETypes;
++ (NSArray *)supportedNonImageMIMETypes;
++ (NSArray *)unsupportedTextMIMETypes;
+
+- (void)close;
+
+// Modifier (flagsChanged) tracking SPI
++ (void)_postFlagsChangedEvent:(NSEvent *)flagsChangedEvent;
+- (void)_updateMouseoverWithFakeEvent;
+
+- (void)_setAsideSubviews;
+- (void)_restoreSubviews;
+
+- (BOOL)_insideAnotherHTMLView;
+- (void)_clearLastHitViewIfSelf;
+- (void)_updateMouseoverWithEvent:(NSEvent *)event;
+
++ (NSArray *)_insertablePasteboardTypes;
++ (NSArray *)_selectionPasteboardTypes;
+- (void)_writeSelectionToPasteboard:(NSPasteboard *)pasteboard;
+
+- (void)_frameOrBoundsChanged;
+
+- (NSImage *)_dragImageForLinkElement:(NSDictionary *)element;
+- (NSImage *)_dragImageForURL:(NSString*)linkURL withLabel:(NSString*)label;
+- (void)_handleAutoscrollForMouseDragged:(NSEvent *)event;
+- (WebPluginController *)_pluginController;
+
+// FIXME: _selectionRect is deprecated in favor of selectionRect, which is in protocol WebDocumentSelection.
+// We can't remove this yet because it's still in use by Mail.
+- (NSRect)_selectionRect;
+
+- (void)_startAutoscrollTimer:(NSEvent *)event;
+- (void)_stopAutoscrollTimer;
+
+- (BOOL)_canEdit;
+- (BOOL)_canEditRichly;
+- (BOOL)_canAlterCurrentSelection;
+- (BOOL)_hasSelection;
+- (BOOL)_hasSelectionOrInsertionPoint;
+- (BOOL)_isEditable;
+
+- (BOOL)_transparentBackground;
+- (void)_setTransparentBackground:(BOOL)f;
+
+- (void)_setToolTip:(NSString *)string;
+
+// SPI's for Mail.
+- (NSImage *)_selectionDraggingImage;
+- (NSRect)_selectionDraggingRect;
+- (DOMNode *)_insertOrderedList;
+- (DOMNode *)_insertUnorderedList;
+- (BOOL)_canIncreaseSelectionListLevel;
+- (BOOL)_canDecreaseSelectionListLevel;
+- (DOMNode *)_increaseSelectionListLevel;
+- (DOMNode *)_increaseSelectionListLevelOrdered;
+- (DOMNode *)_increaseSelectionListLevelUnordered;
+- (void)_decreaseSelectionListLevel;
+- (void)_setHighlighter:(id<WebHTMLHighlighter>)highlighter ofType:(NSString*)type;
+- (void)_removeHighlighterOfType:(NSString*)type;
+- (DOMDocumentFragment *)_documentFragmentFromPasteboard:(NSPasteboard *)pasteboard forType:(NSString *)pboardType inContext:(DOMRange *)context subresources:(NSArray **)subresources;
+
+// SPI for DumpRenderTree
+- (void)_updateFocusedAndActiveState;
+
+// SPI for printing (should be converted to API someday). When the WebHTMLView isn't being printed
+// directly, this method must be called before paginating, or the computed height might be incorrect.
+// Typically this would be called from inside an override of -[NSView knowsPageRange:].
+- (void)_layoutForPrinting;
+
+- (BOOL)_canSmartReplaceWithPasteboard:(NSPasteboard *)pasteboard;
+
+
+@end
diff --git a/WebKit/mac/WebView/WebPDFRepresentation.h b/WebKit/mac/WebView/WebPDFRepresentation.h
new file mode 100644
index 0000000..6b60d4c
--- /dev/null
+++ b/WebKit/mac/WebView/WebPDFRepresentation.h
@@ -0,0 +1,35 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@protocol WebDocumentRepresentation;
+
+@interface WebPDFRepresentation : NSObject <WebDocumentRepresentation>
++ (NSArray *)supportedMIMETypes;
+@end
diff --git a/WebKit/mac/WebView/WebPDFRepresentation.m b/WebKit/mac/WebView/WebPDFRepresentation.m
new file mode 100644
index 0000000..beba1fa
--- /dev/null
+++ b/WebKit/mac/WebView/WebPDFRepresentation.m
@@ -0,0 +1,145 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <JavaScriptCore/Assertions.h>
+#import <WebKit/WebDataSource.h>
+#import <WebKit/WebFrame.h>
+#import <WebKit/WebFrameView.h>
+#import <WebKit/WebNSObjectExtras.h>
+#import <WebKit/WebPDFRepresentation.h>
+#import <WebKit/WebPDFView.h>
+
+#import <PDFKit/PDFDocument.h>
+
+@implementation WebPDFRepresentation
+
++ (NSArray *)postScriptMIMETypes
+{
+ return [NSArray arrayWithObjects:
+ @"application/postscript",
+ nil];
+}
+
++ (NSArray *)supportedMIMETypes
+{
+ return [[[self class] postScriptMIMETypes] arrayByAddingObjectsFromArray:
+ [NSArray arrayWithObjects:
+ @"text/pdf",
+ @"application/pdf",
+ nil]];
+}
+
++ (Class)PDFDocumentClass
+{
+ static Class PDFDocumentClass = nil;
+ if (PDFDocumentClass == nil) {
+ PDFDocumentClass = [[WebPDFView PDFKitBundle] classNamed:@"PDFDocument"];
+ if (PDFDocumentClass == nil) {
+ LOG_ERROR("Couldn't find PDFDocument class in PDFKit.framework");
+ }
+ }
+ return PDFDocumentClass;
+}
+
+- (void)setDataSource:(WebDataSource *)dataSource;
+{
+}
+
+- (void)receivedData:(NSData *)data withDataSource:(WebDataSource *)dataSource;
+{
+}
+
+- (void)receivedError:(NSError *)error withDataSource:(WebDataSource *)dataSource;
+{
+}
+
+- (NSData *)convertPostScriptDataSourceToPDF:(NSData *)data
+{
+ // Convert PostScript to PDF using Quartz 2D API
+ // http://developer.apple.com/documentation/GraphicsImaging/Conceptual/drawingwithquartz2d/dq_ps_convert/chapter_16_section_1.html
+
+ CGPSConverterCallbacks callbacks = { 0, 0, 0, 0, 0, 0, 0, 0 };
+ CGPSConverterRef converter = CGPSConverterCreate(0, &callbacks, 0);
+ ASSERT(converter);
+
+ CGDataProviderRef provider = CGDataProviderCreateWithCFData((CFDataRef)data);
+ ASSERT(provider);
+
+ CFMutableDataRef result = CFDataCreateMutable(kCFAllocatorDefault, 0);
+ ASSERT(result);
+
+ CGDataConsumerRef consumer = CGDataConsumerCreateWithCFData(result);
+ ASSERT(consumer);
+
+ // Error handled by detecting zero-length 'result' in caller
+ CGPSConverterConvert(converter, provider, consumer, 0);
+
+ CFRelease(converter);
+ CFRelease(provider);
+ CFRelease(consumer);
+
+ return WebCFAutorelease(result);
+}
+
+- (void)finishedLoadingWithDataSource:(WebDataSource *)dataSource
+{
+ NSData *data = [dataSource data];
+
+ NSArray *postScriptMIMETypes = [[self class] postScriptMIMETypes];
+ NSString *mimeType = [[dataSource response] MIMEType];
+ if ([postScriptMIMETypes containsObject:mimeType]) {
+ data = [self convertPostScriptDataSourceToPDF:data];
+ if ([data length] == 0)
+ return;
+ }
+
+ WebPDFView *view = (WebPDFView *)[[[dataSource webFrame] frameView] documentView];
+ PDFDocument *doc = [[[[self class] PDFDocumentClass] alloc] initWithData:data];
+ [view setPDFDocument:doc];
+ [doc release];
+}
+
+
+- (BOOL)canProvideDocumentSource
+{
+ return NO;
+}
+
+
+- (NSString *)documentSource
+{
+ return nil;
+}
+
+
+- (NSString *)title
+{
+ return nil;
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebPDFView.h b/WebKit/mac/WebView/WebPDFView.h
new file mode 100644
index 0000000..5d9ce1f
--- /dev/null
+++ b/WebKit/mac/WebView/WebPDFView.h
@@ -0,0 +1,55 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebDocumentInternal.h>
+
+@class PDFDocument;
+@class PDFView;
+@class WebDataSource;
+
+@interface WebPDFView : NSView <WebDocumentView, WebDocumentSearching, WebDocumentIncrementalSearching, WebMultipleTextMatches, WebDocumentSelection, WebDocumentElement, _WebDocumentViewState, _WebDocumentTextSizing>
+{
+ NSView *previewView;
+ PDFView *PDFSubview;
+ NSString *path;
+ id trackedFirstResponder;
+ BOOL written;
+ BOOL _ignoreScaleAndDisplayModeAndPageNotifications;
+ BOOL _willUpdatePreferencesSoon;
+ PDFView *PDFSubviewProxy;
+ WebDataSource *dataSource;
+ NSArray *textMatches;
+ NSPoint lastScrollPosition;
+}
+
++ (NSArray *)supportedMIMETypes;
++ (NSBundle *)PDFKitBundle;
+
+- (void)setPDFDocument:(PDFDocument *)doc;
+
+@end
diff --git a/WebKit/mac/WebView/WebPDFView.mm b/WebKit/mac/WebView/WebPDFView.mm
new file mode 100644
index 0000000..0c3da43
--- /dev/null
+++ b/WebKit/mac/WebView/WebPDFView.mm
@@ -0,0 +1,1486 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebPDFView.h"
+
+#import "WebDataSourceInternal.h"
+#import "WebDocumentInternal.h"
+#import "WebDocumentPrivate.h"
+#import "WebFrame.h"
+#import "WebFrameInternal.h"
+#import "WebFrameView.h"
+#import "WebLocalizableStrings.h"
+#import "WebNSArrayExtras.h"
+#import "WebNSAttributedStringExtras.h"
+#import "WebNSPasteboardExtras.h"
+#import "WebNSViewExtras.h"
+#import "WebPDFRepresentation.h"
+#import "WebPreferencesPrivate.h"
+#import "WebUIDelegate.h"
+#import "WebUIDelegatePrivate.h"
+#import "WebView.h"
+#import "WebViewInternal.h"
+#import <JavaScriptCore/Assertions.h>
+#import <PDFKit/PDFKit.h>
+#import <WebCore/EventNames.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/KURL.h>
+#import <WebCore/KeyboardEvent.h>
+#import <WebCore/MouseEvent.h>
+#import <WebCore/PlatformKeyboardEvent.h>
+
+using namespace WebCore;
+using namespace EventNames;
+
+// Redeclarations of PDFKit notifications. We can't use the API since we use a weak link to the framework.
+#define _webkit_PDFViewDisplayModeChangedNotification @"PDFViewDisplayModeChanged"
+#define _webkit_PDFViewScaleChangedNotification @"PDFViewScaleChanged"
+#define _webkit_PDFViewPageChangedNotification @"PDFViewChangedPage"
+
+@interface PDFDocument (PDFKitSecretsIKnow)
+- (NSPrintOperation *)getPrintOperationForPrintInfo:(NSPrintInfo *)printInfo autoRotate:(BOOL)doRotate;
+@end
+
+extern "C" NSString *_NSPathForSystemFramework(NSString *framework);
+
+@interface WebPDFView (FileInternal)
++ (Class)_PDFPreviewViewClass;
++ (Class)_PDFViewClass;
+- (BOOL)_anyPDFTagsFoundInMenu:(NSMenu *)menu;
+- (void)_applyPDFDefaults;
+- (BOOL)_canLookUpInDictionary;
+- (NSClipView *)_clipViewForPDFDocumentView;
+- (NSEvent *)_fakeKeyEventWithFunctionKey:(unichar)functionKey;
+- (NSMutableArray *)_menuItemsFromPDFKitForEvent:(NSEvent *)theEvent;
+- (PDFSelection *)_nextMatchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag fromSelection:(PDFSelection *)initialSelection startInSelection:(BOOL)startInSelection;
+- (void)_openWithFinder:(id)sender;
+- (NSString *)_path;
+- (void)_PDFDocumentViewMightHaveScrolled:(NSNotification *)notification;
+- (BOOL)_pointIsInSelection:(NSPoint)point;
+- (NSAttributedString *)_scaledAttributedString:(NSAttributedString *)unscaledAttributedString;
+- (void)_setTextMatches:(NSArray *)array;
+- (NSString *)_temporaryPDFDirectoryPath;
+- (void)_trackFirstResponder;
+- (void)_updatePreferencesSoon;
+- (NSSet *)_visiblePDFPages;
+@end;
+
+// PDFPrefUpdatingProxy is a class that forwards everything it gets to a target and updates the PDF viewing prefs
+// after each of those messages. We use it as a way to hook all the places that the PDF viewing attrs change.
+@interface PDFPrefUpdatingProxy : NSProxy {
+ WebPDFView *view;
+}
+- (id)initWithView:(WebPDFView *)view;
+@end
+
+#pragma mark C UTILITY FUNCTIONS
+
+static void _applicationInfoForMIMEType(NSString *type, NSString **name, NSImage **image)
+{
+ NSURL *appURL = nil;
+
+ OSStatus error = LSCopyApplicationForMIMEType((CFStringRef)type, kLSRolesAll, (CFURLRef *)&appURL);
+ if (error != noErr)
+ return;
+
+ NSString *appPath = [appURL path];
+ CFRelease (appURL);
+
+ *image = [[NSWorkspace sharedWorkspace] iconForFile:appPath];
+ [*image setSize:NSMakeSize(16.f,16.f)];
+
+ NSString *appName = [[NSFileManager defaultManager] displayNameAtPath:appPath];
+ *name = appName;
+}
+
+// FIXME 4182876: We can eliminate this function in favor if -isEqual: if [PDFSelection isEqual:] is overridden
+// to compare contents.
+static BOOL _PDFSelectionsAreEqual(PDFSelection *selectionA, PDFSelection *selectionB)
+{
+ NSArray *aPages = [selectionA pages];
+ NSArray *bPages = [selectionB pages];
+
+ if (![aPages isEqual:bPages])
+ return NO;
+
+ int count = [aPages count];
+ int i;
+ for (i = 0; i < count; ++i) {
+ NSRect aBounds = [selectionA boundsForPage:[aPages objectAtIndex:i]];
+ NSRect bBounds = [selectionB boundsForPage:[bPages objectAtIndex:i]];
+ if (!NSEqualRects(aBounds, bBounds)) {
+ return NO;
+ }
+ }
+
+ return YES;
+}
+
+@implementation WebPDFView
+
+#pragma mark WebPDFView API
+
++ (NSBundle *)PDFKitBundle
+{
+ static NSBundle *PDFKitBundle = nil;
+ if (PDFKitBundle == nil) {
+ NSString *PDFKitPath = [_NSPathForSystemFramework(@"Quartz.framework") stringByAppendingString:@"/Frameworks/PDFKit.framework"];
+ if (PDFKitPath == nil) {
+ LOG_ERROR("Couldn't find PDFKit.framework");
+ return nil;
+ }
+ PDFKitBundle = [NSBundle bundleWithPath:PDFKitPath];
+ if (![PDFKitBundle load]) {
+ LOG_ERROR("Couldn't load PDFKit.framework");
+ }
+ }
+ return PDFKitBundle;
+}
+
++ (NSArray *)supportedMIMETypes
+{
+ return [WebPDFRepresentation supportedMIMETypes];
+}
+
+- (void)setPDFDocument:(PDFDocument *)doc
+{
+ // Both setDocument: and _applyPDFDefaults will trigger scale and mode-changed notifications.
+ // Those aren't reflecting user actions, so we need to ignore them.
+ _ignoreScaleAndDisplayModeAndPageNotifications = YES;
+ [PDFSubview setDocument:doc];
+ [self _applyPDFDefaults];
+ _ignoreScaleAndDisplayModeAndPageNotifications = NO;
+}
+
+#pragma mark NSObject OVERRIDES
+
+- (void)dealloc
+{
+ ASSERT(!trackedFirstResponder);
+ [dataSource release];
+ [previewView release];
+ [PDFSubview release];
+ [path release];
+ [PDFSubviewProxy release];
+ [textMatches release];
+ [super dealloc];
+}
+
+#pragma mark NSResponder OVERRIDES
+
+- (void)centerSelectionInVisibleArea:(id)sender
+{
+ [PDFSubview scrollSelectionToVisible:nil];
+}
+
+- (void)scrollPageDown:(id)sender
+{
+ // PDFView doesn't support this responder method directly, so we pass it a fake key event
+ [PDFSubview keyDown:[self _fakeKeyEventWithFunctionKey:NSPageDownFunctionKey]];
+}
+
+- (void)scrollPageUp:(id)sender
+{
+ // PDFView doesn't support this responder method directly, so we pass it a fake key event
+ [PDFSubview keyDown:[self _fakeKeyEventWithFunctionKey:NSPageUpFunctionKey]];
+}
+
+- (void)scrollLineDown:(id)sender
+{
+ // PDFView doesn't support this responder method directly, so we pass it a fake key event
+ [PDFSubview keyDown:[self _fakeKeyEventWithFunctionKey:NSDownArrowFunctionKey]];
+}
+
+- (void)scrollLineUp:(id)sender
+{
+ // PDFView doesn't support this responder method directly, so we pass it a fake key event
+ [PDFSubview keyDown:[self _fakeKeyEventWithFunctionKey:NSUpArrowFunctionKey]];
+}
+
+- (void)scrollToBeginningOfDocument:(id)sender
+{
+ // PDFView doesn't support this responder method directly, so we pass it a fake key event
+ [PDFSubview keyDown:[self _fakeKeyEventWithFunctionKey:NSHomeFunctionKey]];
+}
+
+- (void)scrollToEndOfDocument:(id)sender
+{
+ // PDFView doesn't support this responder method directly, so we pass it a fake key event
+ [PDFSubview keyDown:[self _fakeKeyEventWithFunctionKey:NSEndFunctionKey]];
+}
+
+// jumpToSelection is the old name for what AppKit now calls centerSelectionInVisibleArea. Safari
+// was using the old jumpToSelection selector in its menu. Newer versions of Safari will us the
+// selector centerSelectionInVisibleArea. We'll leave this old selector in place for two reasons:
+// (1) compatibility between older Safari and newer WebKit; (2) other WebKit-based applications
+// might be using the jumpToSelection: selector, and we don't want to break them.
+- (void)jumpToSelection:(id)sender
+{
+ [self centerSelectionInVisibleArea:nil];
+}
+
+#pragma mark NSView OVERRIDES
+
+- (BOOL)acceptsFirstResponder {
+ return YES;
+}
+
+- (BOOL)becomeFirstResponder
+{
+ // This works together with setNextKeyView to splice our PDFSubview into
+ // the key loop similar to the way NSScrollView does this.
+ NSWindow *window = [self window];
+ id newFirstResponder = nil;
+
+ if ([window keyViewSelectionDirection] == NSSelectingPrevious) {
+ NSView *previousValidKeyView = [self previousValidKeyView];
+ if ((previousValidKeyView != self) && (previousValidKeyView != PDFSubview))
+ newFirstResponder = previousValidKeyView;
+ } else {
+ NSView *PDFDocumentView = [PDFSubview documentView];
+ if ([PDFDocumentView acceptsFirstResponder])
+ newFirstResponder = PDFDocumentView;
+ }
+
+ if (!newFirstResponder)
+ return NO;
+
+ if (![window makeFirstResponder:newFirstResponder])
+ return NO;
+
+ [[dataSource webFrame] _clearSelectionInOtherFrames];
+
+ return YES;
+}
+
+- (NSView *)hitTest:(NSPoint)point
+{
+ // Override hitTest so we can override menuForEvent.
+ NSEvent *event = [NSApp currentEvent];
+ NSEventType type = [event type];
+ if (type == NSRightMouseDown || (type == NSLeftMouseDown && ([event modifierFlags] & NSControlKeyMask)))
+ return self;
+
+ return [super hitTest:point];
+}
+
+- (id)initWithFrame:(NSRect)frame
+{
+ self = [super initWithFrame:frame];
+ if (self) {
+ [self setAutoresizingMask:NSViewWidthSizable | NSViewHeightSizable];
+
+ Class previewViewClass = [[self class] _PDFPreviewViewClass];
+
+ // We might not have found a previewViewClass, but if we did find it
+ // then we should be able to create an instance.
+ if (previewViewClass) {
+ previewView = [[previewViewClass alloc] initWithFrame:frame];
+ ASSERT(previewView);
+ }
+
+ NSView *topLevelPDFKitView = nil;
+ if (previewView) {
+ // We'll retain the PDFSubview here so that it is equally retained in all
+ // code paths. That way we don't need to worry about conditionally releasing
+ // it later.
+ PDFSubview = [[previewView performSelector:@selector(pdfView)] retain];
+ topLevelPDFKitView = previewView;
+ } else {
+ PDFSubview = [[[[self class] _PDFViewClass] alloc] initWithFrame:frame];
+ topLevelPDFKitView = PDFSubview;
+ }
+
+ ASSERT(PDFSubview);
+
+ [topLevelPDFKitView setAutoresizingMask:NSViewWidthSizable | NSViewHeightSizable];
+ [self addSubview:topLevelPDFKitView];
+
+ [PDFSubview setDelegate:self];
+ written = NO;
+ // Messaging this proxy is the same as messaging PDFSubview, with the side effect that the
+ // PDF viewing defaults are updated afterwards
+ PDFSubviewProxy = (PDFView *)[[PDFPrefUpdatingProxy alloc] initWithView:self];
+ }
+
+ return self;
+}
+
+- (NSMenu *)menuForEvent:(NSEvent *)theEvent
+{
+ // Start with the menu items supplied by PDFKit, with WebKit tags applied
+ NSMutableArray *items = [self _menuItemsFromPDFKitForEvent:theEvent];
+
+ // Add in an "Open with <default PDF viewer>" item
+ NSString *appName = nil;
+ NSImage *appIcon = nil;
+
+ _applicationInfoForMIMEType([[dataSource response] MIMEType], &appName, &appIcon);
+ if (!appName)
+ appName = UI_STRING("Finder", "Default application name for Open With context menu");
+
+ // To match the PDFKit style, we'll add Open with Preview even when there's no document yet to view, and
+ // disable it using validateUserInterfaceItem.
+ NSString *title = [NSString stringWithFormat:UI_STRING("Open with %@", "context menu item for PDF"), appName];
+ NSMenuItem *item = [[NSMenuItem alloc] initWithTitle:title action:@selector(_openWithFinder:) keyEquivalent:@""];
+ [item setTag:WebMenuItemTagOpenWithDefaultApplication];
+ if (appIcon)
+ [item setImage:appIcon];
+ [items insertObject:item atIndex:0];
+ [item release];
+
+ [items insertObject:[NSMenuItem separatorItem] atIndex:1];
+
+ // pass the items off to the WebKit context menu mechanism
+ WebView *webView = [[dataSource webFrame] webView];
+ ASSERT(webView);
+ NSMenu *menu = [webView _menuForElement:[self elementAtPoint:[self convertPoint:[theEvent locationInWindow] fromView:nil]] defaultItems:items];
+
+ // The delegate has now had the opportunity to add items to the standard PDF-related items, or to
+ // remove or modify some of the PDF-related items. In 10.4, the PDF context menu did not go through
+ // the standard WebKit delegate path, and so the standard PDF-related items always appeared. For
+ // clients that create their own context menu by hand-picking specific items from the default list, such as
+ // Safari, none of the PDF-related items will appear until the client is rewritten to explicitly
+ // include these items. For backwards compatibility of tip-of-tree WebKit with the 10.4 version of Safari
+ // (the configuration that people building open source WebKit use), we'll use the entire set of PDFKit-supplied
+ // menu items. This backward-compatibility hack won't work with any non-Safari clients, but this seems OK since
+ // (1) the symptom is fairly minor, and (2) we suspect that non-Safari clients are probably using the entire
+ // set of default items, rather than manually choosing from them. We can remove this code entirely when we
+ // ship a version of Safari that includes the fix for radar 3796579.
+ if (![self _anyPDFTagsFoundInMenu:menu] && [[[NSBundle mainBundle] bundleIdentifier] isEqualToString:@"com.apple.Safari"]) {
+ [menu addItem:[NSMenuItem separatorItem]];
+ NSEnumerator *e = [items objectEnumerator];
+ NSMenuItem *menuItem;
+ while ((menuItem = [e nextObject]) != nil) {
+ // copy menuItem since a given menuItem can be in only one menu at a time, and we don't
+ // want to mess with the menu returned from PDFKit.
+ [menu addItem:[menuItem copy]];
+ }
+ }
+
+ return menu;
+}
+
+- (void)setNextKeyView:(NSView *)aView
+{
+ // This works together with becomeFirstResponder to splice PDFSubview into
+ // the key loop similar to the way NSScrollView and NSClipView do this.
+ NSView *documentView = [PDFSubview documentView];
+ if (documentView) {
+ [documentView setNextKeyView:aView];
+
+ // We need to make the documentView be the next view in the keyview loop.
+ // It would seem more sensible to do this in our init method, but it turns out
+ // that [NSClipView setDocumentView] won't call this method if our next key view
+ // is already set, so we wait until we're called before adding this connection.
+ // We'll also clear it when we're called with nil, so this could go through the
+ // same code path more than once successfully.
+ [super setNextKeyView: aView ? documentView : nil];
+ } else
+ [super setNextKeyView:aView];
+}
+
+- (void)viewDidMoveToWindow
+{
+ // FIXME 2573089: we can observe a notification for first responder changes
+ // instead of the very frequent NSWindowDidUpdateNotification if/when 2573089 is addressed.
+ NSWindow *newWindow = [self window];
+ if (!newWindow)
+ return;
+
+ [self _trackFirstResponder];
+ NSNotificationCenter *notificationCenter = [NSNotificationCenter defaultCenter];
+ [notificationCenter addObserver:self
+ selector:@selector(_trackFirstResponder)
+ name:NSWindowDidUpdateNotification
+ object:newWindow];
+
+ [notificationCenter addObserver:self
+ selector:@selector(_scaleOrDisplayModeOrPageChanged:)
+ name:_webkit_PDFViewScaleChangedNotification
+ object:PDFSubview];
+
+ [notificationCenter addObserver:self
+ selector:@selector(_scaleOrDisplayModeOrPageChanged:)
+ name:_webkit_PDFViewDisplayModeChangedNotification
+ object:PDFSubview];
+
+ [notificationCenter addObserver:self
+ selector:@selector(_scaleOrDisplayModeOrPageChanged:)
+ name:_webkit_PDFViewPageChangedNotification
+ object:PDFSubview];
+
+ [notificationCenter addObserver:self
+ selector:@selector(_PDFDocumentViewMightHaveScrolled:)
+ name:NSViewBoundsDidChangeNotification
+ object:[self _clipViewForPDFDocumentView]];
+}
+
+- (void)viewWillMoveToWindow:(NSWindow *)window
+{
+ // FIXME 2573089: we can observe a notification for changes to the first responder
+ // instead of the very frequent NSWindowDidUpdateNotification if/when 2573089 is addressed.
+ NSWindow *oldWindow = [self window];
+ if (!oldWindow)
+ return;
+
+ NSNotificationCenter *notificationCenter = [NSNotificationCenter defaultCenter];
+ [notificationCenter removeObserver:self
+ name:NSWindowDidUpdateNotification
+ object:oldWindow];
+ [notificationCenter removeObserver:self
+ name:_webkit_PDFViewScaleChangedNotification
+ object:PDFSubview];
+ [notificationCenter removeObserver:self
+ name:_webkit_PDFViewDisplayModeChangedNotification
+ object:PDFSubview];
+ [notificationCenter removeObserver:self
+ name:_webkit_PDFViewPageChangedNotification
+ object:PDFSubview];
+
+ [notificationCenter removeObserver:self
+ name:NSViewBoundsDidChangeNotification
+ object:[self _clipViewForPDFDocumentView]];
+
+ [trackedFirstResponder release];
+ trackedFirstResponder = nil;
+}
+
+#pragma mark NSUserInterfaceValidations PROTOCOL IMPLEMENTATION
+
+- (BOOL)validateUserInterfaceItemWithoutDelegate:(id <NSValidatedUserInterfaceItem>)item
+{
+ SEL action = [item action];
+ if (action == @selector(takeFindStringFromSelection:) || action == @selector(centerSelectionInVisibleArea:) || action == @selector(jumpToSelection:))
+ return [PDFSubview currentSelection] != nil;
+
+ if (action == @selector(_openWithFinder:))
+ return [PDFSubview document] != nil;
+
+ if (action == @selector(_lookUpInDictionaryFromMenu:))
+ return [self _canLookUpInDictionary];
+
+ return YES;
+}
+
+- (BOOL)validateUserInterfaceItem:(id <NSValidatedUserInterfaceItem>)item
+{
+ BOOL result = [self validateUserInterfaceItemWithoutDelegate:item];
+ return CallUIDelegateReturningBoolean(result, [self _webView], @selector(webView:validateUserInterfaceItem:defaultValidation:), item, result);
+}
+
+#pragma mark INTERFACE BUILDER ACTIONS FOR SAFARI
+
+// Surprisingly enough, this isn't defined in any superclass, though it is defined in assorted AppKit classes since
+// it's a standard menu item IBAction.
+- (IBAction)copy:(id)sender
+{
+ [PDFSubview copy:sender];
+}
+
+// This used to be a standard IBAction (for Use Selection For Find), but AppKit now uses performFindPanelAction:
+// with a menu item tag for this purpose.
+- (IBAction)takeFindStringFromSelection:(id)sender
+{
+ [NSPasteboard _web_setFindPasteboardString:[[PDFSubview currentSelection] string] withOwner:self];
+}
+
+#pragma mark WebFrameView UNDECLARED "DELEGATE METHODS"
+
+// This is tested in -[WebFrameView canPrintHeadersAndFooters], but isn't declared anywhere (yuck)
+- (BOOL)canPrintHeadersAndFooters
+{
+ return NO;
+}
+
+// This is tested in -[WebFrameView printOperationWithPrintInfo:], but isn't declared anywhere (yuck)
+- (NSPrintOperation *)printOperationWithPrintInfo:(NSPrintInfo *)printInfo
+{
+ return [[PDFSubview document] getPrintOperationForPrintInfo:printInfo autoRotate:YES];
+}
+
+#pragma mark WebDocumentView PROTOCOL IMPLEMENTATION
+
+- (void)setDataSource:(WebDataSource *)ds
+{
+ if (dataSource == ds)
+ return;
+
+ dataSource = [ds retain];
+
+ // FIXME: There must be some better place to put this. There is no comment in ChangeLog
+ // explaining why it's in this method.
+ [self setFrame:[[self superview] frame]];
+}
+
+- (void)dataSourceUpdated:(WebDataSource *)dataSource
+{
+}
+
+- (void)setNeedsLayout:(BOOL)flag
+{
+}
+
+- (void)layout
+{
+}
+
+- (void)viewWillMoveToHostWindow:(NSWindow *)hostWindow
+{
+}
+
+- (void)viewDidMoveToHostWindow
+{
+}
+
+#pragma mark WebDocumentElement PROTOCOL IMPLEMENTATION
+
+- (NSDictionary *)elementAtPoint:(NSPoint)point
+{
+ WebFrame *frame = [dataSource webFrame];
+ ASSERT(frame);
+
+ return [NSDictionary dictionaryWithObjectsAndKeys:
+ frame, WebElementFrameKey,
+ [NSNumber numberWithBool:[self _pointIsInSelection:point]], WebElementIsSelectedKey,
+ nil];
+}
+
+- (NSDictionary *)elementAtPoint:(NSPoint)point allowShadowContent:(BOOL)allow
+{
+ return [self elementAtPoint:point];
+}
+
+#pragma mark WebDocumentSearching PROTOCOL IMPLEMENTATION
+
+- (BOOL)searchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag
+{
+ return [self searchFor:string direction:forward caseSensitive:caseFlag wrap:wrapFlag startInSelection:NO];
+}
+
+#pragma mark WebDocumentIncrementalSearching PROTOCOL IMPLEMENTATION
+
+- (BOOL)searchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag startInSelection:(BOOL)startInSelection
+{
+ PDFSelection *selection = [self _nextMatchFor:string direction:forward caseSensitive:caseFlag wrap:wrapFlag fromSelection:[PDFSubview currentSelection] startInSelection:startInSelection];
+ if (!selection)
+ return NO;
+
+ [PDFSubview setCurrentSelection:selection];
+ [PDFSubview scrollSelectionToVisible:nil];
+ return YES;
+}
+
+#pragma mark WebMultipleTextMatches PROTOCOL IMPLEMENTATION
+
+- (void)setMarkedTextMatchesAreHighlighted:(BOOL)newValue
+{
+ // This method is part of the WebMultipleTextMatches algorithm, but this class doesn't support
+ // highlighting text matches inline.
+#ifndef NDEBUG
+ if (newValue)
+ LOG_ERROR("[WebPDFView setMarkedTextMatchesAreHighlighted:] called with YES, which isn't supported");
+#endif
+}
+
+- (BOOL)markedTextMatchesAreHighlighted
+{
+ return NO;
+}
+
+- (NSUInteger)markAllMatchesForText:(NSString *)string caseSensitive:(BOOL)caseFlag limit:(NSUInteger)limit
+{
+ PDFSelection *previousMatch = nil;
+ PDFSelection *nextMatch = nil;
+ NSMutableArray *matches = [[NSMutableArray alloc] initWithCapacity:limit];
+
+ for (;;) {
+ nextMatch = [self _nextMatchFor:string direction:YES caseSensitive:caseFlag wrap:NO fromSelection:previousMatch startInSelection:NO];
+ if (!nextMatch)
+ break;
+
+ [matches addObject:nextMatch];
+ previousMatch = nextMatch;
+
+ if ([matches count] >= limit)
+ break;
+ }
+
+ [self _setTextMatches:matches];
+ [matches release];
+
+ return [matches count];
+}
+
+- (void)unmarkAllTextMatches
+{
+ [self _setTextMatches:nil];
+}
+
+- (NSArray *)rectsForTextMatches
+{
+ NSMutableArray *result = [NSMutableArray arrayWithCapacity:[textMatches count]];
+ NSSet *visiblePages = [self _visiblePDFPages];
+ NSEnumerator *matchEnumerator = [textMatches objectEnumerator];
+ PDFSelection *match;
+
+ while ((match = [matchEnumerator nextObject]) != nil) {
+ NSEnumerator *pages = [[match pages] objectEnumerator];
+ PDFPage *page;
+ while ((page = [pages nextObject]) != nil) {
+
+ // Skip pages that aren't visible (needed for non-continuous modes, see 5362989)
+ if (![visiblePages containsObject:page])
+ continue;
+
+ NSRect selectionOnPageInPDFViewCoordinates = [PDFSubview convertRect:[match boundsForPage:page] fromPage:page];
+ [result addObject:[NSValue valueWithRect:selectionOnPageInPDFViewCoordinates]];
+ }
+ }
+
+ return result;
+}
+
+#pragma mark WebDocumentText PROTOCOL IMPLEMENTATION
+
+- (BOOL)supportsTextEncoding
+{
+ return NO;
+}
+
+- (NSString *)string
+{
+ return [[PDFSubview document] string];
+}
+
+- (NSAttributedString *)attributedString
+{
+ // changing the selection is a hack, but the only way to get an attr string is via PDFSelection
+
+ // must copy this selection object because we change the selection which seems to release it
+ PDFSelection *savedSelection = [[PDFSubview currentSelection] copy];
+ [PDFSubview selectAll:nil];
+ NSAttributedString *result = [[PDFSubview currentSelection] attributedString];
+ if (savedSelection) {
+ [PDFSubview setCurrentSelection:savedSelection];
+ [savedSelection release];
+ } else {
+ // FIXME: behavior of setCurrentSelection:nil is not documented - check 4182934 for progress
+ // Otherwise, we could collapse this code with the case above.
+ [PDFSubview clearSelection];
+ }
+
+ result = [self _scaledAttributedString:result];
+
+ return result;
+}
+
+- (NSString *)selectedString
+{
+ return [[PDFSubview currentSelection] string];
+}
+
+- (NSAttributedString *)selectedAttributedString
+{
+ return [self _scaledAttributedString:[[PDFSubview currentSelection] attributedString]];
+}
+
+- (void)selectAll
+{
+ [PDFSubview selectAll:nil];
+}
+
+- (void)deselectAll
+{
+ [PDFSubview clearSelection];
+}
+
+#pragma mark WebDocumentViewState PROTOCOL IMPLEMENTATION
+
+// Even though to WebKit we are the "docView", in reality a PDFView contains its own scrollview and docView.
+// And it even turns out there is another PDFKit view between the docView and its enclosing ScrollView, so
+// we have to be sure to do our calculations based on that view, immediately inside the ClipView. We try
+// to make as few assumptions about the PDFKit view hierarchy as possible.
+
+- (NSPoint)scrollPoint
+{
+ NSView *realDocView = [PDFSubview documentView];
+ NSClipView *clipView = [[realDocView enclosingScrollView] contentView];
+ return [clipView bounds].origin;
+}
+
+- (void)setScrollPoint:(NSPoint)p
+{
+ WebFrame *frame = [dataSource webFrame];
+ //FIXME: We only restore scroll state in the non-frames case because otherwise we get a crash due to
+ // PDFKit calling display from within its drawRect:. See bugzilla 4164.
+ if (![frame parentFrame]) {
+ NSView *realDocView = [PDFSubview documentView];
+ [[[realDocView enclosingScrollView] documentView] scrollPoint:p];
+ }
+}
+
+- (id)viewState
+{
+ NSMutableArray *state = [NSMutableArray arrayWithCapacity:4];
+ PDFDisplayMode mode = [PDFSubview displayMode];
+ [state addObject:[NSNumber numberWithInt:mode]];
+ if (mode == kPDFDisplaySinglePage || mode == kPDFDisplayTwoUp) {
+ unsigned int pageIndex = [[PDFSubview document] indexForPage:[PDFSubview currentPage]];
+ [state addObject:[NSNumber numberWithUnsignedInt:pageIndex]];
+ } // else in continuous modes, scroll position gets us to the right page
+ BOOL autoScaleFlag = [PDFSubview autoScales];
+ [state addObject:[NSNumber numberWithBool:autoScaleFlag]];
+ if (!autoScaleFlag)
+ [state addObject:[NSNumber numberWithFloat:[PDFSubview scaleFactor]]];
+
+ return state;
+}
+
+- (void)setViewState:(id)statePList
+{
+ ASSERT([statePList isKindOfClass:[NSArray class]]);
+ NSArray *state = statePList;
+ int i = 0;
+ PDFDisplayMode mode = [[state objectAtIndex:i++] intValue];
+ [PDFSubview setDisplayMode:mode];
+ if (mode == kPDFDisplaySinglePage || mode == kPDFDisplayTwoUp) {
+ unsigned int pageIndex = [[state objectAtIndex:i++] unsignedIntValue];
+ [PDFSubview goToPage:[[PDFSubview document] pageAtIndex:pageIndex]];
+ } // else in continuous modes, scroll position gets us to the right page
+ BOOL autoScaleFlag = [[state objectAtIndex:i++] boolValue];
+ [PDFSubview setAutoScales:autoScaleFlag];
+ if (!autoScaleFlag)
+ [PDFSubview setScaleFactor:[[state objectAtIndex:i++] floatValue]];
+}
+
+#pragma mark _WebDocumentTextSizing PROTOCOL IMPLEMENTATION
+
+- (IBAction)_makeTextSmaller:(id)sender
+{
+ [PDFSubviewProxy zoomOut:sender];
+}
+
+- (IBAction)_makeTextLarger:(id)sender
+{
+ [PDFSubviewProxy zoomIn:sender];
+}
+
+- (IBAction)_makeTextStandardSize:(id)sender
+{
+ [PDFSubviewProxy setScaleFactor:1.0f];
+}
+
+// never sent because we do not track the common size factor
+- (void)_textSizeMultiplierChanged { ASSERT_NOT_REACHED(); }
+
+- (BOOL)_tracksCommonSizeFactor
+{
+ // We keep our own scale factor instead of tracking the common one in the WebView for a couple reasons.
+ // First, PDFs tend to have visually smaller text because they are laid out for a printed page instead of
+ // the screen. Second, the PDFView feature of AutoScaling means our scaling factor can be quiet variable.
+ return NO;
+}
+
+- (BOOL)_canMakeTextSmaller
+{
+ return [PDFSubview canZoomOut];
+}
+
+- (BOOL)_canMakeTextLarger
+{
+ return [PDFSubview canZoomIn];
+}
+
+- (BOOL)_canMakeTextStandardSize
+{
+ return [PDFSubview scaleFactor] != 1.0;
+}
+
+#pragma mark WebDocumentSelection PROTOCOL IMPLEMENTATION
+
+- (NSRect)selectionRect
+{
+ NSRect result = NSZeroRect;
+ PDFSelection *selection = [PDFSubview currentSelection];
+ NSEnumerator *pages = [[selection pages] objectEnumerator];
+ PDFPage *page;
+ while ((page = [pages nextObject]) != nil) {
+ NSRect selectionOnPageInPDFViewCoordinates = [PDFSubview convertRect:[selection boundsForPage:page] fromPage:page];
+ if (NSIsEmptyRect(result))
+ result = selectionOnPageInPDFViewCoordinates;
+ else
+ result = NSUnionRect(result, selectionOnPageInPDFViewCoordinates);
+ }
+
+ // Convert result to be in documentView (selectionView) coordinates
+ result = [PDFSubview convertRect:result toView:[PDFSubview documentView]];
+
+ return result;
+}
+
+- (NSArray *)selectionTextRects
+{
+ // FIXME: We'd need new PDFKit API/SPI to get multiple text rects for selections that intersect more than one line
+ return [NSArray arrayWithObject:[NSValue valueWithRect:[self selectionRect]]];
+}
+
+- (NSView *)selectionView
+{
+ return [PDFSubview documentView];
+}
+
+- (NSImage *)selectionImageForcingBlackText:(BOOL)forceBlackText
+{
+ // Convert the selection to an attributed string, and draw that.
+ // FIXME 4621154: this doesn't handle italics (and maybe other styles)
+ // FIXME 4604366: this doesn't handle text at non-actual size
+ NSMutableAttributedString *attributedString = [[self selectedAttributedString] mutableCopy];
+ NSRange wholeStringRange = NSMakeRange(0, [attributedString length]);
+
+ // Modify the styles in the attributed string to draw black text, no background, and no underline. We draw
+ // no underline because it would look ugly.
+ [attributedString beginEditing];
+ [attributedString removeAttribute:NSBackgroundColorAttributeName range:wholeStringRange];
+ [attributedString removeAttribute:NSUnderlineStyleAttributeName range:wholeStringRange];
+ if (forceBlackText)
+ [attributedString addAttribute:NSForegroundColorAttributeName value:[NSColor colorWithDeviceWhite:0.0f alpha:1.0f] range:wholeStringRange];
+ [attributedString endEditing];
+
+ NSImage* selectionImage = [[[NSImage alloc] initWithSize:[self selectionRect].size] autorelease];
+
+ [selectionImage lockFocus];
+ [attributedString drawAtPoint:NSZeroPoint];
+ [selectionImage unlockFocus];
+
+ [attributedString release];
+
+ return selectionImage;
+}
+
+- (NSRect)selectionImageRect
+{
+ // FIXME: deal with clipping?
+ return [self selectionRect];
+}
+
+- (NSArray *)pasteboardTypesForSelection
+{
+ return [NSArray arrayWithObjects:NSRTFDPboardType, NSRTFPboardType, NSStringPboardType, nil];
+}
+
+- (void)writeSelectionWithPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard
+{
+ NSAttributedString *attributedString = [self selectedAttributedString];
+
+ if ([types containsObject:NSRTFDPboardType]) {
+ NSData *RTFDData = [attributedString RTFDFromRange:NSMakeRange(0, [attributedString length]) documentAttributes:nil];
+ [pasteboard setData:RTFDData forType:NSRTFDPboardType];
+ }
+
+ if ([types containsObject:NSRTFPboardType]) {
+ if ([attributedString containsAttachments])
+ attributedString = [attributedString _web_attributedStringByStrippingAttachmentCharacters];
+
+ NSData *RTFData = [attributedString RTFFromRange:NSMakeRange(0, [attributedString length]) documentAttributes:nil];
+ [pasteboard setData:RTFData forType:NSRTFPboardType];
+ }
+
+ if ([types containsObject:NSStringPboardType])
+ [pasteboard setString:[self selectedString] forType:NSStringPboardType];
+}
+
+#pragma mark PDFView DELEGATE METHODS
+
+- (void)PDFViewWillClickOnLink:(PDFView *)sender withURL:(NSURL *)URL
+{
+ if (!URL)
+ return;
+
+ NSWindow *window = [sender window];
+ NSEvent *nsEvent = [window currentEvent];
+ const int noButton = -1;
+ int button = noButton;
+ RefPtr<Event> event;
+ switch ([nsEvent type]) {
+ case NSLeftMouseUp:
+ button = 0;
+ break;
+ case NSRightMouseUp:
+ button = 1;
+ break;
+ case NSOtherMouseUp:
+ button = [nsEvent buttonNumber];
+ break;
+ case NSKeyDown: {
+ PlatformKeyboardEvent pe(nsEvent);
+ pe.disambiguateKeyDownEvent(PlatformKeyboardEvent::RawKeyDown);
+ event = new KeyboardEvent(keydownEvent, true, true, 0,
+ pe.keyIdentifier(), pe.windowsVirtualKeyCode(),
+ pe.ctrlKey(), pe.altKey(), pe.shiftKey(), pe.metaKey(), false);
+ }
+ default:
+ break;
+ }
+ if (button != noButton)
+ event = new MouseEvent(clickEvent, true, true, 0, [nsEvent clickCount], 0, 0, 0, 0,
+ [nsEvent modifierFlags] & NSControlKeyMask,
+ [nsEvent modifierFlags] & NSAlternateKeyMask,
+ [nsEvent modifierFlags] & NSShiftKeyMask,
+ [nsEvent modifierFlags] & NSCommandKeyMask,
+ button, 0, 0, true);
+
+ // Call to the frame loader because this is where our security checks are made.
+ [[dataSource webFrame] _frameLoader]->load(URL, event.get());
+}
+
+- (void)PDFViewOpenPDFInNativeApplication:(PDFView *)sender
+{
+ // Delegate method sent when the user requests opening the PDF file in the system's default app
+ [self _openWithFinder:sender];
+}
+
+- (void)PDFViewSavePDFToDownloadFolder:(PDFView *)sender
+{
+ // We don't want to write the file until we have a document to write (see 5267607).
+ if (![PDFSubview document]) {
+ NSBeep();
+ return;
+ }
+
+ // Delegate method sent when the user requests downloading the PDF file to disk. We pass NO for
+ // showingPanel: so that the PDF file is saved to the standard location without user intervention.
+ CallUIDelegate([self _webView], @selector(webView:saveFrameView:showingPanel:), [[dataSource webFrame] frameView], NO);
+}
+
+@end
+
+@implementation WebPDFView (FileInternal)
+
++ (Class)_PDFPreviewViewClass
+{
+ static Class PDFPreviewViewClass = nil;
+ static BOOL checkedForPDFPreviewViewClass = NO;
+
+ if (!checkedForPDFPreviewViewClass) {
+ checkedForPDFPreviewViewClass = YES;
+ PDFPreviewViewClass = [[WebPDFView PDFKitBundle] classNamed:@"PDFPreviewView"];
+ }
+
+ // This class might not be available; callers need to deal with a nil return here.
+ return PDFPreviewViewClass;
+}
+
++ (Class)_PDFViewClass
+{
+ static Class PDFViewClass = nil;
+ if (PDFViewClass == nil) {
+ PDFViewClass = [[WebPDFView PDFKitBundle] classNamed:@"PDFView"];
+ if (!PDFViewClass)
+ LOG_ERROR("Couldn't find PDFView class in PDFKit.framework");
+ }
+ return PDFViewClass;
+}
+
+- (BOOL)_anyPDFTagsFoundInMenu:(NSMenu *)menu
+{
+ NSEnumerator *e = [[menu itemArray] objectEnumerator];
+ NSMenuItem *item;
+ while ((item = [e nextObject]) != nil) {
+ switch ([item tag]) {
+ case WebMenuItemTagOpenWithDefaultApplication:
+ case WebMenuItemPDFActualSize:
+ case WebMenuItemPDFZoomIn:
+ case WebMenuItemPDFZoomOut:
+ case WebMenuItemPDFAutoSize:
+ case WebMenuItemPDFSinglePage:
+ case WebMenuItemPDFSinglePageScrolling:
+ case WebMenuItemPDFFacingPages:
+ case WebMenuItemPDFFacingPagesScrolling:
+ case WebMenuItemPDFContinuous:
+ case WebMenuItemPDFNextPage:
+ case WebMenuItemPDFPreviousPage:
+ return YES;
+ }
+ }
+ return NO;
+}
+
+- (void)_applyPDFDefaults
+{
+ // Set up default viewing params
+ WebPreferences *prefs = [[dataSource _webView] preferences];
+ float scaleFactor = [prefs PDFScaleFactor];
+ if (scaleFactor == 0)
+ [PDFSubview setAutoScales:YES];
+ else {
+ [PDFSubview setAutoScales:NO];
+ [PDFSubview setScaleFactor:scaleFactor];
+ }
+ [PDFSubview setDisplayMode:[prefs PDFDisplayMode]];
+}
+
+- (BOOL)_canLookUpInDictionary
+{
+ return [PDFSubview respondsToSelector:@selector(_searchInDictionary:)];
+}
+
+- (NSClipView *)_clipViewForPDFDocumentView
+{
+ NSClipView *clipView = (NSClipView *)[[PDFSubview documentView] _web_superviewOfClass:[NSClipView class]];
+ ASSERT(clipView);
+ return clipView;
+}
+
+- (NSEvent *)_fakeKeyEventWithFunctionKey:(unichar)functionKey
+{
+ // FIXME 4400480: when PDFView implements the standard scrolling selectors that this
+ // method is used to mimic, we can eliminate this method and call them directly.
+ NSString *keyAsString = [NSString stringWithCharacters:&functionKey length:1];
+ return [NSEvent keyEventWithType:NSKeyDown
+ location:NSZeroPoint
+ modifierFlags:0
+ timestamp:0
+ windowNumber:0
+ context:nil
+ characters:keyAsString
+ charactersIgnoringModifiers:keyAsString
+ isARepeat:NO
+ keyCode:0];
+}
+
+- (void)_lookUpInDictionaryFromMenu:(id)sender
+{
+ // This method is used by WebKit's context menu item. Here we map to the method that
+ // PDFView uses. Since the PDFView method isn't API, and isn't available on all versions
+ // of PDFKit, we use performSelector after a respondsToSelector check, rather than calling it directly.
+ if ([self _canLookUpInDictionary])
+ [PDFSubview performSelector:@selector(_searchInDictionary:) withObject:sender];
+}
+
+- (NSMutableArray *)_menuItemsFromPDFKitForEvent:(NSEvent *)theEvent
+{
+ NSMutableArray *copiedItems = [NSMutableArray array];
+ NSDictionary *actionsToTags = [[NSDictionary alloc] initWithObjectsAndKeys:
+ [NSNumber numberWithInt:WebMenuItemPDFActualSize], NSStringFromSelector(@selector(_setActualSize:)),
+ [NSNumber numberWithInt:WebMenuItemPDFZoomIn], NSStringFromSelector(@selector(zoomIn:)),
+ [NSNumber numberWithInt:WebMenuItemPDFZoomOut], NSStringFromSelector(@selector(zoomOut:)),
+ [NSNumber numberWithInt:WebMenuItemPDFAutoSize], NSStringFromSelector(@selector(_setAutoSize:)),
+ [NSNumber numberWithInt:WebMenuItemPDFSinglePage], NSStringFromSelector(@selector(_setSinglePage:)),
+ [NSNumber numberWithInt:WebMenuItemPDFSinglePageScrolling], NSStringFromSelector(@selector(_setSinglePageScrolling:)),
+ [NSNumber numberWithInt:WebMenuItemPDFFacingPages], NSStringFromSelector(@selector(_setDoublePage:)),
+ [NSNumber numberWithInt:WebMenuItemPDFFacingPagesScrolling], NSStringFromSelector(@selector(_setDoublePageScrolling:)),
+ [NSNumber numberWithInt:WebMenuItemPDFContinuous], NSStringFromSelector(@selector(_toggleContinuous:)),
+ [NSNumber numberWithInt:WebMenuItemPDFNextPage], NSStringFromSelector(@selector(goToNextPage:)),
+ [NSNumber numberWithInt:WebMenuItemPDFPreviousPage], NSStringFromSelector(@selector(goToPreviousPage:)),
+ nil];
+
+ // Leave these menu items out, since WebKit inserts equivalent ones. Note that we leave out PDFKit's "Look Up in Dictionary"
+ // item here because WebKit already includes an item with the same title and purpose. We map WebKit's to PDFKit's
+ // "Look Up in Dictionary" via the implementation of -[WebPDFView _lookUpInDictionaryFromMenu:].
+ NSSet *unwantedActions = [[NSSet alloc] initWithObjects:
+ NSStringFromSelector(@selector(_searchInSpotlight:)),
+ NSStringFromSelector(@selector(_searchInGoogle:)),
+ NSStringFromSelector(@selector(_searchInDictionary:)),
+ NSStringFromSelector(@selector(copy:)),
+ nil];
+
+ NSEnumerator *e = [[[PDFSubview menuForEvent:theEvent] itemArray] objectEnumerator];
+ NSMenuItem *item;
+ while ((item = [e nextObject]) != nil) {
+
+ NSString *actionString = NSStringFromSelector([item action]);
+
+ if ([unwantedActions containsObject:actionString])
+ continue;
+
+ // Copy items since a menu item can be in only one menu at a time, and we don't
+ // want to modify the original menu supplied by PDFKit.
+ NSMenuItem *itemCopy = [item copy];
+ [copiedItems addObject:itemCopy];
+
+ // Include all of PDFKit's separators for now. At the end we'll remove any ones that were made
+ // useless by removing PDFKit's menu items.
+ if ([itemCopy isSeparatorItem])
+ continue;
+
+ NSNumber *tagNumber = [actionsToTags objectForKey:actionString];
+
+ int tag;
+ if (tagNumber != nil)
+ tag = [tagNumber intValue];
+ else {
+ // This should happen only if PDFKit updates behind WebKit's back. It's non-ideal because clients that only include tags
+ // that they recognize (like Safari) won't get these PDFKit additions until WebKit is updated to match.
+ tag = WebMenuItemTagOther;
+ LOG_ERROR("no WebKit menu item tag found for PDF context menu item action \"%@\", using WebMenuItemTagOther", actionString);
+ }
+
+ if ([itemCopy tag] == 0) {
+ [itemCopy setTag:tag];
+ if ([itemCopy target] == PDFSubview) {
+ // Note that updating the defaults is cheap because it catches redundant settings, so installing
+ // the proxy for actions that don't impact the defaults is OK
+ [itemCopy setTarget:PDFSubviewProxy];
+ }
+ } else
+ LOG_ERROR("PDF context menu item %@ came with tag %d, so no WebKit tag was applied. This could mean that the item doesn't appear in clients such as Safari.", [itemCopy title], [itemCopy tag]);
+ }
+
+ [actionsToTags release];
+ [unwantedActions release];
+
+ // Since we might have removed elements supplied by PDFKit, and we want to minimize our hardwired
+ // knowledge of the order and arrangement of PDFKit's menu items, we need to remove any bogus
+ // separators that were left behind.
+ [copiedItems _webkit_removeUselessMenuItemSeparators];
+
+ return copiedItems;
+}
+
+- (PDFSelection *)_nextMatchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag fromSelection:(PDFSelection *)initialSelection startInSelection:(BOOL)startInSelection
+{
+ if (![string length])
+ return nil;
+
+ int options = 0;
+ if (!forward)
+ options |= NSBackwardsSearch;
+
+ if (!caseFlag)
+ options |= NSCaseInsensitiveSearch;
+
+ PDFDocument *document = [PDFSubview document];
+
+ PDFSelection *selectionForInitialSearch = [initialSelection copy];
+ if (startInSelection) {
+ // Initially we want to include the selected text in the search. PDFDocument's API always searches from just
+ // past the passed-in selection, so we need to pass a selection that's modified appropriately.
+ // FIXME 4182863: Ideally we'd use a zero-length selection at the edge of the current selection, but zero-length
+ // selections don't work in PDFDocument. So instead we make a one-length selection just before or after the
+ // current selection, which works for our purposes even when the current selection is at an edge of the
+ // document.
+ int initialSelectionLength = [[initialSelection string] length];
+ if (forward) {
+ [selectionForInitialSearch extendSelectionAtStart:1];
+ [selectionForInitialSearch extendSelectionAtEnd:-initialSelectionLength];
+ } else {
+ [selectionForInitialSearch extendSelectionAtEnd:1];
+ [selectionForInitialSearch extendSelectionAtStart:-initialSelectionLength];
+ }
+ }
+ PDFSelection *foundSelection = [document findString:string fromSelection:selectionForInitialSearch withOptions:options];
+ [selectionForInitialSearch release];
+
+ // If we first searched in the selection, and we found the selection, search again from just past the selection
+ if (startInSelection && _PDFSelectionsAreEqual(foundSelection, initialSelection))
+ foundSelection = [document findString:string fromSelection:initialSelection withOptions:options];
+
+ if (!foundSelection && wrapFlag)
+ foundSelection = [document findString:string fromSelection:nil withOptions:options];
+
+ return foundSelection;
+}
+
+- (void)_openWithFinder:(id)sender
+{
+ // We don't want to write the file until we have a document to write (see 4892525).
+ if (![PDFSubview document]) {
+ NSBeep();
+ return;
+ }
+
+ NSString *opath = [self _path];
+
+ if (opath) {
+ if (!written) {
+ // Create a PDF file with the minimal permissions (only accessible to the current user, see 4145714)
+ NSNumber *permissions = [[NSNumber alloc] initWithInt:S_IRUSR];
+ NSDictionary *fileAttributes = [[NSDictionary alloc] initWithObjectsAndKeys:permissions, NSFilePosixPermissions, nil];
+ [permissions release];
+
+ [[NSFileManager defaultManager] createFileAtPath:opath contents:[dataSource data] attributes:fileAttributes];
+
+ [fileAttributes release];
+ written = YES;
+ }
+
+ if (![[NSWorkspace sharedWorkspace] openFile:opath]) {
+ // NSWorkspace couldn't open file. Do we need an alert
+ // here? We ignore the error elsewhere.
+ }
+ }
+}
+
+- (NSString *)_path
+{
+ // Generate path once.
+ if (path)
+ return path;
+
+ NSString *filename = [[dataSource response] suggestedFilename];
+ NSFileManager *manager = [NSFileManager defaultManager];
+ NSString *temporaryPDFDirectoryPath = [self _temporaryPDFDirectoryPath];
+
+ if (!temporaryPDFDirectoryPath) {
+ // This should never happen; if it does we'll fail silently on non-debug builds.
+ ASSERT_NOT_REACHED();
+ return nil;
+ }
+
+ path = [temporaryPDFDirectoryPath stringByAppendingPathComponent:filename];
+ if ([manager fileExistsAtPath:path]) {
+ NSString *pathTemplatePrefix = [temporaryPDFDirectoryPath stringByAppendingPathComponent:@"XXXXXX-"];
+ NSString *pathTemplate = [pathTemplatePrefix stringByAppendingString:filename];
+ // fileSystemRepresentation returns a const char *; copy it into a char * so we can modify it safely
+ char *cPath = strdup([pathTemplate fileSystemRepresentation]);
+ int fd = mkstemps(cPath, strlen(cPath) - strlen([pathTemplatePrefix fileSystemRepresentation]) + 1);
+ if (fd < 0) {
+ // Couldn't create a temporary file! Should never happen; if it does we'll fail silently on non-debug builds.
+ ASSERT_NOT_REACHED();
+ path = nil;
+ } else {
+ close(fd);
+ path = [manager stringWithFileSystemRepresentation:cPath length:strlen(cPath)];
+ }
+ free(cPath);
+ }
+
+ [path retain];
+
+ return path;
+}
+
+- (void)_PDFDocumentViewMightHaveScrolled:(NSNotification *)notification
+{
+ NSClipView *clipView = [self _clipViewForPDFDocumentView];
+ ASSERT([notification object] == clipView);
+
+ NSPoint scrollPosition = [clipView bounds].origin;
+ if (NSEqualPoints(scrollPosition, lastScrollPosition))
+ return;
+
+ lastScrollPosition = scrollPosition;
+ WebView *webView = [self _webView];
+ [[webView _UIDelegateForwarder] webView:webView didScrollDocumentInFrameView:[[dataSource webFrame] frameView]];
+}
+
+- (PDFView *)_PDFSubview
+{
+ return PDFSubview;
+}
+
+- (BOOL)_pointIsInSelection:(NSPoint)point
+{
+ PDFPage *page = [PDFSubview pageForPoint:point nearest:NO];
+ if (!page)
+ return NO;
+
+ NSRect selectionRect = [PDFSubview convertRect:[[PDFSubview currentSelection] boundsForPage:page] fromPage:page];
+
+ return NSPointInRect(point, selectionRect);
+}
+
+- (void)_scaleOrDisplayModeOrPageChanged:(NSNotification *)notification
+{
+ ASSERT([notification object] == PDFSubview);
+ if (!_ignoreScaleAndDisplayModeAndPageNotifications) {
+ [self _updatePreferencesSoon];
+ // Notify UI delegate that the entire page has been redrawn, since (unlike for WebHTMLView)
+ // we can't hook into the drawing mechanism itself. This fixes 5337529.
+ WebView *webView = [self _webView];
+ [[webView _UIDelegateForwarder] webView:webView didDrawRect:[webView bounds]];
+ }
+}
+
+- (NSAttributedString *)_scaledAttributedString:(NSAttributedString *)unscaledAttributedString
+{
+ if (!unscaledAttributedString)
+ return nil;
+
+ float scaleFactor = [PDFSubview scaleFactor];
+ if (scaleFactor == 1.0)
+ return unscaledAttributedString;
+
+ NSMutableAttributedString *result = [[unscaledAttributedString mutableCopy] autorelease];
+ unsigned int length = [result length];
+ NSRange effectiveRange = NSMakeRange(0,0);
+
+ [result beginEditing];
+ while (NSMaxRange(effectiveRange) < length) {
+ NSFont *unscaledFont = [result attribute:NSFontAttributeName atIndex:NSMaxRange(effectiveRange) effectiveRange:&effectiveRange];
+
+ if (!unscaledFont) {
+ // FIXME: We can't scale the font if we don't know what it is. We should always know what it is,
+ // but sometimes don't due to PDFKit issue 5089411. When that's addressed, we can remove this
+ // early continue.
+ LOG_ERROR("no font attribute found in range %@ for attributed string \"%@\" on page %@ (see radar 5089411)", NSStringFromRange(effectiveRange), result, [[dataSource request] URL]);
+ continue;
+ }
+
+ NSFont *scaledFont = [NSFont fontWithName:[unscaledFont fontName] size:[unscaledFont pointSize]*scaleFactor];
+ [result addAttribute:NSFontAttributeName value:scaledFont range:effectiveRange];
+ }
+ [result endEditing];
+
+ return result;
+}
+
+- (void)_setTextMatches:(NSArray *)array
+{
+ [array retain];
+ [textMatches release];
+ textMatches = array;
+}
+
+- (NSString *)_temporaryPDFDirectoryPath
+{
+ // Returns nil if the temporary PDF directory didn't exist and couldn't be created
+
+ static NSString *_temporaryPDFDirectoryPath = nil;
+
+ if (!_temporaryPDFDirectoryPath) {
+ NSString *temporaryDirectoryTemplate = [NSTemporaryDirectory() stringByAppendingPathComponent:@"WebKitPDFs-XXXXXX"];
+ char *cTemplate = strdup([temporaryDirectoryTemplate fileSystemRepresentation]);
+
+ if (!mkdtemp(cTemplate)) {
+ // This should never happen; if it does we'll fail silently on non-debug builds.
+ ASSERT_NOT_REACHED();
+ } else {
+ // cTemplate has now been modified to be the just-created directory name. This directory has 700 permissions,
+ // so only the current user can add to it or view its contents.
+ _temporaryPDFDirectoryPath = [[[NSFileManager defaultManager] stringWithFileSystemRepresentation:cTemplate length:strlen(cTemplate)] retain];
+ }
+
+ free(cTemplate);
+ }
+
+ return _temporaryPDFDirectoryPath;
+}
+
+- (void)_trackFirstResponder
+{
+ ASSERT([self window]);
+
+ id newFirstResponder = [[self window] firstResponder];
+ if (newFirstResponder == trackedFirstResponder)
+ return;
+
+ // This next clause is the entire purpose of _trackFirstResponder. In other WebDocument
+ // view classes this is done in a resignFirstResponder override, but in this case the
+ // first responder view is a PDFKit class that we can't subclass.
+ if (trackedFirstResponder == [PDFSubview documentView] && ![[dataSource _webView] maintainsInactiveSelection])
+ [self deselectAll];
+
+
+ [trackedFirstResponder release];
+ trackedFirstResponder = [newFirstResponder retain];
+}
+
+- (void)_updatePreferences:(WebPreferences *)prefs
+{
+ float scaleFactor = [PDFSubview autoScales] ? 0.0f : [PDFSubview scaleFactor];
+ [prefs setPDFScaleFactor:scaleFactor];
+ [prefs setPDFDisplayMode:[PDFSubview displayMode]];
+ _willUpdatePreferencesSoon = NO;
+ [prefs release];
+ [self release];
+}
+
+- (void)_updatePreferencesSoon
+{
+ // Consolidate calls; due to the PDFPrefUpdatingProxy method, this can be called multiple times with a single user action
+ // such as showing the context menu.
+ if (_willUpdatePreferencesSoon)
+ return;
+
+ WebPreferences *prefs = [[dataSource _webView] preferences];
+
+ [self retain];
+ [prefs retain];
+ [self performSelector:@selector(_updatePreferences:) withObject:prefs afterDelay:0];
+ _willUpdatePreferencesSoon = YES;
+}
+
+- (NSSet *)_visiblePDFPages
+{
+ // Returns the set of pages that are at least partly visible, used to avoid processing non-visible pages
+ PDFDocument *pdfDocument = [PDFSubview document];
+ if (!pdfDocument)
+ return nil;
+
+ NSRect pdfViewBounds = [PDFSubview bounds];
+ PDFPage *topLeftPage = [PDFSubview pageForPoint:NSMakePoint(NSMinX(pdfViewBounds), NSMaxY(pdfViewBounds)) nearest:YES];
+ PDFPage *bottomRightPage = [PDFSubview pageForPoint:NSMakePoint(NSMaxX(pdfViewBounds), NSMinY(pdfViewBounds)) nearest:YES];
+
+ // only page-free documents should return nil for either of these two since we passed YES for nearest:
+ if (!topLeftPage) {
+ ASSERT(!bottomRightPage);
+ return nil;
+ }
+
+ NSUInteger firstVisiblePageIndex = [pdfDocument indexForPage:topLeftPage];
+ NSUInteger lastVisiblePageIndex = [pdfDocument indexForPage:bottomRightPage];
+
+ if (firstVisiblePageIndex > lastVisiblePageIndex) {
+ NSUInteger swap = firstVisiblePageIndex;
+ firstVisiblePageIndex = lastVisiblePageIndex;
+ lastVisiblePageIndex = swap;
+ }
+
+ NSMutableSet *result = [NSMutableSet set];
+ NSUInteger pageIndex;
+ for (pageIndex = firstVisiblePageIndex; pageIndex <= lastVisiblePageIndex; ++pageIndex)
+ [result addObject:[pdfDocument pageAtIndex:pageIndex]];
+
+ return result;
+}
+
+@end
+
+@implementation PDFPrefUpdatingProxy
+
+- (id)initWithView:(WebPDFView *)aView
+{
+ // No [super init], since we inherit from NSProxy
+ view = aView;
+ return self;
+}
+
+- (void)forwardInvocation:(NSInvocation *)invocation
+{
+ [invocation invokeWithTarget:[view _PDFSubview]];
+ [view _updatePreferencesSoon];
+}
+
+- (NSMethodSignature *)methodSignatureForSelector:(SEL)sel
+{
+ return [[view _PDFSubview] methodSignatureForSelector:sel];
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebPolicyDelegate.h b/WebKit/mac/WebView/WebPolicyDelegate.h
new file mode 100644
index 0000000..01d0843
--- /dev/null
+++ b/WebKit/mac/WebView/WebPolicyDelegate.h
@@ -0,0 +1,198 @@
+/*
+ * Copyright (C) 2003, 2004, 2005, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+@class NSError;
+@class NSURLResponse;
+@class NSURLRequest;
+@class WebView;
+@class WebFrame;
+@class WebPolicyPrivate;
+
+/*!
+ @enum WebNavigationType
+ @abstract The type of action that triggered a possible navigation.
+ @constant WebNavigationTypeLinkClicked A link with an href was clicked.
+ @constant WebNavigationTypeFormSubmitted A form was submitted.
+ @constant WebNavigationTypeBackForward The user chose back or forward.
+ @constant WebNavigationTypeReload The User hit the reload button.
+ @constant WebNavigationTypeFormResubmitted A form was resubmitted (by virtue of doing back, forward or reload).
+ @constant WebNavigationTypeOther Navigation is taking place for some other reason.
+*/
+
+typedef enum {
+ WebNavigationTypeLinkClicked,
+ WebNavigationTypeFormSubmitted,
+ WebNavigationTypeBackForward,
+ WebNavigationTypeReload,
+ WebNavigationTypeFormResubmitted,
+ WebNavigationTypeOther
+} WebNavigationType;
+
+extern NSString *WebActionNavigationTypeKey; // NSNumber (WebNavigationType)
+extern NSString *WebActionElementKey; // NSDictionary of element info
+extern NSString *WebActionButtonKey; // NSNumber (0 for left button, 1 for middle button, 2 for right button)
+extern NSString *WebActionModifierFlagsKey; // NSNumber (unsigned)
+extern NSString *WebActionOriginalURLKey; // NSURL
+
+/*!
+ @protocol WebPolicyDecisionListener
+ @discussion This protocol is used to call back with the results of a
+ policy decision. This provides the ability to make these decisions
+ asyncrhonously, which means the decision can be made by prompting
+ with a sheet, for example.
+*/
+
+@protocol WebPolicyDecisionListener <NSObject>
+
+/*!
+ @method use
+ @abstract Use the resource
+ @discussion If there remain more policy decisions to be made, then
+ the next policy delegate method gets to decide. This will be
+ either the next navigation policy delegate if there is a redirect,
+ or the content policy delegate. If there are no more policy
+ decisions to be made, the resource will be displayed inline if
+ possible. If there is no view available to display the resource
+ inline, then unableToImplementPolicyWithError:frame: will be
+ called with an appropriate error.
+
+ <p>If a new window is going to be created for this navigation as a
+ result of frame targetting, then it will be created once you call
+ this method.
+*/
+- (void)use;
+/*!
+ @method download
+ @abstract Download the resource instead of displaying it.
+ @discussion This method is more than just a convenience because it
+ allows an in-progress navigation to be converted to a download
+ based on content type, without having to stop and restart the
+ load.
+*/
+- (void)download;
+
+/*!
+ @method ignore
+ @abstract Do nothing (but the client may choose to handle the request itself)
+ @discussion A policy of ignore prevents WebKit from doing anything
+ further with the load, however, the client is still free to handle
+ the request in some other way, such as opening a new window,
+ opening a new window behind the current one, opening the URL in an
+ external app, revealing the location in Finder if a file URL, etc.
+*/
+- (void)ignore;
+
+@end
+
+
+/*!
+ @category WebPolicyDelegate
+ @discussion While loading a URL, WebKit asks the WebPolicyDelegate for
+ policies that determine the action of what to do with the URL or the data that
+ the URL represents. Typically, the policy handler methods are called in this order:
+
+ decidePolicyForNewWindowAction:request:newFrameName:decisionListener: (at most once)<BR>
+ decidePolicyForNavigationAction:request:frame:decisionListener: (zero or more times)<BR>
+ decidePolicyForMIMEType:request:frame: (zero or more times)<BR>
+
+ New window policy is always checked. Navigation policy is checked
+ for the initial load and every redirect unless blocked by an
+ earlier policy. Content policy is checked once the content type is
+ known, unless an earlier policy prevented it.
+
+ In rare cases, content policy might be checked more than
+ once. This occurs when loading a "multipart/x-mixed-replace"
+ document, also known as "server push". In this case, multiple
+ documents come in one navigation, with each replacing the last. In
+ this case, conent policy will be checked for each one.
+*/
+@interface NSObject (WebPolicyDelegate)
+
+/*!
+ @method webView:decidePolicyForNavigationAction:request:frame:decisionListener:
+ @abstract This method is called to decide what to do with a proposed navigation.
+ @param actionInformation Dictionary that describes the action that triggered this navigation.
+ @param request The request for the proposed navigation
+ @param frame The WebFrame in which the navigation is happening
+ @param listener The object to call when the decision is made
+ @discussion This method will be called before loading starts, and
+ on every redirect.
+*/
+- (void)webView:(WebView *)webView decidePolicyForNavigationAction:(NSDictionary *)actionInformation
+ request:(NSURLRequest *)request
+ frame:(WebFrame *)frame
+ decisionListener:(id<WebPolicyDecisionListener>)listener;
+
+/*!
+ @method webView:decidePolicyForNewWindowAction:request:newFrameName:decisionListener:
+ @discussion This method is called to decide what to do with an targetted nagivation that would open a new window.
+ @param actionInformation Dictionary that describes the action that triggered this navigation.
+ @param request The request for the proposed navigation
+ @param frame The frame in which the navigation is taking place
+ @param listener The object to call when the decision is made
+ @discussion This method is provided so that modified clicks on a targetted link which
+ opens a new frame can prevent the new window from being opened if they decide to
+ do something else, like download or present the new frame in a specialized way.
+
+ <p>If this method picks a policy of Use, the new window will be
+ opened, and decidePolicyForNavigationAction:request:frame:decisionListner:
+ will be called with a WebNavigationType of WebNavigationTypeOther
+ in its action. This is to avoid possible confusion about the modifiers.
+*/
+- (void)webView:(WebView *)webView decidePolicyForNewWindowAction:(NSDictionary *)actionInformation
+ request:(NSURLRequest *)request
+ newFrameName:(NSString *)frameName
+ decisionListener:(id<WebPolicyDecisionListener>)listener;
+
+/*!
+ @method webView:decidePolicyForMIMEType:request:frame:
+ @discussion Returns the policy for content which has been partially loaded.
+ Sent after webView:didStartProvisionalLoadForFrame: is sent on the WebFrameLoadDelegate.
+ @param type MIME type for the resource.
+ @param request A NSURLRequest for the partially loaded content.
+ @param frame The frame which is loading the URL.
+ @param listener The object to call when the decision is made
+*/
+- (void)webView:(WebView *)webView decidePolicyForMIMEType:(NSString *)type
+ request:(NSURLRequest *)request
+ frame:(WebFrame *)frame
+ decisionListener:(id<WebPolicyDecisionListener>)listener;
+
+/*!
+ @method webView:unableToImplementPolicy:error:forURL:inFrame:
+ @discussion Called when a WebPolicy could not be implemented. It is up to the client to display appropriate feedback.
+ @param policy The policy that could not be implemented.
+ @param error The error that caused the policy to not be implemented.
+ @param URL The URL of the resource for which a particular action was requested but failed.
+ @param frame The frame in which the policy could not be implemented.
+*/
+- (void)webView:(WebView *)webView unableToImplementPolicyWithError:(NSError *)error frame:(WebFrame *)frame;
+
+@end
diff --git a/WebKit/mac/WebView/WebPolicyDelegate.mm b/WebKit/mac/WebView/WebPolicyDelegate.mm
new file mode 100644
index 0000000..147e761
--- /dev/null
+++ b/WebKit/mac/WebView/WebPolicyDelegate.mm
@@ -0,0 +1,120 @@
+/*
+ * Copyright (C) 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebPolicyDelegatePrivate.h"
+
+#import <WebCore/FrameLoaderTypes.h>
+#import <objc/objc-runtime.h>
+
+using namespace WebCore;
+
+NSString *WebActionNavigationTypeKey = @"WebActionNavigationTypeKey";
+NSString *WebActionElementKey = @"WebActionElementKey";
+NSString *WebActionButtonKey = @"WebActionButtonKey";
+NSString *WebActionModifierFlagsKey = @"WebActionModifierFlagsKey";
+NSString *WebActionOriginalURLKey = @"WebActionOriginalURLKey";
+
+@interface WebPolicyDecisionListenerPrivate : NSObject
+{
+@public
+ id target;
+ SEL action;
+}
+
+- (id)initWithTarget:(id)target action:(SEL)action;
+
+@end
+
+@implementation WebPolicyDecisionListenerPrivate
+
+- (id)initWithTarget:(id)t action:(SEL)a
+{
+ self = [super init];
+ if (!self)
+ return nil;
+ target = [t retain];
+ action = a;
+ return self;
+}
+
+- (void)dealloc
+{
+ [target release];
+ [super dealloc];
+}
+
+@end
+
+@implementation WebPolicyDecisionListener
+
+- (id)_initWithTarget:(id)target action:(SEL)action
+{
+ self = [super init];
+ if (!self)
+ return nil;
+ _private = [[WebPolicyDecisionListenerPrivate alloc] initWithTarget:target action:action];
+ return self;
+}
+
+-(void)dealloc
+{
+ [_private release];
+ [super dealloc];
+}
+
+- (void)_usePolicy:(PolicyAction)policy
+{
+ if (_private->target)
+ ((void (*)(id, SEL, PolicyAction))objc_msgSend)(_private->target, _private->action, policy);
+}
+
+- (void)_invalidate
+{
+ id target = _private->target;
+ _private->target = nil;
+ [target release];
+}
+
+// WebPolicyDecisionListener implementation
+
+- (void)use
+{
+ [self _usePolicy:PolicyUse];
+}
+
+- (void)ignore
+{
+ [self _usePolicy:PolicyIgnore];
+}
+
+- (void)download
+{
+ [self _usePolicy:PolicyDownload];
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebPolicyDelegatePrivate.h b/WebKit/mac/WebView/WebPolicyDelegatePrivate.h
new file mode 100644
index 0000000..f7bbbd5
--- /dev/null
+++ b/WebKit/mac/WebView/WebPolicyDelegatePrivate.h
@@ -0,0 +1,50 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebPolicyDelegate.h>
+
+@class WebHistoryItem;
+@class WebPolicyDecisionListenerPrivate;
+
+typedef enum {
+ WebNavigationTypePlugInRequest = WebNavigationTypeOther + 1
+} WebExtraNavigationType;
+
+@interface WebPolicyDecisionListener : NSObject <WebPolicyDecisionListener>
+{
+@private
+ WebPolicyDecisionListenerPrivate *_private;
+}
+- (id)_initWithTarget:(id)target action:(SEL)action;
+- (void)_invalidate;
+@end
+
+@interface NSObject (WebPolicyDelegatePrivate)
+// Needed for <rdar://problem/3951283> can view pages from the back/forward cache that should be disallowed by Parental Controls
+- (BOOL)webView:(WebView *)webView shouldGoToHistoryItem:(WebHistoryItem *)item;
+@end
diff --git a/WebKit/mac/WebView/WebPreferenceKeysPrivate.h b/WebKit/mac/WebView/WebPreferenceKeysPrivate.h
new file mode 100644
index 0000000..d7a798c
--- /dev/null
+++ b/WebKit/mac/WebView/WebPreferenceKeysPrivate.h
@@ -0,0 +1,85 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// These are private because callers should be using the cover methods. They are in
+// a Private (as opposed to Internal) header file because Safari uses some of them
+// for managed preferences.
+#define WebKitLogLevelPreferenceKey @"WebKitLogLevel"
+#define WebKitStandardFontPreferenceKey @"WebKitStandardFont"
+#define WebKitFixedFontPreferenceKey @"WebKitFixedFont"
+#define WebKitSerifFontPreferenceKey @"WebKitSerifFont"
+#define WebKitSansSerifFontPreferenceKey @"WebKitSansSerifFont"
+#define WebKitCursiveFontPreferenceKey @"WebKitCursiveFont"
+#define WebKitFantasyFontPreferenceKey @"WebKitFantasyFont"
+#define WebKitMinimumFontSizePreferenceKey @"WebKitMinimumFontSize"
+#define WebKitMinimumLogicalFontSizePreferenceKey @"WebKitMinimumLogicalFontSize"
+#define WebKitDefaultFontSizePreferenceKey @"WebKitDefaultFontSize"
+#define WebKitDefaultFixedFontSizePreferenceKey @"WebKitDefaultFixedFontSize"
+#define WebKitDefaultTextEncodingNamePreferenceKey @"WebKitDefaultTextEncodingName"
+#define WebKitUserStyleSheetEnabledPreferenceKey @"WebKitUserStyleSheetEnabledPreferenceKey"
+#define WebKitUserStyleSheetLocationPreferenceKey @"WebKitUserStyleSheetLocationPreferenceKey"
+#define WebKitShouldPrintBackgroundsPreferenceKey @"WebKitShouldPrintBackgroundsPreferenceKey"
+#define WebKitTextAreasAreResizablePreferenceKey @"WebKitTextAreasAreResizable"
+#define WebKitShrinksStandaloneImagesToFitPreferenceKey @"WebKitShrinksStandaloneImagesToFit"
+#define WebKitJavaEnabledPreferenceKey @"WebKitJavaEnabled"
+#define WebKitJavaScriptEnabledPreferenceKey @"WebKitJavaScriptEnabled"
+#define WebKitJavaScriptCanOpenWindowsAutomaticallyPreferenceKey @"WebKitJavaScriptCanOpenWindowsAutomatically"
+#define WebKitPluginsEnabledPreferenceKey @"WebKitPluginsEnabled"
+#define WebKitAllowAnimatedImagesPreferenceKey @"WebKitAllowAnimatedImagesPreferenceKey"
+#define WebKitAllowAnimatedImageLoopingPreferenceKey @"WebKitAllowAnimatedImageLoopingPreferenceKey"
+#define WebKitDisplayImagesKey @"WebKitDisplayImagesKey"
+#define WebKitBackForwardCacheExpirationIntervalKey @"WebKitBackForwardCacheExpirationIntervalKey"
+#define WebKitTabToLinksPreferenceKey @"WebKitTabToLinksPreferenceKey"
+#define WebKitPrivateBrowsingEnabledPreferenceKey @"WebKitPrivateBrowsingEnabled"
+#define WebContinuousSpellCheckingEnabled @"WebContinuousSpellCheckingEnabled"
+#define WebGrammarCheckingEnabled @"WebGrammarCheckingEnabled"
+#define WebKitDOMPasteAllowedPreferenceKey @"WebKitDOMPasteAllowedPreferenceKey"
+#define WebKitUsesPageCachePreferenceKey @"WebKitUsesPageCachePreferenceKey"
+#define WebKitFTPDirectoryTemplatePath @"WebKitFTPDirectoryTemplatePath"
+#define WebKitForceFTPDirectoryListings @"WebKitForceFTPDirectoryListings"
+#define WebKitDeveloperExtrasEnabledPreferenceKey @"WebKitDeveloperExtrasEnabledPreferenceKey"
+#define WebKitAuthorAndUserStylesEnabledPreferenceKey @"WebKitAuthorAndUserStylesEnabledPreferenceKey"
+
+// These are private both because callers should be using the cover methods and because the
+// cover methods themselves are private.
+#define WebKitRespectStandardStyleKeyEquivalentsPreferenceKey @"WebKitRespectStandardStyleKeyEquivalents"
+#define WebKitShowsURLsInToolTipsPreferenceKey @"WebKitShowsURLsInToolTips"
+#define WebKitPDFDisplayModePreferenceKey @"WebKitPDFDisplayMode"
+#define WebKitPDFScaleFactorPreferenceKey @"WebKitPDFScaleFactor"
+#define WebKitUseSiteSpecificSpoofingPreferenceKey @"WebKitUseSiteSpecificSpoofing"
+#define WebKitEditableLinkBehaviorPreferenceKey @"WebKitEditableLinkBehavior"
+#define WebKitCacheModelPreferenceKey @"WebKitCacheModelPreferenceKey"
+
+// CoreGraphics deferred updates are disabled if WebKitEnableCoalescedUpdatesPreferenceKey is set
+// to NO, or has no value. For compatibility with Mac OS X 10.4.6, deferred updates are OFF by
+// default.
+#define WebKitEnableDeferredUpdatesPreferenceKey @"WebKitEnableDeferredUpdates"
+
+// For debugging only. Don't use these.
+#define WebKitPageCacheSizePreferenceKey @"WebKitPageCacheSizePreferenceKey"
+#define WebKitObjectCacheSizePreferenceKey @"WebKitObjectCacheSizePreferenceKey"
diff --git a/WebKit/mac/WebView/WebPreferences.h b/WebKit/mac/WebView/WebPreferences.h
new file mode 100644
index 0000000..1988acc
--- /dev/null
+++ b/WebKit/mac/WebView/WebPreferences.h
@@ -0,0 +1,442 @@
+/*
+ * Copyright (C) 2003, 2004, 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define WebNSUInteger unsigned int
+#else
+#define WebNSUInteger NSUInteger
+#endif
+
+/*!
+@enum WebCacheModel
+
+@abstract Specifies a usage model for a WebView, which WebKit will use to
+determine its caching behavior.
+
+@constant WebCacheModelDocumentViewer Appropriate for a WebView displaying
+a fixed document -- like a splash screen, a chat document, or a word processing
+document -- with no UI for navigation. The WebView will behave like any other
+view, releasing resources when they are no longer referenced. Remote resources,
+if any, will be cached to disk. This is the most memory-efficient setting.
+
+Examples: iChat, Mail, TextMate, Growl.
+
+@constant WebCacheModelDocumentBrowser Appropriate for a WebView displaying
+a browsable series of documents with a UI for navigating between them -- for
+example, a reference materials browser or a website designer. The WebView will
+cache a reasonable number of resources and previously viewed documents in
+memory and/or on disk.
+
+Examples: Dictionary, Help Viewer, Coda.
+
+@constant WebCacheModelPrimaryWebBrowser Appropriate for a WebView in the
+application that acts as the user's primary web browser. The WebView will cache
+a very large number of resources and previously viewed documents in memory
+and/or on disk.
+
+Examples: Safari, OmniWeb, Shiira.
+*/
+enum {
+ WebCacheModelDocumentViewer = 0,
+ WebCacheModelDocumentBrowser = 1,
+ WebCacheModelPrimaryWebBrowser = 2
+};
+typedef WebNSUInteger WebCacheModel;
+
+@class WebPreferencesPrivate;
+
+extern NSString *WebPreferencesChangedNotification;
+
+/*!
+ @class WebPreferences
+*/
+@interface WebPreferences: NSObject <NSCoding>
+{
+@private
+ WebPreferencesPrivate *_private;
+}
+
+/*!
+ @method standardPreferences
+*/
++ (WebPreferences *)standardPreferences;
+
+/*!
+ @method initWithIdentifier:
+ @param anIdentifier A string used to identify the WebPreferences.
+ @discussion WebViews can share instances of WebPreferences by using an instance of WebPreferences with
+ the same identifier. Typically, instance are not created directly. Instead you set the preferences
+ identifier on a WebView. The identifier is used as a prefix that is added to the user defaults keys
+ for the WebPreferences.
+ @result Returns a new instance of WebPreferences or a previously allocated instance with the same identifier.
+*/
+- (id)initWithIdentifier:(NSString *)anIdentifier;
+
+/*!
+ @method identifier
+ @result Returns the identifier for this WebPreferences.
+*/
+- (NSString *)identifier;
+
+/*!
+ @method standardFontFamily
+*/
+- (NSString *)standardFontFamily;
+
+/*!
+ @method setStandardFontFamily:
+ @param family
+*/
+- (void)setStandardFontFamily:(NSString *)family;
+
+/*!
+ @method fixedFontFamily
+*/
+- (NSString *)fixedFontFamily;
+
+/*!
+ @method setFixedFontFamily:
+ @param family
+*/
+- (void)setFixedFontFamily:(NSString *)family;
+
+/*!
+ @method serifFontFamily
+*/
+- (NSString *)serifFontFamily;
+
+/*!
+ @method setSerifFontFamily:
+ @param family
+*/
+- (void)setSerifFontFamily:(NSString *)family;
+
+/*!
+ @method sansSerifFontFamily
+*/
+- (NSString *)sansSerifFontFamily;
+
+/*!
+ @method setSansSerifFontFamily:
+ @param family
+*/
+- (void)setSansSerifFontFamily:(NSString *)family;
+
+/*!
+ @method cursiveFontFamily
+*/
+- (NSString *)cursiveFontFamily;
+
+/*!
+ @method setCursiveFontFamily:
+ @param family
+*/
+- (void)setCursiveFontFamily:(NSString *)family;
+
+/*!
+ @method fantasyFontFamily
+*/
+- (NSString *)fantasyFontFamily;
+
+/*!
+ @method setFantasyFontFamily:
+ @param family
+*/
+- (void)setFantasyFontFamily:(NSString *)family;
+
+/*!
+ @method defaultFontSize
+*/
+- (int)defaultFontSize;
+
+/*!
+ @method setDefaultFontSize:
+ @param size
+*/
+- (void)setDefaultFontSize:(int)size;
+
+/*!
+ @method defaultFixedFontSize
+*/
+- (int)defaultFixedFontSize;
+
+/*!
+ @method setDefaultFixedFontSize:
+ @param size
+*/
+- (void)setDefaultFixedFontSize:(int)size;
+
+/*!
+ @method minimumFontSize
+*/
+- (int)minimumFontSize;
+
+/*!
+ @method setMinimumFontSize:
+ @param size
+*/
+- (void)setMinimumFontSize:(int)size;
+
+/*!
+ @method minimumLogicalFontSize
+*/
+- (int)minimumLogicalFontSize;
+
+/*!
+ @method setMinimumLogicalFontSize:
+ @param size
+*/
+- (void)setMinimumLogicalFontSize:(int)size;
+
+/*!
+ @method defaultTextEncodingName
+*/
+- (NSString *)defaultTextEncodingName;
+
+/*!
+ @method setDefaultTextEncodingName:
+ @param encoding
+*/
+- (void)setDefaultTextEncodingName:(NSString *)encoding;
+
+/*!
+ @method userStyleSheetEnabled
+*/
+- (BOOL)userStyleSheetEnabled;
+
+/*!
+ @method setUserStyleSheetEnabled:
+ @param flag
+*/
+- (void)setUserStyleSheetEnabled:(BOOL)flag;
+
+/*!
+ @method userStyleSheetLocation
+ @discussion The location of the user style sheet.
+*/
+- (NSURL *)userStyleSheetLocation;
+
+/*!
+ @method setUserStyleSheetLocation:
+ @param URL The location of the user style sheet.
+*/
+- (void)setUserStyleSheetLocation:(NSURL *)URL;
+
+/*!
+ @method isJavaEnabled
+*/
+- (BOOL)isJavaEnabled;
+
+/*!
+ @method setJavaEnabled:
+ @param flag
+*/
+- (void)setJavaEnabled:(BOOL)flag;
+
+/*!
+ @method isJavaScriptEnabled
+*/
+- (BOOL)isJavaScriptEnabled;
+
+/*!
+ @method setJavaScriptEnabled:
+ @param flag
+*/
+- (void)setJavaScriptEnabled:(BOOL)flag;
+
+/*!
+ @method JavaScriptCanOpenWindowsAutomatically
+*/
+- (BOOL)javaScriptCanOpenWindowsAutomatically;
+
+/*!
+ @method setJavaScriptCanOpenWindowsAutomatically:
+ @param flag
+*/
+- (void)setJavaScriptCanOpenWindowsAutomatically:(BOOL)flag;
+
+/*!
+ @method arePlugInsEnabled
+*/
+- (BOOL)arePlugInsEnabled;
+
+/*!
+ @method setPlugInsEnabled:
+ @param flag
+*/
+- (void)setPlugInsEnabled:(BOOL)flag;
+
+/*!
+ @method allowAnimatedImages
+*/
+- (BOOL)allowsAnimatedImages;
+
+/*!
+ @method setAllowAnimatedImages:
+ @param flag
+*/
+- (void)setAllowsAnimatedImages:(BOOL)flag;
+
+/*!
+ @method allowAnimatedImageLooping
+*/
+- (BOOL)allowsAnimatedImageLooping;
+
+/*!
+ @method setAllowAnimatedImageLooping:
+ @param flag
+*/
+- (void)setAllowsAnimatedImageLooping: (BOOL)flag;
+
+/*!
+ @method setWillLoadImagesAutomatically:
+ @param flag
+*/
+- (void)setLoadsImagesAutomatically: (BOOL)flag;
+
+/*!
+ @method willLoadImagesAutomatically
+*/
+- (BOOL)loadsImagesAutomatically;
+
+/*!
+ @method setAutosaves:
+ @param flag
+ @discussion If autosave preferences is YES the settings represented by
+ WebPreferences will be stored in the user defaults database.
+*/
+- (void)setAutosaves:(BOOL)flag;
+
+/*!
+ @method autosaves
+ @result The value of the autosave preferences flag.
+*/
+- (BOOL)autosaves;
+
+/*!
+ @method setShouldPrintBackgrounds:
+ @param flag
+*/
+- (void)setShouldPrintBackgrounds:(BOOL)flag;
+
+/*!
+ @method shouldPrintBackgrounds
+ @result The value of the shouldPrintBackgrounds preferences flag
+*/
+- (BOOL)shouldPrintBackgrounds;
+
+/*!
+ @method setPrivateBrowsingEnabled:
+ @param flag
+ @abstract If private browsing is enabled, WebKit will not store information
+ about sites the user visits.
+ */
+- (void)setPrivateBrowsingEnabled:(BOOL)flag;
+
+/*!
+ @method privateBrowsingEnabled
+ */
+- (BOOL)privateBrowsingEnabled;
+
+/*!
+ @method setTabsToLinks:
+ @param flag
+ @abstract If tabsToLinks is YES, the tab key will focus links and form controls.
+ The option key temporarily reverses this preference.
+*/
+- (void)setTabsToLinks:(BOOL)flag;
+
+/*!
+ @method tabsToLinks
+*/
+- (BOOL)tabsToLinks;
+
+/*!
+ @method setUsesPageCache:
+ @abstract Sets whether the receiver's associated WebViews use the shared
+ page cache.
+ @param UsesPageCache Whether the receiver's associated WebViews use the
+ shared page cache.
+ @discussion Pages are cached as they are added to a WebBackForwardList, and
+ removed from the cache as they are removed from a WebBackForwardList. Because
+ the page cache is global, caching a page in one WebBackForwardList may cause
+ a page in another WebBackForwardList to be evicted from the cache.
+*/
+- (void)setUsesPageCache:(BOOL)usesPageCache;
+
+/*!
+ @method usesPageCache
+ @abstract Returns whether the receiver should use the shared page cache.
+ @result Whether the receiver should use the shared page cache.
+ @discussion Pages are cached as they are added to a WebBackForwardList, and
+ removed from the cache as they are removed from a WebBackForwardList. Because
+ the page cache is global, caching a page in one WebBackForwardList may cause
+ a page in another WebBackForwardList to be evicted from the cache.
+*/
+- (BOOL)usesPageCache;
+
+/*!
+@method setCacheModel:
+
+@abstract Specifies a usage model for a WebView, which WebKit will use to
+determine its caching behavior.
+
+@param cacheModel The WebView's usage model for WebKit. If necessary, WebKit
+will prune its caches to match cacheModel.
+
+@discussion Research indicates that users tend to browse within clusters of
+documents that hold resources in common, and to revisit previously visited
+documents. WebKit and the frameworks below it include built-in caches that take
+advantage of these patterns, substantially improving document load speed in
+browsing situations. The WebKit cache model controls the behaviors of all of
+these caches, including NSURLCache and the various WebCore caches.
+
+Applications with a browsing interface can improve document load speed
+substantially by specifying WebCacheModelDocumentBrowser. Applications without
+a browsing interface can reduce memory usage substantially by specifying
+WebCacheModelDocumentViewer.
+
+If setCacheModel: is not called, WebKit will select a cache model automatically.
+*/
+- (void)setCacheModel:(WebCacheModel)cacheModel;
+
+/*!
+@method cacheModel:
+
+@abstract Returns the usage model according to which WebKit determines its
+caching behavior.
+
+@result The usage model.
+*/
+- (WebCacheModel)cacheModel;
+
+@end
+
+#undef WebNSUInteger
diff --git a/WebKit/mac/WebView/WebPreferences.m b/WebKit/mac/WebView/WebPreferences.m
new file mode 100644
index 0000000..1d5f480
--- /dev/null
+++ b/WebKit/mac/WebView/WebPreferences.m
@@ -0,0 +1,996 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ * (C) 2006 Graham Dennis (graham.dennis@gmail.com)
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebPreferencesPrivate.h"
+#import "WebPreferenceKeysPrivate.h"
+
+#import "WebKitLogging.h"
+#import "WebKitNSStringExtras.h"
+#import "WebKitSystemBits.h"
+#import "WebKitSystemInterface.h"
+#import "WebKitVersionChecks.h"
+#import "WebNSDictionaryExtras.h"
+#import "WebNSURLExtras.h"
+
+NSString *WebPreferencesChangedNotification = @"WebPreferencesChangedNotification";
+NSString *WebPreferencesRemovedNotification = @"WebPreferencesRemovedNotification";
+
+#define KEY(x) (_private->identifier ? [_private->identifier stringByAppendingString:(x)] : (x))
+
+enum { WebPreferencesVersion = 1 };
+
+static WebPreferences *_standardPreferences;
+static NSMutableDictionary *webPreferencesInstances;
+
+static bool contains(const char* const array[], int count, const char* item)
+{
+ if (!item)
+ return false;
+
+ for (int i = 0; i < count; i++)
+ if (!strcasecmp(array[i], item))
+ return true;
+ return false;
+}
+
+static WebCacheModel cacheModelForMainBundle(void)
+{
+ NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
+
+ // Apps that probably need the small setting
+ static const char* const documentViewerIDs[] = {
+ "Microsoft/com.microsoft.Messenger",
+ "com.adiumX.adiumX",
+ "com.alientechnology.Proteus",
+ "com.apple.Dashcode",
+ "com.apple.iChat",
+ "com.barebones.bbedit",
+ "com.barebones.textwrangler",
+ "com.barebones.yojimbo",
+ "com.equinux.iSale4",
+ "com.growl.growlframework",
+ "com.intrarts.PandoraMan",
+ "com.karelia.Sandvox",
+ "com.macromates.textmate",
+ "com.realmacsoftware.rapidweaverpro",
+ "com.red-sweater.marsedit",
+ "com.yahoo.messenger3",
+ "de.codingmonkeys.SubEthaEdit",
+ "fi.karppinen.Pyro",
+ "info.colloquy",
+ "kungfoo.tv.ecto",
+ };
+
+ // Apps that probably need the medium setting
+ static const char* const documentBrowserIDs[] = {
+ "com.apple.Dictionary",
+ "com.apple.Xcode",
+ "com.apple.dashboard.client",
+ "com.apple.helpviewer",
+ "com.culturedcode.xyle",
+ "com.macrabbit.CSSEdit",
+ "com.panic.Coda",
+ "com.ranchero.NetNewsWire",
+ "com.thinkmac.NewsLife",
+ "org.xlife.NewsFire",
+ "uk.co.opencommunity.vienna2",
+ };
+
+ // Apps that probably need the large setting
+ static const char* const primaryWebBrowserIDs[] = {
+ "com.app4mac.KidsBrowser"
+ "com.app4mac.wKiosk",
+ "com.freeverse.bumpercar",
+ "com.omnigroup.OmniWeb5",
+ "com.sunrisebrowser.Sunrise",
+ "net.hmdt-web.Shiira",
+ };
+
+ WebCacheModel cacheModel;
+
+ const char* bundleID = [[[NSBundle mainBundle] bundleIdentifier] UTF8String];
+ if (contains(documentViewerIDs, sizeof(documentViewerIDs) / sizeof(documentViewerIDs[0]), bundleID))
+ cacheModel = WebCacheModelDocumentViewer;
+ else if (contains(documentBrowserIDs, sizeof(documentBrowserIDs) / sizeof(documentBrowserIDs[0]), bundleID))
+ cacheModel = WebCacheModelDocumentBrowser;
+ else if (contains(primaryWebBrowserIDs, sizeof(primaryWebBrowserIDs) / sizeof(primaryWebBrowserIDs[0]), bundleID))
+ cacheModel = WebCacheModelPrimaryWebBrowser;
+ else {
+ bool isLegacyApp = !WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITH_CACHE_MODEL_API);
+ if (isLegacyApp)
+ cacheModel = WebCacheModelDocumentBrowser; // To avoid regressions in apps that depended on old WebKit's large cache.
+ else
+ cacheModel = WebCacheModelDocumentViewer; // To save memory.
+ }
+
+ [pool drain];
+
+ return cacheModel;
+}
+
+@interface WebPreferencesPrivate : NSObject
+{
+@public
+ NSMutableDictionary *values;
+ NSString *identifier;
+ NSString *IBCreatorID;
+ BOOL autosaves;
+ BOOL automaticallyDetectsCacheModel;
+ unsigned numWebViews;
+}
+@end
+
+@implementation WebPreferencesPrivate
+- (void)dealloc
+{
+ [values release];
+ [identifier release];
+ [IBCreatorID release];
+ [super dealloc];
+}
+@end
+
+@interface WebPreferences (WebInternal)
++ (NSString *)_concatenateKeyWithIBCreatorID:(NSString *)key;
++ (NSString *)_IBCreatorID;
+@end
+
+@interface WebPreferences (WebForwardDeclarations)
+// This pseudo-category is needed so these methods can be used from within other category implementations
+// without being in the public header file.
+- (BOOL)_boolValueForKey:(NSString *)key;
+- (void)_setBoolValue:(BOOL)value forKey:(NSString *)key;
+- (int)_integerValueForKey:(NSString *)key;
+- (void)_setIntegerValue:(int)value forKey:(NSString *)key;
+- (float)_floatValueForKey:(NSString *)key;
+- (void)_setFloatValue:(float)value forKey:(NSString *)key;
+- (void)_setUnsignedLongLongValue:(unsigned long long)value forKey:(NSString *)key;
+- (unsigned long long)_unsignedLongLongValueForKey:(NSString *)key;
+@end
+
+@implementation WebPreferences
+
+- init
+{
+ // Create fake identifier
+ static int instanceCount = 1;
+ NSString *fakeIdentifier;
+
+ // At least ensure that identifier hasn't been already used.
+ fakeIdentifier = [NSString stringWithFormat:@"WebPreferences%d", instanceCount++];
+ while ([[self class] _getInstanceForIdentifier:fakeIdentifier]){
+ fakeIdentifier = [NSString stringWithFormat:@"WebPreferences%d", instanceCount++];
+ }
+
+ return [self initWithIdentifier:fakeIdentifier];
+}
+
+- (id)initWithIdentifier:(NSString *)anIdentifier
+{
+ self = [super init];
+ if (!self)
+ return nil;
+
+ _private = [[WebPreferencesPrivate alloc] init];
+ _private->IBCreatorID = [[WebPreferences _IBCreatorID] retain];
+
+ WebPreferences *instance = [[self class] _getInstanceForIdentifier:anIdentifier];
+ if (instance){
+ [self release];
+ return [instance retain];
+ }
+
+ _private->values = [[NSMutableDictionary alloc] init];
+ _private->identifier = [anIdentifier copy];
+ _private->automaticallyDetectsCacheModel = YES;
+
+ [[self class] _setInstance:self forIdentifier:_private->identifier];
+
+ [self _postPreferencesChangesNotification];
+
+ return self;
+}
+
+- (id)initWithCoder:(NSCoder *)decoder
+{
+ self = [super init];
+ if (!self)
+ return nil;
+
+ _private = [[WebPreferencesPrivate alloc] init];
+ _private->IBCreatorID = [[WebPreferences _IBCreatorID] retain];
+ _private->automaticallyDetectsCacheModel = YES;
+
+ @try {
+ id identifier = nil;
+ id values = nil;
+ if ([decoder allowsKeyedCoding]) {
+ identifier = [decoder decodeObjectForKey:@"Identifier"];
+ values = [decoder decodeObjectForKey:@"Values"];
+ } else {
+ int version;
+ [decoder decodeValueOfObjCType:@encode(int) at:&version];
+ if (version == 1) {
+ identifier = [decoder decodeObject];
+ values = [decoder decodeObject];
+ }
+ }
+
+ if ([identifier isKindOfClass:[NSString class]])
+ _private->identifier = [identifier copy];
+ if ([values isKindOfClass:[NSDictionary class]])
+ _private->values = [values mutableCopy]; // ensure dictionary is mutable
+
+ LOG(Encoding, "Identifier = %@, Values = %@\n", _private->identifier, _private->values);
+ } @catch(id) {
+ [self release];
+ return nil;
+ }
+
+ // If we load a nib multiple times, or have instances in multiple
+ // nibs with the same name, the first guy up wins.
+ WebPreferences *instance = [[self class] _getInstanceForIdentifier:_private->identifier];
+ if (instance) {
+ [self release];
+ self = [instance retain];
+ } else {
+ [[self class] _setInstance:self forIdentifier:_private->identifier];
+ }
+
+ return self;
+}
+
+- (void)encodeWithCoder:(NSCoder *)encoder
+{
+ if ([encoder allowsKeyedCoding]){
+ [encoder encodeObject:_private->identifier forKey:@"Identifier"];
+ [encoder encodeObject:_private->values forKey:@"Values"];
+ LOG (Encoding, "Identifier = %@, Values = %@\n", _private->identifier, _private->values);
+ }
+ else {
+ int version = WebPreferencesVersion;
+ [encoder encodeValueOfObjCType:@encode(int) at:&version];
+ [encoder encodeObject:_private->identifier];
+ [encoder encodeObject:_private->values];
+ }
+}
+
++ (WebPreferences *)standardPreferences
+{
+ if (_standardPreferences == nil) {
+ _standardPreferences = [[WebPreferences alloc] initWithIdentifier:nil];
+ [_standardPreferences setAutosaves:YES];
+ }
+
+ return _standardPreferences;
+}
+
+// if we ever have more than one WebPreferences object, this would move to init
++ (void)initialize
+{
+ NSDictionary *dict = [NSDictionary dictionaryWithObjectsAndKeys:
+ @"Times", WebKitStandardFontPreferenceKey,
+ @"Courier", WebKitFixedFontPreferenceKey,
+ @"Times", WebKitSerifFontPreferenceKey,
+ @"Helvetica", WebKitSansSerifFontPreferenceKey,
+ @"Apple Chancery", WebKitCursiveFontPreferenceKey,
+ @"Papyrus", WebKitFantasyFontPreferenceKey,
+ @"1", WebKitMinimumFontSizePreferenceKey,
+ @"9", WebKitMinimumLogicalFontSizePreferenceKey,
+ @"16", WebKitDefaultFontSizePreferenceKey,
+ @"13", WebKitDefaultFixedFontSizePreferenceKey,
+ @"ISO-8859-1", WebKitDefaultTextEncodingNamePreferenceKey,
+ [NSNumber numberWithBool:NO], WebKitUserStyleSheetEnabledPreferenceKey,
+ @"", WebKitUserStyleSheetLocationPreferenceKey,
+ [NSNumber numberWithBool:NO], WebKitShouldPrintBackgroundsPreferenceKey,
+ [NSNumber numberWithBool:NO], WebKitTextAreasAreResizablePreferenceKey,
+ [NSNumber numberWithBool:NO], WebKitShrinksStandaloneImagesToFitPreferenceKey,
+ [NSNumber numberWithBool:YES], WebKitJavaEnabledPreferenceKey,
+ [NSNumber numberWithBool:YES], WebKitJavaScriptEnabledPreferenceKey,
+ [NSNumber numberWithBool:YES], WebKitJavaScriptCanOpenWindowsAutomaticallyPreferenceKey,
+ [NSNumber numberWithBool:YES], WebKitPluginsEnabledPreferenceKey,
+ [NSNumber numberWithBool:YES], WebKitAllowAnimatedImagesPreferenceKey,
+ [NSNumber numberWithBool:YES], WebKitAllowAnimatedImageLoopingPreferenceKey,
+ [NSNumber numberWithBool:YES], WebKitDisplayImagesKey,
+ @"1800", WebKitBackForwardCacheExpirationIntervalKey,
+ [NSNumber numberWithBool:NO], WebKitTabToLinksPreferenceKey,
+ [NSNumber numberWithBool:NO], WebKitPrivateBrowsingEnabledPreferenceKey,
+ [NSNumber numberWithBool:NO], WebKitRespectStandardStyleKeyEquivalentsPreferenceKey,
+ [NSNumber numberWithBool:NO], WebKitShowsURLsInToolTipsPreferenceKey,
+ @"1", WebKitPDFDisplayModePreferenceKey,
+ @"0", WebKitPDFScaleFactorPreferenceKey,
+ @"0", WebKitUseSiteSpecificSpoofingPreferenceKey,
+ [NSNumber numberWithInt:WebKitEditableLinkDefaultBehavior], WebKitEditableLinkBehaviorPreferenceKey,
+ [NSNumber numberWithBool:NO], WebKitDOMPasteAllowedPreferenceKey,
+ [NSNumber numberWithBool:YES], WebKitUsesPageCachePreferenceKey,
+ [NSNumber numberWithInt:cacheModelForMainBundle()], WebKitCacheModelPreferenceKey,
+ [NSNumber numberWithBool:NO], WebKitDeveloperExtrasEnabledPreferenceKey,
+ [NSNumber numberWithBool:YES], WebKitAuthorAndUserStylesEnabledPreferenceKey,
+ nil];
+
+ // This value shouldn't ever change, which is assumed in the initialization of WebKitPDFDisplayModePreferenceKey above
+ ASSERT(kPDFDisplaySinglePageContinuous == 1);
+ [[NSUserDefaults standardUserDefaults] registerDefaults:dict];
+}
+
+- (void)dealloc
+{
+ [_private release];
+ [super dealloc];
+}
+
+- (NSString *)identifier
+{
+ return _private->identifier;
+}
+
+- (id)_valueForKey:(NSString *)key
+{
+ NSString *_key = KEY(key);
+ id o = [_private->values objectForKey:_key];
+ if (o)
+ return o;
+ o = [[NSUserDefaults standardUserDefaults] objectForKey:_key];
+ if (!o && key != _key)
+ o = [[NSUserDefaults standardUserDefaults] objectForKey:key];
+ return o;
+}
+
+- (NSString *)_stringValueForKey:(NSString *)key
+{
+ id s = [self _valueForKey:key];
+ return [s isKindOfClass:[NSString class]] ? (NSString *)s : nil;
+}
+
+- (void)_setStringValue:(NSString *)value forKey:(NSString *)key
+{
+ if ([[self _stringValueForKey:key] isEqualToString:value])
+ return;
+ NSString *_key = KEY(key);
+ [_private->values setObject:value forKey:_key];
+ if (_private->autosaves)
+ [[NSUserDefaults standardUserDefaults] setObject:value forKey:_key];
+ [self _postPreferencesChangesNotification];
+}
+
+- (int)_integerValueForKey:(NSString *)key
+{
+ id o = [self _valueForKey:key];
+ return [o respondsToSelector:@selector(intValue)] ? [o intValue] : 0;
+}
+
+- (void)_setIntegerValue:(int)value forKey:(NSString *)key
+{
+ if ([self _integerValueForKey:key] == value)
+ return;
+ NSString *_key = KEY(key);
+ [_private->values _webkit_setInt:value forKey:_key];
+ if (_private->autosaves)
+ [[NSUserDefaults standardUserDefaults] setInteger:value forKey:_key];
+ [self _postPreferencesChangesNotification];
+}
+
+- (float)_floatValueForKey:(NSString *)key
+{
+ id o = [self _valueForKey:key];
+ return [o respondsToSelector:@selector(floatValue)] ? [o floatValue] : 0.0f;
+}
+
+- (void)_setFloatValue:(float)value forKey:(NSString *)key
+{
+ if ([self _floatValueForKey:key] == value)
+ return;
+ NSString *_key = KEY(key);
+ [_private->values _webkit_setFloat:value forKey:_key];
+ if (_private->autosaves)
+ [[NSUserDefaults standardUserDefaults] setFloat:value forKey:_key];
+ [self _postPreferencesChangesNotification];
+}
+
+- (BOOL)_boolValueForKey:(NSString *)key
+{
+ return [self _integerValueForKey:key] != 0;
+}
+
+- (void)_setBoolValue:(BOOL)value forKey:(NSString *)key
+{
+ if ([self _boolValueForKey:key] == value)
+ return;
+ NSString *_key = KEY(key);
+ [_private->values _webkit_setBool:value forKey:_key];
+ if (_private->autosaves)
+ [[NSUserDefaults standardUserDefaults] setBool:value forKey:_key];
+ [self _postPreferencesChangesNotification];
+}
+
+- (unsigned long long)_unsignedLongLongValueForKey:(NSString *)key
+{
+ id o = [self _valueForKey:key];
+ return [o respondsToSelector:@selector(unsignedLongLongValue)] ? [o unsignedLongLongValue] : 0;
+}
+
+- (void)_setUnsignedLongLongValue:(unsigned long long)value forKey:(NSString *)key
+{
+ if ([self _unsignedLongLongValueForKey:key] == value)
+ return;
+ NSString *_key = KEY(key);
+ [_private->values _webkit_setUnsignedLongLong:value forKey:_key];
+ if (_private->autosaves)
+ [[NSUserDefaults standardUserDefaults] setObject:[NSNumber numberWithUnsignedLongLong:value] forKey:_key];
+ [self _postPreferencesChangesNotification];
+}
+
+- (NSString *)standardFontFamily
+{
+ return [self _stringValueForKey: WebKitStandardFontPreferenceKey];
+}
+
+- (void)setStandardFontFamily:(NSString *)family
+{
+ [self _setStringValue: family forKey: WebKitStandardFontPreferenceKey];
+}
+
+- (NSString *)fixedFontFamily
+{
+ return [self _stringValueForKey: WebKitFixedFontPreferenceKey];
+}
+
+- (void)setFixedFontFamily:(NSString *)family
+{
+ [self _setStringValue: family forKey: WebKitFixedFontPreferenceKey];
+}
+
+- (NSString *)serifFontFamily
+{
+ return [self _stringValueForKey: WebKitSerifFontPreferenceKey];
+}
+
+- (void)setSerifFontFamily:(NSString *)family
+{
+ [self _setStringValue: family forKey: WebKitSerifFontPreferenceKey];
+}
+
+- (NSString *)sansSerifFontFamily
+{
+ return [self _stringValueForKey: WebKitSansSerifFontPreferenceKey];
+}
+
+- (void)setSansSerifFontFamily:(NSString *)family
+{
+ [self _setStringValue: family forKey: WebKitSansSerifFontPreferenceKey];
+}
+
+- (NSString *)cursiveFontFamily
+{
+ return [self _stringValueForKey: WebKitCursiveFontPreferenceKey];
+}
+
+- (void)setCursiveFontFamily:(NSString *)family
+{
+ [self _setStringValue: family forKey: WebKitCursiveFontPreferenceKey];
+}
+
+- (NSString *)fantasyFontFamily
+{
+ return [self _stringValueForKey: WebKitFantasyFontPreferenceKey];
+}
+
+- (void)setFantasyFontFamily:(NSString *)family
+{
+ [self _setStringValue: family forKey: WebKitFantasyFontPreferenceKey];
+}
+
+- (int)defaultFontSize
+{
+ return [self _integerValueForKey: WebKitDefaultFontSizePreferenceKey];
+}
+
+- (void)setDefaultFontSize:(int)size
+{
+ [self _setIntegerValue: size forKey: WebKitDefaultFontSizePreferenceKey];
+}
+
+- (int)defaultFixedFontSize
+{
+ return [self _integerValueForKey: WebKitDefaultFixedFontSizePreferenceKey];
+}
+
+- (void)setDefaultFixedFontSize:(int)size
+{
+ [self _setIntegerValue: size forKey: WebKitDefaultFixedFontSizePreferenceKey];
+}
+
+- (int)minimumFontSize
+{
+ return [self _integerValueForKey: WebKitMinimumFontSizePreferenceKey];
+}
+
+- (void)setMinimumFontSize:(int)size
+{
+ [self _setIntegerValue: size forKey: WebKitMinimumFontSizePreferenceKey];
+}
+
+- (int)minimumLogicalFontSize
+{
+ return [self _integerValueForKey: WebKitMinimumLogicalFontSizePreferenceKey];
+}
+
+- (void)setMinimumLogicalFontSize:(int)size
+{
+ [self _setIntegerValue: size forKey: WebKitMinimumLogicalFontSizePreferenceKey];
+}
+
+- (NSString *)defaultTextEncodingName
+{
+ return [self _stringValueForKey: WebKitDefaultTextEncodingNamePreferenceKey];
+}
+
+- (void)setDefaultTextEncodingName:(NSString *)encoding
+{
+ [self _setStringValue: encoding forKey: WebKitDefaultTextEncodingNamePreferenceKey];
+}
+
+- (BOOL)userStyleSheetEnabled
+{
+ return [self _boolValueForKey: WebKitUserStyleSheetEnabledPreferenceKey];
+}
+
+- (void)setUserStyleSheetEnabled:(BOOL)flag
+{
+ [self _setBoolValue: flag forKey: WebKitUserStyleSheetEnabledPreferenceKey];
+}
+
+- (NSURL *)userStyleSheetLocation
+{
+ NSString *locationString = [self _stringValueForKey: WebKitUserStyleSheetLocationPreferenceKey];
+
+ if ([locationString _webkit_looksLikeAbsoluteURL]) {
+ return [NSURL _web_URLWithDataAsString:locationString];
+ } else {
+ locationString = [locationString stringByExpandingTildeInPath];
+ return [NSURL fileURLWithPath:locationString];
+ }
+}
+
+- (void)setUserStyleSheetLocation:(NSURL *)URL
+{
+ NSString *locationString;
+
+ if ([URL isFileURL]) {
+ locationString = [[URL path] _web_stringByAbbreviatingWithTildeInPath];
+ } else {
+ locationString = [URL _web_originalDataAsString];
+ }
+
+ [self _setStringValue:locationString forKey: WebKitUserStyleSheetLocationPreferenceKey];
+}
+
+- (BOOL)shouldPrintBackgrounds
+{
+ return [self _boolValueForKey: WebKitShouldPrintBackgroundsPreferenceKey];
+}
+
+- (void)setShouldPrintBackgrounds:(BOOL)flag
+{
+ [self _setBoolValue: flag forKey: WebKitShouldPrintBackgroundsPreferenceKey];
+}
+
+- (BOOL)isJavaEnabled
+{
+ return [self _boolValueForKey: WebKitJavaEnabledPreferenceKey];
+}
+
+- (void)setJavaEnabled:(BOOL)flag
+{
+ [self _setBoolValue: flag forKey: WebKitJavaEnabledPreferenceKey];
+}
+
+- (BOOL)isJavaScriptEnabled
+{
+ return [self _boolValueForKey: WebKitJavaScriptEnabledPreferenceKey];
+}
+
+- (void)setJavaScriptEnabled:(BOOL)flag
+{
+ [self _setBoolValue: flag forKey: WebKitJavaScriptEnabledPreferenceKey];
+}
+
+- (BOOL)javaScriptCanOpenWindowsAutomatically
+{
+ return [self _boolValueForKey: WebKitJavaScriptCanOpenWindowsAutomaticallyPreferenceKey];
+}
+
+- (void)setJavaScriptCanOpenWindowsAutomatically:(BOOL)flag
+{
+ [self _setBoolValue: flag forKey: WebKitJavaScriptCanOpenWindowsAutomaticallyPreferenceKey];
+}
+
+- (BOOL)arePlugInsEnabled
+{
+ return [self _boolValueForKey: WebKitPluginsEnabledPreferenceKey];
+}
+
+- (void)setPlugInsEnabled:(BOOL)flag
+{
+ [self _setBoolValue: flag forKey: WebKitPluginsEnabledPreferenceKey];
+}
+
+- (BOOL)allowsAnimatedImages
+{
+ return [self _boolValueForKey: WebKitAllowAnimatedImagesPreferenceKey];
+}
+
+- (void)setAllowsAnimatedImages:(BOOL)flag;
+{
+ [self _setBoolValue: flag forKey: WebKitAllowAnimatedImagesPreferenceKey];
+}
+
+- (BOOL)allowsAnimatedImageLooping
+{
+ return [self _boolValueForKey: WebKitAllowAnimatedImageLoopingPreferenceKey];
+}
+
+- (void)setAllowsAnimatedImageLooping: (BOOL)flag
+{
+ [self _setBoolValue: flag forKey: WebKitAllowAnimatedImageLoopingPreferenceKey];
+}
+
+- (void)setLoadsImagesAutomatically: (BOOL)flag
+{
+ [self _setBoolValue: flag forKey: WebKitDisplayImagesKey];
+}
+
+- (BOOL)loadsImagesAutomatically
+{
+ return [self _boolValueForKey: WebKitDisplayImagesKey];
+}
+
+- (void)setAutosaves:(BOOL)flag;
+{
+ _private->autosaves = flag;
+}
+
+- (BOOL)autosaves
+{
+ return _private->autosaves;
+}
+
+- (void)setTabsToLinks:(BOOL)flag
+{
+ [self _setBoolValue: flag forKey: WebKitTabToLinksPreferenceKey];
+}
+
+- (BOOL)tabsToLinks
+{
+ return [self _boolValueForKey:WebKitTabToLinksPreferenceKey];
+}
+
+- (void)setPrivateBrowsingEnabled:(BOOL)flag
+{
+ [self _setBoolValue:flag forKey:WebKitPrivateBrowsingEnabledPreferenceKey];
+}
+
+- (BOOL)privateBrowsingEnabled
+{
+ return [self _boolValueForKey:WebKitPrivateBrowsingEnabledPreferenceKey];
+}
+
+- (void)setUsesPageCache:(BOOL)usesPageCache
+{
+ [self _setBoolValue:usesPageCache forKey:WebKitUsesPageCachePreferenceKey];
+}
+
+- (BOOL)usesPageCache
+{
+ return [self _boolValueForKey:WebKitUsesPageCachePreferenceKey];
+}
+
+- (void)setCacheModel:(WebCacheModel)cacheModel
+{
+ [self _setIntegerValue:cacheModel forKey:WebKitCacheModelPreferenceKey];
+ [self setAutomaticallyDetectsCacheModel:NO];
+}
+
+- (WebCacheModel)cacheModel
+{
+ return [self _integerValueForKey:WebKitCacheModelPreferenceKey];
+}
+
+@end
+
+@implementation WebPreferences (WebPrivate)
+
+- (BOOL)developerExtrasEnabled
+{
+ NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
+ if ([defaults boolForKey:@"DisableWebKitDeveloperExtras"])
+ return NO;
+#ifdef NDEBUG
+ if ([defaults boolForKey:@"WebKitDeveloperExtras"] || [defaults boolForKey:@"IncludeDebugMenu"])
+ return YES;
+ return [self _boolValueForKey:WebKitDeveloperExtrasEnabledPreferenceKey];
+#else
+ return YES; // always enable in debug builds
+#endif
+}
+
+- (void)setDeveloperExtrasEnabled:(BOOL)flag
+{
+ [self _setBoolValue:flag forKey:WebKitDeveloperExtrasEnabledPreferenceKey];
+}
+
+- (BOOL)authorAndUserStylesEnabled
+{
+ return [self _boolValueForKey:WebKitAuthorAndUserStylesEnabledPreferenceKey];
+}
+
+- (void)setAuthorAndUserStylesEnabled:(BOOL)flag
+{
+ [self _setBoolValue:flag forKey:WebKitAuthorAndUserStylesEnabledPreferenceKey];
+}
+
+- (BOOL)respectStandardStyleKeyEquivalents
+{
+ return [self _boolValueForKey:WebKitRespectStandardStyleKeyEquivalentsPreferenceKey];
+}
+
+- (void)setRespectStandardStyleKeyEquivalents:(BOOL)flag
+{
+ [self _setBoolValue:flag forKey:WebKitRespectStandardStyleKeyEquivalentsPreferenceKey];
+}
+
+- (BOOL)showsURLsInToolTips
+{
+ return [self _boolValueForKey:WebKitShowsURLsInToolTipsPreferenceKey];
+}
+
+- (void)setShowsURLsInToolTips:(BOOL)flag
+{
+ [self _setBoolValue:flag forKey:WebKitShowsURLsInToolTipsPreferenceKey];
+}
+
+- (BOOL)textAreasAreResizable
+{
+ return [self _boolValueForKey: WebKitTextAreasAreResizablePreferenceKey];
+}
+
+- (void)setTextAreasAreResizable:(BOOL)flag
+{
+ [self _setBoolValue: flag forKey: WebKitTextAreasAreResizablePreferenceKey];
+}
+
+- (BOOL)shrinksStandaloneImagesToFit
+{
+ return [self _boolValueForKey:WebKitShrinksStandaloneImagesToFitPreferenceKey];
+}
+
+- (void)setShrinksStandaloneImagesToFit:(BOOL)flag
+{
+ [self _setBoolValue:flag forKey:WebKitShrinksStandaloneImagesToFitPreferenceKey];
+}
+
+- (BOOL)automaticallyDetectsCacheModel
+{
+ return _private->automaticallyDetectsCacheModel;
+}
+
+- (void)setAutomaticallyDetectsCacheModel:(BOOL)automaticallyDetectsCacheModel
+{
+ _private->automaticallyDetectsCacheModel = automaticallyDetectsCacheModel;
+}
+
+- (NSTimeInterval)_backForwardCacheExpirationInterval
+{
+ // FIXME: There's probably no good reason to read from the standard user defaults instead of self.
+ return (NSTimeInterval)[[NSUserDefaults standardUserDefaults] floatForKey:WebKitBackForwardCacheExpirationIntervalKey];
+}
+
+- (float)PDFScaleFactor
+{
+ return [self _floatValueForKey:WebKitPDFScaleFactorPreferenceKey];
+}
+
+- (void)setPDFScaleFactor:(float)factor
+{
+ [self _setFloatValue:factor forKey:WebKitPDFScaleFactorPreferenceKey];
+}
+
+- (PDFDisplayMode)PDFDisplayMode;
+{
+ PDFDisplayMode value = [self _integerValueForKey:WebKitPDFDisplayModePreferenceKey];
+ if (value != kPDFDisplaySinglePage && value != kPDFDisplaySinglePageContinuous && value != kPDFDisplayTwoUp && value != kPDFDisplayTwoUpContinuous) {
+ // protect against new modes from future versions of OS X stored in defaults
+ value = kPDFDisplaySinglePageContinuous;
+ }
+ return value;
+}
+
+- (void)setPDFDisplayMode:(PDFDisplayMode)mode
+{
+ [self _setIntegerValue:mode forKey:WebKitPDFDisplayModePreferenceKey];
+}
+
+- (WebKitEditableLinkBehavior)editableLinkBehavior
+{
+ WebKitEditableLinkBehavior value = [self _integerValueForKey:WebKitEditableLinkBehaviorPreferenceKey];
+ if (value != WebKitEditableLinkDefaultBehavior &&
+ value != WebKitEditableLinkAlwaysLive &&
+ value != WebKitEditableLinkNeverLive &&
+ value != WebKitEditableLinkOnlyLiveWithShiftKey &&
+ value != WebKitEditableLinkLiveWhenNotFocused) {
+ // ensure that a valid result is returned
+ value = WebKitEditableLinkDefaultBehavior;
+ }
+
+ return value;
+}
+
+- (void)setEditableLinkBehavior:(WebKitEditableLinkBehavior)behavior
+{
+ [self _setIntegerValue:behavior forKey:WebKitEditableLinkBehaviorPreferenceKey];
+}
+
+- (BOOL)_useSiteSpecificSpoofing
+{
+ return [self _boolValueForKey:WebKitUseSiteSpecificSpoofingPreferenceKey];
+}
+
+- (void)_setUseSiteSpecificSpoofing:(BOOL)newValue
+{
+ [self _setBoolValue:newValue forKey:WebKitUseSiteSpecificSpoofingPreferenceKey];
+}
+
++ (WebPreferences *)_getInstanceForIdentifier:(NSString *)ident
+{
+ LOG(Encoding, "requesting for %@\n", ident);
+
+ if (!ident)
+ return _standardPreferences;
+
+ WebPreferences *instance = [webPreferencesInstances objectForKey:[self _concatenateKeyWithIBCreatorID:ident]];
+
+ return instance;
+}
+
++ (void)_setInstance:(WebPreferences *)instance forIdentifier:(NSString *)ident
+{
+ if (!webPreferencesInstances)
+ webPreferencesInstances = [[NSMutableDictionary alloc] init];
+ if (ident) {
+ [webPreferencesInstances setObject:instance forKey:[self _concatenateKeyWithIBCreatorID:ident]];
+ LOG(Encoding, "recording %p for %@\n", instance, [self _concatenateKeyWithIBCreatorID:ident]);
+ }
+}
+
++ (void)_checkLastReferenceForIdentifier:(id)identifier
+{
+ // FIXME: This won't work at all under garbage collection because retainCount returns a constant.
+ // We may need to change WebPreferences API so there's an explicit way to end the lifetime of one.
+ WebPreferences *instance = [webPreferencesInstances objectForKey:identifier];
+ if ([instance retainCount] == 1)
+ [webPreferencesInstances removeObjectForKey:identifier];
+}
+
++ (void)_removeReferenceForIdentifier:(NSString *)ident
+{
+ if (ident)
+ [self performSelector:@selector(_checkLastReferenceForIdentifier:) withObject:[self _concatenateKeyWithIBCreatorID:ident] afterDelay:0.1];
+}
+
+- (void)_postPreferencesChangesNotification
+{
+ [[NSNotificationCenter defaultCenter]
+ postNotificationName:WebPreferencesChangedNotification object:self
+ userInfo:nil];
+}
+
++ (CFStringEncoding)_systemCFStringEncoding
+{
+ return WKGetWebDefaultCFStringEncoding();
+}
+
++ (void)_setInitialDefaultTextEncodingToSystemEncoding
+{
+ [[NSUserDefaults standardUserDefaults] registerDefaults:
+ [NSDictionary dictionaryWithObject:(NSString *)CFStringConvertEncodingToIANACharSetName([self _systemCFStringEncoding])
+ forKey:WebKitDefaultTextEncodingNamePreferenceKey]];
+}
+
+static NSString *classIBCreatorID = nil;
+
++ (void)_setIBCreatorID:(NSString *)string
+{
+ NSString *old = classIBCreatorID;
+ classIBCreatorID = [string copy];
+ [old release];
+}
+
+- (BOOL)isDOMPasteAllowed
+{
+ return [self _boolValueForKey:WebKitDOMPasteAllowedPreferenceKey];
+}
+
+- (void)setDOMPasteAllowed:(BOOL)DOMPasteAllowed
+{
+ [self _setBoolValue:DOMPasteAllowed forKey:WebKitDOMPasteAllowedPreferenceKey];
+}
+
+- (void)_setFTPDirectoryTemplatePath:(NSString *)path
+{
+ [self _setStringValue:path forKey:WebKitFTPDirectoryTemplatePath];
+}
+
+- (NSString *)_ftpDirectoryTemplatePath
+{
+ return [self _stringValueForKey:WebKitFTPDirectoryTemplatePath];
+}
+
+- (void)_setForceFTPDirectoryListings:(BOOL)force
+{
+ [self _setBoolValue:force forKey:WebKitForceFTPDirectoryListings];
+}
+
+- (BOOL)_forceFTPDirectoryListings
+{
+ return [self _boolValueForKey:WebKitForceFTPDirectoryListings];
+}
+
+- (void)didRemoveFromWebView
+{
+ ASSERT(_private->numWebViews);
+ if (--_private->numWebViews == 0)
+ [[NSNotificationCenter defaultCenter]
+ postNotificationName:WebPreferencesRemovedNotification
+ object:self
+ userInfo:nil];
+}
+
+- (void)willAddToWebView
+{
+ ++_private->numWebViews;
+}
+
+@end
+
+@implementation WebPreferences (WebInternal)
+
++ (NSString *)_IBCreatorID
+{
+ return classIBCreatorID;
+}
+
++ (NSString *)_concatenateKeyWithIBCreatorID:(NSString *)key
+{
+ NSString *IBCreatorID = [WebPreferences _IBCreatorID];
+ if (!IBCreatorID)
+ return key;
+ return [IBCreatorID stringByAppendingString:key];
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebPreferencesPrivate.h b/WebKit/mac/WebView/WebPreferencesPrivate.h
new file mode 100644
index 0000000..a6b5cb2
--- /dev/null
+++ b/WebKit/mac/WebView/WebPreferencesPrivate.h
@@ -0,0 +1,108 @@
+/*
+ * Copyright (C) 2005, 2007 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebPreferences.h>
+#import <Quartz/Quartz.h>
+
+// WebKitEditableLinkBehavior needs to match the EditableLinkBehavior enum in WebCore
+typedef enum {
+ WebKitEditableLinkDefaultBehavior = 0,
+ WebKitEditableLinkAlwaysLive,
+ WebKitEditableLinkOnlyLiveWithShiftKey,
+ WebKitEditableLinkLiveWhenNotFocused,
+ WebKitEditableLinkNeverLive
+} WebKitEditableLinkBehavior;
+
+extern NSString *WebPreferencesChangedNotification;
+extern NSString *WebPreferencesRemovedNotification;
+
+@interface WebPreferences (WebPrivate)
+
+// Preferences that might be public in a future release
+
+- (BOOL)developerExtrasEnabled;
+- (void)setDeveloperExtrasEnabled:(BOOL)flag;
+
+- (BOOL)authorAndUserStylesEnabled;
+- (void)setAuthorAndUserStylesEnabled:(BOOL)flag;
+
+- (BOOL)respectStandardStyleKeyEquivalents;
+- (void)setRespectStandardStyleKeyEquivalents:(BOOL)flag;
+
+- (BOOL)showsURLsInToolTips;
+- (void)setShowsURLsInToolTips:(BOOL)flag;
+
+- (BOOL)textAreasAreResizable;
+- (void)setTextAreasAreResizable:(BOOL)flag;
+
+- (PDFDisplayMode)PDFDisplayMode;
+- (void)setPDFDisplayMode:(PDFDisplayMode)mode;
+
+- (BOOL)shrinksStandaloneImagesToFit;
+- (void)setShrinksStandaloneImagesToFit:(BOOL)flag;
+
+- (BOOL)automaticallyDetectsCacheModel;
+- (void)setAutomaticallyDetectsCacheModel:(BOOL)automaticallyDetectsCacheModel;
+
+// zero means do AutoScale
+- (float)PDFScaleFactor;
+- (void)setPDFScaleFactor:(float)scale;
+
+- (WebKitEditableLinkBehavior)editableLinkBehavior;
+- (void)setEditableLinkBehavior:(WebKitEditableLinkBehavior)behavior;
+
+// If site-specific spoofing is enabled, some pages that do inappropriate user-agent string checks will be
+// passed a nonstandard user-agent string to get them to work correctly. This method might be removed in
+// the future when there's no more need for it.
+- (BOOL)_useSiteSpecificSpoofing;
+- (void)_setUseSiteSpecificSpoofing:(BOOL)newValue;
+
+// WARNING: Allowing paste through the DOM API opens a security hole. We only use it for testing purposes.
+- (BOOL)isDOMPasteAllowed;
+- (void)setDOMPasteAllowed:(BOOL)DOMPasteAllowed;
+
+- (NSString *)_ftpDirectoryTemplatePath;
+- (void)_setFTPDirectoryTemplatePath:(NSString *)path;
+- (void)_setForceFTPDirectoryListings:(BOOL)force;
+- (BOOL)_forceFTPDirectoryListings;
+
+// Other private methods
+- (void)_postPreferencesChangesNotification;
++ (WebPreferences *)_getInstanceForIdentifier:(NSString *)identifier;
++ (void)_setInstance:(WebPreferences *)instance forIdentifier:(NSString *)identifier;
++ (void)_removeReferenceForIdentifier:(NSString *)identifier;
+- (NSTimeInterval)_backForwardCacheExpirationInterval;
++ (CFStringEncoding)_systemCFStringEncoding;
++ (void)_setInitialDefaultTextEncodingToSystemEncoding;
++ (void)_setIBCreatorID:(NSString *)string;
+
+// For WebView's use only.
+- (void)willAddToWebView;
+- (void)didRemoveFromWebView;
+
+@end
diff --git a/WebKit/mac/WebView/WebRenderNode.h b/WebKit/mac/WebView/WebRenderNode.h
new file mode 100644
index 0000000..8e6b40f
--- /dev/null
+++ b/WebKit/mac/WebView/WebRenderNode.h
@@ -0,0 +1,51 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@class WebFrameView;
+
+@interface WebRenderNode : NSObject
+{
+ NSArray *children;
+ NSString *name;
+ NSRect rect;
+ NSPoint absolutePosition;
+}
+
+- (id)initWithWebFrameView:(WebFrameView *)view;
+
+- (NSArray *)children;
+
+- (NSString *)name;
+- (NSString *)positionString;
+- (NSString *)absolutePositionString;
+- (NSString *)widthString;
+- (NSString *)heightString;
+
+@end
diff --git a/WebKit/mac/WebView/WebRenderNode.mm b/WebKit/mac/WebView/WebRenderNode.mm
new file mode 100644
index 0000000..8d626e8
--- /dev/null
+++ b/WebKit/mac/WebView/WebRenderNode.mm
@@ -0,0 +1,137 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebRenderNode.h"
+
+#import <WebKit/WebFrameBridge.h>
+#import <WebKit/WebFrameView.h>
+#import <WebKit/WebHTMLView.h>
+#import <WebKit/WebDataSourceInternal.h>
+#import <WebKit/WebNSViewExtras.h>
+#import "WebFrameInternal.h"
+
+@interface WebKitRenderTreeCopier : NSObject <WebCoreRenderTreeCopier>
+@end
+
+@implementation WebRenderNode
+
+- initWithName:(NSString *)n position: (NSPoint)p rect:(NSRect)r view:(NSView *)view children:(NSArray *)c
+{
+ NSMutableArray *collectChildren;
+
+ self = [super init];
+ if (!self)
+ return nil;
+
+ collectChildren = [c mutableCopy];
+
+ name = [n retain];
+ rect = r;
+ absolutePosition = p;
+
+ if ([view isKindOfClass:[NSScrollView class]]) {
+ NSScrollView *scrollView = (NSScrollView *)view;
+ view = [scrollView superview];
+ }
+ if ([view isKindOfClass:[WebFrameView class]]) {
+ WebFrameView *webFrameView = (WebFrameView *)view;
+ WebRenderNode *node = [[WebRenderNode alloc] initWithWebFrameView:webFrameView];
+ [collectChildren addObject:node];
+ [node release];
+ }
+
+ children = [collectChildren copy];
+ [collectChildren release];
+
+ return self;
+}
+
+- initWithWebFrameView:(WebFrameView *)view
+{
+ WebKitRenderTreeCopier *copier;
+
+ [self release];
+
+ if (![[view documentView] isMemberOfClass:[WebHTMLView class]]) {
+ return nil;
+ }
+
+ copier = [[WebKitRenderTreeCopier alloc] init];
+ self = [[[[[view webFrame] _dataSource] _bridge] copyRenderTree:copier] retain];
+ [copier release];
+
+ return self;
+}
+
+- (void)dealloc
+{
+ [children release];
+ [name release];
+ [super dealloc];
+}
+
+- (NSArray *)children
+{
+ return children;
+}
+
+- (NSString *)name
+{
+ return name;
+}
+
+- (NSString *)absolutePositionString
+{
+ return [NSString stringWithFormat:@"(%.0f, %.0f)", absolutePosition.x, absolutePosition.y];
+}
+
+- (NSString *)positionString
+{
+ return [NSString stringWithFormat:@"(%.0f, %.0f)", rect.origin.x, rect.origin.y];
+}
+
+- (NSString *)widthString
+{
+ return [NSString stringWithFormat:@"%.0f", rect.size.width];
+}
+
+- (NSString *)heightString
+{
+ return [NSString stringWithFormat:@"%.0f", rect.size.height];
+}
+
+@end
+
+@implementation WebKitRenderTreeCopier
+
+- (NSObject *)nodeWithName:(NSString *)name position: (NSPoint)p rect:(NSRect)rect view:(NSView *)view children:(NSArray *)children
+{
+ return [[[WebRenderNode alloc] initWithName:name position: p rect:rect view:view children:children] autorelease];
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebResource.h b/WebKit/mac/WebView/WebResource.h
new file mode 100644
index 0000000..2544d78
--- /dev/null
+++ b/WebKit/mac/WebView/WebResource.h
@@ -0,0 +1,88 @@
+/*
+ * Copyright (C) 2004, 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@class WebMainResourcePrivate;
+@class WebResourcePrivate;
+
+
+/*!
+ @class WebResource
+ @discussion A WebResource represents a fully downloaded URL.
+ It includes the data of the resource as well as the metadata associated with the resource.
+*/
+@interface WebResource : NSObject <NSCoding, NSCopying>
+{
+@private
+ WebResourcePrivate *_private;
+}
+
+/*!
+ @method initWithData:URL:MIMEType:textEncodingName:frameName
+ @abstract The initializer for WebResource.
+ @param data The data of the resource.
+ @param URL The URL of the resource.
+ @param MIMEType The MIME type of the resource.
+ @param textEncodingName The text encoding name of the resource (can be nil).
+ @param frameName The frame name of the resource if the resource represents the contents of an entire HTML frame (can be nil).
+ @result An initialized WebResource.
+*/
+- (id)initWithData:(NSData *)data URL:(NSURL *)URL MIMEType:(NSString *)MIMEType textEncodingName:(NSString *)textEncodingName frameName:(NSString *)frameName;
+
+/*!
+ @method data
+ @result The data of the resource.
+*/
+- (NSData *)data;
+
+/*!
+ @method URL
+ @result The URL of the resource.
+*/
+- (NSURL *)URL;
+
+/*!
+ @method MIMEType
+ @result The MIME type of the resource.
+*/
+- (NSString *)MIMEType;
+
+/*!
+ @method textEncodingName
+ @result The text encoding name of the resource (can be nil).
+*/
+- (NSString *)textEncodingName;
+
+/*!
+ @method frameName
+ @result The frame name of the resource if the resource represents the contents of an entire HTML frame (can be nil).
+*/
+- (NSString *)frameName;
+
+@end
diff --git a/WebKit/mac/WebView/WebResource.mm b/WebKit/mac/WebView/WebResource.mm
new file mode 100644
index 0000000..9866d39
--- /dev/null
+++ b/WebKit/mac/WebView/WebResource.mm
@@ -0,0 +1,349 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebResourcePrivate.h"
+
+#import "WebFrameBridge.h"
+#import "WebNSDictionaryExtras.h"
+#import "WebNSURLExtras.h"
+#import <WebCore/WebCoreURLResponse.h>
+
+static NSString * const WebResourceDataKey = @"WebResourceData";
+static NSString * const WebResourceFrameNameKey = @"WebResourceFrameName";
+static NSString * const WebResourceMIMETypeKey = @"WebResourceMIMEType";
+static NSString * const WebResourceURLKey = @"WebResourceURL";
+static NSString * const WebResourceTextEncodingNameKey = @"WebResourceTextEncodingName";
+static NSString * const WebResourceResponseKey = @"WebResourceResponse";
+
+#define WebResourceVersion 1
+
+@interface WebResourcePrivate : NSObject
+{
+@public
+ NSData *data;
+ NSURL *URL;
+ NSString *frameName;
+ NSString *MIMEType;
+ NSString *textEncodingName;
+ NSURLResponse *response;
+ BOOL shouldIgnoreWhenUnarchiving;
+}
+@end
+
+@implementation WebResourcePrivate
+
+- (void)dealloc
+{
+ [data release];
+ [URL release];
+ [frameName release];
+ [MIMEType release];
+ [textEncodingName release];
+ [response release];
+ [super dealloc];
+}
+
+@end
+
+@implementation WebResource
+
+- (id)init
+{
+ self = [super init];
+ if (!self)
+ return nil;
+ _private = [[WebResourcePrivate alloc] init];
+ return self;
+}
+
+- (id)initWithData:(NSData *)data URL:(NSURL *)URL MIMEType:(NSString *)MIMEType textEncodingName:(NSString *)textEncodingName frameName:(NSString *)frameName
+{
+ return [self _initWithData:data URL:URL MIMEType:MIMEType textEncodingName:textEncodingName frameName:frameName response:nil copyData:YES];
+}
+
+- (id)initWithCoder:(NSCoder *)decoder
+{
+ self = [self init];
+ if (!self)
+ return nil;
+
+ @try {
+ id object = [decoder decodeObjectForKey:WebResourceDataKey];
+ if ([object isKindOfClass:[NSData class]])
+ _private->data = [object retain];
+ object = [decoder decodeObjectForKey:WebResourceURLKey];
+ if ([object isKindOfClass:[NSURL class]])
+ _private->URL = [object retain];
+ object = [decoder decodeObjectForKey:WebResourceMIMETypeKey];
+ if ([object isKindOfClass:[NSString class]])
+ _private->MIMEType = [object retain];
+ object = [decoder decodeObjectForKey:WebResourceTextEncodingNameKey];
+ if ([object isKindOfClass:[NSString class]])
+ _private->textEncodingName = [object retain];
+ object = [decoder decodeObjectForKey:WebResourceFrameNameKey];
+ if ([object isKindOfClass:[NSString class]])
+ _private->frameName = [object retain];
+ object = [decoder decodeObjectForKey:WebResourceResponseKey];
+ if ([object isKindOfClass:[NSURLResponse class]])
+ _private->response = [object retain];
+ } @catch(id) {
+ [self release];
+ return nil;
+ }
+
+ return self;
+}
+
+- (void)encodeWithCoder:(NSCoder *)encoder
+{
+ [encoder encodeObject:_private->data forKey:WebResourceDataKey];
+ [encoder encodeObject:_private->URL forKey:WebResourceURLKey];
+ [encoder encodeObject:_private->MIMEType forKey:WebResourceMIMETypeKey];
+ [encoder encodeObject:_private->textEncodingName forKey:WebResourceTextEncodingNameKey];
+ [encoder encodeObject:_private->frameName forKey:WebResourceFrameNameKey];
+ [encoder encodeObject:_private->response forKey:WebResourceResponseKey];
+}
+
+- (void)dealloc
+{
+ [_private release];
+ [super dealloc];
+}
+
+- (id)copyWithZone:(NSZone *)zone
+{
+ return [self retain];
+}
+
+- (NSData *)data
+{
+ return _private->data;
+}
+
+- (NSURL *)URL
+{
+ return _private->URL;
+}
+
+- (NSString *)MIMEType
+{
+ return _private->MIMEType;
+}
+
+- (NSString *)textEncodingName
+{
+ return _private->textEncodingName;
+}
+
+- (NSString *)frameName
+{
+ return _private->frameName;
+}
+
+- (id)description
+{
+ return [NSString stringWithFormat:@"<%@ %@>", [self className], [self URL]];
+}
+
+@end
+
+@implementation WebResource (WebResourcePrivate)
+
+// SPI for Mail (5066325)
+- (void)_ignoreWhenUnarchiving
+{
+ _private->shouldIgnoreWhenUnarchiving = YES;
+}
+
+- (BOOL)_shouldIgnoreWhenUnarchiving
+{
+ return _private->shouldIgnoreWhenUnarchiving;
+}
+
++ (NSArray *)_resourcesFromPropertyLists:(NSArray *)propertyLists
+{
+ if (![propertyLists isKindOfClass:[NSArray class]]) {
+ return nil;
+ }
+ NSEnumerator *enumerator = [propertyLists objectEnumerator];
+ NSMutableArray *resources = [NSMutableArray array];
+ NSDictionary *propertyList;
+ while ((propertyList = [enumerator nextObject]) != nil) {
+ WebResource *resource = [[WebResource alloc] _initWithPropertyList:propertyList];
+ if (resource) {
+ [resources addObject:resource];
+ [resource release];
+ }
+ }
+ return resources;
+}
+
++ (NSArray *)_propertyListsFromResources:(NSArray *)resources
+{
+ NSEnumerator *enumerator = [resources objectEnumerator];
+ NSMutableArray *propertyLists = [NSMutableArray array];
+ WebResource *resource;
+ while ((resource = [enumerator nextObject]) != nil) {
+ [propertyLists addObject:[resource _propertyListRepresentation]];
+ }
+ return propertyLists;
+}
+
+- (id)_initWithData:(NSData *)data
+ URL:(NSURL *)URL
+ MIMEType:(NSString *)MIMEType
+ textEncodingName:(NSString *)textEncodingName
+ frameName:(NSString *)frameName
+ response:(NSURLResponse *)response
+ copyData:(BOOL)copyData
+{
+ [self init];
+
+ if (!data) {
+ [self release];
+ return nil;
+ }
+ _private->data = copyData ? [data copy] : [data retain];
+
+ if (!URL) {
+ [self release];
+ return nil;
+ }
+ _private->URL = [URL copy];
+
+ if (!MIMEType) {
+ [self release];
+ return nil;
+ }
+ _private->MIMEType = [MIMEType copy];
+
+ _private->textEncodingName = [textEncodingName copy];
+ _private->frameName = [frameName copy];
+ _private->response = [response retain];
+
+ return self;
+}
+
+- (id)_initWithData:(NSData *)data URL:(NSURL *)URL response:(NSURLResponse *)response
+{
+ // Pass NO for copyData since the data doesn't need to be copied since we know that callers will no longer modify it.
+ // Copying it will also cause a performance regression.
+ return [self _initWithData:data
+ URL:URL
+ MIMEType:[response _webcore_MIMEType]
+ textEncodingName:[response textEncodingName]
+ frameName:nil
+ response:response
+ copyData:NO];
+}
+
+- (id)_initWithPropertyList:(id)propertyList
+{
+ if (![propertyList isKindOfClass:[NSDictionary class]]) {
+ [self release];
+ return nil;
+ }
+
+ NSURLResponse *response = nil;
+ NSData *responseData = [propertyList objectForKey:WebResourceResponseKey];
+ if ([responseData isKindOfClass:[NSData class]]) {
+ NSKeyedUnarchiver *unarchiver = [[NSKeyedUnarchiver alloc] initForReadingWithData:responseData];
+ @try {
+ id responseObject = [unarchiver decodeObjectForKey:WebResourceResponseKey];
+ if ([responseObject isKindOfClass:[NSURLResponse class]])
+ response = responseObject;
+ [unarchiver finishDecoding];
+ } @catch(id) {
+ response = nil;
+ }
+ [unarchiver release];
+ }
+
+ NSData *data = [propertyList objectForKey:WebResourceDataKey];
+ NSString *URLString = [propertyList _webkit_stringForKey:WebResourceURLKey];
+ return [self _initWithData:[data isKindOfClass:[NSData class]] ? data : nil
+ URL:URLString ? [NSURL _web_URLWithDataAsString:URLString] : nil
+ MIMEType:[propertyList _webkit_stringForKey:WebResourceMIMETypeKey]
+ textEncodingName:[propertyList _webkit_stringForKey:WebResourceTextEncodingNameKey]
+ frameName:[propertyList _webkit_stringForKey:WebResourceFrameNameKey]
+ response:response
+ copyData:NO];
+}
+
+- (NSFileWrapper *)_fileWrapperRepresentation
+{
+ NSFileWrapper *wrapper = [[[NSFileWrapper alloc] initRegularFileWithContents:_private->data] autorelease];
+ NSString *preferredFilename = [_private->response suggestedFilename];
+ if (!preferredFilename || ![preferredFilename length])
+ preferredFilename = [_private->URL _webkit_suggestedFilenameWithMIMEType:_private->MIMEType];
+ [wrapper setPreferredFilename:preferredFilename];
+ return wrapper;
+}
+
+- (id)_propertyListRepresentation
+{
+ NSMutableDictionary *propertyList = [NSMutableDictionary dictionary];
+ [propertyList setObject:_private->data forKey:WebResourceDataKey];
+ [propertyList setObject:[_private->URL _web_originalDataAsString] forKey:WebResourceURLKey];
+ [propertyList setObject:_private->MIMEType forKey:WebResourceMIMETypeKey];
+ if (_private->textEncodingName != nil) {
+ [propertyList setObject:_private->textEncodingName forKey:WebResourceTextEncodingNameKey];
+ }
+ if (_private->frameName != nil) {
+ [propertyList setObject:_private->frameName forKey:WebResourceFrameNameKey];
+ }
+ if (_private->response != nil) {
+ NSMutableData *responseData = [[NSMutableData alloc] init];
+ NSKeyedArchiver *archiver = [[NSKeyedArchiver alloc] initForWritingWithMutableData:responseData];
+ [archiver encodeObject:_private->response forKey:WebResourceResponseKey];
+ [archiver finishEncoding];
+ [archiver release];
+ [propertyList setObject:responseData forKey:WebResourceResponseKey];
+ [responseData release];
+ }
+ return propertyList;
+}
+
+- (NSURLResponse *)_response
+{
+ if (_private->response != nil) {
+ return _private->response;
+ }
+ return [[[NSURLResponse alloc] initWithURL:_private->URL
+ MIMEType:_private->MIMEType
+ expectedContentLength:[_private->data length]
+ textEncodingName:_private->textEncodingName] autorelease];
+}
+
+- (NSString *)_stringValue
+{
+ NSString *textEncodingName = [self textEncodingName];
+ return [WebFrameBridge stringWithData:_private->data textEncodingName:textEncodingName];
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebResourceLoadDelegate.h b/WebKit/mac/WebView/WebResourceLoadDelegate.h
new file mode 100644
index 0000000..f92466b
--- /dev/null
+++ b/WebKit/mac/WebView/WebResourceLoadDelegate.h
@@ -0,0 +1,166 @@
+/*
+ * Copyright (C) 2003, 2004, 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define WebNSInteger int
+#else
+#define WebNSInteger NSInteger
+#endif
+
+@class WebView;
+@class WebDataSource;
+@class NSURLAuthenticationChallenge;
+@class NSURLResponse;
+@class NSURLRequest;
+
+/*!
+ @category WebResourceLoadDelegate
+ @discussion Implementors of this protocol will receive messages indicating
+ that a resource is about to be loaded, data has been received for a resource,
+ an error has been received for a resource, and completion of a resource load.
+ Implementors are also given the opportunity to mutate requests before they are sent.
+ The various progress methods of this protocol all receive an identifier as the
+ parameter. This identifier can be used to track messages associated with a single
+ resource. For example, a single resource may generate multiple
+ resource:willSendRequest:redirectResponse:fromDataSource: messages as it's URL is redirected.
+*/
+@interface NSObject (WebResourceLoadDelegate)
+
+/*!
+ @method webView:identifierForInitialRequest:fromDataSource:
+ @param webView The WebView sending the message.
+ @param request The request about to be sent.
+ @param dataSource The datasource that initiated the load.
+ @discussion An implementor of WebResourceLoadDelegate should provide an identifier
+ that can be used to track the load of a single resource. This identifier will be
+ passed as the first argument for all of the other WebResourceLoadDelegate methods. The
+ identifier is useful to track changes to a resources request, which will be
+ provided by one or more calls to resource:willSendRequest:redirectResponse:fromDataSource:.
+ @result An identifier that will be passed back to the implementor for each callback.
+ The identifier will be retained.
+*/
+- (id)webView:(WebView *)sender identifierForInitialRequest:(NSURLRequest *)request fromDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method resource:willSendRequest:redirectResponse:fromDataSource:
+ @discussion This message is sent before a load is initiated. The request may be modified
+ as necessary by the receiver.
+ @param webView The WebView sending the message.
+ @param identifier An identifier that can be used to track the progress of a resource load across
+ multiple call backs.
+ @param request The request about to be sent.
+ @param redirectResponse If the request is being made in response to a redirect we received,
+ the response that conveyed that redirect.
+ @param dataSource The dataSource that initiated the load.
+ @result Returns the request, which may be mutated by the implementor, although typically
+ will be request.
+*/
+- (NSURLRequest *)webView:(WebView *)sender resource:(id)identifier willSendRequest:(NSURLRequest *)request redirectResponse:(NSURLResponse *)redirectResponse fromDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method webView:resource:didReceiveAuthenticationChallenge:fromDataSource:
+ @abstract Start authentication for the resource, providing a challenge
+ @discussion Call useCredential::, continueWithoutCredential or
+ cancel on the challenge when done.
+ @param challenge The NSURLAuthenticationChallenge to start authentication for
+ @discussion If you do not implement this delegate method, WebKit will handle authentication
+ automatically by prompting with a sheet on the window that the WebView is associated with.
+*/
+- (void)webView:(WebView *)sender resource:(id)identifier didReceiveAuthenticationChallenge:(NSURLAuthenticationChallenge *)challenge fromDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method webView:resource:didCancelAuthenticationChallenge:fromDataSource:
+ @abstract Cancel authentication for a given request
+ @param challenge The NSURLAuthenticationChallenge for which to cancel authentication
+*/
+- (void)webView:(WebView *)sender resource:(id)identifier didCancelAuthenticationChallenge:(NSURLAuthenticationChallenge *)challenge fromDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method webView:resource:didReceiveResponse:fromDataSource:
+ @abstract This message is sent after a response has been received for this load.
+ @param webView The WebView sending the message.
+ @param identifier An identifier that can be used to track the progress of a resource load across
+ multiple call backs.
+ @param response The response for the request.
+ @param dataSource The dataSource that initiated the load.
+ @discussion In some rare cases, multiple responses may be received for a single load.
+ This occurs with multipart/x-mixed-replace, or "server push". In this case, the client
+ should assume that each new response resets progress so far for the resource back to 0,
+ and should check the new response for the expected content length.
+*/
+- (void)webView:(WebView *)sender resource:(id)identifier didReceiveResponse:(NSURLResponse *)response fromDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method webView:resource:didReceiveContentLength:fromDataSource:
+ @discussion Multiple of these messages may be sent as data arrives.
+ @param webView The WebView sending the message.
+ @param identifier An identifier that can be used to track the progress of a resource load across
+ multiple call backs.
+ @param length The amount of new data received. This is not the total amount, just the new amount received.
+ @param dataSource The dataSource that initiated the load.
+*/
+- (void)webView:(WebView *)sender resource:(id)identifier didReceiveContentLength:(WebNSInteger)length fromDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method webView:resource:didFinishLoadingFromDataSource:
+ @discussion This message is sent after a load has successfully completed.
+ @param webView The WebView sending the message.
+ @param identifier An identifier that can be used to track the progress of a resource load across
+ multiple call backs.
+ @param dataSource The dataSource that initiated the load.
+*/
+- (void)webView:(WebView *)sender resource:(id)identifier didFinishLoadingFromDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method webView:resource:didFailLoadingWithError:fromDataSource:
+ @discussion This message is sent after a load has failed to load due to an error.
+ @param webView The WebView sending the message.
+ @param identifier An identifier that can be used to track the progress of a resource load across
+ multiple call backs.
+ @param error The error associated with this load.
+ @param dataSource The dataSource that initiated the load.
+*/
+- (void)webView:(WebView *)sender resource:(id)identifier didFailLoadingWithError:(NSError *)error fromDataSource:(WebDataSource *)dataSource;
+
+/*!
+ @method webView:plugInFailedWithError:dataSource:
+ @discussion Called when a plug-in is not found, fails to load or is not available for some reason.
+ @param webView The WebView sending the message.
+ @param error The plug-in error. In the userInfo dictionary of the error, the object for the
+ NSErrorFailingURLKey key is a URL string of the SRC attribute, the object for the WebKitErrorPlugInNameKey
+ key is a string of the plug-in's name, the object for the WebKitErrorPlugInPageURLStringKey key is a URL string
+ of the PLUGINSPAGE attribute and the object for the WebKitErrorMIMETypeKey key is a string of the TYPE attribute.
+ Some, none or all of the mentioned attributes can be present in the userInfo. The error returns nil for userInfo
+ when none are present.
+ @param dataSource The dataSource that contains the plug-in.
+*/
+- (void)webView:(WebView *)sender plugInFailedWithError:(NSError *)error dataSource:(WebDataSource *)dataSource;
+
+@end
+
+#undef WebNSInteger
diff --git a/WebKit/mac/WebView/WebResourceLoadDelegatePrivate.h b/WebKit/mac/WebView/WebResourceLoadDelegatePrivate.h
new file mode 100644
index 0000000..5fd13ee
--- /dev/null
+++ b/WebKit/mac/WebView/WebResourceLoadDelegatePrivate.h
@@ -0,0 +1,47 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define WebNSInteger int
+#else
+#define WebNSInteger NSInteger
+#endif
+
+@class WebView;
+@class WebDataSource;
+@class NSURLAuthenticationChallenge;
+@class NSURLResponse;
+@class NSURLRequest;
+
+@interface NSObject (WebResourceLoadDelegatePrivate)
+
+- (void)webView:(WebView *)webView didLoadResourceFromMemoryCache:(NSURLRequest *)request response:(NSURLResponse *)response length:(WebNSInteger)length fromDataSource:(WebDataSource *)dataSource;
+
+@end
+
+#undef WebNSInteger
diff --git a/WebKit/mac/WebView/WebResourcePrivate.h b/WebKit/mac/WebView/WebResourcePrivate.h
new file mode 100644
index 0000000..3a7ee41
--- /dev/null
+++ b/WebKit/mac/WebView/WebResourcePrivate.h
@@ -0,0 +1,56 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebResource.h>
+
+@interface WebResource (WebResourcePrivate)
+
+- (id)_initWithData:(NSData *)data
+ URL:(NSURL *)URL
+ MIMEType:(NSString *)MIMEType
+ textEncodingName:(NSString *)textEncodingName
+ frameName:(NSString *)frameName
+ response:(NSURLResponse *)response
+ copyData:(BOOL)copyData;
+
+- (id)_initWithData:(NSData *)data URL:(NSURL *)URL response:(NSURLResponse *)response;
+
+- (BOOL)_shouldIgnoreWhenUnarchiving;
+- (void)_ignoreWhenUnarchiving;
+
++ (NSArray *)_resourcesFromPropertyLists:(NSArray *)propertyLists;
++ (NSArray *)_propertyListsFromResources:(NSArray *)resources;
+
+- (id)_initWithPropertyList:(id)propertyList;
+
+- (NSFileWrapper *)_fileWrapperRepresentation;
+- (id)_propertyListRepresentation;
+- (NSURLResponse *)_response;
+- (NSString *)_stringValue;
+
+@end
diff --git a/WebKit/mac/WebView/WebScriptDebugDelegate.h b/WebKit/mac/WebView/WebScriptDebugDelegate.h
new file mode 100644
index 0000000..7a4c349
--- /dev/null
+++ b/WebKit/mac/WebView/WebScriptDebugDelegate.h
@@ -0,0 +1,136 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define WebNSUInteger unsigned int
+#else
+#define WebNSUInteger NSUInteger
+#endif
+
+@class WebView;
+@class WebFrame;
+@class WebScriptCallFrame;
+@class WebCoreScriptCallFrame;
+
+extern NSString * const WebScriptErrorDomain;
+extern NSString * const WebScriptErrorDescriptionKey;
+extern NSString * const WebScriptErrorLineNumberKey;
+
+enum {
+ WebScriptGeneralErrorCode = -100
+};
+
+// WebScriptDebugDelegate messages
+
+@interface NSObject (WebScriptDebugDelegate)
+
+// some source was parsed, establishing a "source ID" (>= 0) for future reference
+// this delegate method is deprecated, please switch to the new version below
+- (void)webView:(WebView *)webView didParseSource:(NSString *)source
+ fromURL:(NSString *)url
+ sourceId:(int)sid
+ forWebFrame:(WebFrame *)webFrame;
+
+// some source was parsed, establishing a "source ID" (>= 0) for future reference
+- (void)webView:(WebView *)webView didParseSource:(NSString *)source
+ baseLineNumber:(WebNSUInteger)lineNumber
+ fromURL:(NSURL *)url
+ sourceId:(int)sid
+ forWebFrame:(WebFrame *)webFrame;
+
+// some source failed to parse
+- (void)webView:(WebView *)webView failedToParseSource:(NSString *)source
+ baseLineNumber:(WebNSUInteger)lineNumber
+ fromURL:(NSURL *)url
+ withError:(NSError *)error
+ forWebFrame:(WebFrame *)webFrame;
+
+// just entered a stack frame (i.e. called a function, or started global scope)
+- (void)webView:(WebView *)webView didEnterCallFrame:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame;
+
+// about to execute some code
+- (void)webView:(WebView *)webView willExecuteStatement:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame;
+
+// about to leave a stack frame (i.e. return from a function)
+- (void)webView:(WebView *)webView willLeaveCallFrame:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame;
+
+// exception is being thrown
+- (void)webView:(WebView *)webView exceptionWasRaised:(WebScriptCallFrame *)frame
+ sourceId:(int)sid
+ line:(int)lineno
+ forWebFrame:(WebFrame *)webFrame;
+@end
+
+
+
+// WebScriptCallFrame interface
+//
+// These objects are passed as arguments to the debug delegate.
+
+@interface WebScriptCallFrame : NSObject
+{
+@private
+ WebCoreScriptCallFrame *_private;
+ id _userInfo;
+}
+
+// associate user info with frame
+- (void)setUserInfo:(id)userInfo;
+
+// retrieve user info
+- (id)userInfo;
+
+// get next frame on call stack (or nil if this is already the "global" frame)
+- (WebScriptCallFrame *)caller;
+
+// get array of WebScriptObjects for each scope (innermost first, last is always global object)
+- (NSArray *)scopeChain;
+
+// get name of function (if available) or nil
+- (NSString *)functionName;
+
+// get pending exception (if any) or nil
+- (id)exception;
+
+// evaluate a script (as if by "eval") in the context of this frame
+- (id)evaluateWebScript:(NSString *)script;
+
+@end
+
+#undef WebNSUInteger
diff --git a/WebKit/mac/WebView/WebScriptDebugDelegate.mm b/WebKit/mac/WebView/WebScriptDebugDelegate.mm
new file mode 100644
index 0000000..71ad1ef
--- /dev/null
+++ b/WebKit/mac/WebView/WebScriptDebugDelegate.mm
@@ -0,0 +1,195 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebScriptDebugDelegatePrivate.h"
+
+#import "WebDataSource.h"
+#import "WebDataSourceInternal.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebScriptDebugServerPrivate.h"
+#import "WebViewInternal.h"
+#import <WebCore/Frame.h>
+#import <WebCore/WebCoreScriptDebugger.h>
+
+using namespace WebCore;
+
+// FIXME: these error strings should be public for future use by WebScriptObject and in WebScriptObject.h
+NSString * const WebScriptErrorDomain = @"WebScriptErrorDomain";
+NSString * const WebScriptErrorDescriptionKey = @"WebScriptErrorDescription";
+NSString * const WebScriptErrorLineNumberKey = @"WebScriptErrorLineNumber";
+
+@interface WebScriptCallFrame (WebScriptDebugDelegateInternal)
+
+- (WebScriptCallFrame *)_initWithFrame:(WebCoreScriptCallFrame *)frame;
+
+@end
+
+@implementation WebScriptDebugger
+
+- (WebScriptDebugger *)initWithWebFrame:(WebFrame *)webFrame
+{
+ if ((self = [super init])) {
+ _webFrame = webFrame;
+ _debugger = [[WebCoreScriptDebugger alloc] initWithDelegate:self];
+ }
+ return self;
+}
+
+- (void)dealloc
+{
+ [_debugger release];
+ [super dealloc];
+}
+
+- (WebScriptObject *)globalObject
+{
+ return core(_webFrame)->windowScriptObject();
+}
+
+- (id)newWrapperForFrame:(WebCoreScriptCallFrame *)frame
+{
+ return [[WebScriptCallFrame alloc] _initWithFrame:frame];
+}
+
+- (void)parsedSource:(NSString *)source fromURL:(NSURL *)url sourceId:(int)sid startLine:(int)startLine errorLine:(int)errorLine errorMessage:(NSString *)errorMessage
+{
+ WebView *webView = [_webFrame webView];
+ if (errorLine == -1) {
+ [[webView _scriptDebugDelegateForwarder] webView:webView didParseSource:source baseLineNumber:startLine fromURL:url sourceId:sid forWebFrame:_webFrame];
+ [[webView _scriptDebugDelegateForwarder] webView:webView didParseSource:source fromURL:[url absoluteString] sourceId:sid forWebFrame:_webFrame]; // deprecated delegate method
+ if ([WebScriptDebugServer listenerCount])
+ [[WebScriptDebugServer sharedScriptDebugServer] webView:webView didParseSource:source baseLineNumber:startLine fromURL:url sourceId:sid forWebFrame:_webFrame];
+ } else {
+ NSDictionary *info = [[NSDictionary alloc] initWithObjectsAndKeys:errorMessage, WebScriptErrorDescriptionKey, [NSNumber numberWithUnsignedInt:errorLine], WebScriptErrorLineNumberKey, nil];
+ NSError *error = [[NSError alloc] initWithDomain:WebScriptErrorDomain code:WebScriptGeneralErrorCode userInfo:info];
+ [[webView _scriptDebugDelegateForwarder] webView:webView failedToParseSource:source baseLineNumber:startLine fromURL:url withError:error forWebFrame:_webFrame];
+ if ([WebScriptDebugServer listenerCount])
+ [[WebScriptDebugServer sharedScriptDebugServer] webView:webView failedToParseSource:source baseLineNumber:startLine fromURL:url withError:error forWebFrame:_webFrame];
+ [error release];
+ [info release];
+ }
+}
+
+- (void)enteredFrame:(WebCoreScriptCallFrame *)frame sourceId:(int)sid line:(int)lineno
+{
+ WebView *webView = [_webFrame webView];
+ [[webView _scriptDebugDelegateForwarder] webView:webView didEnterCallFrame:[frame wrapper] sourceId:sid line:lineno forWebFrame:_webFrame];
+ if ([WebScriptDebugServer listenerCount])
+ [[WebScriptDebugServer sharedScriptDebugServer] webView:webView didEnterCallFrame:[frame wrapper] sourceId:sid line:lineno forWebFrame:_webFrame];
+}
+
+- (void)hitStatement:(WebCoreScriptCallFrame *)frame sourceId:(int)sid line:(int)lineno
+{
+ WebView *webView = [_webFrame webView];
+ [[webView _scriptDebugDelegateForwarder] webView:webView willExecuteStatement:[frame wrapper] sourceId:sid line:lineno forWebFrame:_webFrame];
+ if ([WebScriptDebugServer listenerCount])
+ [[WebScriptDebugServer sharedScriptDebugServer] webView:webView willExecuteStatement:[frame wrapper] sourceId:sid line:lineno forWebFrame:_webFrame];
+}
+
+- (void)leavingFrame:(WebCoreScriptCallFrame *)frame sourceId:(int)sid line:(int)lineno
+{
+ WebView *webView = [_webFrame webView];
+ [[webView _scriptDebugDelegateForwarder] webView:webView willLeaveCallFrame:[frame wrapper] sourceId:sid line:lineno forWebFrame:_webFrame];
+ if ([WebScriptDebugServer listenerCount])
+ [[WebScriptDebugServer sharedScriptDebugServer] webView:webView willLeaveCallFrame:[frame wrapper] sourceId:sid line:lineno forWebFrame:_webFrame];
+}
+
+- (void)exceptionRaised:(WebCoreScriptCallFrame *)frame sourceId:(int)sid line:(int)lineno
+{
+ WebView *webView = [_webFrame webView];
+ [[webView _scriptDebugDelegateForwarder] webView:webView exceptionWasRaised:[frame wrapper] sourceId:sid line:lineno forWebFrame:_webFrame];
+ if ([WebScriptDebugServer listenerCount])
+ [[WebScriptDebugServer sharedScriptDebugServer] webView:webView exceptionWasRaised:[frame wrapper] sourceId:sid line:lineno forWebFrame:_webFrame];
+}
+
+@end
+
+
+
+@implementation WebScriptCallFrame (WebScriptDebugDelegateInternal)
+
+- (WebScriptCallFrame *)_initWithFrame:(WebCoreScriptCallFrame *)frame
+{
+ if ((self = [super init])) {
+ _private = frame;
+ }
+ return self;
+}
+
+@end
+
+
+
+@implementation WebScriptCallFrame
+
+- (void) dealloc
+{
+ [_userInfo release];
+ [super dealloc];
+}
+
+- (void)setUserInfo:(id)userInfo
+{
+ if (userInfo != _userInfo) {
+ [_userInfo release];
+ _userInfo = [userInfo retain];
+ }
+}
+
+- (id)userInfo
+{
+ return _userInfo;
+}
+
+- (WebScriptCallFrame *)caller
+{
+ return [[_private caller] wrapper];
+}
+
+- (NSArray *)scopeChain
+{
+ return [_private scopeChain];
+}
+
+- (NSString *)functionName
+{
+ return [_private functionName];
+}
+
+- (id)exception
+{
+ return [_private exception];
+}
+
+- (id)evaluateWebScript:(NSString *)script
+{
+ return [_private evaluateWebScript:script];
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebScriptDebugDelegatePrivate.h b/WebKit/mac/WebView/WebScriptDebugDelegatePrivate.h
new file mode 100644
index 0000000..6bda4a7
--- /dev/null
+++ b/WebKit/mac/WebView/WebScriptDebugDelegatePrivate.h
@@ -0,0 +1,41 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebScriptDebugDelegate.h>
+#import <WebCore/WebCoreScriptDebugger.h>
+
+@interface WebScriptDebugger : NSObject <WebScriptDebugger>
+{
+@private
+ WebFrame *_webFrame;
+ WebCoreScriptDebugger *_debugger;
+}
+
+- (WebScriptDebugger *)initWithWebFrame:(WebFrame *)webFrame;
+
+@end
diff --git a/WebKit/mac/WebView/WebUIDelegate.h b/WebKit/mac/WebView/WebUIDelegate.h
new file mode 100644
index 0000000..15c4444
--- /dev/null
+++ b/WebKit/mac/WebView/WebUIDelegate.h
@@ -0,0 +1,556 @@
+/*
+ * Copyright (C) 2003, 2004, 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+#import <Foundation/NSURLRequest.h>
+
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define WebNSUInteger unsigned int
+#else
+#define WebNSUInteger NSUInteger
+#endif
+
+/*!
+ @enum WebMenuItemTag
+ @discussion Each menu item in the default menu items array passed in
+ contextMenuItemsForElement:defaultMenuItems: has its tag set to one of the WebMenuItemTags.
+ When iterating through the default menu items array, use the tag to differentiate between them.
+*/
+
+enum {
+ WebMenuItemTagOpenLinkInNewWindow=1,
+ WebMenuItemTagDownloadLinkToDisk,
+ WebMenuItemTagCopyLinkToClipboard,
+ WebMenuItemTagOpenImageInNewWindow,
+ WebMenuItemTagDownloadImageToDisk,
+ WebMenuItemTagCopyImageToClipboard,
+ WebMenuItemTagOpenFrameInNewWindow,
+ WebMenuItemTagCopy,
+ WebMenuItemTagGoBack,
+ WebMenuItemTagGoForward,
+ WebMenuItemTagStop,
+ WebMenuItemTagReload,
+ WebMenuItemTagCut,
+ WebMenuItemTagPaste,
+ WebMenuItemTagSpellingGuess,
+ WebMenuItemTagNoGuessesFound,
+ WebMenuItemTagIgnoreSpelling,
+ WebMenuItemTagLearnSpelling,
+ WebMenuItemTagOther,
+ WebMenuItemTagSearchInSpotlight,
+ WebMenuItemTagSearchWeb,
+ WebMenuItemTagLookUpInDictionary,
+ WebMenuItemTagOpenWithDefaultApplication,
+ WebMenuItemPDFActualSize,
+ WebMenuItemPDFZoomIn,
+ WebMenuItemPDFZoomOut,
+ WebMenuItemPDFAutoSize,
+ WebMenuItemPDFSinglePage,
+ WebMenuItemPDFFacingPages,
+ WebMenuItemPDFContinuous,
+ WebMenuItemPDFNextPage,
+ WebMenuItemPDFPreviousPage,
+};
+
+/*!
+ @enum WebDragDestinationAction
+ @abstract Actions that the destination of a drag can perform.
+ @constant WebDragDestinationActionNone No action
+ @constant WebDragDestinationActionDHTML Allows DHTML (such as JavaScript) to handle the drag
+ @constant WebDragDestinationActionEdit Allows editable documents to be edited from the drag
+ @constant WebDragDestinationActionLoad Allows a location change from the drag
+ @constant WebDragDestinationActionAny Allows any of the above to occur
+*/
+typedef enum {
+ WebDragDestinationActionNone = 0,
+ WebDragDestinationActionDHTML = 1,
+ WebDragDestinationActionEdit = 2,
+ WebDragDestinationActionLoad = 4,
+ WebDragDestinationActionAny = UINT_MAX
+} WebDragDestinationAction;
+
+/*!
+ @enum WebDragSourceAction
+ @abstract Actions that the source of a drag can perform.
+ @constant WebDragSourceActionNone No action
+ @constant WebDragSourceActionDHTML Allows DHTML (such as JavaScript) to start a drag
+ @constant WebDragSourceActionImage Allows an image drag to occur
+ @constant WebDragSourceActionLink Allows a link drag to occur
+ @constant WebDragSourceActionSelection Allows a selection drag to occur
+ @constant WebDragSourceActionAny Allows any of the above to occur
+*/
+typedef enum {
+ WebDragSourceActionNone = 0,
+ WebDragSourceActionDHTML = 1,
+ WebDragSourceActionImage = 2,
+ WebDragSourceActionLink = 4,
+ WebDragSourceActionSelection = 8,
+ WebDragSourceActionAny = UINT_MAX
+} WebDragSourceAction;
+
+/*!
+ @protocol WebOpenPanelResultListener
+ @discussion This protocol is used to call back with the results of
+ the file open panel requested by runOpenPanelForFileButtonWithResultListener:
+*/
+@protocol WebOpenPanelResultListener <NSObject>
+
+/*!
+ @method chooseFilename:
+ @abstract Call this method to return a filename from the file open panel.
+ @param fileName
+*/
+- (void)chooseFilename:(NSString *)fileName;
+
+/*!
+ @method cancel
+ @abstract Call this method to indicate that the file open panel was cancelled.
+*/
+- (void)cancel;
+
+@end
+
+@class WebView;
+
+/*!
+ @category WebUIDelegate
+ @discussion A class that implements WebUIDelegate provides
+ window-related methods that may be used by Javascript, plugins and
+ other aspects of web pages. These methods are used to open new
+ windows and control aspects of existing windows.
+*/
+@interface NSObject (WebUIDelegate)
+
+/*!
+ @method webView:createWebViewWithRequest:
+ @abstract Create a new window and begin to load the specified request.
+ @discussion The newly created window is hidden, and the window operations delegate on the
+ new WebViews will get a webViewShow: call.
+ @param sender The WebView sending the delegate method.
+ @param request The request to load.
+ @result The WebView for the new window.
+*/
+- (WebView *)webView:(WebView *)sender createWebViewWithRequest:(NSURLRequest *)request;
+
+/*!
+ @method webViewShow:
+ @param sender The WebView sending the delegate method.
+ @abstract Show the window that contains the top level view of the WebView,
+ ordering it frontmost.
+ @discussion This will only be called just after createWindowWithRequest:
+ is used to create a new window.
+*/
+- (void)webViewShow:(WebView *)sender;
+
+/*!
+ @method webView:createWebViewModalDialogWithRequest:
+ @abstract Create a new window and begin to load the specified request.
+ @discussion The newly created window is hidden, and the window operations delegate on the
+ new WebViews will get a webViewShow: call.
+ @param sender The WebView sending the delegate method.
+ @param request The request to load.
+ @result The WebView for the new window.
+*/
+- (WebView *)webView:(WebView *)sender createWebViewModalDialogWithRequest:(NSURLRequest *)request;
+
+/*!
+ @method webViewRunModal:
+ @param sender The WebView sending the delegate method.
+ @abstract Show the window that contains the top level view of the WebView,
+ ordering it frontmost. The window should be run modal in the application.
+ @discussion This will only be called just after createWebViewModalDialogWithRequest:
+ is used to create a new window.
+*/
+- (void)webViewRunModal:(WebView *)sender;
+
+/*!
+ @method webViewClose:
+ @abstract Close the current window.
+ @param sender The WebView sending the delegate method.
+ @discussion Clients showing multiple views in one window may
+ choose to close only the one corresponding to this
+ WebView. Other clients may choose to ignore this method
+ entirely.
+*/
+- (void)webViewClose:(WebView *)sender;
+
+/*!
+ @method webViewFocus:
+ @abstract Focus the current window (i.e. makeKeyAndOrderFront:).
+ @param The WebView sending the delegate method.
+ @discussion Clients showing multiple views in one window may want to
+ also do something to focus the one corresponding to this WebView.
+*/
+- (void)webViewFocus:(WebView *)sender;
+
+/*!
+ @method webViewUnfocus:
+ @abstract Unfocus the current window.
+ @param sender The WebView sending the delegate method.
+ @discussion Clients showing multiple views in one window may want to
+ also do something to unfocus the one corresponding to this WebView.
+*/
+- (void)webViewUnfocus:(WebView *)sender;
+
+/*!
+ @method webViewFirstResponder:
+ @abstract Get the first responder for this window.
+ @param sender The WebView sending the delegate method.
+ @discussion This method should return the focused control in the
+ WebView's view, if any. If the view is out of the window
+ hierarchy, this might return something than calling firstResponder
+ on the real NSWindow would. It's OK to return either nil or the
+ real first responder if some control not in the window has focus.
+*/
+- (NSResponder *)webViewFirstResponder:(WebView *)sender;
+
+/*!
+ @method webView:makeFirstResponder:
+ @abstract Set the first responder for this window.
+ @param sender The WebView sending the delegate method.
+ @param responder The responder to make first (will always be a view)
+ @discussion responder will always be a view that is in the view
+ subhierarchy of the top-level web view for this WebView. If the
+ WebView's top level view is currently out of the view
+ hierarchy, it may be desirable to save the first responder
+ elsewhere, or possibly ignore this call.
+*/
+- (void)webView:(WebView *)sender makeFirstResponder:(NSResponder *)responder;
+
+/*!
+ @method webView:setStatusText:
+ @abstract Set the window's status display, if any, to the specified string.
+ @param sender The WebView sending the delegate method.
+ @param text The status text to set
+*/
+- (void)webView:(WebView *)sender setStatusText:(NSString *)text;
+
+/*!
+ @method webViewStatusText:
+ @abstract Get the currently displayed status text.
+ @param sender The WebView sending the delegate method.
+ @result The status text
+*/
+- (NSString *)webViewStatusText:(WebView *)sender;
+
+/*!
+ @method webViewAreToolbarsVisible:
+ @abstract Determine whether the window's toolbars are currently visible
+ @param sender The WebView sending the delegate method.
+ @discussion This method should return YES if the window has any
+ toolbars that are currently on, besides the status bar. If the app
+ has more than one toolbar per window, for example a regular
+ command toolbar and a favorites bar, it should return YES from
+ this method if at least one is on.
+ @result YES if at least one toolbar is visible, otherwise NO.
+*/
+- (BOOL)webViewAreToolbarsVisible:(WebView *)sender;
+
+/*!
+ @method webView:setToolbarsVisible:
+ @param sender The WebView sending the delegate method.
+ @abstract Set whether the window's toolbars are currently visible.
+ @param visible New value for toolbar visibility
+ @discussion Setting this to YES should turn on all toolbars
+ (except for a possible status bar). Setting it to NO should turn
+ off all toolbars (with the same exception).
+*/
+- (void)webView:(WebView *)sender setToolbarsVisible:(BOOL)visible;
+
+/*!
+ @method webViewIsStatusBarVisible:
+ @abstract Determine whether the status bar is visible.
+ @param sender The WebView sending the delegate method.
+ @result YES if the status bar is visible, otherwise NO.
+*/
+- (BOOL)webViewIsStatusBarVisible:(WebView *)sender;
+
+/*!
+ @method webView:setStatusBarVisible:
+ @abstract Set whether the status bar is currently visible.
+ @param visible The new visibility value
+ @discussion Setting this to YES should show the status bar,
+ setting it to NO should hide it.
+*/
+- (void)webView:(WebView *)sender setStatusBarVisible:(BOOL)visible;
+
+/*!
+ @method webViewIsResizable:
+ @abstract Determine whether the window is resizable or not.
+ @param sender The WebView sending the delegate method.
+ @result YES if resizable, NO if not.
+ @discussion If there are multiple views in the same window, they
+ have have their own separate resize controls and this may need to
+ be handled specially.
+*/
+- (BOOL)webViewIsResizable:(WebView *)sender;
+
+/*!
+ @method webView:setResizable:
+ @abstract Set the window to resizable or not
+ @param sender The WebView sending the delegate method.
+ @param resizable YES if the window should be made resizable, NO if not.
+ @discussion If there are multiple views in the same window, they
+ have have their own separate resize controls and this may need to
+ be handled specially.
+*/
+- (void)webView:(WebView *)sender setResizable:(BOOL)resizable;
+
+/*!
+ @method webView:setFrame:
+ @abstract Set the window's frame rect
+ @param sender The WebView sending the delegate method.
+ @param frame The new window frame size
+ @discussion Even though a caller could set the frame directly using the NSWindow,
+ this method is provided so implementors of this protocol can do special
+ things on programmatic move/resize, like avoiding autosaving of the size.
+*/
+- (void)webView:(WebView *)sender setFrame:(NSRect)frame;
+
+/*!
+ @method webViewFrame:
+ @param sender The WebView sending the delegate method.
+ @abstract REturn the window's frame rect
+ @discussion
+*/
+- (NSRect)webViewFrame:(WebView *)sender;
+
+/*!
+ @method webView:runJavaScriptAlertPanelWithMessage:initiatedByFrame:
+ @abstract Display a JavaScript alert panel.
+ @param sender The WebView sending the delegate method.
+ @param message The message to display.
+ @param frame The WebFrame whose JavaScript initiated this call.
+ @discussion Clients should visually indicate that this panel comes
+ from JavaScript initiated by the specified frame. The panel should have
+ a single OK button.
+*/
+- (void)webView:(WebView *)sender runJavaScriptAlertPanelWithMessage:(NSString *)message initiatedByFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:runJavaScriptConfirmPanelWithMessage:initiatedByFrame:
+ @abstract Display a JavaScript confirm panel.
+ @param sender The WebView sending the delegate method.
+ @param message The message to display.
+ @param frame The WebFrame whose JavaScript initiated this call.
+ @result YES if the user hit OK, NO if the user chose Cancel.
+ @discussion Clients should visually indicate that this panel comes
+ from JavaScript initiated by the specified frame. The panel should have
+ two buttons, e.g. "OK" and "Cancel".
+*/
+- (BOOL)webView:(WebView *)sender runJavaScriptConfirmPanelWithMessage:(NSString *)message initiatedByFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:runJavaScriptTextInputPanelWithPrompt:defaultText:initiatedByFrame:
+ @abstract Display a JavaScript text input panel.
+ @param sender The WebView sending the delegate method.
+ @param message The message to display.
+ @param defaultText The initial text for the text entry area.
+ @param frame The WebFrame whose JavaScript initiated this call.
+ @result The typed text if the user hit OK, otherwise nil.
+ @discussion Clients should visually indicate that this panel comes
+ from JavaScript initiated by the specified frame. The panel should have
+ two buttons, e.g. "OK" and "Cancel", and an area to type text.
+*/
+- (NSString *)webView:(WebView *)sender runJavaScriptTextInputPanelWithPrompt:(NSString *)prompt defaultText:(NSString *)defaultText initiatedByFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:runJavaScriptConfirmPanelWithMessage:initiatedByFrame:
+ @abstract Display a confirm panel by an "before unload" event handler.
+ @param sender The WebView sending the delegate method.
+ @param message The message to display.
+ @param frame The WebFrame whose JavaScript initiated this call.
+ @result YES if the user hit OK, NO if the user chose Cancel.
+ @discussion Clients should include a message in addition to the one
+ supplied by the web page that indicates. The panel should have
+ two buttons, e.g. "OK" and "Cancel".
+*/
+- (BOOL)webView:(WebView *)sender runBeforeUnloadConfirmPanelWithMessage:(NSString *)message initiatedByFrame:(WebFrame *)frame;
+
+/*!
+ @method webView:runOpenPanelForFileButtonWithResultListener:
+ @abstract Display a file open panel for a file input control.
+ @param sender The WebView sending the delegate method.
+ @param resultListener The object to call back with the results.
+ @discussion This method is passed a callback object instead of giving a return
+ value so that it can be handled with a sheet.
+*/
+- (void)webView:(WebView *)sender runOpenPanelForFileButtonWithResultListener:(id<WebOpenPanelResultListener>)resultListener;
+
+/*!
+ @method webView:mouseDidMoveOverElement:modifierFlags:
+ @abstract Update the window's feedback for mousing over links to reflect a new item the mouse is over
+ or new modifier flags.
+ @param sender The WebView sending the delegate method.
+ @param elementInformation Dictionary that describes the element that the mouse is over, or nil.
+ @param modifierFlags The modifier flags as in NSEvent.
+*/
+- (void)webView:(WebView *)sender mouseDidMoveOverElement:(NSDictionary *)elementInformation modifierFlags:(WebNSUInteger)modifierFlags;
+
+/*!
+ @method webView:contextMenuItemsForElement:defaultMenuItems:
+ @abstract Returns the menu items to display in an element's contextual menu.
+ @param sender The WebView sending the delegate method.
+ @param element A dictionary representation of the clicked element.
+ @param defaultMenuItems An array of default NSMenuItems to include in all contextual menus.
+ @result An array of NSMenuItems to include in the contextual menu.
+*/
+- (NSArray *)webView:(WebView *)sender contextMenuItemsForElement:(NSDictionary *)element defaultMenuItems:(NSArray *)defaultMenuItems;
+
+/*!
+ @method webView:validateUserInterfaceItem:defaultValidation:
+ @abstract Controls UI validation
+ @param webView The WebView sending the delegate method
+ @param item The user interface item being validated
+ @pararm defaultValidation Whether or not the WebView thinks the item is valid
+ @discussion This method allows the UI delegate to control WebView's validation of user interface items.
+ See WebView.h to see the methods to that WebView can currently validate. See NSUserInterfaceValidations and
+ NSValidatedUserInterfaceItem for information about UI validation.
+*/
+- (BOOL)webView:(WebView *)webView validateUserInterfaceItem:(id <NSValidatedUserInterfaceItem>)item defaultValidation:(BOOL)defaultValidation;
+
+/*!
+ @method webView:shouldPerformAction:fromSender:
+ @abstract Controls actions
+ @param webView The WebView sending the delegate method
+ @param action The action being sent
+ @param sender The sender of the action
+ @discussion This method allows the UI delegate to control WebView's behavior when an action is being sent.
+ For example, if the action is copy:, the delegate can return YES to allow WebView to perform its default
+ copy behavior or return NO and perform copy: in some other way. See WebView.h to see the actions that
+ WebView can perform.
+*/
+- (BOOL)webView:(WebView *)webView shouldPerformAction:(SEL)action fromSender:(id)sender;
+
+/*!
+ @method webView:dragDestinationActionMaskForDraggingInfo:
+ @abstract Controls behavior when dragging to a WebView
+ @param webView The WebView sending the delegate method
+ @param draggingInfo The dragging info of the drag
+ @discussion This method is called periodically as something is dragged over a WebView. The UI delegate can return a mask
+ indicating which drag destination actions can occur, WebDragDestinationActionAny to allow any kind of action or
+ WebDragDestinationActionNone to not accept the drag.
+*/
+- (WebNSUInteger)webView:(WebView *)webView dragDestinationActionMaskForDraggingInfo:(id <NSDraggingInfo>)draggingInfo;
+
+/*!
+ @method webView:willPerformDragDestinationAction:forDraggingInfo:
+ @abstract Informs that WebView will perform a drag destination action
+ @param webView The WebView sending the delegate method
+ @param action The drag destination action
+ @param draggingInfo The dragging info of the drag
+ @discussion This method is called after the last call to webView:dragDestinationActionMaskForDraggingInfo: after something is dropped on a WebView.
+ This method informs the UI delegate of the drag destination action that WebView will perform.
+*/
+- (void)webView:(WebView *)webView willPerformDragDestinationAction:(WebDragDestinationAction)action forDraggingInfo:(id <NSDraggingInfo>)draggingInfo;
+
+/*!
+ @method webView:dragSourceActionMaskForPoint:
+ @abstract Controls behavior when dragging from a WebView
+ @param webView The WebView sending the delegate method
+ @param point The point where the drag started in the coordinates of the WebView
+ @discussion This method is called after the user has begun a drag from a WebView. The UI delegate can return a mask indicating
+ which drag source actions can occur, WebDragSourceActionAny to allow any kind of action or WebDragSourceActionNone to not begin a drag.
+*/
+- (WebNSUInteger)webView:(WebView *)webView dragSourceActionMaskForPoint:(NSPoint)point;
+
+/*!
+ @method webView:willPerformDragSourceAction:fromPoint:withPasteboard:
+ @abstract Informs that a drag a has begun from a WebView
+ @param webView The WebView sending the delegate method
+ @param action The drag source action
+ @param point The point where the drag started in the coordinates of the WebView
+ @param pasteboard The drag pasteboard
+ @discussion This method is called after webView:dragSourceActionMaskForPoint: is called after the user has begun a drag from a WebView.
+ This method informs the UI delegate of the drag source action that will be performed and gives the delegate an opportunity to modify
+ the contents of the dragging pasteboard.
+*/
+- (void)webView:(WebView *)webView willPerformDragSourceAction:(WebDragSourceAction)action fromPoint:(NSPoint)point withPasteboard:(NSPasteboard *)pasteboard;
+
+/*!
+ @method webView:printFrameView:
+ @abstract Informs that a WebFrameView needs to be printed
+ @param webView The WebView sending the delegate method
+ @param frameView The WebFrameView needing to be printed
+ @discussion This method is called when a script or user requests the page to be printed.
+ In this method the delegate can prepare the WebFrameView to be printed. Some content that WebKit
+ displays can be printed directly by the WebFrameView, other content will need to be handled by
+ the delegate. To determine if the WebFrameView can handle printing the delegate should check
+ WebFrameView's documentViewShouldHandlePrint, if YES then the delegate can call printDocumentView
+ on the WebFrameView. Otherwise the delegate will need to request a NSPrintOperation from
+ the WebFrameView's printOperationWithPrintInfo to handle the printing.
+*/
+- (void)webView:(WebView *)sender printFrameView:(WebFrameView *)frameView;
+
+/*!
+ @method webViewHeaderHeight:
+ @param webView The WebView sending the delegate method
+ @abstract Reserve a height for the printed page header.
+ @result The height to reserve for the printed page header, return 0.0 to not reserve any space for a header.
+ @discussion The height returned will be used to calculate the rect passed to webView:drawHeaderInRect:.
+*/
+- (float)webViewHeaderHeight:(WebView *)sender;
+
+/*!
+ @method webViewFooterHeight:
+ @param webView The WebView sending the delegate method
+ @abstract Reserve a height for the printed page footer.
+ @result The height to reserve for the printed page footer, return 0.0 to not reserve any space for a footer.
+ @discussion The height returned will be used to calculate the rect passed to webView:drawFooterInRect:.
+*/
+- (float)webViewFooterHeight:(WebView *)sender;
+
+/*!
+ @method webView:drawHeaderInRect:
+ @param webView The WebView sending the delegate method
+ @param rect The NSRect reserved for the header of the page
+ @abstract The delegate should draw a header for the sender in the supplied rect.
+*/
+- (void)webView:(WebView *)sender drawHeaderInRect:(NSRect)rect;
+
+/*!
+ @method webView:drawFooterInRect:
+ @param webView The WebView sending the delegate method
+ @param rect The NSRect reserved for the footer of the page
+ @abstract The delegate should draw a footer for the sender in the supplied rect.
+*/
+- (void)webView:(WebView *)sender drawFooterInRect:(NSRect)rect;
+
+// The following delegate methods are deprecated in favor of the ones above that specify
+// the WebFrame whose JavaScript initiated this call.
+- (void)webView:(WebView *)sender runJavaScriptAlertPanelWithMessage:(NSString *)message;
+- (BOOL)webView:(WebView *)sender runJavaScriptConfirmPanelWithMessage:(NSString *)message;
+- (NSString *)webView:(WebView *)sender runJavaScriptTextInputPanelWithPrompt:(NSString *)prompt defaultText:(NSString *)defaultText;
+
+// The following delegate methods are deprecated. Content rect calculations are now done automatically.
+- (void)webView:(WebView *)sender setContentRect:(NSRect)frame;
+- (NSRect)webViewContentRect:(WebView *)sender;
+
+@end
+
+#undef WebNSUInteger
diff --git a/WebKit/mac/WebView/WebUIDelegatePrivate.h b/WebKit/mac/WebView/WebUIDelegatePrivate.h
new file mode 100644
index 0000000..62ef3f9
--- /dev/null
+++ b/WebKit/mac/WebView/WebUIDelegatePrivate.h
@@ -0,0 +1,100 @@
+/*
+ * Copyright (C) 2005, 2006, 2007, 2008 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebUIDelegate.h>
+
+// Mail on Tiger expects the old value for WebMenuItemTagSearchInGoogle
+#define WebMenuItemTagSearchInGoogle OldWebMenuItemTagSearchWeb
+
+#define WEBMENUITEMTAG_WEBKIT_3_0_SPI_START 2000
+enum {
+ // The next three values were used in WebKit 2.0 for SPI. In WebKit 3.0 these are API, with different values.
+ OldWebMenuItemTagSearchInSpotlight = 1000,
+ OldWebMenuItemTagSearchWeb,
+ OldWebMenuItemTagLookUpInDictionary,
+ // FIXME: These should move to WebUIDelegate.h as part of the WebMenuItemTag enum there, when we're not in API freeze
+ // Note that these values must be kept aligned with values in WebCore/ContextMenuItem.h
+ WebMenuItemTagOpenLink = WEBMENUITEMTAG_WEBKIT_3_0_SPI_START,
+ WebMenuItemTagIgnoreGrammar,
+ WebMenuItemTagSpellingMenu,
+ WebMenuItemTagShowSpellingPanel,
+ WebMenuItemTagCheckSpelling,
+ WebMenuItemTagCheckSpellingWhileTyping,
+ WebMenuItemTagCheckGrammarWithSpelling,
+ WebMenuItemTagFontMenu,
+ WebMenuItemTagShowFonts,
+ WebMenuItemTagBold,
+ WebMenuItemTagItalic,
+ WebMenuItemTagUnderline,
+ WebMenuItemTagOutline,
+ WebMenuItemTagStyles,
+ WebMenuItemTagShowColors,
+ WebMenuItemTagSpeechMenu,
+ WebMenuItemTagStartSpeaking,
+ WebMenuItemTagStopSpeaking,
+ WebMenuItemTagWritingDirectionMenu,
+ WebMenuItemTagDefaultDirection,
+ WebMenuItemTagLeftToRight,
+ WebMenuItemTagRightToLeft,
+ WebMenuItemPDFSinglePageScrolling,
+ WebMenuItemPDFFacingPagesScrolling,
+ WebMenuItemTagInspectElement,
+ WebMenuItemTagBaseApplication = 10000
+};
+@class WebSecurityOrigin;
+
+@interface NSObject (WebUIDelegatePrivate)
+
+- (void)webView:(WebView *)webView addMessageToConsole:(NSDictionary *)message;
+
+- (NSView *)webView:(WebView *)webView plugInViewWithArguments:(NSDictionary *)arguments;
+
+// regions is an dictionary whose keys are regions label and values are arrays of WebDashboardRegions.
+- (void)webView:(WebView *)webView dashboardRegionsChanged:(NSDictionary *)regions;
+
+- (void)webView:(WebView *)sender dragImage:(NSImage *)anImage at:(NSPoint)viewLocation offset:(NSSize)initialOffset event:(NSEvent *)event pasteboard:(NSPasteboard *)pboard source:(id)sourceObj slideBack:(BOOL)slideFlag forView:(NSView *)view;
+- (void)webView:(WebView *)sender didDrawRect:(NSRect)rect;
+- (void)webView:(WebView *)sender didScrollDocumentInFrameView:(WebFrameView *)frameView;
+// FIXME: If we ever make this method public, it should include a WebFrame parameter.
+- (BOOL)webViewShouldInterruptJavaScript:(WebView *)sender;
+- (void)webView:(WebView *)sender willPopupMenu:(NSMenu *)menu;
+- (void)webView:(WebView *)sender contextMenuItemSelected:(NSMenuItem *)item forElement:(NSDictionary *)element;
+- (void)webView:(WebView *)sender saveFrameView:(WebFrameView *)frameView showingPanel:(BOOL)showingPanel;
+
+/*!
+ @method webView:frame:exceededDatabaseQuotaForSecurityOrigin:database:
+ @param sender The WebView sending the delegate method.
+ @param frame The WebFrame whose JavaScript initiated this call.
+ @param origin The security origin that needs a larger quota.
+ @param databaseIdentifier The identifier of the database involved.
+*/
+- (void)webView:(WebView *)sender frame:(WebFrame *)frame exceededDatabaseQuotaForSecurityOrigin:(WebSecurityOrigin *)origin database:(NSString *)databaseIdentifier;
+
+- (WebView *)webView:(WebView *)sender createWebViewWithRequest:(NSURLRequest *)request windowFeatures:(NSDictionary *)features;
+
+@end
diff --git a/WebKit/mac/WebView/WebUnarchivingState.h b/WebKit/mac/WebView/WebUnarchivingState.h
new file mode 100644
index 0000000..84d808b
--- /dev/null
+++ b/WebKit/mac/WebView/WebUnarchivingState.h
@@ -0,0 +1,45 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Foundation/Foundation.h>
+
+@class WebArchive;
+@class WebResource;
+
+@interface WebUnarchivingState : NSObject
+{
+ NSMutableDictionary *archivedSubframes;
+ NSMutableDictionary *archivedResources;
+}
+
+- (void)addArchive:(WebArchive *)archive;
+- (void)addResource:(WebResource *)resource;
+- (WebResource *)archivedResourceForURL:(NSURL *)URL;
+- (WebArchive *)popSubframeArchiveWithFrameName:(NSString *)frameName;
+
+@end
diff --git a/WebKit/mac/WebView/WebUnarchivingState.m b/WebKit/mac/WebView/WebUnarchivingState.m
new file mode 100644
index 0000000..c1b975a
--- /dev/null
+++ b/WebKit/mac/WebView/WebUnarchivingState.m
@@ -0,0 +1,98 @@
+/*
+ * Copyright (C) 2006 Apple Computer, Inc. All rights reserved.
+ * (C) 2007 Graham Dennis (graham.dennis@gmail.com)
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebUnarchivingState.h"
+
+#import "WebArchive.h"
+#import <JavaScriptCore/Assertions.h>
+#import "WebResource.h"
+#import "WebResourcePrivate.h"
+#import "WebNSURLExtras.h"
+
+@implementation WebUnarchivingState
+
+- (id)init
+{
+ if (!(self = [super init]))
+ return nil;
+
+ archivedSubframes = [[NSMutableDictionary alloc] init];
+ archivedResources = [[NSMutableDictionary alloc] init];
+
+ return self;
+}
+
+- (void)dealloc
+{
+ [archivedSubframes release];
+ [archivedResources release];
+ [super dealloc];
+}
+
+- (void)addArchive:(WebArchive *)archive
+{
+ NSEnumerator *enumerator = [[archive subresources] objectEnumerator];
+ WebResource *subresource;
+ while ((subresource = [enumerator nextObject]) != nil)
+ [archivedResources setObject:subresource forKey:[[subresource URL] _web_originalDataAsString]];
+
+ enumerator = [[archive subframeArchives] objectEnumerator];
+ WebArchive *subframeArchive;
+ while ((subframeArchive = [enumerator nextObject]) != nil) {
+ NSString *frameName = [[subframeArchive mainResource] frameName];
+ if (frameName)
+ [archivedSubframes setObject:subframeArchive forKey:frameName];
+ }
+}
+
+- (void)addResource:(WebResource *)subresource
+{
+ [archivedResources setObject:subresource forKey:[[subresource URL] _web_originalDataAsString]];
+}
+
+- (WebResource *)archivedResourceForURL:(NSURL *)URL
+{
+ WebResource *resource = [archivedResources objectForKey:[URL _web_originalDataAsString]];
+ if ([resource _shouldIgnoreWhenUnarchiving])
+ return nil;
+ return resource;
+}
+
+- (WebArchive *)popSubframeArchiveWithFrameName:(NSString *)frameName
+{
+ ASSERT(frameName != nil);
+
+ WebArchive *archive = [[[archivedSubframes objectForKey:frameName] retain] autorelease];
+ if (archive != nil)
+ [archivedSubframes removeObjectForKey:frameName];
+
+ return archive;
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebView.h b/WebKit/mac/WebView/WebView.h
new file mode 100644
index 0000000..6038703
--- /dev/null
+++ b/WebKit/mac/WebView/WebView.h
@@ -0,0 +1,819 @@
+/*
+ * Copyright (C) 2003, 2004, 2005, 2006 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <Cocoa/Cocoa.h>
+
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define WebNSInteger int
+#else
+#define WebNSInteger NSInteger
+#endif
+
+@class DOMCSSStyleDeclaration;
+@class DOMDocument;
+@class DOMElement;
+@class DOMNode;
+@class DOMRange;
+
+@class WebArchive;
+@class WebBackForwardList;
+@class WebDataSource;
+@class WebFrame;
+@class WebFrameView;
+@class WebHistoryItem;
+@class WebPreferences;
+@class WebScriptObject;
+@class WebViewPrivate;
+
+// Element dictionary keys
+extern NSString *WebElementDOMNodeKey; // DOMNode of the element
+extern NSString *WebElementFrameKey; // WebFrame of the element
+extern NSString *WebElementImageAltStringKey; // NSString of the ALT attribute of the image element
+extern NSString *WebElementImageKey; // NSImage of the image element
+extern NSString *WebElementImageRectKey; // NSValue of an NSRect, the rect of the image element
+extern NSString *WebElementImageURLKey; // NSURL of the image element
+extern NSString *WebElementIsSelectedKey; // NSNumber of BOOL indicating whether the element is selected or not
+extern NSString *WebElementLinkURLKey; // NSURL of the link if the element is within an anchor
+extern NSString *WebElementLinkTargetFrameKey; // WebFrame of the target of the anchor
+extern NSString *WebElementLinkTitleKey; // NSString of the title of the anchor
+extern NSString *WebElementLinkLabelKey; // NSString of the text within the anchor
+
+/*
+ @discussion Notifications sent by WebView to mark the progress of loads.
+ @constant WebViewProgressStartedNotification Posted whenever a load begins in the WebView, including
+ a load that is initiated in a subframe. After receiving this notification zero or more
+ WebViewProgressEstimateChangedNotifications will be sent. The userInfo will be nil.
+ @constant WebViewProgressEstimateChangedNotification Posted whenever the value of
+ estimatedProgress changes. The userInfo will be nil.
+ @constant WebViewProgressFinishedNotification Posted when the load for a WebView has finished.
+ The userInfo will be nil.
+*/
+extern NSString *WebViewProgressStartedNotification;
+extern NSString *WebViewProgressEstimateChangedNotification;
+extern NSString *WebViewProgressFinishedNotification;
+
+/*!
+ @class WebView
+ WebView manages the interaction between WebFrameViews and WebDataSources. Modification
+ of the policies and behavior of the WebKit is largely managed by WebViews and their
+ delegates.
+
+ <p>
+ Typical usage:
+ </p>
+ <pre>
+ WebView *webView;
+ WebFrame *mainFrame;
+
+ webView = [[WebView alloc] initWithFrame: NSMakeRect (0,0,640,480)];
+ mainFrame = [webView mainFrame];
+ [mainFrame loadRequest:request];
+ </pre>
+
+ WebViews have the following delegates: WebUIDelegate, WebResourceLoadDelegate,
+ WebFrameLoadDelegate, and WebPolicyDelegate.
+
+ WebKit depends on the WebView's WebUIDelegate for all window
+ related management, including opening new windows and controlling the user interface
+ elements in those windows.
+
+ WebResourceLoadDelegate is used to monitor the progress of resources as they are
+ loaded. This delegate may be used to present users with a progress monitor.
+
+ The WebFrameLoadDelegate receives messages when the URL in a WebFrame is
+ changed.
+
+ WebView's WebPolicyDelegate can make determinations about how
+ content should be handled, based on the resource's URL and MIME type.
+*/
+@interface WebView : NSView
+{
+@private
+ WebViewPrivate *_private;
+}
+
+/*!
+ @method canShowMIMEType:
+ @abstract Checks if the WebKit can show content of a certain MIME type.
+ @param MIMEType The MIME type to check.
+ @result YES if the WebKit can show content with MIMEtype.
+*/
++ (BOOL)canShowMIMEType:(NSString *)MIMEType;
+
+
+/*!
+ @method canShowMIMETypeAsHTML:
+ @abstract Checks if the the MIME type is a type that the WebKit will interpret as HTML.
+ @param MIMEType The MIME type to check.
+ @result YES if the MIMEtype in an HTML type.
+*/
++ (BOOL)canShowMIMETypeAsHTML:(NSString *)MIMEType;
+
+/*!
+ @method MIMETypesShownAsHTML
+ @result Returns an array of NSStrings that describe the MIME types
+ WebKit will attempt to render as HTML.
+*/
++ (NSArray *)MIMETypesShownAsHTML;
+
+/*!
+ @method setMIMETypesShownAsHTML:
+ @discussion Sets the array of NSString MIME types that WebKit will
+ attempt to render as HTML. Typically you will retrieve the built-in
+ array using MIMETypesShownAsHTML and add additional MIME types to that
+ array.
+*/
++ (void)setMIMETypesShownAsHTML:(NSArray *)MIMETypes;
+
+/*!
+ @method URLFromPasteboard:
+ @abstract Returns a URL from a pasteboard
+ @param pasteboard The pasteboard with a URL
+ @result A URL if the pasteboard has one. Nil if it does not.
+ @discussion This method differs than NSURL's URLFromPasteboard method in that it tries multiple pasteboard types
+ including NSURLPboardType to find a URL on the pasteboard.
+*/
++ (NSURL *)URLFromPasteboard:(NSPasteboard *)pasteboard;
+
+/*!
+ @method URLTitleFromPasteboard:
+ @abstract Returns a URL title from a pasteboard
+ @param pasteboard The pasteboard with a URL title
+ @result A URL title if the pasteboard has one. Nil if it does not.
+ @discussion This method returns a title that refers a URL on the pasteboard. An example of this is the link label
+ which is the text inside the anchor tag.
+*/
++ (NSString *)URLTitleFromPasteboard:(NSPasteboard *)pasteboard;
+
+/*!
+ @method registerURLSchemeAsLocal:
+ @abstract Adds the scheme to the list of schemes to be treated as local.
+ @param scheme The scheme to register
+*/
++ (void)registerURLSchemeAsLocal:(NSString *)scheme;
+
+/*!
+ @method initWithFrame:frameName:groupName:
+ @abstract The designated initializer for WebView.
+ @discussion Initialize a WebView with the supplied parameters. This method will
+ create a main WebFrame with the view. Passing a top level frame name is useful if you
+ handle a targetted frame navigation that would normally open a window in some other
+ way that still ends up creating a new WebView.
+ @param frame The frame used to create the view.
+ @param frameName The name to use for the top level frame. May be nil.
+ @param groupName The name of the webView set to which this webView will be added. May be nil.
+ @result Returns an initialized WebView.
+*/
+- (id)initWithFrame:(NSRect)frame frameName:(NSString *)frameName groupName:(NSString *)groupName;
+
+/*!
+ @method close
+ @abstract Closes the receiver, unloading its web page and canceling any pending loads.
+ Once the receiver has closed, it will no longer respond to requests or fire delegate methods.
+ (However, the -close method itself may fire delegate methods.)
+ @discussion A garbage collected application is required to call close when the receiver is no longer needed.
+ The close method will be called automatically when the window or hostWindow closes and shouldCloseWithWindow returns YES.
+ A non-garbage collected application can still call close, providing a convenient way to prevent receiver
+ from doing any more loading and firing any future delegate methods.
+*/
+- (void)close;
+
+/*!
+ @method setShouldCloseWithWindow:
+ @abstract Set whether the receiver closes when either it's window or hostWindow closes.
+ @param close YES if the receiver should close when either it's window or hostWindow closes, otherwise NO.
+*/
+- (void)setShouldCloseWithWindow:(BOOL)close;
+
+/*!
+ @method shouldCloseWithWindow
+ @abstract Returns whether the receiver closes when either it's window or hostWindow closes.
+ @discussion Defaults to YES in garbage collected applications, otherwise NO to maintain backwards compatibility.
+ @result YES if the receiver closes when either it's window or hostWindow closes, otherwise NO.
+*/
+- (BOOL)shouldCloseWithWindow;
+
+/*!
+ @method setUIDelegate:
+ @abstract Set the WebView's WebUIDelegate.
+ @param delegate The WebUIDelegate to set as the delegate.
+*/
+- (void)setUIDelegate:(id)delegate;
+
+/*!
+ @method UIDelegate
+ @abstract Return the WebView's WebUIDelegate.
+ @result The WebView's WebUIDelegate.
+*/
+- (id)UIDelegate;
+
+/*!
+ @method setResourceLoadDelegate:
+ @abstract Set the WebView's WebResourceLoadDelegate load delegate.
+ @param delegate The WebResourceLoadDelegate to set as the load delegate.
+*/
+- (void)setResourceLoadDelegate:(id)delegate;
+
+/*!
+ @method resourceLoadDelegate
+ @result Return the WebView's WebResourceLoadDelegate.
+*/
+- (id)resourceLoadDelegate;
+
+/*!
+ @method setDownloadDelegate:
+ @abstract Set the WebView's WebDownloadDelegate.
+ @discussion The download delegate is retained by WebDownload when any downloads are in progress.
+ @param delegate The WebDownloadDelegate to set as the download delegate.
+*/
+- (void)setDownloadDelegate:(id)delegate;
+
+/*!
+ @method downloadDelegate
+ @abstract Return the WebView's WebDownloadDelegate.
+ @result The WebView's WebDownloadDelegate.
+*/
+- (id)downloadDelegate;
+
+/*!
+ @method setFrameLoadDelegate:
+ @abstract Set the WebView's WebFrameLoadDelegate delegate.
+ @param delegate The WebFrameLoadDelegate to set as the delegate.
+*/
+- (void)setFrameLoadDelegate:(id)delegate;
+
+/*!
+ @method frameLoadDelegate
+ @abstract Return the WebView's WebFrameLoadDelegate delegate.
+ @result The WebView's WebFrameLoadDelegate delegate.
+*/
+- (id)frameLoadDelegate;
+
+/*!
+ @method setPolicyDelegate:
+ @abstract Set the WebView's WebPolicyDelegate delegate.
+ @param delegate The WebPolicyDelegate to set as the delegate.
+*/
+- (void)setPolicyDelegate:(id)delegate;
+
+/*!
+ @method policyDelegate
+ @abstract Return the WebView's WebPolicyDelegate.
+ @result The WebView's WebPolicyDelegate.
+*/
+- (id)policyDelegate;
+
+/*!
+ @method mainFrame
+ @abstract Return the top level frame.
+ @discussion Note that even document that are not framesets will have a
+ mainFrame.
+ @result The main frame.
+*/
+- (WebFrame *)mainFrame;
+
+/*!
+ @method selectedFrame
+ @abstract Return the frame that has the active selection.
+ @discussion Returns the frame that contains the first responder, if any. Otherwise returns the
+ frame that contains a non-zero-length selection, if any. Returns nil if no frame meets these criteria.
+ @result The selected frame.
+*/
+- (WebFrame *)selectedFrame;
+
+/*!
+ @method backForwardList
+ @result The backforward list for this webView.
+*/
+- (WebBackForwardList *)backForwardList;
+
+/*!
+ @method setMaintainsBackForwardList:
+ @abstract Enable or disable the use of a backforward list for this webView.
+ @param flag Turns use of the back forward list on or off
+*/
+- (void)setMaintainsBackForwardList:(BOOL)flag;
+
+/*!
+ @method goBack
+ @abstract Go back to the previous URL in the backforward list.
+ @result YES if able to go back in the backforward list, NO otherwise.
+*/
+- (BOOL)goBack;
+
+/*!
+ @method goForward
+ @abstract Go forward to the next URL in the backforward list.
+ @result YES if able to go forward in the backforward list, NO otherwise.
+*/
+- (BOOL)goForward;
+
+/*!
+ @method goToBackForwardItem:
+ @abstract Go back or forward to an item in the backforward list.
+ @result YES if able to go to the item, NO otherwise.
+*/
+- (BOOL)goToBackForwardItem:(WebHistoryItem *)item;
+
+/*!
+ @method setTextSizeMultiplier:
+ @abstract Change the size of the text rendering in views managed by this webView.
+ @param multiplier A fractional percentage value, 1.0 is 100%.
+*/
+- (void)setTextSizeMultiplier:(float)multiplier;
+
+/*!
+ @method textSizeMultiplier
+ @result The text size multipler.
+*/
+- (float)textSizeMultiplier;
+
+/*!
+ @method setApplicationNameForUserAgent:
+ @abstract Set the application name.
+ @discussion This name will be used in user-agent strings
+ that are chosen for best results in rendering web pages.
+ @param applicationName The application name
+*/
+- (void)setApplicationNameForUserAgent:(NSString *)applicationName;
+
+/*!
+ @method applicationNameForUserAgent
+ @result The name of the application as used in the user-agent string.
+*/
+- (NSString *)applicationNameForUserAgent;
+
+/*!
+ @method setCustomUserAgent:
+ @abstract Set the user agent.
+ @discussion Setting this means that the webView should use this user-agent string
+ instead of constructing a user-agent string for each URL. Setting it to nil
+ causes the webView to construct the user-agent string for each URL
+ for best results rendering web pages.
+ @param userAgentString The user agent description
+*/
+- (void)setCustomUserAgent:(NSString *)userAgentString;
+
+/*!
+ @method customUserAgent
+ @result The custom user-agent string or nil if no custom user-agent string has been set.
+*/
+- (NSString *)customUserAgent;
+
+/*!
+ @method userAgentForURL:
+ @abstract Get the appropriate user-agent string for a particular URL.
+ @param URL The URL.
+ @result The user-agent string for the supplied URL.
+*/
+- (NSString *)userAgentForURL:(NSURL *)URL;
+
+
+/*!
+ @method supportsTextEncoding
+ @abstract Find out if the current web page supports text encodings.
+ @result YES if the document view of the current web page can
+ support different text encodings.
+*/
+- (BOOL)supportsTextEncoding;
+
+/*!
+ @method setCustomTextEncodingName:
+ @discussion Make the page display with a different text encoding; stops any load in progress.
+ The text encoding passed in overrides the normal text encoding smarts including
+ what's specified in a web page's header or HTTP response.
+ The text encoding automatically goes back to the default when the top level frame
+ changes to a new location.
+ Setting the text encoding name to nil makes the webView use default encoding rules.
+ @param encoding The text encoding name to use to display a page or nil.
+*/
+- (void)setCustomTextEncodingName:(NSString *)encodingName;
+
+/*!
+ @method customTextEncodingName
+ @result The custom text encoding name or nil if no custom text encoding name has been set.
+*/
+- (NSString *)customTextEncodingName;
+
+/*!
+ @method setMediaStyle:
+ @discussion Set the media style for the WebView. The mediaStyle will override the normal value
+ of the CSS media property. Setting the value to nil will restore the normal value.
+ @param mediaStyle The value to use for the CSS media property.
+*/
+- (void)setMediaStyle:(NSString *)mediaStyle;
+
+/*!
+ @method mediaStyle
+ @result mediaStyle The value to use for the CSS media property, as set by setMediaStyle:. It
+ will be nil unless set by that method.
+*/
+- (NSString *)mediaStyle;
+
+/*!
+ @method stringByEvaluatingJavaScriptFromString:
+ @param script The text of the JavaScript.
+ @result The result of the script, converted to a string, or nil for failure.
+*/
+- (NSString *)stringByEvaluatingJavaScriptFromString:(NSString *)script;
+
+/*!
+ @method windowScriptObject
+ @discussion windowScriptObject return a WebScriptObject that represents the
+ window object from the script environment.
+ @result Returns the window object from the script environment.
+*/
+- (WebScriptObject *)windowScriptObject;
+
+/*!
+ @method setPreferences:
+ @param preferences The preferences to use for the webView.
+ @abstract Override the standard setting for the webView.
+*/
+- (void)setPreferences: (WebPreferences *)prefs;
+
+/*!
+ @method preferences
+ @result Returns the preferences used by this webView.
+ @discussion This method will return [WebPreferences standardPreferences] if no
+ other instance of WebPreferences has been set.
+*/
+- (WebPreferences *)preferences;
+
+/*!
+ @method setPreferencesIdentifier:
+ @param anIdentifier The string to use a prefix for storing values for this WebView in the user
+ defaults database.
+ @discussion If the WebPreferences for this WebView are stored in the user defaults database, the
+ string set in this method will be used a key prefix.
+*/
+- (void)setPreferencesIdentifier:(NSString *)anIdentifier;
+
+/*!
+ @method preferencesIdentifier
+ @result Returns the WebPreferences key prefix.
+*/
+- (NSString *)preferencesIdentifier;
+
+
+/*!
+ @method setHostWindow:
+ @param hostWindow The host window for the web view.
+ @discussion Parts of WebKit (such as plug-ins and JavaScript) depend on a window to function
+ properly. Set a host window so these parts continue to function even when the web view is
+ not in an actual window.
+*/
+- (void)setHostWindow:(NSWindow *)hostWindow;
+
+/*!
+ @method hostWindow
+ @result The host window for the web view.
+*/
+- (NSWindow *)hostWindow;
+
+/*!
+ @method searchFor:direction:caseSensitive:
+ @abstract Searches a document view for a string and highlights the string if it is found.
+ Starts the search from the current selection. Will search across all frames.
+ @param string The string to search for.
+ @param forward YES to search forward, NO to seach backwards.
+ @param caseFlag YES to for case-sensitive search, NO for case-insensitive search.
+ @result YES if found, NO if not found.
+*/
+- (BOOL)searchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag;
+
+/*!
+ @method registerViewClass:representationClass:forMIMEType:
+ @discussion Register classes that implement WebDocumentView and WebDocumentRepresentation respectively.
+ A document class may register for a primary MIME type by excluding
+ a subtype, i.e. "video/" will match the document class with
+ all video types. More specific matching takes precedence
+ over general matching.
+ @param viewClass The WebDocumentView class to use to render data for a given MIME type.
+ @param representationClass The WebDocumentRepresentation class to use to represent data of the given MIME type.
+ @param MIMEType The MIME type to represent with an object of the given class.
+*/
++ (void)registerViewClass:(Class)viewClass representationClass:(Class)representationClass forMIMEType:(NSString *)MIMEType;
+
+
+/*!
+ @method setGroupName:
+ @param groupName The name of the group for this WebView.
+ @discussion JavaScript may access named frames within the same group.
+*/
+- (void)setGroupName:(NSString *)groupName;
+
+/*!
+ @method groupName
+ @discussion The group name for this WebView.
+*/
+- (NSString *)groupName;
+
+/*!
+ @method estimatedProgress
+ @discussion An estimate of the percent complete for a document load. This
+ value will range from 0 to 1.0 and, once a load completes, will remain at 1.0
+ until a new load starts, at which point it will be reset to 0. The value is an
+ estimate based on the total number of bytes expected to be received
+ for a document, including all it's possible subresources. For more accurate progress
+ indication it is recommended that you implement a WebFrameLoadDelegate and a
+ WebResourceLoadDelegate.
+*/
+- (double)estimatedProgress;
+
+/*!
+ @method isLoading
+ @discussion Returns YES if there are any pending loads.
+*/
+- (BOOL)isLoading;
+
+/*!
+ @method elementAtPoint:
+ @param point A point in the coordinates of the WebView
+ @result An element dictionary describing the point
+*/
+- (NSDictionary *)elementAtPoint:(NSPoint)point;
+
+/*!
+ @method pasteboardTypesForSelection
+ @abstract Returns the pasteboard types that WebView can use for the current selection
+*/
+- (NSArray *)pasteboardTypesForSelection;
+
+/*!
+ @method writeSelectionWithPasteboardTypes:toPasteboard:
+ @abstract Writes the current selection to the pasteboard
+ @param types The types that WebView will write to the pasteboard
+ @param pasteboard The pasteboard to write to
+*/
+- (void)writeSelectionWithPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard;
+
+/*!
+ @method pasteboardTypesForElement:
+ @abstract Returns the pasteboard types that WebView can use for an element
+ @param element The element
+*/
+- (NSArray *)pasteboardTypesForElement:(NSDictionary *)element;
+
+/*!
+ @method writeElement:withPasteboardTypes:toPasteboard:
+ @abstract Writes an element to the pasteboard
+ @param element The element to write to the pasteboard
+ @param types The types that WebView will write to the pasteboard
+ @param pasteboard The pasteboard to write to
+*/
+- (void)writeElement:(NSDictionary *)element withPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard;
+
+/*!
+ @method moveDragCaretToPoint:
+ @param point A point in the coordinates of the WebView
+ @discussion This method moves the caret that shows where something being dragged will be dropped. It may cause the WebView to scroll
+ to make the new position of the drag caret visible.
+*/
+- (void)moveDragCaretToPoint:(NSPoint)point;
+
+/*!
+ @method removeDragCaret
+ @abstract Removes the drag caret from the WebView
+*/
+- (void)removeDragCaret;
+
+/*!
+ @method setDrawsBackground:
+ @param drawsBackround YES to cause the receiver to draw a default white background, NO otherwise.
+ @abstract Sets whether the receiver draws a default white background when the loaded page has no background specified.
+*/
+- (void)setDrawsBackground:(BOOL)drawsBackround;
+
+/*!
+ @method drawsBackground
+ @result Returns YES if the receiver draws a default white background, NO otherwise.
+*/
+- (BOOL)drawsBackground;
+
+/*!
+ @method setMainFrameURL:
+ @param URLString The URL to load in the mainFrame.
+*/
+- (void)setMainFrameURL:(NSString *)URLString;
+
+/*!
+ @method mainFrameURL
+ @result Returns the main frame's current URL.
+*/
+- (NSString *)mainFrameURL;
+
+/*!
+ @method mainFrameDocument
+ @result Returns the main frame's DOMDocument.
+*/
+- (DOMDocument *)mainFrameDocument;
+
+/*!
+ @method mainFrameTitle
+ @result Returns the main frame's title if any, otherwise an empty string.
+*/
+- (NSString *)mainFrameTitle;
+
+/*!
+ @method mainFrameIcon
+ @discussion The methods returns the site icon for the current page loaded in the mainFrame.
+ @result Returns the main frame's icon if any, otherwise nil.
+*/
+- (NSImage *)mainFrameIcon;
+
+@end
+
+
+@interface WebView (WebIBActions) <NSUserInterfaceValidations>
+- (IBAction)takeStringURLFrom:(id)sender;
+- (IBAction)stopLoading:(id)sender;
+- (IBAction)reload:(id)sender;
+- (BOOL)canGoBack;
+- (IBAction)goBack:(id)sender;
+- (BOOL)canGoForward;
+- (IBAction)goForward:(id)sender;
+- (BOOL)canMakeTextLarger;
+- (IBAction)makeTextLarger:(id)sender;
+- (BOOL)canMakeTextSmaller;
+- (IBAction)makeTextSmaller:(id)sender;
+- (BOOL)canMakeTextStandardSize;
+- (IBAction)makeTextStandardSize:(id)sender;
+- (IBAction)toggleContinuousSpellChecking:(id)sender;
+- (IBAction)toggleSmartInsertDelete:(id)sender;
+@end
+
+
+// WebView editing support
+
+extern NSString * const WebViewDidBeginEditingNotification;
+extern NSString * const WebViewDidChangeNotification;
+extern NSString * const WebViewDidEndEditingNotification;
+extern NSString * const WebViewDidChangeTypingStyleNotification;
+extern NSString * const WebViewDidChangeSelectionNotification;
+
+@interface WebView (WebViewCSS)
+- (DOMCSSStyleDeclaration *)computedStyleForElement:(DOMElement *)element pseudoElement:(NSString *)pseudoElement;
+@end
+
+@interface WebView (WebViewEditing)
+- (DOMRange *)editableDOMRangeForPoint:(NSPoint)point;
+- (void)setSelectedDOMRange:(DOMRange *)range affinity:(NSSelectionAffinity)selectionAffinity;
+- (DOMRange *)selectedDOMRange;
+- (NSSelectionAffinity)selectionAffinity;
+- (BOOL)maintainsInactiveSelection;
+- (void)setEditable:(BOOL)flag;
+- (BOOL)isEditable;
+- (void)setTypingStyle:(DOMCSSStyleDeclaration *)style;
+- (DOMCSSStyleDeclaration *)typingStyle;
+- (void)setSmartInsertDeleteEnabled:(BOOL)flag;
+- (BOOL)smartInsertDeleteEnabled;
+- (void)setContinuousSpellCheckingEnabled:(BOOL)flag;
+- (BOOL)isContinuousSpellCheckingEnabled;
+- (WebNSInteger)spellCheckerDocumentTag;
+- (NSUndoManager *)undoManager;
+- (void)setEditingDelegate:(id)delegate;
+- (id)editingDelegate;
+- (DOMCSSStyleDeclaration *)styleDeclarationWithText:(NSString *)text;
+@end
+
+@interface WebView (WebViewUndoableEditing)
+- (void)replaceSelectionWithNode:(DOMNode *)node;
+- (void)replaceSelectionWithText:(NSString *)text;
+- (void)replaceSelectionWithMarkupString:(NSString *)markupString;
+- (void)replaceSelectionWithArchive:(WebArchive *)archive;
+- (void)deleteSelection;
+- (void)applyStyle:(DOMCSSStyleDeclaration *)style;
+@end
+
+@interface WebView (WebViewEditingActions)
+
+- (void)copy:(id)sender;
+- (void)cut:(id)sender;
+- (void)paste:(id)sender;
+- (void)copyFont:(id)sender;
+- (void)pasteFont:(id)sender;
+- (void)delete:(id)sender;
+- (void)pasteAsPlainText:(id)sender;
+- (void)pasteAsRichText:(id)sender;
+
+- (void)changeFont:(id)sender;
+- (void)changeAttributes:(id)sender;
+- (void)changeDocumentBackgroundColor:(id)sender;
+- (void)changeColor:(id)sender;
+
+- (void)alignCenter:(id)sender;
+- (void)alignJustified:(id)sender;
+- (void)alignLeft:(id)sender;
+- (void)alignRight:(id)sender;
+
+- (void)checkSpelling:(id)sender;
+- (void)showGuessPanel:(id)sender;
+- (void)performFindPanelAction:(id)sender;
+
+- (void)startSpeaking:(id)sender;
+- (void)stopSpeaking:(id)sender;
+
+- (void)moveToBeginningOfSentence:(id)sender;
+- (void)moveToBeginningOfSentenceAndModifySelection:(id)sender;
+- (void)moveToEndOfSentence:(id)sender;
+- (void)moveToEndOfSentenceAndModifySelection:(id)sender;
+- (void)selectSentence:(id)sender;
+
+/*
+The following methods are declared in NSResponder.h.
+WebView overrides each method in this list, providing
+a custom implementation for each.
+
+- (void)capitalizeWord:(id)sender;
+- (void)centerSelectionInVisibleArea:(id)sender;
+- (void)changeCaseOfLetter:(id)sender;
+- (void)complete:(id)sender;
+- (void)deleteBackward:(id)sender;
+- (void)deleteBackwardByDecomposingPreviousCharacter:(id)sender;
+- (void)deleteForward:(id)sender;
+- (void)deleteToBeginningOfLine:(id)sender;
+- (void)deleteToBeginningOfParagraph:(id)sender;
+- (void)deleteToEndOfLine:(id)sender;
+- (void)deleteToEndOfParagraph:(id)sender;
+- (void)deleteWordBackward:(id)sender;
+- (void)deleteWordForward:(id)sender;
+- (void)indent:(id)sender;
+- (void)insertBacktab:(id)sender;
+- (void)insertNewline:(id)sender;
+- (void)insertParagraphSeparator:(id)sender;
+- (void)insertTab:(id)sender;
+- (void)lowercaseWord:(id)sender;
+- (void)moveBackward:(id)sender;
+- (void)moveBackwardAndModifySelection:(id)sender;
+- (void)moveDown:(id)sender;
+- (void)moveDownAndModifySelection:(id)sender;
+- (void)moveForward:(id)sender;
+- (void)moveForwardAndModifySelection:(id)sender;
+- (void)moveLeft:(id)sender;
+- (void)moveLeftAndModifySelection:(id)sender;
+- (void)moveRight:(id)sender;
+- (void)moveRightAndModifySelection:(id)sender;
+- (void)moveToBeginningOfDocument:(id)sender;
+- (void)moveToBeginningOfDocumentAndModifySelection:(id)sender;
+- (void)moveToBeginningOfLine:(id)sender;
+- (void)moveToBeginningOfLineAndModifySelection:(id)sender;
+- (void)moveToBeginningOfParagraph:(id)sender;
+- (void)moveToBeginningOfParagraphAndModifySelection:(id)sender;
+- (void)moveToEndOfDocument:(id)sender;
+- (void)moveToEndOfDocumentAndModifySelection:(id)sender;
+- (void)moveToEndOfLine:(id)sender;
+- (void)moveToEndOfLineAndModifySelection:(id)sender;
+- (void)moveToEndOfParagraph:(id)sender;
+- (void)moveToEndOfParagraphAndModifySelection:(id)sender;
+- (void)moveUp:(id)sender;
+- (void)moveUpAndModifySelection:(id)sender;
+- (void)moveWordBackward:(id)sender;
+- (void)moveWordBackwardAndModifySelection:(id)sender;
+- (void)moveWordForward:(id)sender;
+- (void)moveWordForwardAndModifySelection:(id)sender;
+- (void)moveWordLeft:(id)sender;
+- (void)moveWordLeftAndModifySelection:(id)sender;
+- (void)moveWordRight:(id)sender;
+- (void)moveWordRightAndModifySelection:(id)sender;
+- (void)pageDown:(id)sender;
+- (void)pageUp:(id)sender;
+- (void)scrollLineDown:(id)sender;
+- (void)scrollLineUp:(id)sender;
+- (void)scrollPageDown:(id)sender;
+- (void)scrollPageUp:(id)sender;
+- (void)selectAll:(id)sender;
+- (void)selectLine:(id)sender;
+- (void)selectParagraph:(id)sender;
+- (void)selectWord:(id)sender;
+- (void)uppercaseWord:(id)sender;
+*/
+
+@end
+
+#undef WebNSInteger
diff --git a/WebKit/mac/WebView/WebView.mm b/WebKit/mac/WebView/WebView.mm
new file mode 100644
index 0000000..d259294
--- /dev/null
+++ b/WebKit/mac/WebView/WebView.mm
@@ -0,0 +1,4626 @@
+/*
+ * Copyright (C) 2005, 2006, 2007, 2008 Apple Inc. All rights reserved.
+ * Copyright (C) 2006 David Smith (catfish.man@gmail.com)
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import "WebViewInternal.h"
+
+#import "DOMRangeInternal.h"
+#import "WebBackForwardList.h"
+#import "WebBackForwardListInternal.h"
+#import "WebBaseNetscapePluginView.h"
+#import "WebChromeClient.h"
+#import "WebContextMenuClient.h"
+#import "WebDOMOperationsPrivate.h"
+#import "WebDatabaseManagerInternal.h"
+#import "WebDatabaseManagerPrivate.h"
+#import "WebDataSourceInternal.h"
+#import "WebDefaultEditingDelegate.h"
+#import "WebDefaultPolicyDelegate.h"
+#import "WebDefaultScriptDebugDelegate.h"
+#import "WebDefaultUIDelegate.h"
+#import "WebDocument.h"
+#import "WebDocumentInternal.h"
+#import "WebDownload.h"
+#import "WebDownloadInternal.h"
+#import "WebDragClient.h"
+#import "WebDynamicScrollBarsView.h"
+#import "WebEditingDelegate.h"
+#import "WebEditorClient.h"
+#import "WebFormDelegatePrivate.h"
+#import "WebFrameBridge.h"
+#import "WebFrameInternal.h"
+#import "WebFrameViewInternal.h"
+#import "WebHTMLRepresentation.h"
+#import "WebHTMLViewInternal.h"
+#import "WebHistoryItemInternal.h"
+#import "WebIconDatabase.h"
+#import "WebIconDatabaseInternal.h"
+#import "WebInspector.h"
+#import "WebInspectorClient.h"
+#import "WebKitErrors.h"
+#import "WebKitLogging.h"
+#import "WebKitNSStringExtras.h"
+#import "WebKitStatisticsPrivate.h"
+#import "WebKitSystemBits.h"
+#import "WebKitVersionChecks.h"
+#import "WebLocalizableStrings.h"
+#import "WebNSDataExtras.h"
+#import "WebNSDataExtrasPrivate.h"
+#import "WebNSDictionaryExtras.h"
+#import "WebNSEventExtras.h"
+#import "WebNSObjectExtras.h"
+#import "WebNSPasteboardExtras.h"
+#import "WebNSPrintOperationExtras.h"
+#import "WebNSURLExtras.h"
+#import "WebNSURLRequestExtras.h"
+#import "WebNSUserDefaultsExtras.h"
+#import "WebNSViewExtras.h"
+#import "WebPanelAuthenticationHandler.h"
+#import "WebPasteboardHelper.h"
+#import "WebPDFView.h"
+#import "WebPluginDatabase.h"
+#import "WebPolicyDelegate.h"
+#import "WebPreferenceKeysPrivate.h"
+#import "WebPreferencesPrivate.h"
+#import "WebScriptDebugDelegatePrivate.h"
+#import "WebScriptDebugServerPrivate.h"
+#import "WebUIDelegate.h"
+#import "WebUIDelegatePrivate.h"
+#import <CoreFoundation/CFSet.h>
+#import <Foundation/NSURLConnection.h>
+#import <JavaScriptCore/Assertions.h>
+#import <WebCore/Cache.h>
+#import <WebCore/ColorMac.h>
+#import <WebCore/Document.h>
+#import <WebCore/DocumentLoader.h>
+#import <WebCore/DragController.h>
+#import <WebCore/DragData.h>
+#import <WebCore/Editor.h>
+#import <WebCore/ExceptionHandlers.h>
+#import <WebCore/Frame.h>
+#import <WebCore/FrameLoader.h>
+#import <WebCore/FrameTree.h>
+#import <WebCore/HTMLNames.h>
+#import <WebCore/HistoryItem.h>
+#import <WebCore/Logging.h>
+#import <WebCore/MIMETypeRegistry.h>
+#import <WebCore/Page.h>
+#import <WebCore/PageCache.h>
+#import <WebCore/PlatformMouseEvent.h>
+#import <WebCore/ProgressTracker.h>
+#import <WebCore/SelectionController.h>
+#import <WebCore/Settings.h>
+#import <WebCore/TextResourceDecoder.h>
+#import <WebCore/WebCoreFrameBridge.h>
+#import <WebCore/WebCoreObjCExtras.h>
+#import <WebCore/WebCoreTextRenderer.h>
+#import <WebCore/WebCoreView.h>
+#import <WebKit/DOM.h>
+#import <WebKit/DOMExtensions.h>
+#import <WebKit/DOMPrivate.h>
+#import <WebKit/WebDashboardRegion.h>
+#import <WebKitSystemInterface.h>
+#import <mach-o/dyld.h>
+#import <objc/objc-auto.h>
+#import <objc/objc-runtime.h>
+#import <wtf/RefPtr.h>
+#import <wtf/HashTraits.h>
+
+using namespace WebCore;
+
+#if defined(__ppc__) || defined(__ppc64__)
+#define PROCESSOR "PPC"
+#elif defined(__i386__) || defined(__x86_64__)
+#define PROCESSOR "Intel"
+#else
+#error Unknown architecture
+#endif
+
+#define FOR_EACH_RESPONDER_SELECTOR(macro) \
+macro(alignCenter) \
+macro(alignJustified) \
+macro(alignLeft) \
+macro(alignRight) \
+macro(capitalizeWord) \
+macro(centerSelectionInVisibleArea) \
+macro(changeAttributes) \
+macro(changeBaseWritingDirection) \
+macro(changeBaseWritingDirectionToLTR) \
+macro(changeBaseWritingDirectionToRTL) \
+macro(changeColor) \
+macro(changeDocumentBackgroundColor) \
+macro(changeFont) \
+macro(changeSpelling) \
+macro(checkSpelling) \
+macro(complete) \
+macro(copy) \
+macro(copyFont) \
+macro(cut) \
+macro(delete) \
+macro(deleteBackward) \
+macro(deleteBackwardByDecomposingPreviousCharacter) \
+macro(deleteForward) \
+macro(deleteToBeginningOfLine) \
+macro(deleteToBeginningOfParagraph) \
+macro(deleteToEndOfLine) \
+macro(deleteToEndOfParagraph) \
+macro(deleteToMark) \
+macro(deleteWordBackward) \
+macro(deleteWordForward) \
+macro(ignoreSpelling) \
+macro(indent) \
+macro(insertBacktab) \
+macro(insertLineBreak) \
+macro(insertNewline) \
+macro(insertNewlineIgnoringFieldEditor) \
+macro(insertParagraphSeparator) \
+macro(insertTab) \
+macro(insertTabIgnoringFieldEditor) \
+macro(lowercaseWord) \
+macro(moveBackward) \
+macro(moveBackwardAndModifySelection) \
+macro(moveDown) \
+macro(moveDownAndModifySelection) \
+macro(moveForward) \
+macro(moveForwardAndModifySelection) \
+macro(moveLeft) \
+macro(moveLeftAndModifySelection) \
+macro(moveParagraphBackwardAndModifySelection) \
+macro(moveParagraphForwardAndModifySelection) \
+macro(moveRight) \
+macro(moveRightAndModifySelection) \
+macro(moveToBeginningOfDocument) \
+macro(moveToBeginningOfDocumentAndModifySelection) \
+macro(moveToBeginningOfLine) \
+macro(moveToBeginningOfLineAndModifySelection) \
+macro(moveToBeginningOfParagraph) \
+macro(moveToBeginningOfParagraphAndModifySelection) \
+macro(moveToBeginningOfSentence) \
+macro(moveToBeginningOfSentenceAndModifySelection) \
+macro(moveToEndOfDocument) \
+macro(moveToEndOfDocumentAndModifySelection) \
+macro(moveToEndOfLine) \
+macro(moveToEndOfLineAndModifySelection) \
+macro(moveToEndOfParagraph) \
+macro(moveToEndOfParagraphAndModifySelection) \
+macro(moveToEndOfSentence) \
+macro(moveToEndOfSentenceAndModifySelection) \
+macro(moveUp) \
+macro(moveUpAndModifySelection) \
+macro(moveWordBackward) \
+macro(moveWordBackwardAndModifySelection) \
+macro(moveWordForward) \
+macro(moveWordForwardAndModifySelection) \
+macro(moveWordLeft) \
+macro(moveWordLeftAndModifySelection) \
+macro(moveWordRight) \
+macro(moveWordRightAndModifySelection) \
+macro(outdent) \
+macro(pageDown) \
+macro(pageDownAndModifySelection) \
+macro(pageUp) \
+macro(pageUpAndModifySelection) \
+macro(paste) \
+macro(pasteAsPlainText) \
+macro(pasteAsRichText) \
+macro(pasteFont) \
+macro(performFindPanelAction) \
+macro(scrollLineDown) \
+macro(scrollLineUp) \
+macro(scrollPageDown) \
+macro(scrollPageUp) \
+macro(scrollToBeginningOfDocument) \
+macro(scrollToEndOfDocument) \
+macro(selectAll) \
+macro(selectLine) \
+macro(selectParagraph) \
+macro(selectSentence) \
+macro(selectToMark) \
+macro(selectWord) \
+macro(setMark) \
+macro(showGuessPanel) \
+macro(startSpeaking) \
+macro(stopSpeaking) \
+macro(subscript) \
+macro(superscript) \
+macro(swapWithMark) \
+macro(takeFindStringFromSelection) \
+macro(toggleBaseWritingDirection) \
+macro(transpose) \
+macro(underline) \
+macro(unscript) \
+macro(uppercaseWord) \
+macro(yank) \
+macro(yankAndSelect) \
+
+#define WebKitOriginalTopPrintingMarginKey @"WebKitOriginalTopMargin"
+#define WebKitOriginalBottomPrintingMarginKey @"WebKitOriginalBottomMargin"
+
+static BOOL s_didSetCacheModel;
+static WebCacheModel s_cacheModel = WebCacheModelDocumentViewer;
+
+static BOOL applicationIsTerminating;
+static int pluginDatabaseClientCount = 0;
+
+@interface NSSpellChecker (AppKitSecretsIKnow)
+- (void)_preflightChosenSpellServer;
+@end
+
+@interface NSView (AppKitSecretsIKnow)
+- (NSView *)_hitTest:(NSPoint *)aPoint dragTypes:(NSSet *)types;
+- (void)_autoscrollForDraggingInfo:(id)dragInfo timeDelta:(NSTimeInterval)repeatDelta;
+- (BOOL)_shouldAutoscrollForDraggingInfo:(id)dragInfo;
+@end
+
+@interface NSWindow (AppKitSecretsIKnow)
+- (id)_oldFirstResponderBeforeBecoming;
+@end
+
+@interface NSObject (ValidateWithoutDelegate)
+- (BOOL)validateUserInterfaceItemWithoutDelegate:(id <NSValidatedUserInterfaceItem>)item;
+@end
+
+@interface _WebSafeForwarder : NSObject
+{
+ id target; // Non-retained. Don't retain delegates.
+ id defaultTarget;
+ BOOL catchExceptions;
+}
+- (id)initWithTarget:(id)target defaultTarget:(id)defaultTarget catchExceptions:(BOOL)catchExceptions;
+@end
+
+@interface WebViewPrivate : NSObject
+{
+@public
+ Page* page;
+
+ id UIDelegate;
+ id UIDelegateForwarder;
+ id resourceProgressDelegate;
+ id downloadDelegate;
+ id policyDelegate;
+ id policyDelegateForwarder;
+ id frameLoadDelegate;
+ id frameLoadDelegateForwarder;
+ id <WebFormDelegate> formDelegate;
+ id editingDelegate;
+ id editingDelegateForwarder;
+ id scriptDebugDelegate;
+ id scriptDebugDelegateForwarder;
+
+ WebInspector *inspector;
+
+ BOOL allowsUndo;
+
+ float textSizeMultiplier;
+
+ NSString *applicationNameForUserAgent;
+ String* userAgent;
+ BOOL userAgentOverridden;
+
+ WebPreferences *preferences;
+ BOOL useSiteSpecificSpoofing;
+
+ NSWindow *hostWindow;
+
+ int programmaticFocusCount;
+
+ WebResourceDelegateImplementationCache resourceLoadDelegateImplementations;
+ WebFrameLoadDelegateImplementationCache frameLoadDelegateImplementations;
+
+ void *observationInfo;
+
+ BOOL closed;
+ BOOL shouldCloseWithWindow;
+ BOOL mainFrameDocumentReady;
+ BOOL drawsBackground;
+ BOOL editable;
+ BOOL tabKeyCyclesThroughElementsChanged;
+ BOOL becomingFirstResponder;
+ BOOL becomingFirstResponderFromOutside;
+ BOOL hoverFeedbackSuspended;
+ BOOL usesPageCache;
+ BOOL catchesDelegateExceptions;
+
+ NSColor *backgroundColor;
+
+ NSString *mediaStyle;
+
+ BOOL hasSpellCheckerDocumentTag;
+ NSInteger spellCheckerDocumentTag;
+
+ BOOL smartInsertDeleteEnabled;
+
+ BOOL dashboardBehaviorAlwaysSendMouseEventsToAllWindows;
+ BOOL dashboardBehaviorAlwaysSendActiveNullEventsToPlugIns;
+ BOOL dashboardBehaviorAlwaysAcceptsFirstMouse;
+ BOOL dashboardBehaviorAllowWheelScrolling;
+
+ // WebKit has both a global plug-in database and a separate, per WebView plug-in database. Dashboard uses the per WebView database.
+ WebPluginDatabase *pluginDatabase;
+
+ HashMap<unsigned long, RetainPtr<id> >* identifierMap;
+}
+@end
+
+@interface WebView (WebFileInternal)
+- (WebFrame *)_selectedOrMainFrame;
+- (WebFrameBridge *)_bridgeForSelectedOrMainFrame;
+- (BOOL)_isLoading;
+- (WebFrameView *)_frameViewAtWindowPoint:(NSPoint)point;
+- (WebFrame *)_focusedFrame;
++ (void)_preflightSpellChecker;
+- (BOOL)_continuousCheckingAllowed;
+- (NSResponder *)_responderForResponderOperations;
+- (BOOL)_performTextSizingSelector:(SEL)sel withObject:(id)arg onTrackingDocs:(BOOL)doTrackingViews selForNonTrackingDocs:(SEL)testSel newScaleFactor:(float)newScaleFactor;
+- (void)_notifyTextSizeMultiplierChanged;
+@end
+
+@interface WebView (WebCallDelegateFunctions)
+@end
+
+NSString *WebElementDOMNodeKey = @"WebElementDOMNode";
+NSString *WebElementFrameKey = @"WebElementFrame";
+NSString *WebElementImageKey = @"WebElementImage";
+NSString *WebElementImageAltStringKey = @"WebElementImageAltString";
+NSString *WebElementImageRectKey = @"WebElementImageRect";
+NSString *WebElementImageURLKey = @"WebElementImageURL";
+NSString *WebElementIsSelectedKey = @"WebElementIsSelected";
+NSString *WebElementLinkLabelKey = @"WebElementLinkLabel";
+NSString *WebElementLinkTargetFrameKey = @"WebElementTargetFrame";
+NSString *WebElementLinkTitleKey = @"WebElementLinkTitle";
+NSString *WebElementLinkURLKey = @"WebElementLinkURL";
+NSString *WebElementSpellingToolTipKey = @"WebElementSpellingToolTip";
+NSString *WebElementTitleKey = @"WebElementTitle";
+NSString *WebElementLinkIsLiveKey = @"WebElementLinkIsLive";
+NSString *WebElementIsContentEditableKey = @"WebElementIsContentEditableKey";
+
+NSString *WebViewProgressStartedNotification = @"WebProgressStartedNotification";
+NSString *WebViewProgressEstimateChangedNotification = @"WebProgressEstimateChangedNotification";
+NSString *WebViewProgressFinishedNotification = @"WebProgressFinishedNotification";
+
+NSString * const WebViewDidBeginEditingNotification = @"WebViewDidBeginEditingNotification";
+NSString * const WebViewDidChangeNotification = @"WebViewDidChangeNotification";
+NSString * const WebViewDidEndEditingNotification = @"WebViewDidEndEditingNotification";
+NSString * const WebViewDidChangeTypingStyleNotification = @"WebViewDidChangeTypingStyleNotification";
+NSString * const WebViewDidChangeSelectionNotification = @"WebViewDidChangeSelectionNotification";
+
+enum { WebViewVersion = 4 };
+
+#define timedLayoutSize 4096
+
+static NSMutableSet *schemesWithRepresentationsSet;
+
+NSString *_WebCanGoBackKey = @"canGoBack";
+NSString *_WebCanGoForwardKey = @"canGoForward";
+NSString *_WebEstimatedProgressKey = @"estimatedProgress";
+NSString *_WebIsLoadingKey = @"isLoading";
+NSString *_WebMainFrameIconKey = @"mainFrameIcon";
+NSString *_WebMainFrameTitleKey = @"mainFrameTitle";
+NSString *_WebMainFrameURLKey = @"mainFrameURL";
+NSString *_WebMainFrameDocumentKey = @"mainFrameDocument";
+
+@interface WebProgressItem : NSObject
+{
+@public
+ long long bytesReceived;
+ long long estimatedLength;
+}
+@end
+
+@implementation WebProgressItem
+@end
+
+static BOOL continuousSpellCheckingEnabled;
+#ifndef BUILDING_ON_TIGER
+static BOOL grammarCheckingEnabled;
+#endif
+
+@implementation WebViewPrivate
+
+#ifndef BUILDING_ON_TIGER
++ (void)initialize
+{
+ WebCoreObjCFinalizeOnMainThread(self);
+}
+#endif
+
+- init
+{
+ self = [super init];
+ if (!self)
+ return nil;
+ allowsUndo = YES;
+ textSizeMultiplier = 1;
+ dashboardBehaviorAllowWheelScrolling = YES;
+ shouldCloseWithWindow = objc_collecting_enabled();
+ continuousSpellCheckingEnabled = [[NSUserDefaults standardUserDefaults] boolForKey:WebContinuousSpellCheckingEnabled];
+
+#ifndef BUILDING_ON_TIGER
+ grammarCheckingEnabled = [[NSUserDefaults standardUserDefaults] boolForKey:WebGrammarCheckingEnabled];
+#endif
+ userAgent = new String;
+
+ usesPageCache = YES;
+
+ identifierMap = new HashMap<unsigned long, RetainPtr<id> >();
+ pluginDatabaseClientCount++;
+
+ return self;
+}
+
+- (void)dealloc
+{
+ ASSERT(!page);
+ ASSERT(!preferences);
+
+ delete userAgent;
+ delete identifierMap;
+
+ [applicationNameForUserAgent release];
+ [backgroundColor release];
+
+ [inspector release];
+ [hostWindow release];
+
+ [policyDelegateForwarder release];
+ [UIDelegateForwarder release];
+ [frameLoadDelegateForwarder release];
+ [editingDelegateForwarder release];
+ [scriptDebugDelegateForwarder release];
+
+ [mediaStyle release];
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT_MAIN_THREAD();
+
+ delete userAgent;
+ delete identifierMap;
+
+ [super finalize];
+}
+
+@end
+
+@implementation WebView (AllWebViews)
+
+static CFSetCallBacks NonRetainingSetCallbacks = {
+ 0,
+ NULL,
+ NULL,
+ CFCopyDescription,
+ CFEqual,
+ CFHash
+};
+
+static CFMutableSetRef allWebViewsSet;
+
++ (void)_makeAllWebViewsPerformSelector:(SEL)selector
+{
+ if (!allWebViewsSet)
+ return;
+
+ [(NSMutableSet *)allWebViewsSet makeObjectsPerformSelector:selector];
+}
+
+- (void)_removeFromAllWebViewsSet
+{
+ if (allWebViewsSet)
+ CFSetRemoveValue(allWebViewsSet, self);
+}
+
+- (void)_addToAllWebViewsSet
+{
+ if (!allWebViewsSet)
+ allWebViewsSet = CFSetCreateMutable(NULL, 0, &NonRetainingSetCallbacks);
+
+ CFSetSetValue(allWebViewsSet, self);
+}
+
+@end
+
+@implementation WebView (WebPrivate)
+
+#ifdef DEBUG_WIDGET_DRAWING
+static bool debugWidget = true;
+- (void)drawRect:(NSRect)rect
+{
+ [[NSColor blueColor] set];
+ NSRectFill (rect);
+
+ NSRect htmlViewRect = [[[[self mainFrame] frameView] documentView] frame];
+
+ if (debugWidget) {
+ while (debugWidget) {
+ sleep (1);
+ }
+ }
+
+ NSLog (@"%s: rect: (%0.f,%0.f) %0.f %0.f, htmlViewRect: (%0.f,%0.f) %0.f %0.f\n",
+ __PRETTY_FUNCTION__, rect.origin.x, rect.origin.y, rect.size.width, rect.size.height,
+ htmlViewRect.origin.x, htmlViewRect.origin.y, htmlViewRect.size.width, htmlViewRect.size.height
+ );
+
+ [super drawRect:rect];
+}
+#endif
+
++ (BOOL)_scriptDebuggerEnabled
+{
+#ifdef NDEBUG
+ return [[NSUserDefaults standardUserDefaults] boolForKey:@"WebKitScriptDebuggerEnabled"];
+#else
+ return YES; // always enable in debug builds
+#endif
+}
+
++ (NSArray *)_supportedMIMETypes
+{
+ // Load the plug-in DB allowing plug-ins to install types.
+ [WebPluginDatabase sharedDatabase];
+ return [[WebFrameView _viewTypesAllowImageTypeOmission:NO] allKeys];
+}
+
++ (NSArray *)_supportedFileExtensions
+{
+ NSMutableSet *extensions = [[NSMutableSet alloc] init];
+ NSArray *MIMETypes = [self _supportedMIMETypes];
+ NSEnumerator *enumerator = [MIMETypes objectEnumerator];
+ NSString *MIMEType;
+ while ((MIMEType = [enumerator nextObject]) != nil) {
+ NSArray *extensionsForType = WKGetExtensionsForMIMEType(MIMEType);
+ if (extensionsForType) {
+ [extensions addObjectsFromArray:extensionsForType];
+ }
+ }
+ NSArray *uniqueExtensions = [extensions allObjects];
+ [extensions release];
+ return uniqueExtensions;
+}
+
++ (BOOL)_viewClass:(Class *)vClass andRepresentationClass:(Class *)rClass forMIMEType:(NSString *)MIMEType;
+{
+ MIMEType = [MIMEType lowercaseString];
+ Class viewClass = [[WebFrameView _viewTypesAllowImageTypeOmission:YES] _webkit_objectForMIMEType:MIMEType];
+ Class repClass = [[WebDataSource _repTypesAllowImageTypeOmission:YES] _webkit_objectForMIMEType:MIMEType];
+
+ if (!viewClass || !repClass || [[WebPDFView supportedMIMETypes] containsObject:MIMEType]) {
+ // Our optimization to avoid loading the plug-in DB and image types for the HTML case failed.
+ // Load the plug-in DB allowing plug-ins to install types.
+ [WebPluginDatabase sharedDatabase];
+
+ // Load the image types and get the view class and rep class. This should be the fullest picture of all handled types.
+ viewClass = [[WebFrameView _viewTypesAllowImageTypeOmission:NO] _webkit_objectForMIMEType:MIMEType];
+ repClass = [[WebDataSource _repTypesAllowImageTypeOmission:NO] _webkit_objectForMIMEType:MIMEType];
+ }
+
+ if (viewClass && repClass) {
+ // Special-case WebHTMLView for text types that shouldn't be shown.
+ if (viewClass == [WebHTMLView class] &&
+ repClass == [WebHTMLRepresentation class] &&
+ [[WebHTMLView unsupportedTextMIMETypes] containsObject:MIMEType]) {
+ return NO;
+ }
+ if (vClass)
+ *vClass = viewClass;
+ if (rClass)
+ *rClass = repClass;
+ return YES;
+ }
+
+ return NO;
+}
+
+- (BOOL)_viewClass:(Class *)vClass andRepresentationClass:(Class *)rClass forMIMEType:(NSString *)MIMEType;
+{
+ if ([[self class] _viewClass:vClass andRepresentationClass:rClass forMIMEType:MIMEType])
+ return YES;
+
+ if (_private->pluginDatabase) {
+ WebBasePluginPackage *pluginPackage = [_private->pluginDatabase pluginForMIMEType:MIMEType];
+ if (pluginPackage) {
+ if (vClass)
+ *vClass = [WebHTMLView class];
+ if (rClass)
+ *rClass = [WebHTMLRepresentation class];
+ return YES;
+ }
+ }
+
+ return NO;
+}
+
++ (void)_setAlwaysUseATSU:(BOOL)f
+{
+ WebCoreSetAlwaysUseATSU(f);
+}
+
++ (BOOL)canShowFile:(NSString *)path
+{
+ return [[self class] canShowMIMEType:[WebView _MIMETypeForFile:path]];
+}
+
++ (NSString *)suggestedFileExtensionForMIMEType:(NSString *)type
+{
+ return WKGetPreferredExtensionForMIMEType(type);
+}
+
+- (BOOL)_isClosed
+{
+ if (!_private || _private->closed)
+ return YES;
+ return NO;
+}
+
+- (void)_close
+{
+ if (!_private || _private->closed)
+ return;
+
+ FrameLoader* mainFrameLoader = [[self mainFrame] _frameLoader];
+ if (mainFrameLoader)
+ mainFrameLoader->detachFromParent();
+
+ [self _removeFromAllWebViewsSet];
+ [self setGroupName:nil];
+ [self setHostWindow:nil];
+
+ [self setDownloadDelegate:nil];
+ [self setEditingDelegate:nil];
+ [self setFrameLoadDelegate:nil];
+ [self setPolicyDelegate:nil];
+ [self setResourceLoadDelegate:nil];
+ [self setScriptDebugDelegate:nil];
+ [self setUIDelegate:nil];
+
+ [_private->inspector webViewClosed];
+
+ // setHostWindow:nil must be called before this value is set (see 5408186)
+ _private->closed = YES;
+
+ // To avoid leaks, call removeDragCaret in case it wasn't called after moveDragCaretToPoint.
+ [self removeDragCaret];
+
+ // Deleteing the WebCore::Page will clear the page cache so we call destroy on
+ // all the plug-ins in the page cache to break any retain cycles.
+ // See comment in HistoryItem::releaseAllPendingPageCaches() for more information.
+ delete _private->page;
+ _private->page = 0;
+
+ if (_private->hasSpellCheckerDocumentTag) {
+ [[NSSpellChecker sharedSpellChecker] closeSpellDocumentWithTag:_private->spellCheckerDocumentTag];
+ _private->hasSpellCheckerDocumentTag = NO;
+ }
+
+ [[NSNotificationCenter defaultCenter] removeObserver:self];
+
+ [WebPreferences _removeReferenceForIdentifier:[self preferencesIdentifier]];
+
+ WebPreferences *preferences = _private->preferences;
+ _private->preferences = nil;
+ [preferences didRemoveFromWebView];
+ [preferences release];
+
+ pluginDatabaseClientCount--;
+
+ // Make sure to close both sets of plug-ins databases because plug-ins need an opportunity to clean up files, etc.
+
+ // Unload the WebView local plug-in database.
+ if (_private->pluginDatabase) {
+ [_private->pluginDatabase close];
+ [_private->pluginDatabase release];
+ _private->pluginDatabase = nil;
+ }
+
+ // Keep the global plug-in database active until the app terminates to avoid having to reload plug-in bundles.
+ if (!pluginDatabaseClientCount && applicationIsTerminating)
+ [WebPluginDatabase closeSharedDatabase];
+}
+
++ (NSString *)_MIMETypeForFile:(NSString *)path
+{
+ NSString *extension = [path pathExtension];
+ NSString *MIMEType = nil;
+
+ // Get the MIME type from the extension.
+ if ([extension length] != 0) {
+ MIMEType = WKGetMIMETypeForExtension(extension);
+ }
+
+ // If we can't get a known MIME type from the extension, sniff.
+ if ([MIMEType length] == 0 || [MIMEType isEqualToString:@"application/octet-stream"]) {
+ NSFileHandle *handle = [NSFileHandle fileHandleForReadingAtPath:path];
+ NSData *data = [handle readDataOfLength:WEB_GUESS_MIME_TYPE_PEEK_LENGTH];
+ [handle closeFile];
+ if ([data length] != 0) {
+ MIMEType = [data _webkit_guessedMIMEType];
+ }
+ if ([MIMEType length] == 0) {
+ MIMEType = @"application/octet-stream";
+ }
+ }
+
+ return MIMEType;
+}
+
+- (WebDownload *)_downloadURL:(NSURL *)URL
+{
+ ASSERT(URL);
+
+ NSURLRequest *request = [[NSURLRequest alloc] initWithURL:URL];
+ WebDownload *download = [WebDownload _downloadWithRequest:request
+ delegate:_private->downloadDelegate
+ directory:nil];
+ [request release];
+
+ return download;
+}
+
+- (WebView *)_openNewWindowWithRequest:(NSURLRequest *)request
+{
+ NSDictionary *features = [[NSDictionary alloc] init];
+ WebView *newWindowWebView = [[self _UIDelegateForwarder] webView:self
+ createWebViewWithRequest:nil
+ windowFeatures:features];
+ [features release];
+ if (!newWindowWebView)
+ return nil;
+
+ CallUIDelegate(newWindowWebView, @selector(webViewShow:));
+ return newWindowWebView;
+}
+
+- (WebInspector *)inspector
+{
+ if (!_private->inspector)
+ _private->inspector = [[WebInspector alloc] initWithWebView:self];
+ return _private->inspector;
+}
+
+- (WebCore::Page*)page
+{
+ return _private->page;
+}
+
+- (NSMenu *)_menuForElement:(NSDictionary *)element defaultItems:(NSArray *)items
+{
+ NSArray *defaultMenuItems = [[WebDefaultUIDelegate sharedUIDelegate] webView:self contextMenuItemsForElement:element defaultMenuItems:items];
+
+ NSArray *menuItems = CallUIDelegate(self, @selector(webView:contextMenuItemsForElement:defaultMenuItems:), element, defaultMenuItems);
+ if (!menuItems)
+ return nil;
+
+ unsigned count = [menuItems count];
+ if (!count)
+ return nil;
+
+ NSMenu *menu = [[NSMenu alloc] init];
+ for (unsigned i = 0; i < count; i++)
+ [menu addItem:[menuItems objectAtIndex:i]];
+
+ return [menu autorelease];
+}
+
+- (void)_mouseDidMoveOverElement:(NSDictionary *)dictionary modifierFlags:(NSUInteger)modifierFlags
+{
+ // We originally intended to call this delegate method sometimes with a nil dictionary, but due to
+ // a bug dating back to WebKit 1.0 this delegate was never called with nil! Unfortunately we can't
+ // start calling this with nil since it will break Adobe Help Viewer, and possibly other clients.
+ if (!dictionary)
+ return;
+ CallUIDelegate(self, @selector(webView:mouseDidMoveOverElement:modifierFlags:), dictionary, modifierFlags);
+}
+
+- (void)_loadBackForwardListFromOtherView:(WebView *)otherView
+{
+ if (!_private->page)
+ return;
+
+ if (!otherView->_private->page)
+ return;
+
+ // It turns out the right combination of behavior is done with the back/forward load
+ // type. (See behavior matrix at the top of WebFramePrivate.) So we copy all the items
+ // in the back forward list, and go to the current one.
+
+ BackForwardList* backForwardList = _private->page->backForwardList();
+ ASSERT(!backForwardList->currentItem()); // destination list should be empty
+
+ BackForwardList* otherBackForwardList = otherView->_private->page->backForwardList();
+ if (!otherBackForwardList->currentItem())
+ return; // empty back forward list, bail
+
+ HistoryItem* newItemToGoTo = 0;
+
+ int lastItemIndex = otherBackForwardList->forwardListCount();
+ for (int i = -otherBackForwardList->backListCount(); i <= lastItemIndex; ++i) {
+ if (i == 0) {
+ // If this item is showing , save away its current scroll and form state,
+ // since that might have changed since loading and it is normally not saved
+ // until we leave that page.
+ otherView->_private->page->mainFrame()->loader()->saveDocumentAndScrollState();
+ }
+ RefPtr<HistoryItem> newItem = otherBackForwardList->itemAtIndex(i)->copy();
+ if (i == 0)
+ newItemToGoTo = newItem.get();
+ backForwardList->addItem(newItem.release());
+ }
+
+ ASSERT(newItemToGoTo);
+ _private->page->goToItem(newItemToGoTo, FrameLoadTypeIndexedBackForward);
+}
+
+- (void)_setFormDelegate: (id<WebFormDelegate>)delegate
+{
+ _private->formDelegate = delegate;
+}
+
+- (id<WebFormDelegate>)_formDelegate
+{
+ return _private->formDelegate;
+}
+
+- (BOOL)_needsAdobeFrameReloadingQuirk
+{
+ static BOOL checked = NO;
+ static BOOL needsQuirk = NO;
+
+ if (checked)
+ return needsQuirk;
+
+ needsQuirk = WKAppVersionCheckLessThan(@"com.adobe.Acrobat", -1, 9.0)
+ || WKAppVersionCheckLessThan(@"com.adobe.Acrobat.Pro", -1, 9.0)
+ || WKAppVersionCheckLessThan(@"com.adobe.Reader", -1, 9.0)
+ || WKAppVersionCheckLessThan(@"com.adobe.distiller", -1, 9.0)
+ || WKAppVersionCheckLessThan(@"com.adobe.Contribute", -1, 4.2)
+ || WKAppVersionCheckLessThan(@"com.adobe.dreamweaver-9.0", -1, 9.1)
+ || WKAppVersionCheckLessThan(@"com.macromedia.fireworks", -1, 9.1)
+ || WKAppVersionCheckLessThan(@"com.adobe.InCopy", -1, 5.1)
+ || WKAppVersionCheckLessThan(@"com.adobe.InDesign", -1, 5.1)
+ || WKAppVersionCheckLessThan(@"com.adobe.Soundbooth", -1, 2);
+ checked = YES;
+
+ return needsQuirk;
+}
+
+- (BOOL)_needsKeyboardEventDisambiguationQuirks
+{
+ static BOOL checked = NO;
+ static BOOL needsQuirks = NO;
+
+ if (checked)
+ return needsQuirks;
+
+ needsQuirks = !WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITH_IE_COMPATIBLE_KEYBOARD_EVENT_DISPATCH)
+ && ![[[NSBundle mainBundle] bundleIdentifier] isEqualToString:@"com.apple.Safari"];
+ checked = YES;
+
+ return needsQuirks;
+}
+
+- (void)_preferencesChangedNotification:(NSNotification *)notification
+{
+ WebPreferences *preferences = (WebPreferences *)[notification object];
+ ASSERT(preferences == [self preferences]);
+
+ if (!_private->userAgentOverridden)
+ *_private->userAgent = String();
+
+ // Cache this value so we don't have to read NSUserDefaults on each page load
+ _private->useSiteSpecificSpoofing = [preferences _useSiteSpecificSpoofing];
+
+ // Update corresponding WebCore Settings object.
+ if (!_private->page)
+ return;
+
+ Settings* settings = _private->page->settings();
+
+ settings->setCursiveFontFamily([preferences cursiveFontFamily]);
+ settings->setDefaultFixedFontSize([preferences defaultFixedFontSize]);
+ settings->setDefaultFontSize([preferences defaultFontSize]);
+ settings->setDefaultTextEncodingName([preferences defaultTextEncodingName]);
+ settings->setFantasyFontFamily([preferences fantasyFontFamily]);
+ settings->setFixedFontFamily([preferences fixedFontFamily]);
+ settings->setForceFTPDirectoryListings([preferences _forceFTPDirectoryListings]);
+ settings->setFTPDirectoryTemplatePath([preferences _ftpDirectoryTemplatePath]);
+ settings->setJavaEnabled([preferences isJavaEnabled]);
+ settings->setJavaScriptEnabled([preferences isJavaScriptEnabled]);
+ settings->setJavaScriptCanOpenWindowsAutomatically([preferences javaScriptCanOpenWindowsAutomatically]);
+ settings->setMinimumFontSize([preferences minimumFontSize]);
+ settings->setMinimumLogicalFontSize([preferences minimumLogicalFontSize]);
+ settings->setPluginsEnabled([preferences arePlugInsEnabled]);
+ settings->setPrivateBrowsingEnabled([preferences privateBrowsingEnabled]);
+ settings->setSansSerifFontFamily([preferences sansSerifFontFamily]);
+ settings->setSerifFontFamily([preferences serifFontFamily]);
+ settings->setStandardFontFamily([preferences standardFontFamily]);
+ settings->setLoadsImagesAutomatically([preferences loadsImagesAutomatically]);
+ settings->setShouldPrintBackgrounds([preferences shouldPrintBackgrounds]);
+ settings->setTextAreasAreResizable([preferences textAreasAreResizable]);
+ settings->setShrinksStandaloneImagesToFit([preferences shrinksStandaloneImagesToFit]);
+ settings->setEditableLinkBehavior(core([preferences editableLinkBehavior]));
+ settings->setDOMPasteAllowed([preferences isDOMPasteAllowed]);
+ settings->setUsesPageCache([self usesPageCache]);
+ settings->setShowsURLsInToolTips([preferences showsURLsInToolTips]);
+ settings->setDeveloperExtrasEnabled([preferences developerExtrasEnabled]);
+ settings->setAuthorAndUserStylesEnabled([preferences authorAndUserStylesEnabled]);
+ if ([preferences userStyleSheetEnabled]) {
+ NSString* location = [[preferences userStyleSheetLocation] _web_originalDataAsString];
+ settings->setUserStyleSheetLocation([NSURL URLWithString:(location ? location : @"")]);
+ } else
+ settings->setUserStyleSheetLocation([NSURL URLWithString:@""]);
+ settings->setNeedsAdobeFrameReloadingQuirk([self _needsAdobeFrameReloadingQuirk]);
+ settings->setNeedsKeyboardEventDisambiguationQuirks([self _needsKeyboardEventDisambiguationQuirks]);
+ settings->setNeedsSiteSpecificQuirks(_private->useSiteSpecificSpoofing);
+}
+
+static inline IMP getMethod(id o, SEL s)
+{
+ return [o respondsToSelector:s] ? [o methodForSelector:s] : 0;
+}
+
+- (void)_cacheResourceLoadDelegateImplementations
+{
+ WebResourceDelegateImplementationCache *cache = &_private->resourceLoadDelegateImplementations;
+ id delegate = _private->resourceProgressDelegate;
+
+ if (!delegate) {
+ bzero(cache, sizeof(WebResourceDelegateImplementationCache));
+ return;
+ }
+
+ cache->didCancelAuthenticationChallengeFunc = getMethod(delegate, @selector(webView:resource:didReceiveAuthenticationChallenge:fromDataSource:));
+ cache->didFailLoadingWithErrorFromDataSourceFunc = getMethod(delegate, @selector(webView:resource:didFailLoadingWithError:fromDataSource:));
+ cache->didFinishLoadingFromDataSourceFunc = getMethod(delegate, @selector(webView:resource:didFinishLoadingFromDataSource:));
+ cache->didLoadResourceFromMemoryCacheFunc = getMethod(delegate, @selector(webView:didLoadResourceFromMemoryCache:response:length:fromDataSource:));
+ cache->didReceiveAuthenticationChallengeFunc = getMethod(delegate, @selector(webView:resource:didReceiveAuthenticationChallenge:fromDataSource:));
+ cache->didReceiveContentLengthFunc = getMethod(delegate, @selector(webView:resource:didReceiveContentLength:fromDataSource:));
+ cache->didReceiveResponseFunc = getMethod(delegate, @selector(webView:resource:didReceiveResponse:fromDataSource:));
+ cache->identifierForRequestFunc = getMethod(delegate, @selector(webView:identifierForInitialRequest:fromDataSource:));
+ cache->plugInFailedWithErrorFunc = getMethod(delegate, @selector(webView:plugInFailedWithError:dataSource:));
+ cache->willCacheResponseFunc = getMethod(delegate, @selector(webView:resource:willCacheResponse:fromDataSource:));
+ cache->willSendRequestFunc = getMethod(delegate, @selector(webView:resource:willSendRequest:redirectResponse:fromDataSource:));
+}
+
+WebResourceDelegateImplementationCache* WebViewGetResourceLoadDelegateImplementations(WebView *webView)
+{
+ static WebResourceDelegateImplementationCache empty;
+ if (!webView)
+ return &empty;
+ return &webView->_private->resourceLoadDelegateImplementations;
+}
+
+- (void)_cacheFrameLoadDelegateImplementations
+{
+ WebFrameLoadDelegateImplementationCache *cache = &_private->frameLoadDelegateImplementations;
+ id delegate = _private->frameLoadDelegate;
+
+ if (!delegate) {
+ bzero(cache, sizeof(WebFrameLoadDelegateImplementationCache));
+ return;
+ }
+
+ cache->didCancelClientRedirectForFrameFunc = getMethod(delegate, @selector(webView:didCancelClientRedirectForFrame:));
+ cache->didChangeLocationWithinPageForFrameFunc = getMethod(delegate, @selector(webView:didChangeLocationWithinPageForFrame:));
+ cache->didClearWindowObjectForFrameFunc = getMethod(delegate, @selector(webView:didClearWindowObject:forFrame:));
+ cache->didCommitLoadForFrameFunc = getMethod(delegate, @selector(webView:didCommitLoadForFrame:));
+ cache->didFailLoadWithErrorForFrameFunc = getMethod(delegate, @selector(webView:didFailLoadWithError:forFrame:));
+ cache->didFailProvisionalLoadWithErrorForFrameFunc = getMethod(delegate, @selector(webView:didFailProvisionalLoadWithError:forFrame:));
+ cache->didFinishDocumentLoadForFrameFunc = getMethod(delegate, @selector(webView:didFinishDocumentLoadForFrame:));
+ cache->didFinishLoadForFrameFunc = getMethod(delegate, @selector(webView:didFinishLoadForFrame:));
+ cache->didFirstLayoutInFrameFunc = getMethod(delegate, @selector(webView:didFirstLayoutInFrame:));
+ cache->didHandleOnloadEventsForFrameFunc = getMethod(delegate, @selector(webView:didHandleOnloadEventsForFrame:));
+ cache->didReceiveIconForFrameFunc = getMethod(delegate, @selector(webView:didReceiveIcon:forFrame:));
+ cache->didReceiveServerRedirectForProvisionalLoadForFrameFunc = getMethod(delegate, @selector(webView:didReceiveServerRedirectForProvisionalLoadForFrame:));
+ cache->didReceiveTitleForFrameFunc = getMethod(delegate, @selector(webView:didReceiveTitle:forFrame:));
+ cache->didStartProvisionalLoadForFrameFunc = getMethod(delegate, @selector(webView:didStartProvisionalLoadForFrame:));
+ cache->willCloseFrameFunc = getMethod(delegate, @selector(webView:willCloseFrame:));
+ cache->willPerformClientRedirectToURLDelayFireDateForFrameFunc = getMethod(delegate, @selector(webView:willPerformClientRedirectToURL:delay:fireDate:forFrame:));
+ cache->windowScriptObjectAvailableFunc = getMethod(delegate, @selector(webView:windowScriptObjectAvailable:));
+}
+
+WebFrameLoadDelegateImplementationCache* WebViewGetFrameLoadDelegateImplementations(WebView *webView)
+{
+ static WebFrameLoadDelegateImplementationCache empty;
+ if (!webView)
+ return &empty;
+ return &webView->_private->frameLoadDelegateImplementations;
+}
+
+- (id)_policyDelegateForwarder
+{
+ if (!_private->policyDelegateForwarder)
+ _private->policyDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget:_private->policyDelegate defaultTarget:[WebDefaultPolicyDelegate sharedPolicyDelegate] catchExceptions:_private->catchesDelegateExceptions];
+ return _private->policyDelegateForwarder;
+}
+
+- (id)_UIDelegateForwarder
+{
+ if (!_private->UIDelegateForwarder)
+ _private->UIDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget:_private->UIDelegate defaultTarget:[WebDefaultUIDelegate sharedUIDelegate] catchExceptions:_private->catchesDelegateExceptions];
+ return _private->UIDelegateForwarder;
+}
+
+- (id)_editingDelegateForwarder
+{
+ // This can be called during window deallocation by QTMovieView in the QuickTime Cocoa Plug-in.
+ // Not sure if that is a bug or not.
+ if (!_private)
+ return nil;
+
+ if (!_private->editingDelegateForwarder)
+ _private->editingDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget:_private->editingDelegate defaultTarget:[WebDefaultEditingDelegate sharedEditingDelegate] catchExceptions:_private->catchesDelegateExceptions];
+ return _private->editingDelegateForwarder;
+}
+
+- (id)_scriptDebugDelegateForwarder
+{
+ if (!_private->scriptDebugDelegateForwarder)
+ _private->scriptDebugDelegateForwarder = [[_WebSafeForwarder alloc] initWithTarget:_private->scriptDebugDelegate defaultTarget:[WebDefaultScriptDebugDelegate sharedScriptDebugDelegate] catchExceptions:_private->catchesDelegateExceptions];
+ return _private->scriptDebugDelegateForwarder;
+}
+
+- (void)_closeWindow
+{
+ [[self _UIDelegateForwarder] webViewClose:self];
+}
+
++ (void)_unregisterViewClassAndRepresentationClassForMIMEType:(NSString *)MIMEType;
+{
+ [[WebFrameView _viewTypesAllowImageTypeOmission:NO] removeObjectForKey:MIMEType];
+ [[WebDataSource _repTypesAllowImageTypeOmission:NO] removeObjectForKey:MIMEType];
+
+ // FIXME: We also need to maintain MIMEType registrations (which can be dynamically changed)
+ // in the WebCore MIMEType registry. For now we're doing this in a safe, limited manner
+ // to fix <rdar://problem/5372989> - a future revamping of the entire system is neccesary for future robustness
+ MIMETypeRegistry::getSupportedNonImageMIMETypes().remove(MIMEType);
+}
+
++ (void)_registerViewClass:(Class)viewClass representationClass:(Class)representationClass forURLScheme:(NSString *)URLScheme;
+{
+ NSString *MIMEType = [self _generatedMIMETypeForURLScheme:URLScheme];
+ [self registerViewClass:viewClass representationClass:representationClass forMIMEType:MIMEType];
+
+ // FIXME: We also need to maintain MIMEType registrations (which can be dynamically changed)
+ // in the WebCore MIMEType registry. For now we're doing this in a safe, limited manner
+ // to fix <rdar://problem/5372989> - a future revamping of the entire system is neccesary for future robustness
+ if ([viewClass class] == [WebHTMLView class])
+ MIMETypeRegistry::getSupportedNonImageMIMETypes().add(MIMEType);
+
+ // This is used to make _representationExistsForURLScheme faster.
+ // Without this set, we'd have to create the MIME type each time.
+ if (schemesWithRepresentationsSet == nil) {
+ schemesWithRepresentationsSet = [[NSMutableSet alloc] init];
+ }
+ [schemesWithRepresentationsSet addObject:[[[URLScheme lowercaseString] copy] autorelease]];
+}
+
++ (NSString *)_generatedMIMETypeForURLScheme:(NSString *)URLScheme
+{
+ return [@"x-apple-web-kit/" stringByAppendingString:[URLScheme lowercaseString]];
+}
+
++ (BOOL)_representationExistsForURLScheme:(NSString *)URLScheme
+{
+ return [schemesWithRepresentationsSet containsObject:[URLScheme lowercaseString]];
+}
+
++ (BOOL)_canHandleRequest:(NSURLRequest *)request
+{
+ // FIXME: If <rdar://problem/5217309> gets fixed, this check can be removed
+ if (!request)
+ return NO;
+
+ if ([NSURLConnection canHandleRequest:request])
+ return YES;
+
+ NSString *scheme = [[request URL] scheme];
+
+ if ([self _representationExistsForURLScheme:scheme])
+ return YES;
+
+ return ([scheme _webkit_isCaseInsensitiveEqualToString:@"applewebdata"]);
+}
+
++ (NSString *)_decodeData:(NSData *)data
+{
+ HTMLNames::init(); // this method is used for importing bookmarks at startup, so HTMLNames are likely to be uninitialized yet
+ RefPtr<TextResourceDecoder> decoder = new TextResourceDecoder("text/html"); // bookmark files are HTML
+ String result = decoder->decode(static_cast<const char*>([data bytes]), [data length]);
+ result += decoder->flush();
+ return result;
+}
+
+- (void)_pushPerformingProgrammaticFocus
+{
+ _private->programmaticFocusCount++;
+}
+
+- (void)_popPerformingProgrammaticFocus
+{
+ _private->programmaticFocusCount--;
+}
+
+- (BOOL)_isPerformingProgrammaticFocus
+{
+ return _private->programmaticFocusCount != 0;
+}
+
+- (void)_didChangeValueForKey: (NSString *)key
+{
+ LOG (Bindings, "calling didChangeValueForKey: %@", key);
+ [self didChangeValueForKey: key];
+}
+
+- (void)_willChangeValueForKey: (NSString *)key
+{
+ LOG (Bindings, "calling willChangeValueForKey: %@", key);
+ [self willChangeValueForKey: key];
+}
+
++ (BOOL)automaticallyNotifiesObserversForKey:(NSString *)key {
+ static NSSet *manualNotifyKeys = nil;
+ if (!manualNotifyKeys)
+ manualNotifyKeys = [[NSSet alloc] initWithObjects:_WebMainFrameURLKey, _WebIsLoadingKey, _WebEstimatedProgressKey,
+ _WebCanGoBackKey, _WebCanGoForwardKey, _WebMainFrameTitleKey, _WebMainFrameIconKey, _WebMainFrameDocumentKey, nil];
+ if ([manualNotifyKeys containsObject:key])
+ return NO;
+ return YES;
+}
+
+- (NSArray *)_declaredKeys {
+ static NSArray *declaredKeys = nil;
+ if (!declaredKeys)
+ declaredKeys = [[NSArray alloc] initWithObjects:_WebMainFrameURLKey, _WebIsLoadingKey, _WebEstimatedProgressKey,
+ _WebCanGoBackKey, _WebCanGoForwardKey, _WebMainFrameTitleKey, _WebMainFrameIconKey, _WebMainFrameDocumentKey, nil];
+ return declaredKeys;
+}
+
+- (void)setObservationInfo:(void *)info
+{
+ _private->observationInfo = info;
+}
+
+- (void *)observationInfo
+{
+ return _private->observationInfo;
+}
+
+- (void)_willChangeBackForwardKeys
+{
+ [self _willChangeValueForKey: _WebCanGoBackKey];
+ [self _willChangeValueForKey: _WebCanGoForwardKey];
+}
+
+- (void)_didChangeBackForwardKeys
+{
+ [self _didChangeValueForKey: _WebCanGoBackKey];
+ [self _didChangeValueForKey: _WebCanGoForwardKey];
+}
+
+- (void)_didStartProvisionalLoadForFrame:(WebFrame *)frame
+{
+ [self _willChangeBackForwardKeys];
+ if (frame == [self mainFrame]){
+ // Force an observer update by sending a will/did.
+ [self _willChangeValueForKey: _WebIsLoadingKey];
+ [self _didChangeValueForKey: _WebIsLoadingKey];
+
+ [self _willChangeValueForKey: _WebMainFrameURLKey];
+ }
+
+ [NSApp setWindowsNeedUpdate:YES];
+}
+
+- (void)_didCommitLoadForFrame:(WebFrame *)frame
+{
+ if (frame == [self mainFrame])
+ [self _didChangeValueForKey: _WebMainFrameURLKey];
+ [NSApp setWindowsNeedUpdate:YES];
+}
+
+- (void)_didFinishLoadForFrame:(WebFrame *)frame
+{
+ [self _didChangeBackForwardKeys];
+ if (frame == [self mainFrame]){
+ // Force an observer update by sending a will/did.
+ [self _willChangeValueForKey: _WebIsLoadingKey];
+ [self _didChangeValueForKey: _WebIsLoadingKey];
+ }
+ [NSApp setWindowsNeedUpdate:YES];
+}
+
+- (void)_didFailLoadWithError:(NSError *)error forFrame:(WebFrame *)frame
+{
+ [self _didChangeBackForwardKeys];
+ if (frame == [self mainFrame]){
+ // Force an observer update by sending a will/did.
+ [self _willChangeValueForKey: _WebIsLoadingKey];
+ [self _didChangeValueForKey: _WebIsLoadingKey];
+ }
+ [NSApp setWindowsNeedUpdate:YES];
+}
+
+- (void)_didFailProvisionalLoadWithError:(NSError *)error forFrame:(WebFrame *)frame
+{
+ [self _didChangeBackForwardKeys];
+ if (frame == [self mainFrame]){
+ // Force an observer update by sending a will/did.
+ [self _willChangeValueForKey: _WebIsLoadingKey];
+ [self _didChangeValueForKey: _WebIsLoadingKey];
+
+ [self _didChangeValueForKey: _WebMainFrameURLKey];
+ }
+ [NSApp setWindowsNeedUpdate:YES];
+}
+
+- (void)_reloadForPluginChanges
+{
+ [[self mainFrame] _reloadForPluginChanges];
+}
+
+- (NSCachedURLResponse *)_cachedResponseForURL:(NSURL *)URL
+{
+ NSMutableURLRequest *request = [[NSMutableURLRequest alloc] initWithURL:URL];
+ [request _web_setHTTPUserAgent:[self userAgentForURL:URL]];
+ NSCachedURLResponse *cachedResponse = [[NSURLCache sharedURLCache] cachedResponseForRequest:request];
+ [request release];
+ return cachedResponse;
+}
+
+- (void)_writeImageForElement:(NSDictionary *)element withPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard
+{
+ NSURL *linkURL = [element objectForKey:WebElementLinkURLKey];
+ DOMElement *domElement = [element objectForKey:WebElementDOMNodeKey];
+ [pasteboard _web_writeImage:(NSImage *)(domElement ? nil : [element objectForKey:WebElementImageKey])
+ element:domElement
+ URL:linkURL ? linkURL : (NSURL *)[element objectForKey:WebElementImageURLKey]
+ title:[element objectForKey:WebElementImageAltStringKey]
+ archive:[[element objectForKey:WebElementDOMNodeKey] webArchive]
+ types:types
+ source:nil];
+}
+
+- (void)_writeLinkElement:(NSDictionary *)element withPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard
+{
+ [pasteboard _web_writeURL:[element objectForKey:WebElementLinkURLKey]
+ andTitle:[element objectForKey:WebElementLinkLabelKey]
+ types:types];
+}
+
+- (void)_setInitiatedDrag:(BOOL)initiatedDrag
+{
+ if (!_private->page)
+ return;
+ _private->page->dragController()->setDidInitiateDrag(initiatedDrag);
+}
+
+#define DASHBOARD_CONTROL_LABEL @"control"
+
+- (void)_addScrollerDashboardRegions:(NSMutableDictionary *)regions from:(NSArray *)views
+{
+ // Add scroller regions for NSScroller and KWQScrollBar
+ int i, count = [views count];
+
+ for (i = 0; i < count; i++) {
+ NSView *aView = [views objectAtIndex:i];
+
+ if ([aView isKindOfClass:[NSScroller class]] ||
+ [aView isKindOfClass:NSClassFromString (@"KWQScrollBar")]) {
+ NSRect bounds = [aView bounds];
+ NSRect adjustedBounds;
+ adjustedBounds.origin = [self convertPoint:bounds.origin fromView:aView];
+ adjustedBounds.origin.y = [self bounds].size.height - adjustedBounds.origin.y;
+
+ // AppKit has horrible hack of placing absent scrollers at -100,-100
+ if (adjustedBounds.origin.y == -100)
+ continue;
+ adjustedBounds.size = bounds.size;
+ NSRect clip = [aView visibleRect];
+ NSRect adjustedClip;
+ adjustedClip.origin = [self convertPoint:clip.origin fromView:aView];
+ adjustedClip.origin.y = [self bounds].size.height - adjustedClip.origin.y;
+ adjustedClip.size = clip.size;
+ WebDashboardRegion *aRegion =
+ [[[WebDashboardRegion alloc] initWithRect:adjustedBounds
+ clip:adjustedClip type:WebDashboardRegionTypeScrollerRectangle] autorelease];
+ NSMutableArray *scrollerRegions;
+ scrollerRegions = [regions objectForKey:DASHBOARD_CONTROL_LABEL];
+ if (!scrollerRegions) {
+ scrollerRegions = [NSMutableArray array];
+ [regions setObject:scrollerRegions forKey:DASHBOARD_CONTROL_LABEL];
+ }
+ [scrollerRegions addObject:aRegion];
+ }
+ [self _addScrollerDashboardRegions:regions from:[aView subviews]];
+ }
+}
+
+- (void)_addScrollerDashboardRegions:(NSMutableDictionary *)regions
+{
+ [self _addScrollerDashboardRegions:regions from:[self subviews]];
+}
+
+- (NSDictionary *)_dashboardRegions
+{
+ // Only return regions from main frame.
+ Frame* mainFrame = [[[self mainFrame] _bridge] _frame];
+ if (!mainFrame)
+ return nil;
+ NSMutableDictionary *regions = mainFrame->dashboardRegionsDictionary();
+ [self _addScrollerDashboardRegions:regions];
+ return regions;
+}
+
+- (void)_setDashboardBehavior:(WebDashboardBehavior)behavior to:(BOOL)flag
+{
+ // FIXME: Remove this blanket assignment once Dashboard and Dashcode implement
+ // specific support for the backward compatibility mode flag.
+ if (behavior == WebDashboardBehaviorAllowWheelScrolling && flag == NO && _private->page)
+ _private->page->settings()->setUsesDashboardBackwardCompatibilityMode(true);
+
+ switch (behavior) {
+ case WebDashboardBehaviorAlwaysSendMouseEventsToAllWindows: {
+ _private->dashboardBehaviorAlwaysSendMouseEventsToAllWindows = flag;
+ break;
+ }
+ case WebDashboardBehaviorAlwaysSendActiveNullEventsToPlugIns: {
+ _private->dashboardBehaviorAlwaysSendActiveNullEventsToPlugIns = flag;
+ break;
+ }
+ case WebDashboardBehaviorAlwaysAcceptsFirstMouse: {
+ _private->dashboardBehaviorAlwaysAcceptsFirstMouse = flag;
+ break;
+ }
+ case WebDashboardBehaviorAllowWheelScrolling: {
+ _private->dashboardBehaviorAllowWheelScrolling = flag;
+ break;
+ }
+ case WebDashboardBehaviorUseBackwardCompatibilityMode: {
+ if (_private->page)
+ _private->page->settings()->setUsesDashboardBackwardCompatibilityMode(flag);
+ break;
+ }
+ }
+}
+
+- (BOOL)_dashboardBehavior:(WebDashboardBehavior)behavior
+{
+ switch (behavior) {
+ case WebDashboardBehaviorAlwaysSendMouseEventsToAllWindows: {
+ return _private->dashboardBehaviorAlwaysSendMouseEventsToAllWindows;
+ }
+ case WebDashboardBehaviorAlwaysSendActiveNullEventsToPlugIns: {
+ return _private->dashboardBehaviorAlwaysSendActiveNullEventsToPlugIns;
+ }
+ case WebDashboardBehaviorAlwaysAcceptsFirstMouse: {
+ return _private->dashboardBehaviorAlwaysAcceptsFirstMouse;
+ }
+ case WebDashboardBehaviorAllowWheelScrolling: {
+ return _private->dashboardBehaviorAllowWheelScrolling;
+ }
+ case WebDashboardBehaviorUseBackwardCompatibilityMode: {
+ return _private->page && _private->page->settings()->usesDashboardBackwardCompatibilityMode();
+ }
+ }
+ return NO;
+}
+
++ (void)_setShouldUseFontSmoothing:(BOOL)f
+{
+ WebCoreSetShouldUseFontSmoothing(f);
+}
+
++ (BOOL)_shouldUseFontSmoothing
+{
+ return WebCoreShouldUseFontSmoothing();
+}
+
++ (void)_setUsesTestModeFocusRingColor:(BOOL)f
+{
+ setUsesTestModeFocusRingColor(f);
+}
+
++ (BOOL)_usesTestModeFocusRingColor
+{
+ return usesTestModeFocusRingColor();
+}
+
+// This is only used by versions of Safari up to and including 3.0 and should be removed in a future release.
++ (NSString *)_minimumRequiredSafariBuildNumber
+{
+ return @"420+";
+}
+
+- (void)setAlwaysShowVerticalScroller:(BOOL)flag
+{
+ WebDynamicScrollBarsView *scrollview = [[[self mainFrame] frameView] _scrollView];
+ if (flag) {
+ [scrollview setVerticalScrollingMode:WebCoreScrollbarAlwaysOn andLock:YES];
+ } else {
+ [scrollview setVerticalScrollingModeLocked:NO];
+ [scrollview setVerticalScrollingMode:WebCoreScrollbarAuto];
+ }
+}
+
+- (BOOL)alwaysShowVerticalScroller
+{
+ WebDynamicScrollBarsView *scrollview = [[[self mainFrame] frameView] _scrollView];
+ return [scrollview verticalScrollingModeLocked] && [scrollview verticalScrollingMode] == WebCoreScrollbarAlwaysOn;
+}
+
+- (void)setAlwaysShowHorizontalScroller:(BOOL)flag
+{
+ WebDynamicScrollBarsView *scrollview = [[[self mainFrame] frameView] _scrollView];
+ if (flag) {
+ [scrollview setHorizontalScrollingMode:WebCoreScrollbarAlwaysOn andLock:YES];
+ } else {
+ [scrollview setHorizontalScrollingModeLocked:NO];
+ [scrollview setHorizontalScrollingMode:WebCoreScrollbarAuto];
+ }
+}
+
+- (void)setProhibitsMainFrameScrolling:(BOOL)prohibits
+{
+ Frame* mainFrame = [[[self mainFrame] _bridge] _frame];
+ if (mainFrame)
+ mainFrame->setProhibitsScrolling(prohibits);
+}
+
+- (BOOL)alwaysShowHorizontalScroller
+{
+ WebDynamicScrollBarsView *scrollview = [[[self mainFrame] frameView] _scrollView];
+ return [scrollview horizontalScrollingModeLocked] && [scrollview horizontalScrollingMode] == WebCoreScrollbarAlwaysOn;
+}
+
+- (void)_setInViewSourceMode:(BOOL)flag
+{
+ Frame* mainFrame = [[[self mainFrame] _bridge] _frame];
+ if (mainFrame)
+ mainFrame->setInViewSourceMode(flag);
+}
+
+- (BOOL)_inViewSourceMode
+{
+ Frame* mainFrame = [[[self mainFrame] _bridge] _frame];
+ return mainFrame && mainFrame->inViewSourceMode();
+}
+
+- (void)_setUseFastImageScalingMode:(BOOL)flag
+{
+ if (_private->page && _private->page->inLowQualityImageInterpolationMode() != flag) {
+ _private->page->setInLowQualityImageInterpolationMode(flag);
+ [self setNeedsDisplay:YES];
+ }
+}
+
+- (BOOL)_inFastImageScalingMode
+{
+ if (_private->page)
+ return _private->page->inLowQualityImageInterpolationMode();
+ return NO;
+}
+
+- (void)_setAdditionalWebPlugInPaths:(NSArray *)newPaths
+{
+ if (!_private->pluginDatabase)
+ _private->pluginDatabase = [[WebPluginDatabase alloc] init];
+
+ [_private->pluginDatabase setPlugInPaths:newPaths];
+ [_private->pluginDatabase refresh];
+}
+
+- (void)_attachScriptDebuggerToAllFrames
+{
+ for (Frame* frame = core([self mainFrame]); frame; frame = frame->tree()->traverseNext())
+ [kit(frame) _attachScriptDebugger];
+}
+
+- (void)_detachScriptDebuggerFromAllFrames
+{
+ for (Frame* frame = core([self mainFrame]); frame; frame = frame->tree()->traverseNext())
+ [kit(frame) _detachScriptDebugger];
+}
+
+- (void)setBackgroundColor:(NSColor *)backgroundColor
+{
+ if ([_private->backgroundColor isEqual:backgroundColor])
+ return;
+
+ id old = _private->backgroundColor;
+ _private->backgroundColor = [backgroundColor retain];
+ [old release];
+
+ [[self mainFrame] _updateBackground];
+}
+
+- (NSColor *)backgroundColor
+{
+ return _private->backgroundColor;
+}
+
+- (BOOL)defersCallbacks
+{
+ if (!_private->page)
+ return NO;
+ return _private->page->defersLoading();
+}
+
+- (void)setDefersCallbacks:(BOOL)defer
+{
+ if (!_private->page)
+ return;
+ return _private->page->setDefersLoading(defer);
+}
+
+// For backwards compatibility with the WebBackForwardList API, we honor both
+// a per-WebView and a per-preferences setting for whether to use the page cache.
+
+- (BOOL)usesPageCache
+{
+ return _private->usesPageCache && [[self preferences] usesPageCache];
+}
+
+- (void)setUsesPageCache:(BOOL)usesPageCache
+{
+ _private->usesPageCache = usesPageCache;
+
+ // Post a notification so the WebCore settings update.
+ [[self preferences] _postPreferencesChangesNotification];
+}
+
+- (void)handleAuthenticationForResource:(id)identifier challenge:(NSURLAuthenticationChallenge *)challenge fromDataSource:(WebDataSource *)dataSource
+{
+ NSWindow *window = [self hostWindow] ? [self hostWindow] : [self window];
+ [[WebPanelAuthenticationHandler sharedHandler] startAuthentication:challenge window:window];
+}
+
+- (void)_clearUndoRedoOperations
+{
+ if (!_private->page)
+ return;
+ _private->page->clearUndoRedoOperations();
+}
+
+- (void)_setCatchesDelegateExceptions:(BOOL)f
+{
+ _private->catchesDelegateExceptions = f;
+}
+
+- (BOOL)_catchesDelegateExceptions
+{
+ return _private->catchesDelegateExceptions;
+}
+
+- (void)_executeCoreCommandByName:(NSString *)name value:(NSString *)value
+{
+ Frame* coreFrame = [[[self mainFrame] _bridge] _frame];
+ if (!coreFrame)
+ return;
+ coreFrame->editor()->command(name).execute(value);
+}
+
+@end
+
+@implementation _WebSafeForwarder
+
+// Used to send messages to delegates that implement informal protocols.
+
+- (id)initWithTarget:(id)t defaultTarget:(id)dt catchExceptions:(BOOL)c
+{
+ self = [super init];
+ if (!self)
+ return nil;
+ target = t; // Non retained.
+ defaultTarget = dt;
+ catchExceptions = c;
+ return self;
+}
+
+- (void)forwardInvocation:(NSInvocation *)invocation
+{
+ if ([target respondsToSelector:[invocation selector]]) {
+ if (catchExceptions) {
+ @try {
+ [invocation invokeWithTarget:target];
+ } @catch(id exception) {
+ ReportDiscardedDelegateException([invocation selector], exception);
+ }
+ } else
+ [invocation invokeWithTarget:target];
+ return;
+ }
+
+ if ([defaultTarget respondsToSelector:[invocation selector]])
+ [invocation invokeWithTarget:defaultTarget];
+
+ // Do nothing quietly if method not implemented.
+}
+
+- (NSMethodSignature *)methodSignatureForSelector:(SEL)aSelector
+{
+ return [defaultTarget methodSignatureForSelector:aSelector];
+}
+
+@end
+
+@implementation WebView
+
++ (void)initialize
+{
+ static BOOL initialized = NO;
+ if (initialized)
+ return;
+ initialized = YES;
+
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(_applicationWillTerminate) name:NSApplicationWillTerminateNotification object:NSApp];
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(_preferencesChangedNotification:) name:WebPreferencesChangedNotification object:nil];
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(_preferencesRemovedNotification:) name:WebPreferencesRemovedNotification object:nil];
+}
+
++ (void)_applicationWillTerminate
+{
+ applicationIsTerminating = YES;
+ if (!pluginDatabaseClientCount)
+ [WebPluginDatabase closeSharedDatabase];
+}
+
++ (BOOL)canShowMIMEType:(NSString *)MIMEType
+{
+ return [self _viewClass:nil andRepresentationClass:nil forMIMEType:MIMEType];
+}
+
+- (WebBasePluginPackage *)_pluginForMIMEType:(NSString *)MIMEType
+{
+ WebBasePluginPackage *pluginPackage = [[WebPluginDatabase sharedDatabase] pluginForMIMEType:MIMEType];
+ if (pluginPackage)
+ return pluginPackage;
+
+ if (_private->pluginDatabase)
+ return [_private->pluginDatabase pluginForMIMEType:MIMEType];
+
+ return nil;
+}
+
+- (WebBasePluginPackage *)_pluginForExtension:(NSString *)extension
+{
+ WebBasePluginPackage *pluginPackage = [[WebPluginDatabase sharedDatabase] pluginForExtension:extension];
+ if (pluginPackage)
+ return pluginPackage;
+
+ if (_private->pluginDatabase)
+ return [_private->pluginDatabase pluginForExtension:extension];
+
+ return nil;
+}
+
+- (BOOL)_isMIMETypeRegisteredAsPlugin:(NSString *)MIMEType
+{
+ if ([[WebPluginDatabase sharedDatabase] isMIMETypeRegistered:MIMEType])
+ return YES;
+
+ if (_private->pluginDatabase && [_private->pluginDatabase isMIMETypeRegistered:MIMEType])
+ return YES;
+
+ return NO;
+}
+
++ (BOOL)canShowMIMETypeAsHTML:(NSString *)MIMEType
+{
+ return [WebFrameView _canShowMIMETypeAsHTML:MIMEType];
+}
+
++ (NSArray *)MIMETypesShownAsHTML
+{
+ NSMutableDictionary *viewTypes = [WebFrameView _viewTypesAllowImageTypeOmission:YES];
+ NSEnumerator *enumerator = [viewTypes keyEnumerator];
+ id key;
+ NSMutableArray *array = [[[NSMutableArray alloc] init] autorelease];
+
+ while ((key = [enumerator nextObject])) {
+ if ([viewTypes objectForKey:key] == [WebHTMLView class])
+ [array addObject:key];
+ }
+
+ return array;
+}
+
++ (void)setMIMETypesShownAsHTML:(NSArray *)MIMETypes
+{
+ NSDictionary *viewTypes = [[WebFrameView _viewTypesAllowImageTypeOmission:YES] copy];
+ NSEnumerator *enumerator = [viewTypes keyEnumerator];
+ id key;
+ while ((key = [enumerator nextObject])) {
+ if ([viewTypes objectForKey:key] == [WebHTMLView class])
+ [WebView _unregisterViewClassAndRepresentationClassForMIMEType:key];
+ }
+
+ int i, count = [MIMETypes count];
+ for (i = 0; i < count; i++) {
+ [WebView registerViewClass:[WebHTMLView class]
+ representationClass:[WebHTMLRepresentation class]
+ forMIMEType:[MIMETypes objectAtIndex:i]];
+ }
+ [viewTypes release];
+}
+
++ (NSURL *)URLFromPasteboard:(NSPasteboard *)pasteboard
+{
+ return [pasteboard _web_bestURL];
+}
+
++ (NSString *)URLTitleFromPasteboard:(NSPasteboard *)pasteboard
+{
+ return [pasteboard stringForType:WebURLNamePboardType];
+}
+
++ (void)registerURLSchemeAsLocal:(NSString *)protocol
+{
+ FrameLoader::registerURLSchemeAsLocal(protocol);
+}
+
+- (void)_registerDraggedTypes
+{
+ NSArray *editableTypes = [WebHTMLView _insertablePasteboardTypes];
+ NSArray *URLTypes = [NSPasteboard _web_dragTypesForURL];
+ NSMutableSet *types = [[NSMutableSet alloc] initWithArray:editableTypes];
+ [types addObjectsFromArray:URLTypes];
+ [self registerForDraggedTypes:[types allObjects]];
+ [types release];
+}
+
+- (void)_commonInitializationWithFrameName:(NSString *)frameName groupName:(NSString *)groupName
+{
+ WebPreferences *standardPreferences = [WebPreferences standardPreferences];
+ [standardPreferences willAddToWebView];
+
+ _private->preferences = [standardPreferences retain];
+ _private->catchesDelegateExceptions = YES;
+ _private->mainFrameDocumentReady = NO;
+ _private->drawsBackground = YES;
+ _private->smartInsertDeleteEnabled = YES;
+ _private->backgroundColor = [[NSColor whiteColor] retain];
+
+ NSRect f = [self frame];
+ WebFrameView *frameView = [[WebFrameView alloc] initWithFrame: NSMakeRect(0,0,f.size.width,f.size.height)];
+ [frameView setAutoresizingMask:NSViewWidthSizable | NSViewHeightSizable];
+ [self addSubview:frameView];
+ [frameView release];
+
+ WebKitInitializeLoggingChannelsIfNecessary();
+ WebCore::InitializeLoggingChannelsIfNecessary();
+ [WebHistoryItem initWindowWatcherIfNecessary];
+ WebKitInitializeDatabasesIfNecessary();
+
+ _private->page = new Page(new WebChromeClient(self), new WebContextMenuClient(self), new WebEditorClient(self), new WebDragClient(self), new WebInspectorClient(self));
+ [[[WebFrameBridge alloc] initMainFrameWithPage:_private->page frameName:frameName frameView:frameView] release];
+
+ [self _addToAllWebViewsSet];
+ [self setGroupName:groupName];
+
+ // If there's already a next key view (e.g., from a nib), wire it up to our
+ // contained frame view. In any case, wire our next key view up to the our
+ // contained frame view. This works together with our becomeFirstResponder
+ // and setNextKeyView overrides.
+ NSView *nextKeyView = [self nextKeyView];
+ if (nextKeyView != nil && nextKeyView != frameView) {
+ [frameView setNextKeyView:nextKeyView];
+ }
+ [super setNextKeyView:frameView];
+
+ ++WebViewCount;
+
+ [self _registerDraggedTypes];
+
+ // initialize WebScriptDebugServer here so listeners can register before any pages are loaded.
+ if ([WebView _scriptDebuggerEnabled])
+ [WebScriptDebugServer sharedScriptDebugServer];
+
+ WebPreferences *prefs = [self preferences];
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(_preferencesChangedNotification:)
+ name:WebPreferencesChangedNotification object:prefs];
+
+ // Post a notification so the WebCore settings update.
+ [[self preferences] _postPreferencesChangesNotification];
+
+ if (!WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITH_LOCAL_RESOURCE_SECURITY_RESTRICTION))
+ FrameLoader::setRestrictAccessToLocal(false);
+}
+
+- (id)initWithFrame:(NSRect)f
+{
+ return [self initWithFrame:f frameName:nil groupName:nil];
+}
+
+- (id)initWithFrame:(NSRect)f frameName:(NSString *)frameName groupName:(NSString *)groupName;
+{
+ self = [super initWithFrame:f];
+ if (!self)
+ return nil;
+
+#ifdef ENABLE_WEBKIT_UNSET_DYLD_FRAMEWORK_PATH
+ // DYLD_FRAMEWORK_PATH is used so Safari will load the development version of WebKit, which
+ // may not work with other WebKit applications. Unsetting DYLD_FRAMEWORK_PATH removes the
+ // need for Safari to unset it to prevent it from being passed to applications it launches.
+ // Unsetting it when a WebView is first created is as good a place as any.
+ // See <http://bugs.webkit.org/show_bug.cgi?id=4286> for more details.
+ if (getenv("WEBKIT_UNSET_DYLD_FRAMEWORK_PATH")) {
+ unsetenv("DYLD_FRAMEWORK_PATH");
+ unsetenv("WEBKIT_UNSET_DYLD_FRAMEWORK_PATH");
+ }
+#endif
+
+ _private = [[WebViewPrivate alloc] init];
+ [self _commonInitializationWithFrameName:frameName groupName:groupName];
+ [self setMaintainsBackForwardList: YES];
+ return self;
+}
+
+- (id)initWithCoder:(NSCoder *)decoder
+{
+ WebView *result = nil;
+
+ @try {
+ NSString *frameName;
+ NSString *groupName;
+ WebPreferences *preferences;
+ BOOL useBackForwardList = NO;
+ BOOL allowsUndo = YES;
+
+ result = [super initWithCoder:decoder];
+ result->_private = [[WebViewPrivate alloc] init];
+
+ // We don't want any of the archived subviews. The subviews will always
+ // be created in _commonInitializationFrameName:groupName:.
+ [[result subviews] makeObjectsPerformSelector:@selector(removeFromSuperview)];
+
+ if ([decoder allowsKeyedCoding]) {
+ frameName = [decoder decodeObjectForKey:@"FrameName"];
+ groupName = [decoder decodeObjectForKey:@"GroupName"];
+ preferences = [decoder decodeObjectForKey:@"Preferences"];
+ useBackForwardList = [decoder decodeBoolForKey:@"UseBackForwardList"];
+ if ([decoder containsValueForKey:@"AllowsUndo"])
+ allowsUndo = [decoder decodeBoolForKey:@"AllowsUndo"];
+ } else {
+ int version;
+ [decoder decodeValueOfObjCType:@encode(int) at:&version];
+ frameName = [decoder decodeObject];
+ groupName = [decoder decodeObject];
+ preferences = [decoder decodeObject];
+ if (version > 1)
+ [decoder decodeValuesOfObjCTypes:"c", &useBackForwardList];
+ // The allowsUndo field is no longer written out in encodeWithCoder, but since there are
+ // version 3 NIBs that have this field encoded, we still need to read it in.
+ if (version == 3)
+ [decoder decodeValuesOfObjCTypes:"c", &allowsUndo];
+ }
+
+ if (![frameName isKindOfClass:[NSString class]])
+ frameName = nil;
+ if (![groupName isKindOfClass:[NSString class]])
+ groupName = nil;
+ if (![preferences isKindOfClass:[WebPreferences class]])
+ preferences = nil;
+
+ LOG(Encoding, "FrameName = %@, GroupName = %@, useBackForwardList = %d\n", frameName, groupName, (int)useBackForwardList);
+ [result _commonInitializationWithFrameName:frameName groupName:groupName];
+ [result page]->backForwardList()->setEnabled(useBackForwardList);
+ result->_private->allowsUndo = allowsUndo;
+ if (preferences)
+ [result setPreferences:preferences];
+ } @catch (NSException *localException) {
+ result = nil;
+ [self release];
+ }
+
+ return result;
+}
+
+- (void)encodeWithCoder:(NSCoder *)encoder
+{
+ // Set asside the subviews before we archive. We don't want to archive any subviews.
+ // The subviews will always be created in _commonInitializationFrameName:groupName:.
+ id originalSubviews = _subviews;
+ _subviews = nil;
+
+ [super encodeWithCoder:encoder];
+
+ // Restore the subviews we set aside.
+ _subviews = originalSubviews;
+
+ BOOL useBackForwardList = _private->page && _private->page->backForwardList()->enabled();
+ if ([encoder allowsKeyedCoding]) {
+ [encoder encodeObject:[[self mainFrame] name] forKey:@"FrameName"];
+ [encoder encodeObject:[self groupName] forKey:@"GroupName"];
+ [encoder encodeObject:[self preferences] forKey:@"Preferences"];
+ [encoder encodeBool:useBackForwardList forKey:@"UseBackForwardList"];
+ [encoder encodeBool:_private->allowsUndo forKey:@"AllowsUndo"];
+ } else {
+ int version = WebViewVersion;
+ [encoder encodeValueOfObjCType:@encode(int) at:&version];
+ [encoder encodeObject:[[self mainFrame] name]];
+ [encoder encodeObject:[self groupName]];
+ [encoder encodeObject:[self preferences]];
+ [encoder encodeValuesOfObjCTypes:"c", &useBackForwardList];
+ // DO NOT encode any new fields here, doing so will break older WebKit releases.
+ }
+
+ LOG(Encoding, "FrameName = %@, GroupName = %@, useBackForwardList = %d\n", [[self mainFrame] name], [self groupName], (int)useBackForwardList);
+}
+
+- (void)dealloc
+{
+ // call close to ensure we tear-down completely
+ // this maintains our old behavior for existing applications
+ [self _close];
+
+ --WebViewCount;
+
+ [_private release];
+ // [super dealloc] can end up dispatching against _private (3466082)
+ _private = nil;
+
+ [super dealloc];
+}
+
+- (void)finalize
+{
+ ASSERT(_private->closed);
+
+ --WebViewCount;
+
+ [super finalize];
+}
+
+- (void)close
+{
+ [self _close];
+}
+
+- (void)setShouldCloseWithWindow:(BOOL)close
+{
+ _private->shouldCloseWithWindow = close;
+}
+
+- (BOOL)shouldCloseWithWindow
+{
+ return _private->shouldCloseWithWindow;
+}
+
+- (void)viewWillMoveToWindow:(NSWindow *)window
+{
+ // Don't do anything if we aren't initialized. This happens when decoding a WebView.
+ if (!_private)
+ return;
+
+ if ([self window])
+ [[NSNotificationCenter defaultCenter] removeObserver:self name:NSWindowWillCloseNotification object:[self window]];
+
+ if (window) {
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(_windowWillClose:) name:NSWindowWillCloseNotification object:window];
+
+ // Ensure that we will receive the events that WebHTMLView (at least) needs. It's expensive enough
+ // that we don't want to call it over and over.
+ [window setAcceptsMouseMovedEvents:YES];
+ WKSetNSWindowShouldPostEventNotifications(window, YES);
+ }
+}
+
+- (void)_windowWillClose:(NSNotification *)notification
+{
+ if ([self shouldCloseWithWindow] && ([self window] == [self hostWindow] || ([self window] && ![self hostWindow]) || (![self window] && [self hostWindow])))
+ [self _close];
+}
+
+- (void)setPreferences:(WebPreferences *)prefs
+{
+ if (!prefs)
+ prefs = [WebPreferences standardPreferences];
+
+ if (_private->preferences == prefs)
+ return;
+
+ [prefs willAddToWebView];
+
+ WebPreferences *oldPrefs = _private->preferences;
+
+ [[NSNotificationCenter defaultCenter] removeObserver:self name:WebPreferencesChangedNotification object:[self preferences]];
+ [WebPreferences _removeReferenceForIdentifier:[oldPrefs identifier]];
+
+ _private->preferences = [prefs retain];
+
+ // After registering for the notification, post it so the WebCore settings update.
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(_preferencesChangedNotification:)
+ name:WebPreferencesChangedNotification object:[self preferences]];
+ [[self preferences] _postPreferencesChangesNotification];
+
+ [oldPrefs didRemoveFromWebView];
+ [oldPrefs release];
+}
+
+- (WebPreferences *)preferences
+{
+ return _private->preferences;
+}
+
+- (void)setPreferencesIdentifier:(NSString *)anIdentifier
+{
+ if (!_private->closed && ![anIdentifier isEqual:[[self preferences] identifier]]) {
+ WebPreferences *prefs = [[WebPreferences alloc] initWithIdentifier:anIdentifier];
+ [self setPreferences:prefs];
+ [prefs release];
+ }
+}
+
+- (NSString *)preferencesIdentifier
+{
+ return [[self preferences] identifier];
+}
+
+
+- (void)setUIDelegate:delegate
+{
+ _private->UIDelegate = delegate;
+ [_private->UIDelegateForwarder release];
+ _private->UIDelegateForwarder = nil;
+}
+
+- UIDelegate
+{
+ return _private->UIDelegate;
+}
+
+- (void)setResourceLoadDelegate: delegate
+{
+ _private->resourceProgressDelegate = delegate;
+ [self _cacheResourceLoadDelegateImplementations];
+}
+
+- resourceLoadDelegate
+{
+ return _private->resourceProgressDelegate;
+}
+
+- (void)setDownloadDelegate: delegate
+{
+ _private->downloadDelegate = delegate;
+}
+
+
+- downloadDelegate
+{
+ return _private->downloadDelegate;
+}
+
+- (void)setPolicyDelegate:delegate
+{
+ _private->policyDelegate = delegate;
+ [_private->policyDelegateForwarder release];
+ _private->policyDelegateForwarder = nil;
+}
+
+- policyDelegate
+{
+ return _private->policyDelegate;
+}
+
+- (void)setFrameLoadDelegate:delegate
+{
+ _private->frameLoadDelegate = delegate;
+ [self _cacheFrameLoadDelegateImplementations];
+
+ // If this delegate wants callbacks for icons, fire up the icon database.
+ if (_private->frameLoadDelegateImplementations.didReceiveIconForFrameFunc)
+ [WebIconDatabase sharedIconDatabase];
+}
+
+- frameLoadDelegate
+{
+ return _private->frameLoadDelegate;
+}
+
+- (WebFrame *)mainFrame
+{
+ // This can be called in initialization, before _private has been set up (3465613)
+ if (!_private)
+ return nil;
+ if (!_private->page)
+ return nil;
+ return kit(_private->page->mainFrame());
+}
+
+- (WebFrame *)selectedFrame
+{
+ // If the first responder is a view in our tree, we get the frame containing the first responder.
+ // This is faster than searching the frame hierarchy, and will give us a result even in the case
+ // where the focused frame doesn't actually contain a selection.
+ WebFrame *focusedFrame = [self _focusedFrame];
+ if (focusedFrame)
+ return focusedFrame;
+
+ // If the first responder is outside of our view tree, we search for a frame containing a selection.
+ // There should be at most only one of these.
+ return [[self mainFrame] _findFrameWithSelection];
+}
+
+- (WebBackForwardList *)backForwardList
+{
+ if (!_private->page)
+ return nil;
+ if (!_private->page->backForwardList()->enabled())
+ return nil;
+ return kit(_private->page->backForwardList());
+}
+
+- (void)setMaintainsBackForwardList: (BOOL)flag
+{
+ if (!_private->page)
+ return;
+ _private->page->backForwardList()->setEnabled(flag);
+}
+
+- (BOOL)goBack
+{
+ if (!_private->page)
+ return NO;
+
+ return _private->page->goBack();
+}
+
+- (BOOL)goForward
+{
+ if (!_private->page)
+ return NO;
+
+ return _private->page->goForward();
+}
+
+- (BOOL)goToBackForwardItem:(WebHistoryItem *)item
+{
+ if (!_private->page)
+ return NO;
+
+ _private->page->goToItem(core(item), FrameLoadTypeIndexedBackForward);
+ return YES;
+}
+
+- (void)setTextSizeMultiplier:(float)m
+{
+ // NOTE: This has no visible effect when viewing a PDF (see <rdar://problem/4737380>)
+ if (_private->textSizeMultiplier == m)
+ return;
+
+ _private->textSizeMultiplier = m;
+ [self _notifyTextSizeMultiplierChanged];
+}
+
+- (float)textSizeMultiplier
+{
+ return _private->textSizeMultiplier;
+}
+
+- (void)setApplicationNameForUserAgent:(NSString *)applicationName
+{
+ NSString *name = [applicationName copy];
+ [_private->applicationNameForUserAgent release];
+ _private->applicationNameForUserAgent = name;
+ if (!_private->userAgentOverridden)
+ *_private->userAgent = String();
+}
+
+- (NSString *)applicationNameForUserAgent
+{
+ return [[_private->applicationNameForUserAgent retain] autorelease];
+}
+
+- (void)setCustomUserAgent:(NSString *)userAgentString
+{
+ *_private->userAgent = userAgentString;
+ _private->userAgentOverridden = userAgentString != nil;
+}
+
+- (NSString *)customUserAgent
+{
+ if (!_private->userAgentOverridden)
+ return nil;
+ return *_private->userAgent;
+}
+
+- (void)setMediaStyle:(NSString *)mediaStyle
+{
+ if (_private->mediaStyle != mediaStyle) {
+ [_private->mediaStyle release];
+ _private->mediaStyle = [mediaStyle copy];
+ }
+}
+
+- (NSString *)mediaStyle
+{
+ return _private->mediaStyle;
+}
+
+- (BOOL)supportsTextEncoding
+{
+ id documentView = [[[self mainFrame] frameView] documentView];
+ return [documentView conformsToProtocol:@protocol(WebDocumentText)]
+ && [documentView supportsTextEncoding];
+}
+
+- (void)setCustomTextEncodingName:(NSString *)encoding
+{
+ NSString *oldEncoding = [self customTextEncodingName];
+ if (encoding == oldEncoding || [encoding isEqualToString:oldEncoding])
+ return;
+ FrameLoader* mainFrameLoader = [[self mainFrame] _frameLoader];
+ if (mainFrameLoader)
+ mainFrameLoader->reloadAllowingStaleData(encoding);
+}
+
+- (NSString *)_mainFrameOverrideEncoding
+{
+ WebDataSource *dataSource = [[self mainFrame] provisionalDataSource];
+ if (dataSource == nil)
+ dataSource = [[self mainFrame] _dataSource];
+ if (dataSource == nil)
+ return nil;
+ return nsStringNilIfEmpty([dataSource _documentLoader]->overrideEncoding());
+}
+
+- (NSString *)customTextEncodingName
+{
+ return [self _mainFrameOverrideEncoding];
+}
+
+- (NSString *)stringByEvaluatingJavaScriptFromString:(NSString *)script
+{
+ // Return statements are only valid in a function but some applications pass in scripts
+ // prefixed with return (<rdar://problems/5103720&4616860>) since older WebKit versions
+ // silently ignored the return. If the application is linked against an earlier version
+ // of WebKit we will strip the return so the script wont fail.
+ if (!WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITHOUT_JAVASCRIPT_RETURN_QUIRK)) {
+ NSRange returnStringRange = [script rangeOfString:@"return "];
+ if (returnStringRange.length && !returnStringRange.location)
+ script = [script substringFromIndex:returnStringRange.location + returnStringRange.length];
+ }
+
+ NSString *result = [[[self mainFrame] _bridge] stringByEvaluatingJavaScriptFromString:script];
+ // The only way stringByEvaluatingJavaScriptFromString can return nil is if the frame was removed by the script
+ // Since there's no way to get rid of the main frame, result will never ever be nil here.
+ ASSERT(result);
+
+ return result;
+}
+
+- (WebScriptObject *)windowScriptObject
+{
+ Frame* coreFrame = core([self mainFrame]);
+ if (!coreFrame)
+ return nil;
+ return coreFrame->windowScriptObject();
+}
+
+// Get the appropriate user-agent string for a particular URL.
+- (NSString *)userAgentForURL:(NSURL *)url
+{
+ return [self _userAgentForURL:KURL([url absoluteURL])];
+}
+
+- (void)setHostWindow:(NSWindow *)hostWindow
+{
+ if (!_private->closed && hostWindow != _private->hostWindow) {
+ [[self mainFrame] _viewWillMoveToHostWindow:hostWindow];
+ if (_private->hostWindow)
+ [[NSNotificationCenter defaultCenter] removeObserver:self name:NSWindowWillCloseNotification object:_private->hostWindow];
+ if (hostWindow)
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(_windowWillClose:) name:NSWindowWillCloseNotification object:hostWindow];
+ [_private->hostWindow release];
+ _private->hostWindow = [hostWindow retain];
+ [[self mainFrame] _viewDidMoveToHostWindow];
+ }
+}
+
+- (NSWindow *)hostWindow
+{
+ return _private->hostWindow;
+}
+
+- (NSView <WebDocumentView> *)documentViewAtWindowPoint:(NSPoint)point
+{
+ return [[self _frameViewAtWindowPoint:point] documentView];
+}
+
+- (NSDictionary *)_elementAtWindowPoint:(NSPoint)windowPoint
+{
+ WebFrameView *frameView = [self _frameViewAtWindowPoint:windowPoint];
+ if (!frameView)
+ return nil;
+ NSView <WebDocumentView> *documentView = [frameView documentView];
+ if ([documentView conformsToProtocol:@protocol(WebDocumentElement)]) {
+ NSPoint point = [documentView convertPoint:windowPoint fromView:nil];
+ return [(NSView <WebDocumentElement> *)documentView elementAtPoint:point];
+ }
+ return [NSDictionary dictionaryWithObject:[frameView webFrame] forKey:WebElementFrameKey];
+}
+
+- (NSDictionary *)elementAtPoint:(NSPoint)point
+{
+ return [self _elementAtWindowPoint:[self convertPoint:point toView:nil]];
+}
+
+// The following 2 internal NSView methods are called on the drag destination by make scrolling while dragging work.
+// Scrolling while dragging will only work if the drag destination is in a scroll view. The WebView is the drag destination.
+// When dragging to a WebView, the document subview should scroll, but it doesn't because it is not the drag destination.
+// Forward these calls to the document subview to make its scroll view scroll.
+- (void)_autoscrollForDraggingInfo:(id)draggingInfo timeDelta:(NSTimeInterval)repeatDelta
+{
+ NSView <WebDocumentView> *documentView = [self documentViewAtWindowPoint:[draggingInfo draggingLocation]];
+ [documentView _autoscrollForDraggingInfo:draggingInfo timeDelta:repeatDelta];
+}
+
+- (BOOL)_shouldAutoscrollForDraggingInfo:(id)draggingInfo
+{
+ NSView <WebDocumentView> *documentView = [self documentViewAtWindowPoint:[draggingInfo draggingLocation]];
+ return [documentView _shouldAutoscrollForDraggingInfo:draggingInfo];
+}
+
+- (NSDragOperation)draggingEntered:(id <NSDraggingInfo>)draggingInfo
+{
+ NSView <WebDocumentView>* view = [self documentViewAtWindowPoint:[draggingInfo draggingLocation]];
+ WebPasteboardHelper helper([view isKindOfClass:[WebHTMLView class]] ? (WebHTMLView*)view : nil);
+ IntPoint client([draggingInfo draggingLocation]);
+ IntPoint global(globalPoint([draggingInfo draggingLocation], [self window]));
+ DragData dragData(draggingInfo, client, global, (DragOperation)[draggingInfo draggingSourceOperationMask], &helper);
+ return core(self)->dragController()->dragEntered(&dragData);
+}
+
+- (NSDragOperation)draggingUpdated:(id <NSDraggingInfo>)draggingInfo
+{
+ NSView <WebDocumentView>* view = [self documentViewAtWindowPoint:[draggingInfo draggingLocation]];
+ WebPasteboardHelper helper([view isKindOfClass:[WebHTMLView class]] ? (WebHTMLView*)view : nil);
+ IntPoint client([draggingInfo draggingLocation]);
+ IntPoint global(globalPoint([draggingInfo draggingLocation], [self window]));
+ DragData dragData(draggingInfo, client, global, (DragOperation)[draggingInfo draggingSourceOperationMask], &helper);
+ return core(self)->dragController()->dragUpdated(&dragData);
+}
+
+- (void)draggingExited:(id <NSDraggingInfo>)draggingInfo
+{
+ NSView <WebDocumentView>* view = [self documentViewAtWindowPoint:[draggingInfo draggingLocation]];
+ WebPasteboardHelper helper([view isKindOfClass:[WebHTMLView class]] ? (WebHTMLView*)view : nil);
+ IntPoint client([draggingInfo draggingLocation]);
+ IntPoint global(globalPoint([draggingInfo draggingLocation], [self window]));
+ DragData dragData(draggingInfo, client, global, (DragOperation)[draggingInfo draggingSourceOperationMask], &helper);
+ core(self)->dragController()->dragExited(&dragData);
+}
+
+- (BOOL)prepareForDragOperation:(id <NSDraggingInfo>)draggingInfo
+{
+ return YES;
+}
+
+- (BOOL)performDragOperation:(id <NSDraggingInfo>)draggingInfo
+{
+ NSView <WebDocumentView>* view = [self documentViewAtWindowPoint:[draggingInfo draggingLocation]];
+ WebPasteboardHelper helper([view isKindOfClass:[WebHTMLView class]]? (WebHTMLView*)view : nil);
+ IntPoint client([draggingInfo draggingLocation]);
+ IntPoint global(globalPoint([draggingInfo draggingLocation], [self window]));
+ DragData dragData(draggingInfo, client, global, (DragOperation)[draggingInfo draggingSourceOperationMask], &helper);
+ return core(self)->dragController()->performDrag(&dragData);
+}
+
+- (NSView *)_hitTest:(NSPoint *)aPoint dragTypes:(NSSet *)types
+{
+ NSView *hitView = [super _hitTest:aPoint dragTypes:types];
+ if (!hitView && [[self superview] mouse:*aPoint inRect:[self frame]]) {
+ return self;
+ } else {
+ return hitView;
+ }
+}
+
+- (BOOL)acceptsFirstResponder
+{
+ return [[[self mainFrame] frameView] acceptsFirstResponder];
+}
+
+- (BOOL)becomeFirstResponder
+{
+ if (_private->becomingFirstResponder) {
+ // Fix for unrepro infinite recursion reported in radar 4448181. If we hit this assert on
+ // a debug build, we should figure out what causes the problem and do a better fix.
+ ASSERT_NOT_REACHED();
+ return NO;
+ }
+
+ // This works together with setNextKeyView to splice the WebView into
+ // the key loop similar to the way NSScrollView does this. Note that
+ // WebFrameView has very similar code.
+ NSWindow *window = [self window];
+ WebFrameView *mainFrameView = [[self mainFrame] frameView];
+
+ NSResponder *previousFirstResponder = [[self window] _oldFirstResponderBeforeBecoming];
+ BOOL fromOutside = ![previousFirstResponder isKindOfClass:[NSView class]] || (![(NSView *)previousFirstResponder isDescendantOf:self] && previousFirstResponder != self);
+
+ if ([window keyViewSelectionDirection] == NSSelectingPrevious) {
+ NSView *previousValidKeyView = [self previousValidKeyView];
+ if ((previousValidKeyView != self) && (previousValidKeyView != mainFrameView)) {
+ _private->becomingFirstResponder = YES;
+ _private->becomingFirstResponderFromOutside = fromOutside;
+ [window makeFirstResponder:previousValidKeyView];
+ _private->becomingFirstResponderFromOutside = NO;
+ _private->becomingFirstResponder = NO;
+ return YES;
+ } else {
+ return NO;
+ }
+ }
+
+ if ([mainFrameView acceptsFirstResponder]) {
+ _private->becomingFirstResponder = YES;
+ _private->becomingFirstResponderFromOutside = fromOutside;
+ [window makeFirstResponder:mainFrameView];
+ _private->becomingFirstResponderFromOutside = NO;
+ _private->becomingFirstResponder = NO;
+ return YES;
+ }
+
+ return NO;
+}
+
+- (NSView *)_webcore_effectiveFirstResponder
+{
+ WebFrameView *frameView = [[self mainFrame] frameView];
+ return frameView ? [frameView _webcore_effectiveFirstResponder] : [super _webcore_effectiveFirstResponder];
+}
+
+- (void)setNextKeyView:(NSView *)aView
+{
+ // This works together with becomeFirstResponder to splice the WebView into
+ // the key loop similar to the way NSScrollView does this. Note that
+ // WebFrameView has very similar code.
+ WebFrameView *mainFrameView = [[self mainFrame] frameView];
+ if (mainFrameView != nil) {
+ [mainFrameView setNextKeyView:aView];
+ } else {
+ [super setNextKeyView:aView];
+ }
+}
+
+static WebFrame *incrementFrame(WebFrame *curr, BOOL forward, BOOL wrapFlag)
+{
+ Frame* coreFrame = core(curr);
+ return kit(forward
+ ? coreFrame->tree()->traverseNextWithWrap(wrapFlag)
+ : coreFrame->tree()->traversePreviousWithWrap(wrapFlag));
+}
+
+- (BOOL)searchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag
+{
+ return [self searchFor:string direction:forward caseSensitive:caseFlag wrap:wrapFlag startInSelection:NO];
+}
+
++ (void)registerViewClass:(Class)viewClass representationClass:(Class)representationClass forMIMEType:(NSString *)MIMEType
+{
+ [[WebFrameView _viewTypesAllowImageTypeOmission:YES] setObject:viewClass forKey:MIMEType];
+ [[WebDataSource _repTypesAllowImageTypeOmission:YES] setObject:representationClass forKey:MIMEType];
+
+ // FIXME: We also need to maintain MIMEType registrations (which can be dynamically changed)
+ // in the WebCore MIMEType registry. For now we're doing this in a safe, limited manner
+ // to fix <rdar://problem/5372989> - a future revamping of the entire system is neccesary for future robustness
+ if ([viewClass class] == [WebHTMLView class])
+ MIMETypeRegistry::getSupportedNonImageMIMETypes().add(MIMEType);
+}
+
+- (void)setGroupName:(NSString *)groupName
+{
+ if (!_private->page)
+ return;
+ _private->page->setGroupName(groupName);
+}
+
+- (NSString *)groupName
+{
+ if (!_private->page)
+ return nil;
+ return _private->page->groupName();
+}
+
+- (double)estimatedProgress
+{
+ if (!_private->page)
+ return 0.0;
+
+ return _private->page->progress()->estimatedProgress();
+}
+
+- (NSArray *)pasteboardTypesForSelection
+{
+ NSView <WebDocumentView> *documentView = [[[self _selectedOrMainFrame] frameView] documentView];
+ if ([documentView conformsToProtocol:@protocol(WebDocumentSelection)]) {
+ return [(NSView <WebDocumentSelection> *)documentView pasteboardTypesForSelection];
+ }
+ return [NSArray array];
+}
+
+- (void)writeSelectionWithPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard
+{
+ WebFrame *frame = [self _selectedOrMainFrame];
+ if (frame && [frame _hasSelection]) {
+ NSView <WebDocumentView> *documentView = [[frame frameView] documentView];
+ if ([documentView conformsToProtocol:@protocol(WebDocumentSelection)])
+ [(NSView <WebDocumentSelection> *)documentView writeSelectionWithPasteboardTypes:types toPasteboard:pasteboard];
+ }
+}
+
+- (NSArray *)pasteboardTypesForElement:(NSDictionary *)element
+{
+ if ([element objectForKey:WebElementImageURLKey] != nil) {
+ return [NSPasteboard _web_writableTypesForImageIncludingArchive:([element objectForKey:WebElementDOMNodeKey] != nil)];
+ } else if ([element objectForKey:WebElementLinkURLKey] != nil) {
+ return [NSPasteboard _web_writableTypesForURL];
+ } else if ([[element objectForKey:WebElementIsSelectedKey] boolValue]) {
+ return [self pasteboardTypesForSelection];
+ }
+ return [NSArray array];
+}
+
+- (void)writeElement:(NSDictionary *)element withPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard
+{
+ if ([element objectForKey:WebElementImageURLKey] != nil) {
+ [self _writeImageForElement:element withPasteboardTypes:types toPasteboard:pasteboard];
+ } else if ([element objectForKey:WebElementLinkURLKey] != nil) {
+ [self _writeLinkElement:element withPasteboardTypes:types toPasteboard:pasteboard];
+ } else if ([[element objectForKey:WebElementIsSelectedKey] boolValue]) {
+ [self writeSelectionWithPasteboardTypes:types toPasteboard:pasteboard];
+ }
+}
+
+- (void)moveDragCaretToPoint:(NSPoint)point
+{
+ if (Page* page = core(self))
+ page->dragController()->placeDragCaret(IntPoint([self convertPoint:point toView:nil]));
+}
+
+- (void)removeDragCaret
+{
+ if (Page* page = core(self))
+ page->dragController()->dragEnded();
+}
+
+- (void)setMainFrameURL:(NSString *)URLString
+{
+ [[self mainFrame] loadRequest: [NSURLRequest requestWithURL: [NSURL _web_URLWithDataAsString: URLString]]];
+}
+
+- (NSString *)mainFrameURL
+{
+ WebDataSource *ds;
+ ds = [[self mainFrame] provisionalDataSource];
+ if (!ds)
+ ds = [[self mainFrame] _dataSource];
+ return [[[ds request] URL] _web_originalDataAsString];
+}
+
+- (BOOL)isLoading
+{
+ LOG (Bindings, "isLoading = %d", (int)[self _isLoading]);
+ return [self _isLoading];
+}
+
+- (NSString *)mainFrameTitle
+{
+ NSString *mainFrameTitle = [[[self mainFrame] _dataSource] pageTitle];
+ return (mainFrameTitle != nil) ? mainFrameTitle : (NSString *)@"";
+}
+
+- (NSImage *)mainFrameIcon
+{
+ return [[WebIconDatabase sharedIconDatabase] iconForURL:[[[[self mainFrame] _dataSource] _URL] _web_originalDataAsString] withSize:WebIconSmallSize];
+}
+
+- (DOMDocument *)mainFrameDocument
+{
+ // only return the actual value if the state we're in gives NSTreeController
+ // enough time to release its observers on the old model
+ if (_private->mainFrameDocumentReady)
+ return [[self mainFrame] DOMDocument];
+ return nil;
+}
+
+- (void)setDrawsBackground:(BOOL)drawsBackground
+{
+ if (_private->drawsBackground == drawsBackground)
+ return;
+ _private->drawsBackground = drawsBackground;
+ [[self mainFrame] _updateBackground];
+}
+
+- (BOOL)drawsBackground
+{
+ return _private->drawsBackground;
+}
+
+@end
+
+@implementation WebView (WebIBActions)
+
+- (IBAction)takeStringURLFrom: sender
+{
+ NSString *URLString = [sender stringValue];
+
+ [[self mainFrame] loadRequest: [NSURLRequest requestWithURL: [NSURL _web_URLWithDataAsString: URLString]]];
+}
+
+- (BOOL)canGoBack
+{
+ if (!_private->page)
+ return NO;
+
+ return !!_private->page->backForwardList()->backItem();
+}
+
+- (BOOL)canGoForward
+{
+ if (!_private->page)
+ return NO;
+
+ return !!_private->page->backForwardList()->forwardItem();
+}
+
+- (IBAction)goBack:(id)sender
+{
+ [self goBack];
+}
+
+- (IBAction)goForward:(id)sender
+{
+ [self goForward];
+}
+
+- (IBAction)stopLoading:(id)sender
+{
+ [[self mainFrame] stopLoading];
+}
+
+- (IBAction)reload:(id)sender
+{
+ [[self mainFrame] reload];
+}
+
+#define MinimumTextSizeMultiplier 0.5f
+#define MaximumTextSizeMultiplier 3.0f
+#define TextSizeMultiplierRatio 1.2f
+
+- (BOOL)canMakeTextSmaller
+{
+ BOOL canShrinkMore = _private->textSizeMultiplier/TextSizeMultiplierRatio > MinimumTextSizeMultiplier;
+ return [self _performTextSizingSelector:(SEL)0 withObject:nil onTrackingDocs:canShrinkMore selForNonTrackingDocs:@selector(_canMakeTextSmaller) newScaleFactor:0];
+}
+
+- (BOOL)canMakeTextLarger
+{
+ BOOL canGrowMore = _private->textSizeMultiplier*TextSizeMultiplierRatio < MaximumTextSizeMultiplier;
+ return [self _performTextSizingSelector:(SEL)0 withObject:nil onTrackingDocs:canGrowMore selForNonTrackingDocs:@selector(_canMakeTextLarger) newScaleFactor:0];
+}
+
+- (IBAction)makeTextSmaller:(id)sender
+{
+ float newScale = _private->textSizeMultiplier / TextSizeMultiplierRatio;
+ BOOL canShrinkMore = newScale > MinimumTextSizeMultiplier;
+ [self _performTextSizingSelector:@selector(_makeTextSmaller:) withObject:sender onTrackingDocs:canShrinkMore selForNonTrackingDocs:@selector(_canMakeTextSmaller) newScaleFactor:newScale];
+}
+
+- (IBAction)makeTextLarger:(id)sender
+{
+ float newScale = _private->textSizeMultiplier*TextSizeMultiplierRatio;
+ BOOL canGrowMore = newScale < MaximumTextSizeMultiplier;
+ [self _performTextSizingSelector:@selector(_makeTextLarger:) withObject:sender onTrackingDocs:canGrowMore selForNonTrackingDocs:@selector(_canMakeTextLarger) newScaleFactor:newScale];
+}
+
+- (IBAction)toggleSmartInsertDelete:(id)sender
+{
+ [self setSmartInsertDeleteEnabled:![self smartInsertDeleteEnabled]];
+}
+
+- (IBAction)toggleContinuousSpellChecking:(id)sender
+{
+ [self setContinuousSpellCheckingEnabled:![self isContinuousSpellCheckingEnabled]];
+}
+
+- (BOOL)_responderValidateUserInterfaceItem:(id <NSValidatedUserInterfaceItem>)item
+{
+ id responder = [self _responderForResponderOperations];
+ if (responder != self && [responder respondsToSelector:[item action]]) {
+ if ([responder respondsToSelector:@selector(validateUserInterfaceItemWithoutDelegate:)])
+ return [responder validateUserInterfaceItemWithoutDelegate:item];
+ if ([responder respondsToSelector:@selector(validateUserInterfaceItem:)])
+ return [responder validateUserInterfaceItem:item];
+ return YES;
+ }
+ return NO;
+}
+
+- (BOOL)canMakeTextStandardSize
+{
+ BOOL notAlreadyStandard = _private->textSizeMultiplier != 1.0f;
+ return [self _performTextSizingSelector:(SEL)0 withObject:nil onTrackingDocs:notAlreadyStandard selForNonTrackingDocs:@selector(_canMakeTextStandardSize) newScaleFactor:0.0f];
+}
+
+- (IBAction)makeTextStandardSize:(id)sender
+{
+ BOOL notAlreadyStandard = _private->textSizeMultiplier != 1.0f;
+ [self _performTextSizingSelector:@selector(_makeTextStandardSize:) withObject:sender onTrackingDocs:notAlreadyStandard selForNonTrackingDocs:@selector(_canMakeTextStandardSize) newScaleFactor:1.0f];
+}
+
+#define VALIDATE(name) \
+ else if (action == @selector(name:)) { return [self _responderValidateUserInterfaceItem:item]; }
+
+- (BOOL)validateUserInterfaceItemWithoutDelegate:(id <NSValidatedUserInterfaceItem>)item
+{
+ SEL action = [item action];
+
+ if (action == @selector(goBack:)) {
+ return [self canGoBack];
+ } else if (action == @selector(goForward:)) {
+ return [self canGoForward];
+ } else if (action == @selector(makeTextLarger:)) {
+ return [self canMakeTextLarger];
+ } else if (action == @selector(makeTextSmaller:)) {
+ return [self canMakeTextSmaller];
+ } else if (action == @selector(makeTextStandardSize:)) {
+ return [self canMakeTextStandardSize];
+ } else if (action == @selector(reload:)) {
+ return [[self mainFrame] _dataSource] != nil;
+ } else if (action == @selector(stopLoading:)) {
+ return [self _isLoading];
+ } else if (action == @selector(toggleContinuousSpellChecking:)) {
+ BOOL checkMark = NO;
+ BOOL retVal = NO;
+ if ([self _continuousCheckingAllowed]) {
+ checkMark = [self isContinuousSpellCheckingEnabled];
+ retVal = YES;
+ }
+ if ([(NSObject *)item isKindOfClass:[NSMenuItem class]]) {
+ NSMenuItem *menuItem = (NSMenuItem *)item;
+ [menuItem setState:checkMark ? NSOnState : NSOffState];
+ }
+ return retVal;
+#ifndef BUILDING_ON_TIGER
+ } else if (action == @selector(toggleGrammarChecking:)) {
+ BOOL checkMark = [self isGrammarCheckingEnabled];
+ if ([(NSObject *)item isKindOfClass:[NSMenuItem class]]) {
+ NSMenuItem *menuItem = (NSMenuItem *)item;
+ [menuItem setState:checkMark ? NSOnState : NSOffState];
+ }
+ return YES;
+#endif
+ }
+ FOR_EACH_RESPONDER_SELECTOR(VALIDATE)
+
+ return YES;
+}
+
+- (BOOL)validateUserInterfaceItem:(id <NSValidatedUserInterfaceItem>)item
+{
+ BOOL result = [self validateUserInterfaceItemWithoutDelegate:item];
+ return CallUIDelegateReturningBoolean(result, self, @selector(webView:validateUserInterfaceItem:defaultValidation:), item, result);
+}
+
+@end
+
+@implementation WebView (WebPendingPublic)
+
+- (BOOL)searchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag startInSelection:(BOOL)startInSelection
+{
+ if (_private->closed)
+ return NO;
+
+ // Get the frame holding the selection, or start with the main frame
+ WebFrame *startFrame = [self _selectedOrMainFrame];
+
+ // Search the first frame, then all the other frames, in order
+ NSView <WebDocumentSearching> *startSearchView = nil;
+ WebFrame *frame = startFrame;
+ do {
+ WebFrame *nextFrame = incrementFrame(frame, forward, wrapFlag);
+
+ BOOL onlyOneFrame = (frame == nextFrame);
+ ASSERT(!onlyOneFrame || frame == startFrame);
+
+ id <WebDocumentView> view = [[frame frameView] documentView];
+ if ([view conformsToProtocol:@protocol(WebDocumentSearching)]) {
+ NSView <WebDocumentSearching> *searchView = (NSView <WebDocumentSearching> *)view;
+
+ if (frame == startFrame)
+ startSearchView = searchView;
+
+ BOOL foundString;
+ // In some cases we have to search some content twice; see comment later in this method.
+ // We can avoid ever doing this in the common one-frame case by passing YES for wrapFlag
+ // here, and then bailing out before we get to the code that would search again in the
+ // same content.
+ BOOL wrapOnThisPass = wrapFlag && onlyOneFrame;
+ if ([searchView conformsToProtocol:@protocol(WebDocumentIncrementalSearching)])
+ foundString = [(NSView <WebDocumentIncrementalSearching> *)searchView searchFor:string direction:forward caseSensitive:caseFlag wrap:wrapOnThisPass startInSelection:startInSelection];
+ else
+ foundString = [searchView searchFor:string direction:forward caseSensitive:caseFlag wrap:wrapOnThisPass];
+
+ if (foundString) {
+ if (frame != startFrame)
+ [startFrame _clearSelection];
+ [[self window] makeFirstResponder:searchView];
+ return YES;
+ }
+
+ if (onlyOneFrame)
+ return NO;
+ }
+ frame = nextFrame;
+ } while (frame && frame != startFrame);
+
+ // If there are multiple frames and wrapFlag is true and we've visited each one without finding a result, we still need to search in the
+ // first-searched frame up to the selection. However, the API doesn't provide a way to search only up to a particular point. The only
+ // way to make sure the entire frame is searched is to pass YES for the wrapFlag. When there are no matches, this will search again
+ // some content that we already searched on the first pass. In the worst case, we could search the entire contents of this frame twice.
+ // To fix this, we'd need to add a mechanism to specify a range in which to search.
+ if (wrapFlag && startSearchView) {
+ BOOL foundString;
+ if ([startSearchView conformsToProtocol:@protocol(WebDocumentIncrementalSearching)])
+ foundString = [(NSView <WebDocumentIncrementalSearching> *)startSearchView searchFor:string direction:forward caseSensitive:caseFlag wrap:YES startInSelection:startInSelection];
+ else
+ foundString = [startSearchView searchFor:string direction:forward caseSensitive:caseFlag wrap:YES];
+ if (foundString) {
+ [[self window] makeFirstResponder:startSearchView];
+ return YES;
+ }
+ }
+ return NO;
+}
+
+- (void)setHoverFeedbackSuspended:(BOOL)newValue
+{
+ if (_private->hoverFeedbackSuspended == newValue)
+ return;
+
+ _private->hoverFeedbackSuspended = newValue;
+ id <WebDocumentView> documentView = [[[self mainFrame] frameView] documentView];
+ // FIXME: in a perfect world we'd do this in a general way that worked with any document view,
+ // such as by calling a protocol method or using respondsToSelector or sending a notification.
+ // But until there is any need for these more general solutions, we'll just hardwire it to work
+ // with WebHTMLView.
+ // Note that _hoverFeedbackSuspendedChanged needs to be called only on the main WebHTMLView, not
+ // on each subframe separately.
+ if ([documentView isKindOfClass:[WebHTMLView class]])
+ [(WebHTMLView *)documentView _hoverFeedbackSuspendedChanged];
+}
+
+- (BOOL)isHoverFeedbackSuspended
+{
+ return _private->hoverFeedbackSuspended;
+}
+
+- (void)setMainFrameDocumentReady:(BOOL)mainFrameDocumentReady
+{
+ // by setting this to NO, calls to mainFrameDocument are forced to return nil
+ // setting this to YES lets it return the actual DOMDocument value
+ // we use this to tell NSTreeController to reset its observers and clear its state
+ if (_private->mainFrameDocumentReady == mainFrameDocumentReady)
+ return;
+ [self _willChangeValueForKey:_WebMainFrameDocumentKey];
+ _private->mainFrameDocumentReady = mainFrameDocumentReady;
+ [self _didChangeValueForKey:_WebMainFrameDocumentKey];
+ // this will cause observers to call mainFrameDocument where this flag will be checked
+}
+
+// This method name is used by Mail on Tiger (but not post-Tiger), so we shouldn't delete it
+// until the day comes when we're no longer supporting Mail on Tiger.
+- (WebFrame *)_frameForCurrentSelection
+{
+ return [self _selectedOrMainFrame];
+}
+
+- (void)setTabKeyCyclesThroughElements:(BOOL)cyclesElements
+{
+ _private->tabKeyCyclesThroughElementsChanged = YES;
+ if (_private->page)
+ _private->page->setTabKeyCyclesThroughElements(cyclesElements);
+}
+
+- (BOOL)tabKeyCyclesThroughElements
+{
+ return _private->page && _private->page->tabKeyCyclesThroughElements();
+}
+
+- (void)setScriptDebugDelegate:(id)delegate
+{
+ _private->scriptDebugDelegate = delegate;
+ [_private->scriptDebugDelegateForwarder release];
+ _private->scriptDebugDelegateForwarder = nil;
+ if (delegate)
+ [self _attachScriptDebuggerToAllFrames];
+ else
+ [self _detachScriptDebuggerFromAllFrames];
+}
+
+- (id)scriptDebugDelegate
+{
+ return _private->scriptDebugDelegate;
+}
+
+- (BOOL)shouldClose
+{
+ Frame* coreFrame = core([self mainFrame]);
+ if (!coreFrame)
+ return YES;
+ return coreFrame->shouldClose();
+}
+
+- (NSAppleEventDescriptor *)aeDescByEvaluatingJavaScriptFromString:(NSString *)script
+{
+ return [[[self mainFrame] _bridge] aeDescByEvaluatingJavaScriptFromString:script];
+}
+
+- (BOOL)canMarkAllTextMatches
+{
+ WebFrame *frame = [self mainFrame];
+ do {
+ id <WebDocumentView> view = [[frame frameView] documentView];
+ if (view && ![view conformsToProtocol:@protocol(WebMultipleTextMatches)])
+ return NO;
+
+ frame = incrementFrame(frame, YES, NO);
+ } while (frame);
+
+ return YES;
+}
+
+- (NSUInteger)markAllMatchesForText:(NSString *)string caseSensitive:(BOOL)caseFlag highlight:(BOOL)highlight limit:(NSUInteger)limit
+{
+ WebFrame *frame = [self mainFrame];
+ unsigned matchCount = 0;
+ do {
+ id <WebDocumentView> view = [[frame frameView] documentView];
+ if ([view conformsToProtocol:@protocol(WebMultipleTextMatches)]) {
+ [(NSView <WebMultipleTextMatches>*)view setMarkedTextMatchesAreHighlighted:highlight];
+
+ ASSERT(limit == 0 || matchCount < limit);
+ matchCount += [(NSView <WebMultipleTextMatches>*)view markAllMatchesForText:string caseSensitive:caseFlag limit:limit == 0 ? 0 : limit - matchCount];
+
+ // Stop looking if we've reached the limit. A limit of 0 means no limit.
+ if (limit > 0 && matchCount >= limit)
+ break;
+ }
+
+ frame = incrementFrame(frame, YES, NO);
+ } while (frame);
+
+ return matchCount;
+}
+
+- (void)unmarkAllTextMatches
+{
+ WebFrame *frame = [self mainFrame];
+ do {
+ id <WebDocumentView> view = [[frame frameView] documentView];
+ if ([view conformsToProtocol:@protocol(WebMultipleTextMatches)])
+ [(NSView <WebMultipleTextMatches>*)view unmarkAllTextMatches];
+
+ frame = incrementFrame(frame, YES, NO);
+ } while (frame);
+}
+
+- (NSArray *)rectsForTextMatches
+{
+ NSMutableArray *result = [NSMutableArray array];
+ WebFrame *frame = [self mainFrame];
+ do {
+ id <WebDocumentView> view = [[frame frameView] documentView];
+ if ([view conformsToProtocol:@protocol(WebMultipleTextMatches)]) {
+ NSView <WebMultipleTextMatches> *documentView = (NSView <WebMultipleTextMatches> *)view;
+ NSRect documentViewVisibleRect = [documentView visibleRect];
+ NSArray *originalRects = [documentView rectsForTextMatches];
+ unsigned rectCount = [originalRects count];
+ unsigned rectIndex;
+ NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
+ for (rectIndex = 0; rectIndex < rectCount; ++rectIndex) {
+ NSRect r = [[originalRects objectAtIndex:rectIndex] rectValue];
+ // Clip rect to document view's visible rect so rect is confined to subframe
+ r = NSIntersectionRect(r, documentViewVisibleRect);
+ if (NSIsEmptyRect(r))
+ continue;
+
+ // Convert rect to our coordinate system
+ r = [documentView convertRect:r toView:self];
+ [result addObject:[NSValue valueWithRect:r]];
+ if (rectIndex % 10 == 0) {
+ [pool drain];
+ pool = [[NSAutoreleasePool alloc] init];
+ }
+ }
+ [pool drain];
+ }
+
+ frame = incrementFrame(frame, YES, NO);
+ } while (frame);
+
+ return result;
+}
+
+- (void)scrollDOMRangeToVisible:(DOMRange *)range
+{
+ [[[range startContainer] _bridge] scrollDOMRangeToVisible:range];
+}
+
+- (BOOL)allowsUndo
+{
+ return _private->allowsUndo;
+}
+
+- (void)setAllowsUndo:(BOOL)flag
+{
+ _private->allowsUndo = flag;
+}
+
+@end
+
+@implementation WebView (WebViewPrintingPrivate)
+
+- (float)_headerHeight
+{
+ return CallUIDelegateReturningFloat(self, @selector(webViewHeaderHeight:));
+}
+
+- (float)_footerHeight
+{
+ return CallUIDelegateReturningFloat(self, @selector(webViewFooterHeight:));
+}
+
+- (void)_drawHeaderInRect:(NSRect)rect
+{
+#ifdef DEBUG_HEADER_AND_FOOTER
+ NSGraphicsContext *currentContext = [NSGraphicsContext currentContext];
+ [currentContext saveGraphicsState];
+ [[NSColor yellowColor] set];
+ NSRectFill(rect);
+ [currentContext restoreGraphicsState];
+#endif
+
+ SEL selector = @selector(webView:drawHeaderInRect:);
+ if (![_private->UIDelegate respondsToSelector:selector])
+ return;
+
+ NSGraphicsContext *currentContext = [NSGraphicsContext currentContext];
+ [currentContext saveGraphicsState];
+
+ NSRectClip(rect);
+ CallUIDelegate(self, selector, rect);
+
+ [currentContext restoreGraphicsState];
+}
+
+- (void)_drawFooterInRect:(NSRect)rect
+{
+#ifdef DEBUG_HEADER_AND_FOOTER
+ NSGraphicsContext *currentContext = [NSGraphicsContext currentContext];
+ [currentContext saveGraphicsState];
+ [[NSColor cyanColor] set];
+ NSRectFill(rect);
+ [currentContext restoreGraphicsState];
+#endif
+
+ SEL selector = @selector(webView:drawFooterInRect:);
+ if (![_private->UIDelegate respondsToSelector:selector])
+ return;
+
+ NSGraphicsContext *currentContext = [NSGraphicsContext currentContext];
+ [currentContext saveGraphicsState];
+
+ NSRectClip(rect);
+ CallUIDelegate(self, selector, rect);
+
+ [currentContext restoreGraphicsState];
+}
+
+- (void)_adjustPrintingMarginsForHeaderAndFooter
+{
+ NSPrintOperation *op = [NSPrintOperation currentOperation];
+ NSPrintInfo *info = [op printInfo];
+ NSMutableDictionary *infoDictionary = [info dictionary];
+
+ // We need to modify the top and bottom margins in the NSPrintInfo to account for the space needed by the
+ // header and footer. Because this method can be called more than once on the same NSPrintInfo (see 5038087),
+ // we stash away the unmodified top and bottom margins the first time this method is called, and we read from
+ // those stashed-away values on subsequent calls.
+ float originalTopMargin;
+ float originalBottomMargin;
+ NSNumber *originalTopMarginNumber = [infoDictionary objectForKey:WebKitOriginalTopPrintingMarginKey];
+ if (!originalTopMarginNumber) {
+ ASSERT(![infoDictionary objectForKey:WebKitOriginalBottomPrintingMarginKey]);
+ originalTopMargin = [info topMargin];
+ originalBottomMargin = [info bottomMargin];
+ [infoDictionary setObject:[NSNumber numberWithFloat:originalTopMargin] forKey:WebKitOriginalTopPrintingMarginKey];
+ [infoDictionary setObject:[NSNumber numberWithFloat:originalBottomMargin] forKey:WebKitOriginalBottomPrintingMarginKey];
+ } else {
+ ASSERT([originalTopMarginNumber isKindOfClass:[NSNumber class]]);
+ ASSERT([[infoDictionary objectForKey:WebKitOriginalBottomPrintingMarginKey] isKindOfClass:[NSNumber class]]);
+ originalTopMargin = [originalTopMarginNumber floatValue];
+ originalBottomMargin = [[infoDictionary objectForKey:WebKitOriginalBottomPrintingMarginKey] floatValue];
+ }
+
+ float scale = [op _web_pageSetupScaleFactor];
+ [info setTopMargin:originalTopMargin + [self _headerHeight] * scale];
+ [info setBottomMargin:originalBottomMargin + [self _footerHeight] * scale];
+}
+
+- (void)_drawHeaderAndFooter
+{
+ // The header and footer rect height scales with the page, but the width is always
+ // all the way across the printed page (inset by printing margins).
+ NSPrintOperation *op = [NSPrintOperation currentOperation];
+ float scale = [op _web_pageSetupScaleFactor];
+ NSPrintInfo *printInfo = [op printInfo];
+ NSSize paperSize = [printInfo paperSize];
+ float headerFooterLeft = [printInfo leftMargin]/scale;
+ float headerFooterWidth = (paperSize.width - ([printInfo leftMargin] + [printInfo rightMargin]))/scale;
+ NSRect footerRect = NSMakeRect(headerFooterLeft, [printInfo bottomMargin]/scale - [self _footerHeight] ,
+ headerFooterWidth, [self _footerHeight]);
+ NSRect headerRect = NSMakeRect(headerFooterLeft, (paperSize.height - [printInfo topMargin])/scale,
+ headerFooterWidth, [self _headerHeight]);
+
+ [self _drawHeaderInRect:headerRect];
+ [self _drawFooterInRect:footerRect];
+}
+@end
+
+@implementation WebView (WebDebugBinding)
+
+- (void)addObserver:(NSObject *)anObserver forKeyPath:(NSString *)keyPath options:(NSKeyValueObservingOptions)options context:(void *)context
+{
+ LOG (Bindings, "addObserver:%p forKeyPath:%@ options:%x context:%p", anObserver, keyPath, options, context);
+ [super addObserver:anObserver forKeyPath:keyPath options:options context:context];
+}
+
+- (void)removeObserver:(NSObject *)anObserver forKeyPath:(NSString *)keyPath
+{
+ LOG (Bindings, "removeObserver:%p forKeyPath:%@", anObserver, keyPath);
+ [super removeObserver:anObserver forKeyPath:keyPath];
+}
+
+@end
+
+//==========================================================================================
+// Editing
+
+@implementation WebView (WebViewCSS)
+
+- (DOMCSSStyleDeclaration *)computedStyleForElement:(DOMElement *)element pseudoElement:(NSString *)pseudoElement
+{
+ // FIXME: is this the best level for this conversion?
+ if (pseudoElement == nil)
+ pseudoElement = @"";
+
+ return [[element ownerDocument] getComputedStyle:element pseudoElement:pseudoElement];
+}
+
+@end
+
+@implementation WebView (WebViewEditing)
+
+- (DOMRange *)editableDOMRangeForPoint:(NSPoint)point
+{
+ Page* page = core(self);
+ if (!page)
+ return nil;
+ return kit(page->mainFrame()->editor()->rangeForPoint(IntPoint([self convertPoint:point toView:nil])).get());
+}
+
+- (BOOL)_shouldChangeSelectedDOMRange:(DOMRange *)currentRange toDOMRange:(DOMRange *)proposedRange affinity:(NSSelectionAffinity)selectionAffinity stillSelecting:(BOOL)flag;
+{
+ // FIXME: This quirk is needed due to <rdar://problem/4985321> - We can phase it out once Aperture can adopt the new behavior on their end
+ if (!WebKitLinkedOnOrAfter(WEBKIT_FIRST_VERSION_WITHOUT_APERTURE_QUIRK) && [[[NSBundle mainBundle] bundleIdentifier] isEqualToString:@"com.apple.Aperture"])
+ return YES;
+ return [[self _editingDelegateForwarder] webView:self shouldChangeSelectedDOMRange:currentRange toDOMRange:proposedRange affinity:selectionAffinity stillSelecting:flag];
+}
+
+- (BOOL)maintainsInactiveSelection
+{
+ return NO;
+}
+
+- (void)setSelectedDOMRange:(DOMRange *)range affinity:(NSSelectionAffinity)selectionAffinity
+{
+ Frame* coreFrame = core([self _selectedOrMainFrame]);
+ if (!coreFrame)
+ return;
+
+ if (range == nil)
+ coreFrame->selectionController()->clear();
+ else {
+ // Derive the frame to use from the range passed in.
+ // Using _bridgeForSelectedOrMainFrame could give us a different document than
+ // the one the range uses.
+ coreFrame = core([range startContainer])->document()->frame();
+ if (!coreFrame)
+ return;
+
+ coreFrame->selectionController()->setSelectedRange([range _range], core(selectionAffinity), true);
+ }
+}
+
+- (DOMRange *)selectedDOMRange
+{
+ Frame* coreFrame = core([self _selectedOrMainFrame]);
+ if (!coreFrame)
+ return nil;
+ return kit(coreFrame->selectionController()->toRange().get());
+}
+
+- (NSSelectionAffinity)selectionAffinity
+{
+ Frame* coreFrame = core([self _selectedOrMainFrame]);
+ if (!coreFrame)
+ return NSSelectionAffinityDownstream;
+ return kit(coreFrame->selectionController()->affinity());
+}
+
+- (void)setEditable:(BOOL)flag
+{
+ if (_private->editable != flag) {
+ _private->editable = flag;
+ if (!_private->tabKeyCyclesThroughElementsChanged && _private->page)
+ _private->page->setTabKeyCyclesThroughElements(!flag);
+ Frame* mainFrame = [[[self mainFrame] _bridge] _frame];
+ if (mainFrame) {
+ if (flag) {
+ mainFrame->applyEditingStyleToBodyElement();
+ // If the WebView is made editable and the selection is empty, set it to something.
+ if (![self selectedDOMRange])
+ mainFrame->setSelectionFromNone();
+ } else
+ mainFrame->removeEditingStyleFromBodyElement();
+ }
+ }
+}
+
+- (BOOL)isEditable
+{
+ return _private->editable;
+}
+
+- (void)setTypingStyle:(DOMCSSStyleDeclaration *)style
+{
+ // We don't know enough at thls level to pass in a relevant WebUndoAction; we'd have to
+ // change the API to allow this.
+ [[self _bridgeForSelectedOrMainFrame] setTypingStyle:style withUndoAction:EditActionUnspecified];
+}
+
+- (DOMCSSStyleDeclaration *)typingStyle
+{
+ return [[self _bridgeForSelectedOrMainFrame] typingStyle];
+}
+
+- (void)setSmartInsertDeleteEnabled:(BOOL)flag
+{
+ _private->smartInsertDeleteEnabled = flag;
+}
+
+- (BOOL)smartInsertDeleteEnabled
+{
+ return _private->smartInsertDeleteEnabled;
+}
+
+- (void)setContinuousSpellCheckingEnabled:(BOOL)flag
+{
+ if (continuousSpellCheckingEnabled != flag) {
+ continuousSpellCheckingEnabled = flag;
+ [[NSUserDefaults standardUserDefaults] setBool:continuousSpellCheckingEnabled forKey:WebContinuousSpellCheckingEnabled];
+ }
+
+ if ([self isContinuousSpellCheckingEnabled]) {
+ [[self class] _preflightSpellChecker];
+ } else {
+ [[self mainFrame] _unmarkAllMisspellings];
+ }
+}
+
+- (BOOL)isContinuousSpellCheckingEnabled
+{
+ return (continuousSpellCheckingEnabled && [self _continuousCheckingAllowed]);
+}
+
+- (NSInteger)spellCheckerDocumentTag
+{
+ if (!_private->hasSpellCheckerDocumentTag) {
+ _private->spellCheckerDocumentTag = [NSSpellChecker uniqueSpellDocumentTag];
+ _private->hasSpellCheckerDocumentTag = YES;
+ }
+ return _private->spellCheckerDocumentTag;
+}
+
+- (NSUndoManager *)undoManager
+{
+ if (!_private->allowsUndo)
+ return nil;
+
+ NSUndoManager *undoManager = [[self _editingDelegateForwarder] undoManagerForWebView:self];
+ if (undoManager)
+ return undoManager;
+
+ return [super undoManager];
+}
+
+- (void)registerForEditingDelegateNotification:(NSString *)name selector:(SEL)selector
+{
+ NSNotificationCenter *defaultCenter = [NSNotificationCenter defaultCenter];
+ if ([_private->editingDelegate respondsToSelector:selector])
+ [defaultCenter addObserver:_private->editingDelegate selector:selector name:name object:self];
+}
+
+- (void)setEditingDelegate:(id)delegate
+{
+ if (_private->editingDelegate == delegate)
+ return;
+
+ NSNotificationCenter *defaultCenter = [NSNotificationCenter defaultCenter];
+
+ // remove notifications from current delegate
+ [defaultCenter removeObserver:_private->editingDelegate name:WebViewDidBeginEditingNotification object:self];
+ [defaultCenter removeObserver:_private->editingDelegate name:WebViewDidChangeNotification object:self];
+ [defaultCenter removeObserver:_private->editingDelegate name:WebViewDidEndEditingNotification object:self];
+ [defaultCenter removeObserver:_private->editingDelegate name:WebViewDidChangeTypingStyleNotification object:self];
+ [defaultCenter removeObserver:_private->editingDelegate name:WebViewDidChangeSelectionNotification object:self];
+
+ _private->editingDelegate = delegate;
+ [_private->editingDelegateForwarder release];
+ _private->editingDelegateForwarder = nil;
+
+ // add notifications for new delegate
+ [self registerForEditingDelegateNotification:WebViewDidBeginEditingNotification selector:@selector(webViewDidBeginEditing:)];
+ [self registerForEditingDelegateNotification:WebViewDidChangeNotification selector:@selector(webViewDidChange:)];
+ [self registerForEditingDelegateNotification:WebViewDidEndEditingNotification selector:@selector(webViewDidEndEditing:)];
+ [self registerForEditingDelegateNotification:WebViewDidChangeTypingStyleNotification selector:@selector(webViewDidChangeTypingStyle:)];
+ [self registerForEditingDelegateNotification:WebViewDidChangeSelectionNotification selector:@selector(webViewDidChangeSelection:)];
+}
+
+- (id)editingDelegate
+{
+ return _private->editingDelegate;
+}
+
+- (DOMCSSStyleDeclaration *)styleDeclarationWithText:(NSString *)text
+{
+ // FIXME: Should this really be attached to the document with the current selection?
+ DOMCSSStyleDeclaration *decl = [[[self _selectedOrMainFrame] DOMDocument] createCSSStyleDeclaration];
+ [decl setCssText:text];
+ return decl;
+}
+
+@end
+
+@implementation WebView (WebViewGrammarChecking)
+
+// FIXME: This method should be merged into WebViewEditing when we're not in API freeze
+- (BOOL)isGrammarCheckingEnabled
+{
+#ifdef BUILDING_ON_TIGER
+ return NO;
+#else
+ return grammarCheckingEnabled;
+#endif
+}
+
+#ifndef BUILDING_ON_TIGER
+// FIXME: This method should be merged into WebViewEditing when we're not in API freeze
+- (void)setGrammarCheckingEnabled:(BOOL)flag
+{
+ if (grammarCheckingEnabled == flag)
+ return;
+
+ grammarCheckingEnabled = flag;
+ [[NSUserDefaults standardUserDefaults] setBool:grammarCheckingEnabled forKey:WebGrammarCheckingEnabled];
+
+ // FIXME 4811447: workaround for lack of API
+ NSSpellChecker *spellChecker = [NSSpellChecker sharedSpellChecker];
+ if ([spellChecker respondsToSelector:@selector(_updateGrammar)])
+ [spellChecker performSelector:@selector(_updateGrammar)];
+
+ // We call _preflightSpellChecker when turning continuous spell checking on, but we don't need to do that here
+ // because grammar checking only occurs on code paths that already preflight spell checking appropriately.
+
+ if (![self isGrammarCheckingEnabled])
+ [[self mainFrame] _unmarkAllBadGrammar];
+}
+
+// FIXME: This method should be merged into WebIBActions when we're not in API freeze
+- (void)toggleGrammarChecking:(id)sender
+{
+ [self setGrammarCheckingEnabled:![self isGrammarCheckingEnabled]];
+}
+#endif
+
+@end
+
+@implementation WebView (WebViewUndoableEditing)
+
+- (void)replaceSelectionWithNode:(DOMNode *)node
+{
+ [[self _bridgeForSelectedOrMainFrame] replaceSelectionWithNode:node selectReplacement:YES smartReplace:NO matchStyle:NO];
+}
+
+- (void)replaceSelectionWithText:(NSString *)text
+{
+ [[self _bridgeForSelectedOrMainFrame] replaceSelectionWithText:text selectReplacement:YES smartReplace:NO];
+}
+
+- (void)replaceSelectionWithMarkupString:(NSString *)markupString
+{
+ [[self _bridgeForSelectedOrMainFrame] replaceSelectionWithMarkupString:markupString baseURLString:nil selectReplacement:YES smartReplace:NO];
+}
+
+- (void)replaceSelectionWithArchive:(WebArchive *)archive
+{
+ [[[[self _bridgeForSelectedOrMainFrame] webFrame] _dataSource] _replaceSelectionWithArchive:archive selectReplacement:YES];
+}
+
+- (void)deleteSelection
+{
+ WebFrame *webFrame = [self _selectedOrMainFrame];
+ Frame* coreFrame = core(webFrame);
+ if (coreFrame)
+ coreFrame->editor()->deleteSelectionWithSmartDelete([(WebHTMLView *)[[webFrame frameView] documentView] _canSmartCopyOrDelete]);
+}
+
+- (void)applyStyle:(DOMCSSStyleDeclaration *)style
+{
+ // We don't know enough at thls level to pass in a relevant WebUndoAction; we'd have to
+ // change the API to allow this.
+ WebFrame *webFrame = [self _selectedOrMainFrame];
+ Frame* coreFrame = core(webFrame);
+ if (coreFrame)
+ coreFrame->editor()->applyStyle(core(style));
+}
+
+@end
+
+@implementation WebView (WebViewEditingActions)
+
+- (void)_performResponderOperation:(SEL)selector with:(id)parameter
+{
+ static BOOL reentered = NO;
+ if (reentered) {
+ [[self nextResponder] tryToPerform:selector with:parameter];
+ return;
+ }
+
+ // There are two possibilities here.
+ //
+ // One is that WebView has been called in its role as part of the responder chain.
+ // In that case, it's fine to call the first responder and end up calling down the
+ // responder chain again. Later we will return here with reentered = YES and continue
+ // past the WebView.
+ //
+ // The other is that we are being called directly, in which case we want to pass the
+ // selector down to the view inside us that can handle it, and continue down the
+ // responder chain as usual.
+
+ // Pass this selector down to the first responder.
+ NSResponder *responder = [self _responderForResponderOperations];
+ reentered = YES;
+ [responder tryToPerform:selector with:parameter];
+ reentered = NO;
+}
+
+#define FORWARD(name) \
+ - (void)name:(id)sender { [self _performResponderOperation:_cmd with:sender]; }
+
+FOR_EACH_RESPONDER_SELECTOR(FORWARD)
+
+- (void)insertText:(NSString *)text
+{
+ [self _performResponderOperation:_cmd with:text];
+}
+
+@end
+
+@implementation WebView (WebViewEditingInMail)
+
+- (void)_insertNewlineInQuotedContent;
+{
+ [[self _bridgeForSelectedOrMainFrame] insertParagraphSeparatorInQuotedContent];
+}
+
+- (void)_replaceSelectionWithNode:(DOMNode *)node matchStyle:(BOOL)matchStyle
+{
+ [[self _bridgeForSelectedOrMainFrame] replaceSelectionWithNode:node selectReplacement:YES smartReplace:NO matchStyle:matchStyle];
+}
+
+@end
+
+static WebFrameView *containingFrameView(NSView *view)
+{
+ while (view && ![view isKindOfClass:[WebFrameView class]])
+ view = [view superview];
+ return (WebFrameView *)view;
+}
+
+@implementation WebView (WebFileInternal)
+
++ (void)_setCacheModel:(WebCacheModel)cacheModel
+{
+ if (s_didSetCacheModel && cacheModel == s_cacheModel)
+ return;
+
+ NSString *nsurlCacheDirectory = [(NSString *)WKCopyFoundationCacheDirectory() autorelease];
+ if (!nsurlCacheDirectory)
+ nsurlCacheDirectory = NSHomeDirectory();
+
+ // As a fudge factor, use 1000 instead of 1024, in case the reported byte
+ // count doesn't align exactly to a megabyte boundary.
+ vm_size_t memSize = WebMemorySize() / 1024 / 1000;
+ unsigned long long diskFreeSize = WebVolumeFreeSize(nsurlCacheDirectory) / 1024 / 1000;
+ NSURLCache *nsurlCache = [NSURLCache sharedURLCache];
+
+ unsigned cacheTotalCapacity = 0;
+ unsigned cacheMinDeadCapacity = 0;
+ unsigned cacheMaxDeadCapacity = 0;
+
+ unsigned pageCacheCapacity = 0;
+
+ NSUInteger nsurlCacheMemoryCapacity = 0;
+ NSUInteger nsurlCacheDiskCapacity = 0;
+
+ switch (cacheModel) {
+ case WebCacheModelDocumentViewer: {
+ // Page cache capacity (in pages)
+ pageCacheCapacity = 0;
+
+ // Object cache capacities (in bytes)
+ if (memSize >= 4096)
+ cacheTotalCapacity = 256 * 1024 * 1024;
+ else if (memSize >= 3072)
+ cacheTotalCapacity = 192 * 1024 * 1024;
+ else if (memSize >= 2048)
+ cacheTotalCapacity = 128 * 1024 * 1024;
+ else if (memSize >= 1536)
+ cacheTotalCapacity = 86 * 1024 * 1024;
+ else if (memSize >= 1024)
+ cacheTotalCapacity = 64 * 1024 * 1024;
+ else if (memSize >= 512)
+ cacheTotalCapacity = 32 * 1024 * 1024;
+ else if (memSize >= 256)
+ cacheTotalCapacity = 16 * 1024 * 1024;
+
+ cacheMinDeadCapacity = 0;
+ cacheMaxDeadCapacity = 0;
+
+ // Foundation memory cache capacity (in bytes)
+ nsurlCacheMemoryCapacity = 0;
+
+ // Foundation disk cache capacity (in bytes)
+ nsurlCacheDiskCapacity = [nsurlCache diskCapacity];
+
+ break;
+ }
+ case WebCacheModelDocumentBrowser: {
+ // Page cache capacity (in pages)
+ if (memSize >= 1024)
+ pageCacheCapacity = 3;
+ else if (memSize >= 512)
+ pageCacheCapacity = 2;
+ else if (memSize >= 256)
+ pageCacheCapacity = 1;
+ else
+ pageCacheCapacity = 0;
+
+ // Object cache capacities (in bytes)
+ if (memSize >= 4096)
+ cacheTotalCapacity = 256 * 1024 * 1024;
+ else if (memSize >= 3072)
+ cacheTotalCapacity = 192 * 1024 * 1024;
+ else if (memSize >= 2048)
+ cacheTotalCapacity = 128 * 1024 * 1024;
+ else if (memSize >= 1536)
+ cacheTotalCapacity = 86 * 1024 * 1024;
+ else if (memSize >= 1024)
+ cacheTotalCapacity = 64 * 1024 * 1024;
+ else if (memSize >= 512)
+ cacheTotalCapacity = 32 * 1024 * 1024;
+ else if (memSize >= 256)
+ cacheTotalCapacity = 16 * 1024 * 1024;
+
+ cacheMinDeadCapacity = cacheTotalCapacity / 8;
+ cacheMaxDeadCapacity = cacheTotalCapacity / 4;
+
+ // Foundation memory cache capacity (in bytes)
+ if (memSize >= 2048)
+ nsurlCacheMemoryCapacity = 4 * 1024 * 1024;
+ else if (memSize >= 1024)
+ nsurlCacheMemoryCapacity = 2 * 1024 * 1024;
+ else if (memSize >= 512)
+ nsurlCacheMemoryCapacity = 1 * 1024 * 1024;
+ else
+ nsurlCacheMemoryCapacity = 512 * 1024;
+
+ // Foundation disk cache capacity (in bytes)
+ if (diskFreeSize >= 16384)
+ nsurlCacheDiskCapacity = 50 * 1024 * 1024;
+ else if (diskFreeSize >= 8192)
+ nsurlCacheDiskCapacity = 40 * 1024 * 1024;
+ else if (diskFreeSize >= 4096)
+ nsurlCacheDiskCapacity = 30 * 1024 * 1024;
+ else
+ nsurlCacheDiskCapacity = 20 * 1024 * 1024;
+
+ break;
+ }
+ case WebCacheModelPrimaryWebBrowser: {
+ // Page cache capacity (in pages)
+ // (Research indicates that value / page drops substantially after 3 pages.)
+ if (memSize >= 8192)
+ pageCacheCapacity = 7;
+ if (memSize >= 4096)
+ pageCacheCapacity = 6;
+ else if (memSize >= 2048)
+ pageCacheCapacity = 5;
+ else if (memSize >= 1024)
+ pageCacheCapacity = 4;
+ else if (memSize >= 512)
+ pageCacheCapacity = 3;
+ else if (memSize >= 256)
+ pageCacheCapacity = 2;
+ else
+ pageCacheCapacity = 1;
+
+ // Object cache capacities (in bytes)
+ // (Testing indicates that value / MB depends heavily on content and
+ // browsing pattern. Even growth above 128MB can have substantial
+ // value / MB for some content / browsing patterns.)
+ if (memSize >= 4096)
+ cacheTotalCapacity = 512 * 1024 * 1024;
+ else if (memSize >= 3072)
+ cacheTotalCapacity = 384 * 1024 * 1024;
+ else if (memSize >= 2048)
+ cacheTotalCapacity = 256 * 1024 * 1024;
+ else if (memSize >= 1536)
+ cacheTotalCapacity = 172 * 1024 * 1024;
+ else if (memSize >= 1024)
+ cacheTotalCapacity = 128 * 1024 * 1024;
+ else if (memSize >= 512)
+ cacheTotalCapacity = 64 * 1024 * 1024;
+ else if (memSize >= 256)
+ cacheTotalCapacity = 32 * 1024 * 1024;
+
+ cacheMinDeadCapacity = cacheTotalCapacity / 4;
+ cacheMaxDeadCapacity = cacheTotalCapacity / 2;
+
+ // This code is here to avoid a PLT regression. We can remove it if we
+ // can prove that the overall system gain would justify the regression.
+ cacheMaxDeadCapacity = max(24u, cacheMaxDeadCapacity);
+
+ // Foundation memory cache capacity (in bytes)
+ // (These values are small because WebCore does most caching itself.)
+ if (memSize >= 1024)
+ nsurlCacheMemoryCapacity = 4 * 1024 * 1024;
+ else if (memSize >= 512)
+ nsurlCacheMemoryCapacity = 2 * 1024 * 1024;
+ else if (memSize >= 256)
+ nsurlCacheMemoryCapacity = 1 * 1024 * 1024;
+ else
+ nsurlCacheMemoryCapacity = 512 * 1024;
+
+ // Foundation disk cache capacity (in bytes)
+ if (diskFreeSize >= 16384)
+ nsurlCacheDiskCapacity = 175 * 1024 * 1024;
+ else if (diskFreeSize >= 8192)
+ nsurlCacheDiskCapacity = 150 * 1024 * 1024;
+ else if (diskFreeSize >= 4096)
+ nsurlCacheDiskCapacity = 125 * 1024 * 1024;
+ else if (diskFreeSize >= 2048)
+ nsurlCacheDiskCapacity = 100 * 1024 * 1024;
+ else if (diskFreeSize >= 1024)
+ nsurlCacheDiskCapacity = 75 * 1024 * 1024;
+ else
+ nsurlCacheDiskCapacity = 50 * 1024 * 1024;
+
+ break;
+ }
+ default:
+ ASSERT_NOT_REACHED();
+ };
+
+#ifdef BUILDING_ON_TIGER
+ // Don't use a big Foundation disk cache on Tiger because, according to the
+ // PLT, the Foundation disk cache on Tiger is slower than the network.
+ nsurlCacheDiskCapacity = [nsurlCache diskCapacity];
+#endif
+
+ // Don't shrink a big disk cache, since that would cause churn.
+ nsurlCacheDiskCapacity = max(nsurlCacheDiskCapacity, [nsurlCache diskCapacity]);
+
+ cache()->setCapacities(cacheMinDeadCapacity, cacheMaxDeadCapacity, cacheTotalCapacity);
+ pageCache()->setCapacity(pageCacheCapacity);
+ [nsurlCache setMemoryCapacity:nsurlCacheMemoryCapacity];
+ [nsurlCache setDiskCapacity:nsurlCacheDiskCapacity];
+
+ s_cacheModel = cacheModel;
+ s_didSetCacheModel = YES;
+}
+
++ (WebCacheModel)_cacheModel
+{
+ return s_cacheModel;
+}
+
++ (WebCacheModel)_didSetCacheModel
+{
+ return s_didSetCacheModel;
+}
+
++ (WebCacheModel)_maxCacheModelInAnyInstance
+{
+ WebCacheModel cacheModel = WebCacheModelDocumentViewer;
+ NSEnumerator *enumerator = [(NSMutableSet *)allWebViewsSet objectEnumerator];
+ while (WebPreferences *preferences = [[enumerator nextObject] preferences])
+ cacheModel = max(cacheModel, [preferences cacheModel]);
+ return cacheModel;
+}
+
++ (void)_preferencesChangedNotification:(NSNotification *)notification
+{
+ WebPreferences *preferences = (WebPreferences *)[notification object];
+ ASSERT([preferences isKindOfClass:[WebPreferences class]]);
+
+ WebCacheModel cacheModel = [preferences cacheModel];
+ if (![self _didSetCacheModel] || cacheModel > [self _cacheModel])
+ [self _setCacheModel:cacheModel];
+ else if (cacheModel < [self _cacheModel])
+ [self _setCacheModel:max([[WebPreferences standardPreferences] cacheModel], [self _maxCacheModelInAnyInstance])];
+}
+
++ (void)_preferencesRemovedNotification:(NSNotification *)notification
+{
+ WebPreferences *preferences = (WebPreferences *)[notification object];
+ ASSERT([preferences isKindOfClass:[WebPreferences class]]);
+
+ if ([preferences cacheModel] == [self _cacheModel])
+ [self _setCacheModel:max([[WebPreferences standardPreferences] cacheModel], [self _maxCacheModelInAnyInstance])];
+}
+
+- (WebFrame *)_focusedFrame
+{
+ NSResponder *resp = [[self window] firstResponder];
+ if (resp && [resp isKindOfClass:[NSView class]] && [(NSView *)resp isDescendantOf:[[self mainFrame] frameView]]) {
+ WebFrameView *frameView = containingFrameView((NSView *)resp);
+ ASSERT(frameView != nil);
+ return [frameView webFrame];
+ }
+
+ return nil;
+}
+
+- (WebFrame *)_selectedOrMainFrame
+{
+ WebFrame *result = [self selectedFrame];
+ if (result == nil)
+ result = [self mainFrame];
+ return result;
+}
+
+- (WebFrameBridge *)_bridgeForSelectedOrMainFrame
+{
+ return [[self _selectedOrMainFrame] _bridge];
+}
+
+- (BOOL)_isLoading
+{
+ WebFrame *mainFrame = [self mainFrame];
+ return [[mainFrame _dataSource] isLoading]
+ || [[mainFrame provisionalDataSource] isLoading];
+}
+
+- (WebFrameView *)_frameViewAtWindowPoint:(NSPoint)point
+{
+ if (_private->closed)
+ return nil;
+ NSView *view = [self hitTest:[[self superview] convertPoint:point fromView:nil]];
+ if (![view isDescendantOf:[[self mainFrame] frameView]])
+ return nil;
+ WebFrameView *frameView = containingFrameView(view);
+ ASSERT(frameView);
+ return frameView;
+}
+
++ (void)_preflightSpellCheckerNow:(id)sender
+{
+ [[NSSpellChecker sharedSpellChecker] _preflightChosenSpellServer];
+}
+
++ (void)_preflightSpellChecker
+{
+ // As AppKit does, we wish to delay tickling the shared spellchecker into existence on application launch.
+ if ([NSSpellChecker sharedSpellCheckerExists]) {
+ [self _preflightSpellCheckerNow:self];
+ } else {
+ [self performSelector:@selector(_preflightSpellCheckerNow:) withObject:self afterDelay:2.0];
+ }
+}
+
+- (BOOL)_continuousCheckingAllowed
+{
+ static BOOL allowContinuousSpellChecking = YES;
+ static BOOL readAllowContinuousSpellCheckingDefault = NO;
+ if (!readAllowContinuousSpellCheckingDefault) {
+ if ([[NSUserDefaults standardUserDefaults] objectForKey:@"NSAllowContinuousSpellChecking"]) {
+ allowContinuousSpellChecking = [[NSUserDefaults standardUserDefaults] boolForKey:@"NSAllowContinuousSpellChecking"];
+ }
+ readAllowContinuousSpellCheckingDefault = YES;
+ }
+ return allowContinuousSpellChecking;
+}
+
+- (NSResponder *)_responderForResponderOperations
+{
+ NSResponder *responder = [[self window] firstResponder];
+ WebFrameView *mainFrameView = [[self mainFrame] frameView];
+
+ // If the current responder is outside of the webview, use our main frameView or its
+ // document view. We also do this for subviews of self that are siblings of the main
+ // frameView since clients might insert non-webview-related views there (see 4552713).
+ if (responder != self && ![mainFrameView _web_firstResponderIsSelfOrDescendantView]) {
+ responder = [mainFrameView documentView];
+ if (!responder)
+ responder = mainFrameView;
+ }
+ return responder;
+}
+
+- (void)_openFrameInNewWindowFromMenu:(NSMenuItem *)sender
+{
+ ASSERT_ARG(sender, [sender isKindOfClass:[NSMenuItem class]]);
+
+ NSDictionary *element = [sender representedObject];
+ ASSERT([element isKindOfClass:[NSDictionary class]]);
+
+ NSURLRequest *request = [[[[element objectForKey:WebElementFrameKey] dataSource] request] copy];
+ ASSERT(request);
+
+ [self _openNewWindowWithRequest:request];
+ [request release];
+}
+
+- (void)_searchWithGoogleFromMenu:(id)sender
+{
+ id documentView = [[[self selectedFrame] frameView] documentView];
+ if (![documentView conformsToProtocol:@protocol(WebDocumentText)]) {
+ return;
+ }
+
+ NSString *selectedString = [(id <WebDocumentText>)documentView selectedString];
+ if ([selectedString length] == 0) {
+ return;
+ }
+
+ NSPasteboard *pasteboard = [NSPasteboard pasteboardWithUniqueName];
+ [pasteboard declareTypes:[NSArray arrayWithObject:NSStringPboardType] owner:nil];
+ NSMutableString *s = [selectedString mutableCopy];
+ const unichar nonBreakingSpaceCharacter = 0xA0;
+ NSString *nonBreakingSpaceString = [NSString stringWithCharacters:&nonBreakingSpaceCharacter length:1];
+ [s replaceOccurrencesOfString:nonBreakingSpaceString withString:@" " options:0 range:NSMakeRange(0, [s length])];
+ [pasteboard setString:s forType:NSStringPboardType];
+ [s release];
+
+ // FIXME: seems fragile to use the service by name, but this is what AppKit does
+ NSPerformService(@"Search With Google", pasteboard);
+}
+
+- (void)_searchWithSpotlightFromMenu:(id)sender
+{
+ id documentView = [[[self selectedFrame] frameView] documentView];
+ if (![documentView conformsToProtocol:@protocol(WebDocumentText)])
+ return;
+
+ NSString *selectedString = [(id <WebDocumentText>)documentView selectedString];
+ if ([selectedString length] == 0) {
+ return;
+ }
+
+ (void)HISearchWindowShow((CFStringRef)selectedString, kNilOptions);
+}
+
+// Slightly funky method that lets us have one copy of the logic for finding docViews that can do
+// text sizing. It returns whether it found any "suitable" doc views. It sends sel to any suitable
+// doc views, or if sel==0 we do nothing to them. For doc views that track our size factor, they are
+// suitable if doTrackingViews==YES (which in practice means that our size factor isn't at its max or
+// min). For doc views that don't track it, we send them testSel to determine suitablility. If we
+// do find any suitable tracking doc views and newScaleFactor!=0, we will set the common scale factor
+// to that new factor before we send sel to any of them.
+- (BOOL)_performTextSizingSelector:(SEL)sel withObject:(id)arg onTrackingDocs:(BOOL)doTrackingViews selForNonTrackingDocs:(SEL)testSel newScaleFactor:(float)newScaleFactor
+{
+ if ([[self mainFrame] _dataSource] == nil)
+ return NO;
+
+ BOOL foundSome = NO;
+ NSArray *docViews = [[self mainFrame] _documentViews];
+ for (int i = [docViews count]-1; i >= 0; i--) {
+ id docView = [docViews objectAtIndex:i];
+ if ([docView conformsToProtocol:@protocol(_WebDocumentTextSizing)]) {
+ id <_WebDocumentTextSizing> sizingDocView = (id <_WebDocumentTextSizing>)docView;
+ BOOL isSuitable;
+ if ([sizingDocView _tracksCommonSizeFactor]) {
+ isSuitable = doTrackingViews;
+ if (isSuitable && newScaleFactor != 0)
+ _private->textSizeMultiplier = newScaleFactor;
+ } else {
+ // Incantation to perform a selector returning a BOOL.
+ isSuitable = ((BOOL(*)(id, SEL))objc_msgSend)(sizingDocView, testSel);
+ }
+
+ if (isSuitable) {
+ if (sel != 0) {
+ foundSome = YES;
+ [sizingDocView performSelector:sel withObject:arg];
+ } else {
+ // if we're just called for the benefit of the return value, we can return at first match
+ return YES;
+ }
+ }
+ }
+ }
+
+ return foundSome;
+}
+
+- (void)_notifyTextSizeMultiplierChanged
+{
+ if ([[self mainFrame] _dataSource] == nil)
+ return;
+
+ NSArray *docViews = [[self mainFrame] _documentViews];
+ for (int i = [docViews count]-1; i >= 0; i--) {
+ id docView = [docViews objectAtIndex:i];
+ if ([docView conformsToProtocol:@protocol(_WebDocumentTextSizing)] == NO)
+ continue;
+
+ id <_WebDocumentTextSizing> sizingDocView = (id <_WebDocumentTextSizing>)docView;
+ if ([sizingDocView _tracksCommonSizeFactor])
+ [sizingDocView _textSizeMultiplierChanged];
+ }
+
+}
+
+@end
+
+@implementation WebView (WebViewInternal)
+
+- (BOOL)_becomingFirstResponderFromOutside
+{
+ return _private->becomingFirstResponderFromOutside;
+}
+
+- (void)_receivedIconChangedNotification:(NSNotification *)notification
+{
+ // Get the URL for this notification
+ NSDictionary *userInfo = [notification userInfo];
+ ASSERT([userInfo isKindOfClass:[NSDictionary class]]);
+ NSString *urlString = [userInfo objectForKey:WebIconNotificationUserInfoURLKey];
+ ASSERT([urlString isKindOfClass:[NSString class]]);
+
+ // If that URL matches the current main frame, dispatch the delegate call, which will also unregister
+ // us for this notification
+ if ([[self mainFrameURL] isEqualTo:urlString])
+ [self _dispatchDidReceiveIconFromWebFrame:[self mainFrame]];
+}
+
+- (void)_registerForIconNotification:(BOOL)listen
+{
+ if (listen)
+ [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(_receivedIconChangedNotification:) name:WebIconDatabaseDidAddIconNotification object:nil];
+ else
+ [[NSNotificationCenter defaultCenter] removeObserver:self name:WebIconDatabaseDidAddIconNotification object:nil];
+}
+
+- (void)_dispatchDidReceiveIconFromWebFrame:(WebFrame *)webFrame
+{
+ // FIXME: This willChangeValueForKey call is too late, because the icon has already changed by now.
+ [self _willChangeValueForKey:_WebMainFrameIconKey];
+
+ // Since we definitely have an icon and are about to send out the delegate call for that, this WebView doesn't need to listen for the general
+ // notification any longer
+ [self _registerForIconNotification:NO];
+
+ WebFrameLoadDelegateImplementationCache* cache = &_private->frameLoadDelegateImplementations;
+ if (cache->didReceiveIconForFrameFunc) {
+ Image* image = iconDatabase()->iconForPageURL(core(webFrame)->loader()->url().string(), IntSize(16, 16));
+ if (NSImage *icon = webGetNSImage(image, NSMakeSize(16, 16)))
+ CallFrameLoadDelegate(cache->didReceiveIconForFrameFunc, self, @selector(webView:didReceiveIcon:forFrame:), icon, webFrame);
+ }
+
+ [self _didChangeValueForKey:_WebMainFrameIconKey];
+}
+
+- (NSString *)_userVisibleBundleVersionFromFullVersion:(NSString *)fullVersion
+{
+ // If the version is 4 digits long or longer, then the first digit represents
+ // the version of the OS. Our user agent string should not include this first digit,
+ // so strip it off and report the rest as the version. <rdar://problem/4997547>
+ NSRange nonDigitRange = [fullVersion rangeOfCharacterFromSet:[[NSCharacterSet decimalDigitCharacterSet] invertedSet]];
+ if (nonDigitRange.location == NSNotFound && [fullVersion length] >= 4)
+ return [fullVersion substringFromIndex:1];
+ if (nonDigitRange.location != NSNotFound && nonDigitRange.location >= 4)
+ return [fullVersion substringFromIndex:1];
+ return fullVersion;
+}
+
+static inline int callGestalt(OSType selector)
+{
+ SInt32 value = 0;
+ Gestalt(selector, &value);
+ return value;
+}
+
+// Uses underscores instead of dots because if "4." ever appears in a user agent string, old DHTML libraries treat it as Netscape 4.
+static NSString *createMacOSXVersionString()
+{
+ // Can't use -[NSProcessInfo operatingSystemVersionString] because it has too much stuff we don't want.
+ int major = callGestalt(gestaltSystemVersionMajor);
+ ASSERT(major);
+
+ int minor = callGestalt(gestaltSystemVersionMinor);
+ int bugFix = callGestalt(gestaltSystemVersionBugFix);
+ if (bugFix)
+ return [[NSString alloc] initWithFormat:@"%d_%d_%d", major, minor, bugFix];
+ if (minor)
+ return [[NSString alloc] initWithFormat:@"%d_%d", major, minor];
+ return [[NSString alloc] initWithFormat:@"%d", major];
+}
+
+- (NSString *)_userAgentWithApplicationName:(NSString *)applicationName andWebKitVersion:(NSString *)version
+{
+ // Note: Do *not* move the initialization of osVersion into the declaration.
+ // Garbage collection won't correctly mark the global variable in that case <rdar://problem/5733674>.
+ static NSString *osVersion;
+ if (!osVersion)
+ osVersion = createMacOSXVersionString();
+ NSString *language = [NSUserDefaults _webkit_preferredLanguageCode];
+ if ([applicationName length])
+ return [NSString stringWithFormat:@"Mozilla/5.0 (Macintosh; U; " PROCESSOR " Mac OS X %@; %@) AppleWebKit/%@ (KHTML, like Gecko) %@",
+ osVersion, language, version, applicationName];
+ return [NSString stringWithFormat:@"Mozilla/5.0 (Macintosh; U; " PROCESSOR " Mac OS X %@; %@) AppleWebKit/%@ (KHTML, like Gecko)",
+ osVersion, language, version];
+}
+
+// Get the appropriate user-agent string for a particular URL.
+- (WebCore::String)_userAgentForURL:(const WebCore::KURL&)url
+{
+ if (_private->useSiteSpecificSpoofing) {
+ // No current site-specific spoofs.
+ }
+
+ if (_private->userAgent->isNull()) {
+ NSString *sourceVersion = [[NSBundle bundleForClass:[WebView class]] objectForInfoDictionaryKey:(NSString *)kCFBundleVersionKey];
+ sourceVersion = [self _userVisibleBundleVersionFromFullVersion:sourceVersion];
+ *_private->userAgent = [self _userAgentWithApplicationName:_private->applicationNameForUserAgent andWebKitVersion:sourceVersion];
+ }
+
+ return *_private->userAgent;
+}
+
+- (void)_addObject:(id)object forIdentifier:(unsigned long)identifier
+{
+ ASSERT(!_private->identifierMap->contains(identifier));
+
+ // If the identifier map is initially empty it means we're starting a load
+ // of something. The semantic is that the web view should be around as long
+ // as something is loading. Because of that we retain the web view.
+ if (_private->identifierMap->isEmpty())
+ CFRetain(self);
+
+ _private->identifierMap->set(identifier, object);
+}
+
+- (id)_objectForIdentifier:(unsigned long)identifier
+{
+ return _private->identifierMap->get(identifier).get();
+}
+
+- (void)_removeObjectForIdentifier:(unsigned long)identifier
+{
+ HashMap<unsigned long, RetainPtr<id> >::iterator it = _private->identifierMap->find(identifier);
+
+ // FIXME: This is currently needed because of a bug that causes didFail to be sent twice
+ // sometimes, see <rdar://problem/5009627> for more information.
+ if (it == _private->identifierMap->end())
+ return;
+
+ _private->identifierMap->remove(it);
+
+ // If the identifier map is now empty it means we're no longer loading anything
+ // and we should release the web view.
+ if (_private->identifierMap->isEmpty())
+ CFRelease(self);
+}
+
+@end
+
+// We use these functions to call the delegates and block exceptions. These functions are
+// declared inside a WebView category to get direct access to the delegate data memebers,
+// preventing more ObjC message dispatch and compensating for the expense of the @try/@catch.
+
+@implementation WebView (WebCallDelegateFunctions)
+
+#if !(defined(__i386__) || defined(__x86_64__))
+typedef double (*ObjCMsgSendFPRet)(id, SEL, ...);
+static const ObjCMsgSendFPRet objc_msgSend_fpret = reinterpret_cast<ObjCMsgSendFPRet>(objc_msgSend);
+#endif
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return objc_msgSend(delegate, selector, self);
+ @try {
+ return objc_msgSend(delegate, selector, self);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, id object)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return objc_msgSend(delegate, selector, self, object);
+ @try {
+ return objc_msgSend(delegate, selector, self, object);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, NSRect rect)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return reinterpret_cast<id (*)(id, SEL, WebView *, NSRect)>(objc_msgSend)(delegate, selector, self, rect);
+ @try {
+ return reinterpret_cast<id (*)(id, SEL, WebView *, NSRect)>(objc_msgSend)(delegate, selector, self, rect);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, id object1, id object2)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return objc_msgSend(delegate, selector, self, object1, object2);
+ @try {
+ return objc_msgSend(delegate, selector, self, object1, object2);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, id object, BOOL boolean)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return objc_msgSend(delegate, selector, self, object, boolean);
+ @try {
+ return objc_msgSend(delegate, selector, self, object, boolean);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, id object1, id object2, id object3)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return objc_msgSend(delegate, selector, self, object1, object2, object3);
+ @try {
+ return objc_msgSend(delegate, selector, self, object1, object2, object3);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(WebView *self, id delegate, SEL selector, id object, NSUInteger integer)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return objc_msgSend(delegate, selector, self, object, integer);
+ @try {
+ return objc_msgSend(delegate, selector, self, object, integer);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline float CallDelegateReturningFloat(WebView *self, id delegate, SEL selector)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return 0.0f;
+ if (!self->_private->catchesDelegateExceptions)
+ return static_cast<float>(objc_msgSend_fpret(delegate, selector, self));
+ @try {
+ return static_cast<float>(objc_msgSend_fpret(delegate, selector, self));
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return 0.0f;
+}
+
+static inline BOOL CallDelegateReturningBoolean(BOOL result, WebView *self, id delegate, SEL selector)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return result;
+ if (!self->_private->catchesDelegateExceptions)
+ return reinterpret_cast<BOOL (*)(id, SEL, WebView *)>(objc_msgSend)(delegate, selector, self);
+ @try {
+ return reinterpret_cast<BOOL (*)(id, SEL, WebView *)>(objc_msgSend)(delegate, selector, self);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return result;
+}
+
+static inline BOOL CallDelegateReturningBoolean(BOOL result, WebView *self, id delegate, SEL selector, id object)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return result;
+ if (!self->_private->catchesDelegateExceptions)
+ return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id)>(objc_msgSend)(delegate, selector, self, object);
+ @try {
+ return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id)>(objc_msgSend)(delegate, selector, self, object);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return result;
+}
+
+static inline BOOL CallDelegateReturningBoolean(BOOL result, WebView *self, id delegate, SEL selector, id object, BOOL boolean)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return result;
+ if (!self->_private->catchesDelegateExceptions)
+ return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id, BOOL)>(objc_msgSend)(delegate, selector, self, object, boolean);
+ @try {
+ return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id, BOOL)>(objc_msgSend)(delegate, selector, self, object, boolean);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return result;
+}
+
+static inline BOOL CallDelegateReturningBoolean(BOOL result, WebView *self, id delegate, SEL selector, id object1, id object2)
+{
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return result;
+ if (!self->_private->catchesDelegateExceptions)
+ return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id, id)>(objc_msgSend)(delegate, selector, self, object1, object2);
+ @try {
+ return reinterpret_cast<BOOL (*)(id, SEL, WebView *, id, id)>(objc_msgSend)(delegate, selector, self, object1, object2);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return result;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector)
+{
+ if (!delegate)
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return implementation(delegate, selector, self);
+ @try {
+ return implementation(delegate, selector, self);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object)
+{
+ if (!delegate)
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return implementation(delegate, selector, self, object);
+ @try {
+ return implementation(delegate, selector, self, object);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, id object2)
+{
+ if (!delegate)
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return implementation(delegate, selector, self, object1, object2);
+ @try {
+ return implementation(delegate, selector, self, object1, object2);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, id object2, id object3)
+{
+ if (!delegate)
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return implementation(delegate, selector, self, object1, object2, object3);
+ @try {
+ return implementation(delegate, selector, self, object1, object2, object3);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, id object2, id object3, id object4)
+{
+ if (!delegate)
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return implementation(delegate, selector, self, object1, object2, object3, object4);
+ @try {
+ return implementation(delegate, selector, self, object1, object2, object3, object4);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, NSInteger integer, id object2)
+{
+ if (!delegate)
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return implementation(delegate, selector, self, object1, integer, object2);
+ @try {
+ return implementation(delegate, selector, self, object1, integer, object2);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, id object2, NSInteger integer, id object3)
+{
+ if (!delegate)
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return implementation(delegate, selector, self, object1, object2, integer, object3);
+ @try {
+ return implementation(delegate, selector, self, object1, object2, integer, object3);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+static inline id CallDelegate(IMP implementation, WebView *self, id delegate, SEL selector, id object1, NSTimeInterval interval, id object2, id object3)
+{
+ if (!delegate)
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return implementation(delegate, selector, self, object1, interval, object2, object3);
+ @try {
+ return implementation(delegate, selector, self, object1, interval, object2, object3);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+id CallUIDelegate(WebView *self, SEL selector)
+{
+ return CallDelegate(self, self->_private->UIDelegate, selector);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, id object)
+{
+ return CallDelegate(self, self->_private->UIDelegate, selector, object);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, id object, BOOL boolean)
+{
+ return CallDelegate(self, self->_private->UIDelegate, selector, object, boolean);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, NSRect rect)
+{
+ return CallDelegate(self, self->_private->UIDelegate, selector, rect);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, id object1, id object2)
+{
+ return CallDelegate(self, self->_private->UIDelegate, selector, object1, object2);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, id object1, id object2, id object3)
+{
+ return CallDelegate(self, self->_private->UIDelegate, selector, object1, object2, object3);
+}
+
+id CallUIDelegate(WebView *self, SEL selector, id object, NSUInteger integer)
+{
+ return CallDelegate(self, self->_private->UIDelegate, selector, object, integer);
+}
+
+float CallUIDelegateReturningFloat(WebView *self, SEL selector)
+{
+ return CallDelegateReturningFloat(self, self->_private->UIDelegate, selector);
+}
+
+BOOL CallUIDelegateReturningBoolean(BOOL result, WebView *self, SEL selector)
+{
+ return CallDelegateReturningBoolean(result, self, self->_private->UIDelegate, selector);
+}
+
+BOOL CallUIDelegateReturningBoolean(BOOL result, WebView *self, SEL selector, id object)
+{
+ return CallDelegateReturningBoolean(result, self, self->_private->UIDelegate, selector, object);
+}
+
+BOOL CallUIDelegateReturningBoolean(BOOL result, WebView *self, SEL selector, id object, BOOL boolean)
+{
+ return CallDelegateReturningBoolean(result, self, self->_private->UIDelegate, selector, object, boolean);
+}
+
+BOOL CallUIDelegateReturningBoolean(BOOL result, WebView *self, SEL selector, id object1, id object2)
+{
+ return CallDelegateReturningBoolean(result, self, self->_private->UIDelegate, selector, object1, object2);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector)
+{
+ return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector, id object)
+{
+ return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector, object);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2)
+{
+ return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector, object1, object2);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2, id object3)
+{
+ return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector, object1, object2, object3);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2, id object3, id object4)
+{
+ return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector, object1, object2, object3, object4);
+}
+
+id CallFrameLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, NSTimeInterval interval, id object2, id object3)
+{
+ return CallDelegate(implementation, self, self->_private->frameLoadDelegate, selector, object1, interval, object2, object3);
+}
+
+id CallResourceLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2)
+{
+ return CallDelegate(implementation, self, self->_private->resourceProgressDelegate, selector, object1, object2);
+}
+
+id CallResourceLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2, id object3)
+{
+ return CallDelegate(implementation, self, self->_private->resourceProgressDelegate, selector, object1, object2, object3);
+}
+
+id CallResourceLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2, id object3, id object4)
+{
+ return CallDelegate(implementation, self, self->_private->resourceProgressDelegate, selector, object1, object2, object3, object4);
+}
+
+id CallResourceLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, NSInteger integer, id object2)
+{
+ return CallDelegate(implementation, self, self->_private->resourceProgressDelegate, selector, object1, integer, object2);
+}
+
+id CallResourceLoadDelegate(IMP implementation, WebView *self, SEL selector, id object1, id object2, NSInteger integer, id object3)
+{
+ return CallDelegate(implementation, self, self->_private->resourceProgressDelegate, selector, object1, object2, integer, object3);
+}
+
+// The form delegate needs to have it's own implementation, because the first argument is never the WebView
+
+id CallFormDelegate(WebView *self, SEL selector, id object1, id object2)
+{
+ id delegate = self->_private->formDelegate;
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return objc_msgSend(delegate, selector, object1, object2);
+ @try {
+ return objc_msgSend(delegate, selector, object1, object2);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+id CallFormDelegate(WebView *self, SEL selector, id object1, id object2, id object3, id object4, id object5)
+{
+ id delegate = self->_private->formDelegate;
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return nil;
+ if (!self->_private->catchesDelegateExceptions)
+ return objc_msgSend(delegate, selector, object1, object2, object3, object4, object5);
+ @try {
+ return objc_msgSend(delegate, selector, object1, object2, object3, object4, object5);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return nil;
+}
+
+BOOL CallFormDelegateReturningBoolean(BOOL result, WebView *self, SEL selector, id object1, SEL selectorArg, id object2)
+{
+ id delegate = self->_private->formDelegate;
+ if (!delegate || ![delegate respondsToSelector:selector])
+ return result;
+ if (!self->_private->catchesDelegateExceptions)
+ return reinterpret_cast<BOOL (*)(id, SEL, id, SEL, id)>(objc_msgSend)(delegate, selector, object1, selectorArg, object2);
+ @try {
+ return reinterpret_cast<BOOL (*)(id, SEL, id, SEL, id)>(objc_msgSend)(delegate, selector, object1, selectorArg, object2);
+ } @catch(id exception) {
+ ReportDiscardedDelegateException(selector, exception);
+ }
+ return result;
+}
+
+@end
diff --git a/WebKit/mac/WebView/WebViewInternal.h b/WebKit/mac/WebView/WebViewInternal.h
new file mode 100644
index 0000000..b6addad
--- /dev/null
+++ b/WebKit/mac/WebView/WebViewInternal.h
@@ -0,0 +1,190 @@
+/*
+ * Copyright (C) 2005, 2006, 2007 Apple Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+// This header contains WebView declarations that can be used anywhere in the Web Kit, but are neither SPI nor API.
+
+#import "WebPreferences.h"
+#import "WebViewPrivate.h"
+#import "WebTypesInternal.h"
+
+#ifdef __cplusplus
+namespace WebCore {
+ class KeyboardEvent;
+ class KURL;
+ class Page;
+ class String;
+}
+typedef WebCore::KeyboardEvent WebCoreKeyboardEvent;
+typedef WebCore::Page WebCorePage;
+#else
+@class WebCoreKeyboardEvent;
+@class WebCorePage;
+#endif
+
+@class WebBasePluginPackage;
+@class WebDownload;
+
+@interface WebView (WebViewEditingExtras)
+- (BOOL)_interceptEditingKeyEvent:(WebCoreKeyboardEvent *)event shouldSaveCommand:(BOOL)shouldSave;
+- (BOOL)_shouldChangeSelectedDOMRange:(DOMRange *)currentRange toDOMRange:(DOMRange *)proposedRange affinity:(NSSelectionAffinity)selectionAffinity stillSelecting:(BOOL)flag;
+@end
+
+@interface WebView (AllWebViews)
++ (void)_makeAllWebViewsPerformSelector:(SEL)selector;
+- (void)_removeFromAllWebViewsSet;
+- (void)_addToAllWebViewsSet;
+@end
+
+@interface WebView (WebViewInternal)
+#ifdef __cplusplus
+- (WebCore::String)_userAgentForURL:(const WebCore::KURL&)url;
+#endif
+@end
+
+@interface WebView (WebViewMiscInternal)
+
++ (void)_setCacheModel:(WebCacheModel)cacheModel;
++ (WebCacheModel)_cacheModel;
+- (WebCorePage*)page;
+- (NSMenu *)_menuForElement:(NSDictionary *)element defaultItems:(NSArray *)items;
+- (id)_UIDelegateForwarder;
+- (id)_editingDelegateForwarder;
+- (id)_policyDelegateForwarder;
+- (id)_scriptDebugDelegateForwarder;
+- (void)_pushPerformingProgrammaticFocus;
+- (void)_popPerformingProgrammaticFocus;
+- (void)_incrementProgressForIdentifier:(id)identifier response:(NSURLResponse *)response;
+- (void)_incrementProgressForIdentifier:(id)identifier length:(int)length;
+- (void)_completeProgressForIdentifier:(id)identifer;
+- (void)_progressStarted:(WebFrame *)frame;
+- (void)_didStartProvisionalLoadForFrame:(WebFrame *)frame;
++ (BOOL)_viewClass:(Class *)vClass andRepresentationClass:(Class *)rClass forMIMEType:(NSString *)MIMEType;
+- (BOOL)_viewClass:(Class *)vClass andRepresentationClass:(Class *)rClass forMIMEType:(NSString *)MIMEType;
++ (NSString *)_MIMETypeForFile:(NSString *)path;
+- (WebDownload *)_downloadURL:(NSURL *)URL;
++ (NSString *)_generatedMIMETypeForURLScheme:(NSString *)URLScheme;
++ (BOOL)_representationExistsForURLScheme:(NSString *)URLScheme;
+- (BOOL)_isPerformingProgrammaticFocus;
+- (void)_mouseDidMoveOverElement:(NSDictionary *)dictionary modifierFlags:(NSUInteger)modifierFlags;
+- (WebView *)_openNewWindowWithRequest:(NSURLRequest *)request;
+- (void)_writeImageForElement:(NSDictionary *)element withPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard;
+- (void)_writeLinkElement:(NSDictionary *)element withPasteboardTypes:(NSArray *)types toPasteboard:(NSPasteboard *)pasteboard;
+- (void)_openFrameInNewWindowFromMenu:(NSMenuItem *)sender;
+- (void)_searchWithGoogleFromMenu:(id)sender;
+- (void)_searchWithSpotlightFromMenu:(id)sender;
+- (void)_progressCompleted:(WebFrame *)frame;
+- (void)_didCommitLoadForFrame:(WebFrame *)frame;
+- (void)_didFinishLoadForFrame:(WebFrame *)frame;
+- (void)_didFailLoadWithError:(NSError *)error forFrame:(WebFrame *)frame;
+- (void)_didFailProvisionalLoadWithError:(NSError *)error forFrame:(WebFrame *)frame;
+- (void)_willChangeValueForKey:(NSString *)key;
+- (void)_didChangeValueForKey:(NSString *)key;
+- (WebBasePluginPackage *)_pluginForMIMEType:(NSString *)MIMEType;
+- (WebBasePluginPackage *)_pluginForExtension:(NSString *)extension;
+- (BOOL)_isMIMETypeRegisteredAsPlugin:(NSString *)MIMEType;
+
+- (void)_addObject:(id)object forIdentifier:(unsigned long)identifier;
+- (id)_objectForIdentifier:(unsigned long)identifier;
+- (void)_removeObjectForIdentifier:(unsigned long)identifier;
+- (BOOL)_becomingFirstResponderFromOutside;
+
+- (void)_registerForIconNotification:(BOOL)listen;
+- (void)_dispatchDidReceiveIconFromWebFrame:(WebFrame *)webFrame;
+
+@end
+
+typedef struct _WebResourceDelegateImplementationCache {
+ IMP didCancelAuthenticationChallengeFunc;
+ IMP didReceiveAuthenticationChallengeFunc;
+ IMP identifierForRequestFunc;
+ IMP willSendRequestFunc;
+ IMP didReceiveResponseFunc;
+ IMP didReceiveContentLengthFunc;
+ IMP didFinishLoadingFromDataSourceFunc;
+ IMP didFailLoadingWithErrorFromDataSourceFunc;
+ IMP didLoadResourceFromMemoryCacheFunc;
+ IMP willCacheResponseFunc;
+ IMP plugInFailedWithErrorFunc;
+} WebResourceDelegateImplementationCache;
+
+typedef struct _WebFrameLoadDelegateImplementationCache {
+ IMP didClearWindowObjectForFrameFunc;
+ IMP windowScriptObjectAvailableFunc;
+ IMP didHandleOnloadEventsForFrameFunc;
+ IMP didReceiveServerRedirectForProvisionalLoadForFrameFunc;
+ IMP didCancelClientRedirectForFrameFunc;
+ IMP willPerformClientRedirectToURLDelayFireDateForFrameFunc;
+ IMP didChangeLocationWithinPageForFrameFunc;
+ IMP willCloseFrameFunc;
+ IMP didStartProvisionalLoadForFrameFunc;
+ IMP didReceiveTitleForFrameFunc;
+ IMP didCommitLoadForFrameFunc;
+ IMP didFailProvisionalLoadWithErrorForFrameFunc;
+ IMP didFailLoadWithErrorForFrameFunc;
+ IMP didFinishLoadForFrameFunc;
+ IMP didFirstLayoutInFrameFunc;
+ IMP didReceiveIconForFrameFunc;
+ IMP didFinishDocumentLoadForFrameFunc;
+} WebFrameLoadDelegateImplementationCache;
+
+WebResourceDelegateImplementationCache* WebViewGetResourceLoadDelegateImplementations(WebView *webView);
+WebFrameLoadDelegateImplementationCache* WebViewGetFrameLoadDelegateImplementations(WebView *webView);
+
+#ifdef __cplusplus
+
+id CallFormDelegate(WebView *, SEL, id, id);
+id CallFormDelegate(WebView *self, SEL selector, id object1, id object2, id object3, id object4, id object5);
+BOOL CallFormDelegateReturningBoolean(BOOL, WebView *, SEL, id, SEL, id);
+
+id CallUIDelegate(WebView *, SEL);
+id CallUIDelegate(WebView *, SEL, id);
+id CallUIDelegate(WebView *, SEL, NSRect);
+id CallUIDelegate(WebView *, SEL, id, id);
+id CallUIDelegate(WebView *, SEL, id, BOOL);
+id CallUIDelegate(WebView *, SEL, id, id, id);
+id CallUIDelegate(WebView *, SEL, id, NSUInteger);
+float CallUIDelegateReturningFloat(WebView *, SEL);
+BOOL CallUIDelegateReturningBoolean(BOOL, WebView *, SEL);
+BOOL CallUIDelegateReturningBoolean(BOOL, WebView *, SEL, id);
+BOOL CallUIDelegateReturningBoolean(BOOL, WebView *, SEL, id, id);
+BOOL CallUIDelegateReturningBoolean(BOOL, WebView *, SEL, id, BOOL);
+
+id CallFrameLoadDelegate(IMP, WebView *, SEL);
+id CallFrameLoadDelegate(IMP, WebView *, SEL, id);
+id CallFrameLoadDelegate(IMP, WebView *, SEL, id, id);
+id CallFrameLoadDelegate(IMP, WebView *, SEL, id, id, id);
+id CallFrameLoadDelegate(IMP, WebView *, SEL, id, id, id, id);
+id CallFrameLoadDelegate(IMP, WebView *, SEL, id, NSTimeInterval, id, id);
+
+id CallResourceLoadDelegate(IMP, WebView *, SEL, id, id);
+id CallResourceLoadDelegate(IMP, WebView *, SEL, id, id, id);
+id CallResourceLoadDelegate(IMP, WebView *, SEL, id, id, id, id);
+id CallResourceLoadDelegate(IMP, WebView *, SEL, id, NSInteger, id);
+id CallResourceLoadDelegate(IMP, WebView *, SEL, id, id, NSInteger, id);
+
+#endif
diff --git a/WebKit/mac/WebView/WebViewPrivate.h b/WebKit/mac/WebView/WebViewPrivate.h
new file mode 100644
index 0000000..9c95ab0
--- /dev/null
+++ b/WebKit/mac/WebView/WebViewPrivate.h
@@ -0,0 +1,400 @@
+/*
+ * Copyright (C) 2005 Apple Computer, Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ *
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. Neither the name of Apple Computer, Inc. ("Apple") nor the names of
+ * its contributors may be used to endorse or promote products derived
+ * from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
+ * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
+ * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
+ * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
+ * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#import <WebKit/WebView.h>
+#import <WebKit/WebFramePrivate.h>
+
+#if MAC_OS_X_VERSION_MAX_ALLOWED <= MAC_OS_X_VERSION_10_4
+#define WebNSInteger int
+#define WebNSUInteger unsigned int
+#else
+#define WebNSInteger NSInteger
+#define WebNSUInteger NSUInteger
+#endif
+
+@class NSError;
+@class WebFrame;
+@class WebInspector;
+@class WebPreferences;
+
+@protocol WebFormDelegate;
+
+extern NSString *_WebCanGoBackKey;
+extern NSString *_WebCanGoForwardKey;
+extern NSString *_WebEstimatedProgressKey;
+extern NSString *_WebIsLoadingKey;
+extern NSString *_WebMainFrameIconKey;
+extern NSString *_WebMainFrameTitleKey;
+extern NSString *_WebMainFrameURLKey;
+extern NSString *_WebMainFrameDocumentKey;
+
+// pending public WebElementDictionary keys
+extern NSString *WebElementTitleKey; // NSString of the title of the element (used by Safari)
+extern NSString *WebElementSpellingToolTipKey; // NSString of a tooltip representing misspelling or bad grammar (used internally)
+extern NSString *WebElementIsContentEditableKey; // NSNumber indicating whether the inner non-shared node is content editable (used internally)
+
+// other WebElementDictionary keys
+extern NSString *WebElementLinkIsLiveKey; // NSNumber of BOOL indictating whether the link is live or not
+
+typedef enum {
+ WebDashboardBehaviorAlwaysSendMouseEventsToAllWindows,
+ WebDashboardBehaviorAlwaysSendActiveNullEventsToPlugIns,
+ WebDashboardBehaviorAlwaysAcceptsFirstMouse,
+ WebDashboardBehaviorAllowWheelScrolling,
+ WebDashboardBehaviorUseBackwardCompatibilityMode
+} WebDashboardBehavior;
+
+@interface WebController : NSTreeController {
+ IBOutlet WebView *webView;
+}
+- (WebView *)webView;
+- (void)setWebView:(WebView *)newWebView;
+@end
+
+@interface WebView (WebViewEditingActionsPendingPublic)
+
+- (void)outdent:(id)sender;
+
+@end
+
+@interface WebView (WebPendingPublic)
+
+/*!
+@method searchFor:direction:caseSensitive:wrap:startInSelection:
+ @abstract Searches a document view for a string and highlights the string if it is found.
+ Starts the search from the current selection. Will search across all frames.
+ @param string The string to search for.
+ @param forward YES to search forward, NO to seach backwards.
+ @param caseFlag YES to for case-sensitive search, NO for case-insensitive search.
+ @param wrapFlag YES to wrap around, NO to avoid wrapping.
+ @param startInSelection YES to begin search in the selected text (useful for incremental searching), NO to begin search after the selected text.
+ @result YES if found, NO if not found.
+ */
+- (BOOL)searchFor:(NSString *)string direction:(BOOL)forward caseSensitive:(BOOL)caseFlag wrap:(BOOL)wrapFlag startInSelection:(BOOL)startInSelection;
+
+- (void)setMainFrameDocumentReady:(BOOL)mainFrameDocumentReady;
+
+- (void)setTabKeyCyclesThroughElements:(BOOL)cyclesElements;
+- (BOOL)tabKeyCyclesThroughElements;
+
+- (void)scrollDOMRangeToVisible:(DOMRange *)range;
+
+// setHoverFeedbackSuspended: can be called by clients that want to temporarily prevent the webView
+// from displaying feedback about mouse position. Each WebDocumentView class that displays feedback
+// about mouse position should honor this setting.
+- (void)setHoverFeedbackSuspended:(BOOL)newValue;
+- (BOOL)isHoverFeedbackSuspended;
+
+/*!
+@method setScriptDebugDelegate:
+@abstract Set the WebView's WebScriptDebugDelegate delegate.
+@param delegate The WebScriptDebugDelegate to set as the delegate.
+*/
+- (void)setScriptDebugDelegate:(id)delegate;
+
+/*!
+@method scriptDebugDelegate
+@abstract Return the WebView's WebScriptDebugDelegate.
+@result The WebView's WebScriptDebugDelegate.
+*/
+- (id)scriptDebugDelegate;
+
+- (BOOL)shouldClose;
+
+/*!
+ @method aeDescByEvaluatingJavaScriptFromString:
+ @param script The text of the JavaScript.
+ @result The result of the script, converted to an NSAppleEventDescriptor, or nil for failure.
+*/
+- (NSAppleEventDescriptor *)aeDescByEvaluatingJavaScriptFromString:(NSString *)script;
+
+// Support for displaying multiple text matches.
+// These methods might end up moving into a protocol, so different document types can specify
+// whether or not they implement the protocol. For now we'll just deal with HTML.
+// These methods are still in flux; don't rely on them yet.
+- (BOOL)canMarkAllTextMatches;
+- (WebNSUInteger)markAllMatchesForText:(NSString *)string caseSensitive:(BOOL)caseFlag highlight:(BOOL)highlight limit:(WebNSUInteger)limit;
+- (void)unmarkAllTextMatches;
+- (NSArray *)rectsForTextMatches;
+
+// Support for disabling registration with the undo manager. This is equivalent to the methods with the same names on NSTextView.
+- (BOOL)allowsUndo;
+- (void)setAllowsUndo:(BOOL)flag;
+
+@end
+
+@interface WebView (WebPrivate)
+
++ (BOOL)_scriptDebuggerEnabled;
+
+- (WebInspector *)inspector;
+
+/*!
+ @method setBackgroundColor:
+ @param backgroundColor Color to use as the default background.
+ @abstract Sets what color the receiver draws under transparent page background colors and images.
+ This color is also used when no page is loaded. A color with alpha should only be used when the receiver is
+ in a non-opaque window, since the color is drawn using NSCompositeCopy.
+*/
+- (void)setBackgroundColor:(NSColor *)backgroundColor;
+
+/*!
+ @method backgroundColor
+ @result Returns the background color drawn under transparent page background colors and images.
+ This color is also used when no page is loaded. A color with alpha should only be used when the receiver is
+ in a non-opaque window, since the color is drawn using NSCompositeCopy.
+*/
+- (NSColor *)backgroundColor;
+
+/*!
+Could be worth adding to the API.
+ @method loadItemsFromOtherView:
+ @abstract Loads the view with the contents of the other view, including its backforward list.
+ @param otherView The WebView from which to copy contents.
+ */
+- (void)_loadBackForwardListFromOtherView:(WebView *)otherView;
+
++ (NSArray *)_supportedFileExtensions;
+
+/*!
+ @method canShowFile:
+ @abstract Checks if the WebKit can show the content of the file at the specified path.
+ @param path The path of the file to check
+ @result YES if the WebKit can show the content of the file at the specified path.
+*/
++ (BOOL)canShowFile:(NSString *)path;
+
+/*!
+ @method suggestedFileExtensionForMIMEType:
+ @param MIMEType The MIME type to check.
+ @result The extension based on the MIME type
+*/
++ (NSString *)suggestedFileExtensionForMIMEType: (NSString *)MIMEType;
+
+// May well become public
+- (void)_setFormDelegate:(id<WebFormDelegate>)delegate;
+- (id<WebFormDelegate>)_formDelegate;
+
+- (BOOL)_isClosed;
+- (void)_close;
+
+/*!
+ @method _registerViewClass:representationClass:forURLScheme:
+ @discussion Register classes that implement WebDocumentView and WebDocumentRepresentation respectively.
+ @param viewClass The WebDocumentView class to use to render data for a given MIME type.
+ @param representationClass The WebDocumentRepresentation class to use to represent data of the given MIME type.
+ @param scheme The URL scheme to represent with an object of the given class.
+*/
++ (void)_registerViewClass:(Class)viewClass representationClass:(Class)representationClass forURLScheme:(NSString *)URLScheme;
+
++ (void)_unregisterViewClassAndRepresentationClassForMIMEType:(NSString *)MIMEType;
+
+/*!
+ @method _canHandleRequest:
+ @abstract Performs a "preflight" operation that performs some
+ speculative checks to see if a request can be used to create
+ a WebDocumentView and WebDocumentRepresentation.
+ @discussion The result of this method is valid only as long as no
+ protocols or schemes are registered or unregistered, and as long as
+ the request is not mutated (if the request is mutable). Hence, clients
+ should be prepared to handle failures even if they have performed request
+ preflighting by caling this method.
+ @param request The request to preflight.
+ @result YES if it is likely that a WebDocumentView and WebDocumentRepresentation
+ can be created for the request, NO otherwise.
+*/
++ (BOOL)_canHandleRequest:(NSURLRequest *)request;
+
++ (NSString *)_decodeData:(NSData *)data;
+
++ (void)_setAlwaysUseATSU:(BOOL)f;
+
+- (NSCachedURLResponse *)_cachedResponseForURL:(NSURL *)URL;
+
+- (void)_addScrollerDashboardRegions:(NSMutableDictionary *)regions;
+- (NSDictionary *)_dashboardRegions;
+
+- (void)_setDashboardBehavior:(WebDashboardBehavior)behavior to:(BOOL)flag;
+- (BOOL)_dashboardBehavior:(WebDashboardBehavior)behavior;
+
++ (void)_setShouldUseFontSmoothing:(BOOL)f;
++ (BOOL)_shouldUseFontSmoothing;
+
+- (void)_setCatchesDelegateExceptions:(BOOL)f;
+- (BOOL)_catchesDelegateExceptions;
+
+// These two methods are useful for a test harness that needs a consistent appearance for the focus rings
+// regardless of OS X version.
++ (void)_setUsesTestModeFocusRingColor:(BOOL)f;
++ (BOOL)_usesTestModeFocusRingColor;
+
++ (NSString *)_minimumRequiredSafariBuildNumber;
+
+/*!
+ @method setAlwaysShowVerticalScroller:
+ @result Forces the vertical scroller to be visible if flag is YES, otherwise
+ if flag is NO the scroller with automatically show and hide as needed.
+ */
+- (void)setAlwaysShowVerticalScroller:(BOOL)flag;
+
+/*!
+ @method alwaysShowVerticalScroller
+ @result YES if the vertical scroller is always shown
+ */
+- (BOOL)alwaysShowVerticalScroller;
+
+/*!
+ @method setAlwaysShowHorizontalScroller:
+ @result Forces the horizontal scroller to be visible if flag is YES, otherwise
+ if flag is NO the scroller with automatically show and hide as needed.
+ */
+- (void)setAlwaysShowHorizontalScroller:(BOOL)flag;
+
+/*!
+ @method alwaysShowHorizontalScroller
+ @result YES if the horizontal scroller is always shown
+ */
+- (BOOL)alwaysShowHorizontalScroller;
+
+/*!
+ @method setProhibitsMainFrameScrolling:
+ @abstract Prohibits scrolling in the WebView's main frame. Used to "lock" a WebView
+ to a specific scroll position.
+ */
+- (void)setProhibitsMainFrameScrolling:(BOOL)prohibits;
+
+/*!
+ @method _setAdditionalWebPlugInPaths:
+ @abstract Sets additional plugin search paths for a specific WebView.
+ */
+- (void)_setAdditionalWebPlugInPaths:(NSArray *)newPaths;
+
+/*!
+ @method _setInViewSourceMode:
+ @abstract Used to place a WebView into a special source-viewing mode.
+ */
+- (void)_setInViewSourceMode:(BOOL)flag;
+
+/*!
+ @method _inViewSourceMode;
+ @abstract Whether or not the WebView is in source-view mode for HTML.
+ */
+- (BOOL)_inViewSourceMode;
+
+/*!
+ @method _attachScriptDebuggerToAllFrames
+ @abstract Attaches a script debugger to all frames belonging to the receiver.
+ */
+- (void)_attachScriptDebuggerToAllFrames;
+
+/*!
+ @method _detachScriptDebuggerFromAllFrames
+ @abstract Detaches any script debuggers from all frames belonging to the receiver.
+ */
+- (void)_detachScriptDebuggerFromAllFrames;
+
+- (BOOL)defersCallbacks; // called by QuickTime plug-in
+- (void)setDefersCallbacks:(BOOL)defer; // called by QuickTime plug-in
+
+- (BOOL)usesPageCache;
+- (void)setUsesPageCache:(BOOL)usesPageCache;
+
+// <rdar://problem/5217124> Clients other than dashboard, don't use this.
+// Do not remove until Dashboard has moved off it
+- (void)handleAuthenticationForResource:(id)identifier challenge:(NSURLAuthenticationChallenge *)challenge fromDataSource:(WebDataSource *)dataSource;
+
+- (void)_clearUndoRedoOperations;
+
+/* Used to do fast (lower quality) scaling of images so that window resize can be quick. */
+- (BOOL)_inFastImageScalingMode;
+- (void)_setUseFastImageScalingMode:(BOOL)flag;
+
+// SPI for DumpRenderTree
+- (void)_executeCoreCommandByName:(NSString *)name value:(NSString *)value;
+
+@end
+
+@interface WebView (WebViewPrintingPrivate)
+/*!
+ @method _adjustPrintingMarginsForHeaderAndFooter:
+ @abstract Increase the top and bottom margins for the current print operation to
+ account for the header and footer height.
+ @discussion Called by <WebDocument> implementors once when a print job begins. If the
+ <WebDocument> implementor implements knowsPageRange:, this should be called from there.
+ Otherwise this should be called from beginDocument. The <WebDocument> implementors need
+ to also call _drawHeaderAndFooter.
+*/
+- (void)_adjustPrintingMarginsForHeaderAndFooter;
+
+/*!
+ @method _drawHeaderAndFooter
+ @abstract Gives the WebView's UIDelegate a chance to draw a header and footer on the
+ printed page.
+ @discussion This should be called by <WebDocument> implementors from an override of
+ drawPageBorderWithSize:.
+*/
+- (void)_drawHeaderAndFooter;
+@end
+
+@interface WebView (WebViewGrammarChecking)
+
+// FIXME: These two methods should be merged into WebViewEditing when we're not in API freeze
+- (BOOL)isGrammarCheckingEnabled;
+#ifndef BUILDING_ON_TIGER
+- (void)setGrammarCheckingEnabled:(BOOL)flag;
+
+// FIXME: This method should be merged into WebIBActions when we're not in API freeze
+- (void)toggleGrammarChecking:(id)sender;
+#endif
+@end
+
+@interface WebView (WebViewEditingInMail)
+- (void)_insertNewlineInQuotedContent;
+- (void)_replaceSelectionWithNode:(DOMNode *)node matchStyle:(BOOL)matchStyle;
+@end
+
+@interface NSObject (WebFrameLoadDelegatePrivate)
+- (void)webView:(WebView *)sender didFirstLayoutInFrame:(WebFrame *)frame;
+
+// didFinishDocumentLoadForFrame is sent when the document has finished loading, though not necessarily all
+// of its subresources.
+// FIXME 5259339: Currently this callback is not sent for (some?) pages loaded entirely from the cache.
+- (void)webView:(WebView *)sender didFinishDocumentLoadForFrame:(WebFrame *)frame;
+
+// Addresses 4192534. SPI for now.
+- (void)webView:(WebView *)sender didHandleOnloadEventsForFrame:(WebFrame *)frame;
+
+@end
+
+@interface NSObject (WebResourceLoadDelegatePrivate)
+// Addresses <rdar://problem/5008925> - SPI for now
+- (NSCachedURLResponse *)webView:(WebView *)sender resource:(id)identifier willCacheResponse:(NSCachedURLResponse *)response fromDataSource:(WebDataSource *)dataSource;
+@end
+
+#undef WebNSInteger
+#undef WebNSUInteger
diff --git a/WebKit/mac/icu/README b/WebKit/mac/icu/README
new file mode 100644
index 0000000..389e2e8
--- /dev/null
+++ b/WebKit/mac/icu/README
@@ -0,0 +1,4 @@
+The headers in this directory are for compiling on Mac OS X 10.4.
+The Mac OS X 10.4 release includes the ICU binary, but not ICU headers.
+For other platforms, installed ICU headers should be used rather than these.
+They are specific to Mac OS X 10.4.
diff --git a/WebKit/mac/icu/unicode/parseerr.h b/WebKit/mac/icu/unicode/parseerr.h
new file mode 100644
index 0000000..d1ba394
--- /dev/null
+++ b/WebKit/mac/icu/unicode/parseerr.h
@@ -0,0 +1,88 @@
+/*
+**********************************************************************
+* Copyright (C) 1999-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+**********************************************************************
+* Date Name Description
+* 03/14/00 aliu Creation.
+* 06/27/00 aliu Change from C++ class to C struct
+**********************************************************************
+*/
+#ifndef PARSEERR_H
+#define PARSEERR_H
+
+#include "unicode/utypes.h"
+
+
+/**
+ * The capacity of the context strings in UParseError.
+ * @stable ICU 2.0
+ */
+enum { U_PARSE_CONTEXT_LEN = 16 };
+
+/**
+ * A UParseError struct is used to returned detailed information about
+ * parsing errors. It is used by ICU parsing engines that parse long
+ * rules, patterns, or programs, where the text being parsed is long
+ * enough that more information than a UErrorCode is needed to
+ * localize the error.
+ *
+ * <p>The line, offset, and context fields are optional; parsing
+ * engines may choose not to use to use them.
+ *
+ * <p>The preContext and postContext strings include some part of the
+ * context surrounding the error. If the source text is "let for=7"
+ * and "for" is the error (e.g., because it is a reserved word), then
+ * some examples of what a parser might produce are the following:
+ *
+ * <pre>
+ * preContext postContext
+ * "" "" The parser does not support context
+ * "let " "=7" Pre- and post-context only
+ * "let " "for=7" Pre- and post-context and error text
+ * "" "for" Error text only
+ * </pre>
+ *
+ * <p>Examples of engines which use UParseError (or may use it in the
+ * future) are Transliterator, RuleBasedBreakIterator, and
+ * RegexPattern.
+ *
+ * @stable ICU 2.0
+ */
+typedef struct UParseError {
+
+ /**
+ * The line on which the error occured. If the parser uses this
+ * field, it sets it to the line number of the source text line on
+ * which the error appears, which will be be a value >= 1. If the
+ * parse does not support line numbers, the value will be <= 0.
+ * @stable ICU 2.0
+ */
+ int32_t line;
+
+ /**
+ * The character offset to the error. If the line field is >= 1,
+ * then this is the offset from the start of the line. Otherwise,
+ * this is the offset from the start of the text. If the parser
+ * does not support this field, it will have a value < 0.
+ * @stable ICU 2.0
+ */
+ int32_t offset;
+
+ /**
+ * Textual context before the error. Null-terminated. The empty
+ * string if not supported by parser.
+ * @stable ICU 2.0
+ */
+ UChar preContext[U_PARSE_CONTEXT_LEN];
+
+ /**
+ * The error itself and/or textual context after the error.
+ * Null-terminated. The empty string if not supported by parser.
+ * @stable ICU 2.0
+ */
+ UChar postContext[U_PARSE_CONTEXT_LEN];
+
+} UParseError;
+
+#endif
diff --git a/WebKit/mac/icu/unicode/platform.h b/WebKit/mac/icu/unicode/platform.h
new file mode 100644
index 0000000..9595a26
--- /dev/null
+++ b/WebKit/mac/icu/unicode/platform.h
@@ -0,0 +1,267 @@
+/*
+******************************************************************************
+*
+* Copyright (C) 1997-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+*
+******************************************************************************
+*
+* FILE NAME : platform.h
+*
+* Date Name Description
+* 05/13/98 nos Creation (content moved here from ptypes.h).
+* 03/02/99 stephen Added AS400 support.
+* 03/30/99 stephen Added Linux support.
+* 04/13/99 stephen Reworked for autoconf.
+******************************************************************************
+*/
+
+/* Define the platform we're on. */
+#ifndef U_DARWIN
+#define U_DARWIN
+#endif
+
+/* Define whether inttypes.h is available */
+#ifndef U_HAVE_INTTYPES_H
+#define U_HAVE_INTTYPES_H 1
+#endif
+
+/*
+ * Define what support for C++ streams is available.
+ * If U_IOSTREAM_SOURCE is set to 199711, then <iostream> is available
+ * (1997711 is the date the ISO/IEC C++ FDIS was published), and then
+ * one should qualify streams using the std namespace in ICU header
+ * files.
+ * If U_IOSTREAM_SOURCE is set to 198506, then <iostream.h> is
+ * available instead (198506 is the date when Stroustrup published
+ * "An Extensible I/O Facility for C++" at the summer USENIX conference).
+ * If U_IOSTREAM_SOURCE is 0, then C++ streams are not available and
+ * support for them will be silently suppressed in ICU.
+ *
+ */
+
+#ifndef U_IOSTREAM_SOURCE
+#define U_IOSTREAM_SOURCE 199711
+#endif
+
+/* Determines whether specific types are available */
+#ifndef U_HAVE_INT8_T
+#define U_HAVE_INT8_T 1
+#endif
+
+#ifndef U_HAVE_UINT8_T
+#define U_HAVE_UINT8_T 0
+#endif
+
+#ifndef U_HAVE_INT16_T
+#define U_HAVE_INT16_T 1
+#endif
+
+#ifndef U_HAVE_UINT16_T
+#define U_HAVE_UINT16_T 0
+#endif
+
+#ifndef U_HAVE_INT32_T
+#define U_HAVE_INT32_T 1
+#endif
+
+#ifndef U_HAVE_UINT32_T
+#define U_HAVE_UINT32_T 0
+#endif
+
+#ifndef U_HAVE_INT64_T
+#define U_HAVE_INT64_T 1
+#endif
+
+#ifndef U_HAVE_UINT64_T
+#define U_HAVE_UINT64_T 0
+#endif
+
+/*===========================================================================*/
+/* Generic data types */
+/*===========================================================================*/
+
+#include <sys/types.h>
+
+/* If your platform does not have the <inttypes.h> header, you may
+ need to edit the typedefs below. */
+#if U_HAVE_INTTYPES_H
+
+/* autoconf 2.13 sometimes can't properly find the data types in <inttypes.h> */
+/* os/390 needs <inttypes.h>, but it doesn't have int8_t, and it sometimes */
+/* doesn't have uint8_t depending on the OS version. */
+/* So we have this work around. */
+#ifdef OS390
+/* The features header is needed to get (u)int64_t sometimes. */
+#include <features.h>
+#if ! U_HAVE_INT8_T
+typedef signed char int8_t;
+#endif
+#if !defined(__uint8_t)
+#define __uint8_t 1
+typedef unsigned char uint8_t;
+#endif
+#endif /* OS390 */
+
+#include <inttypes.h>
+
+#else /* U_HAVE_INTTYPES_H */
+
+#if ! U_HAVE_INT8_T
+typedef signed char int8_t;
+#endif
+
+#if ! U_HAVE_UINT8_T
+typedef unsigned char uint8_t;
+#endif
+
+#if ! U_HAVE_INT16_T
+typedef signed short int16_t;
+#endif
+
+#if ! U_HAVE_UINT16_T
+typedef unsigned short uint16_t;
+#endif
+
+#if ! U_HAVE_INT32_T
+typedef signed int int32_t;
+#endif
+
+#if ! U_HAVE_UINT32_T
+typedef unsigned int uint32_t;
+#endif
+
+#if ! U_HAVE_INT64_T
+ typedef signed long long int64_t;
+/* else we may not have a 64-bit type */
+#endif
+
+#if ! U_HAVE_UINT64_T
+ typedef unsigned long long uint64_t;
+/* else we may not have a 64-bit type */
+#endif
+
+#endif
+
+/*===========================================================================*/
+/* Compiler and environment features */
+/*===========================================================================*/
+
+/* Define whether namespace is supported */
+#ifndef U_HAVE_NAMESPACE
+#define U_HAVE_NAMESPACE 1
+#endif
+
+/* Determines the endianness of the platform
+ It's done this way in case multiple architectures are being built at once.
+ For example, Darwin supports fat binaries, which can be both PPC and x86 based. */
+#if defined(BYTE_ORDER) && defined(BIG_ENDIAN)
+#define U_IS_BIG_ENDIAN (BYTE_ORDER == BIG_ENDIAN)
+#else
+#define U_IS_BIG_ENDIAN 1
+#endif
+
+/* 1 or 0 to enable or disable threads. If undefined, default is: enable threads. */
+#define ICU_USE_THREADS 1
+
+#ifndef U_DEBUG
+#define U_DEBUG 0
+#endif
+
+#ifndef U_RELEASE
+#define U_RELEASE 1
+#endif
+
+/* Determine whether to disable renaming or not. This overrides the
+ setting in umachine.h which is for all platforms. */
+#ifndef U_DISABLE_RENAMING
+#define U_DISABLE_RENAMING 1
+#endif
+
+/* Determine whether to override new and delete. */
+#ifndef U_OVERRIDE_CXX_ALLOCATION
+#define U_OVERRIDE_CXX_ALLOCATION 1
+#endif
+/* Determine whether to override placement new and delete for STL. */
+#ifndef U_HAVE_PLACEMENT_NEW
+#define U_HAVE_PLACEMENT_NEW 1
+#endif
+
+/* Determine whether to enable tracing. */
+#ifndef U_ENABLE_TRACING
+#define U_ENABLE_TRACING 1
+#endif
+
+/* Define the library suffix in a C syntax. */
+#define U_HAVE_LIB_SUFFIX 0
+#define U_LIB_SUFFIX_C_NAME
+#define U_LIB_SUFFIX_C_NAME_STRING ""
+
+/*===========================================================================*/
+/* Character data types */
+/*===========================================================================*/
+
+#if defined(OS390) || defined(OS400)
+# define U_CHARSET_FAMILY 1
+#endif
+
+/*===========================================================================*/
+/* Information about wchar support */
+/*===========================================================================*/
+
+#define U_HAVE_WCHAR_H 1
+#define U_SIZEOF_WCHAR_T 4
+
+#define U_HAVE_WCSCPY 1
+
+/*===========================================================================*/
+/* Information about POSIX support */
+/*===========================================================================*/
+
+#define U_HAVE_NL_LANGINFO 1
+#define U_HAVE_NL_LANGINFO_CODESET 1
+#define U_NL_LANGINFO_CODESET CODESET
+
+#if 1
+#define U_TZSET tzset
+#endif
+#if 0
+#define U_TIMEZONE
+#endif
+#if 1
+#define U_TZNAME tzname
+#endif
+
+#define U_HAVE_MMAP 1
+#define U_HAVE_POPEN 1
+
+/*===========================================================================*/
+/* Symbol import-export control */
+/*===========================================================================*/
+
+#define U_EXPORT
+/* U_CALLCONV is releated to U_EXPORT2 */
+#define U_EXPORT2
+
+/* cygwin needs to export/import data */
+#ifdef U_CYGWIN
+#define U_IMPORT __declspec(dllimport)
+#else
+#define U_IMPORT
+#endif
+
+/*===========================================================================*/
+/* Code alignment and C function inlining */
+/*===========================================================================*/
+
+#ifndef U_INLINE
+#define U_INLINE inline
+#endif
+
+#define U_ALIGN_CODE(n)
+
+/*===========================================================================*/
+/* Programs used by ICU code */
+/*===========================================================================*/
+
+#define U_MAKE "/usr/bin/gnumake"
diff --git a/WebKit/mac/icu/unicode/putil.h b/WebKit/mac/icu/unicode/putil.h
new file mode 100644
index 0000000..685df53
--- /dev/null
+++ b/WebKit/mac/icu/unicode/putil.h
@@ -0,0 +1,180 @@
+/*
+******************************************************************************
+*
+* Copyright (C) 1997-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+*
+******************************************************************************
+*
+* FILE NAME : putil.h
+*
+* Date Name Description
+* 05/14/98 nos Creation (content moved here from utypes.h).
+* 06/17/99 erm Added IEEE_754
+* 07/22/98 stephen Added IEEEremainder, max, min, trunc
+* 08/13/98 stephen Added isNegativeInfinity, isPositiveInfinity
+* 08/24/98 stephen Added longBitsFromDouble
+* 03/02/99 stephen Removed openFile(). Added AS400 support.
+* 04/15/99 stephen Converted to C
+* 11/15/99 helena Integrated S/390 changes for IEEE support.
+* 01/11/00 helena Added u_getVersion.
+******************************************************************************
+*/
+
+#ifndef PUTIL_H
+#define PUTIL_H
+
+#include "unicode/utypes.h"
+
+/* Define this to 1 if your platform supports IEEE 754 floating point,
+ to 0 if it does not. */
+#ifndef IEEE_754
+# define IEEE_754 1
+#endif
+
+/*==========================================================================*/
+/* Platform utilities */
+/*==========================================================================*/
+
+/**
+ * Platform utilities isolates the platform dependencies of the
+ * libarary. For each platform which this code is ported to, these
+ * functions may have to be re-implemented.
+ */
+
+/**
+ * Return the ICU data directory.
+ * The data directory is where common format ICU data files (.dat files)
+ * are loaded from. Note that normal use of the built-in ICU
+ * facilities does not require loading of an external data file;
+ * unless you are adding custom data to ICU, the data directory
+ * does not need to be set.
+ *
+ * The data directory is determined as follows:
+ * If u_setDataDirectory() has been called, that is it, otherwise
+ * if the ICU_DATA environment variable is set, use that, otherwise
+ * If a data directory was specifed at ICU build time
+ * (#define ICU_DATA_DIR "path"), use that,
+ * otherwise no data directory is available.
+ *
+ * @return the data directory, or an empty string ("") if no data directory has
+ * been specified.
+ *
+ * @stable ICU 2.0
+ */
+U_STABLE const char* U_EXPORT2 u_getDataDirectory(void);
+
+/**
+ * Set the ICU data directory.
+ * The data directory is where common format ICU data files (.dat files)
+ * are loaded from. Note that normal use of the built-in ICU
+ * facilities does not require loading of an external data file;
+ * unless you are adding custom data to ICU, the data directory
+ * does not need to be set.
+ *
+ * This function should be called at most once in a process, before the
+ * first ICU operation (e.g., u_init()) that will require the loading of an
+ * ICU data file.
+ * This function is not thread-safe. Use it before calling ICU APIs from
+ * multiple threads.
+ *
+ * @param directory The directory to be set.
+ *
+ * @see u_init
+ * @stable ICU 2.0
+ */
+U_STABLE void U_EXPORT2 u_setDataDirectory(const char *directory);
+
+/**
+ * Please use ucnv_getDefaultName() instead.
+ * Return the default codepage for this platform and locale.
+ * This function can call setlocale() on Unix platforms. Please read the
+ * platform documentation on setlocale() before calling this function.
+ * @return the default codepage for this platform
+ * @internal
+ */
+U_INTERNAL const char* U_EXPORT2 uprv_getDefaultCodepage(void);
+
+/**
+ * Please use uloc_getDefault() instead.
+ * Return the default locale ID string by querying ths system, or
+ * zero if one cannot be found.
+ * This function can call setlocale() on Unix platforms. Please read the
+ * platform documentation on setlocale() before calling this function.
+ * @return the default locale ID string
+ * @internal
+ */
+U_INTERNAL const char* U_EXPORT2 uprv_getDefaultLocaleID(void);
+
+/**
+ * Filesystem file and path separator characters.
+ * Example: '/' and ':' on Unix, '\\' and ';' on Windows.
+ * @stable ICU 2.0
+ */
+#ifdef XP_MAC
+# define U_FILE_SEP_CHAR ':'
+# define U_FILE_ALT_SEP_CHAR ':'
+# define U_PATH_SEP_CHAR ';'
+# define U_FILE_SEP_STRING ":"
+# define U_FILE_ALT_SEP_STRING ":"
+# define U_PATH_SEP_STRING ";"
+#elif defined(WIN32) || defined(OS2)
+# define U_FILE_SEP_CHAR '\\'
+# define U_FILE_ALT_SEP_CHAR '/'
+# define U_PATH_SEP_CHAR ';'
+# define U_FILE_SEP_STRING "\\"
+# define U_FILE_ALT_SEP_STRING "/"
+# define U_PATH_SEP_STRING ";"
+#else
+# define U_FILE_SEP_CHAR '/'
+# define U_FILE_ALT_SEP_CHAR '/'
+# define U_PATH_SEP_CHAR ':'
+# define U_FILE_SEP_STRING "/"
+# define U_FILE_ALT_SEP_STRING "/"
+# define U_PATH_SEP_STRING ":"
+#endif
+
+/**
+ * Convert char characters to UChar characters.
+ * This utility function is useful only for "invariant characters"
+ * that are encoded in the platform default encoding.
+ * They are a small, constant subset of the encoding and include
+ * just the latin letters, digits, and some punctuation.
+ * For details, see U_CHARSET_FAMILY.
+ *
+ * @param cs Input string, points to <code>length</code>
+ * character bytes from a subset of the platform encoding.
+ * @param us Output string, points to memory for <code>length</code>
+ * Unicode characters.
+ * @param length The number of characters to convert; this may
+ * include the terminating <code>NUL</code>.
+ *
+ * @see U_CHARSET_FAMILY
+ * @stable ICU 2.0
+ */
+U_STABLE void U_EXPORT2
+u_charsToUChars(const char *cs, UChar *us, int32_t length);
+
+/**
+ * Convert UChar characters to char characters.
+ * This utility function is useful only for "invariant characters"
+ * that can be encoded in the platform default encoding.
+ * They are a small, constant subset of the encoding and include
+ * just the latin letters, digits, and some punctuation.
+ * For details, see U_CHARSET_FAMILY.
+ *
+ * @param us Input string, points to <code>length</code>
+ * Unicode characters that can be encoded with the
+ * codepage-invariant subset of the platform encoding.
+ * @param cs Output string, points to memory for <code>length</code>
+ * character bytes.
+ * @param length The number of characters to convert; this may
+ * include the terminating <code>NUL</code>.
+ *
+ * @see U_CHARSET_FAMILY
+ * @stable ICU 2.0
+ */
+U_STABLE void U_EXPORT2
+u_UCharsToChars(const UChar *us, char *cs, int32_t length);
+
+#endif
diff --git a/WebKit/mac/icu/unicode/uchar.h b/WebKit/mac/icu/unicode/uchar.h
new file mode 100644
index 0000000..7fd490c
--- /dev/null
+++ b/WebKit/mac/icu/unicode/uchar.h
@@ -0,0 +1,2798 @@
+/*
+**********************************************************************
+* Copyright (C) 1997-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+**********************************************************************
+*
+* File UCHAR.H
+*
+* Modification History:
+*
+* Date Name Description
+* 04/02/97 aliu Creation.
+* 03/29/99 helena Updated for C APIs.
+* 4/15/99 Madhu Updated for C Implementation and Javadoc
+* 5/20/99 Madhu Added the function u_getVersion()
+* 8/19/1999 srl Upgraded scripts to Unicode 3.0
+* 8/27/1999 schererm UCharDirection constants: U_...
+* 11/11/1999 weiv added u_isalnum(), cleaned comments
+* 01/11/2000 helena Renamed u_getVersion to u_getUnicodeVersion().
+******************************************************************************
+*/
+
+#ifndef UCHAR_H
+#define UCHAR_H
+
+#include "unicode/utypes.h"
+
+U_CDECL_BEGIN
+
+/*==========================================================================*/
+/* Unicode version number */
+/*==========================================================================*/
+/**
+ * Unicode version number, default for the current ICU version.
+ * The actual Unicode Character Database (UCD) data is stored in uprops.dat
+ * and may be generated from UCD files from a different Unicode version.
+ * Call u_getUnicodeVersion to get the actual Unicode version of the data.
+ *
+ * @see u_getUnicodeVersion
+ * @stable ICU 2.0
+ */
+#define U_UNICODE_VERSION "4.0.1"
+
+/**
+ * \file
+ * \brief C API: Unicode Properties
+ *
+ * This C API provides low-level access to the Unicode Character Database.
+ * In addition to raw property values, some convenience functions calculate
+ * derived properties, for example for Java-style programming.
+ *
+ * Unicode assigns each code point (not just assigned character) values for
+ * many properties.
+ * Most of them are simple boolean flags, or constants from a small enumerated list.
+ * For some properties, values are strings or other relatively more complex types.
+ *
+ * For more information see
+ * "About the Unicode Character Database" (http://www.unicode.org/ucd/)
+ * and the ICU User Guide chapter on Properties (http://oss.software.ibm.com/icu/userguide/properties.html).
+ *
+ * Many functions are designed to match java.lang.Character functions.
+ * See the individual function documentation,
+ * and see the JDK 1.4.1 java.lang.Character documentation
+ * at http://java.sun.com/j2se/1.4.1/docs/api/java/lang/Character.html
+ *
+ * There are also functions that provide easy migration from C/POSIX functions
+ * like isblank(). Their use is generally discouraged because the C/POSIX
+ * standards do not define their semantics beyond the ASCII range, which means
+ * that different implementations exhibit very different behavior.
+ * Instead, Unicode properties should be used directly.
+ *
+ * There are also only a few, broad C/POSIX character classes, and they tend
+ * to be used for conflicting purposes. For example, the "isalpha()" class
+ * is sometimes used to determine word boundaries, while a more sophisticated
+ * approach would at least distinguish initial letters from continuation
+ * characters (the latter including combining marks).
+ * (In ICU, BreakIterator is the most sophisticated API for word boundaries.)
+ * Another example: There is no "istitle()" class for titlecase characters.
+ *
+ * A summary of the behavior of some C/POSIX character classification implementations
+ * for Unicode is available at http://oss.software.ibm.com/cvs/icu/~checkout~/icuhtml/design/posix_classes.html
+ *
+ * <strong>Important</strong>:
+ * The behavior of the ICU C/POSIX-style character classification
+ * functions is subject to change according to discussion of the above summary.
+ *
+ * Note: There are several ICU whitespace functions.
+ * Comparison:
+ * - u_isUWhiteSpace=UCHAR_WHITE_SPACE: Unicode White_Space property;
+ * most of general categories "Z" (separators) + most whitespace ISO controls
+ * (including no-break spaces, but excluding IS1..IS4 and ZWSP)
+ * - u_isWhitespace: Java isWhitespace; Z + whitespace ISO controls but excluding no-break spaces
+ * - u_isJavaSpaceChar: Java isSpaceChar; just Z (including no-break spaces)
+ * - u_isspace: Z + whitespace ISO controls (including no-break spaces)
+ * - u_isblank: "horizontal spaces" = TAB + Zs - ZWSP
+ */
+
+/**
+ * Constants.
+ */
+
+/** The lowest Unicode code point value. Code points are non-negative. @stable ICU 2.0 */
+#define UCHAR_MIN_VALUE 0
+
+/**
+ * The highest Unicode code point value (scalar value) according to
+ * The Unicode Standard. This is a 21-bit value (20.1 bits, rounded up).
+ * For a single character, UChar32 is a simple type that can hold any code point value.
+ *
+ * @see UChar32
+ * @stable ICU 2.0
+ */
+#define UCHAR_MAX_VALUE 0x10ffff
+
+/**
+ * Get a single-bit bit set (a flag) from a bit number 0..31.
+ * @stable ICU 2.1
+ */
+#define U_MASK(x) ((uint32_t)1<<(x))
+
+/*
+ * !! Note: Several comments in this file are machine-read by the
+ * genpname tool. These comments describe the correspondence between
+ * icu enum constants and UCD entities. Do not delete them. Update
+ * these comments as needed.
+ *
+ * Any comment of the form "/ *[name]* /" (spaces added) is such
+ * a comment.
+ *
+ * The U_JG_* and U_GC_*_MASK constants are matched by their symbolic
+ * name, which must match PropertyValueAliases.txt.
+ */
+
+/**
+ * Selection constants for Unicode properties.
+ * These constants are used in functions like u_hasBinaryProperty to select
+ * one of the Unicode properties.
+ *
+ * The properties APIs are intended to reflect Unicode properties as defined
+ * in the Unicode Character Database (UCD) and Unicode Technical Reports (UTR).
+ * For details about the properties see http://www.unicode.org/ucd/ .
+ * For names of Unicode properties see the UCD file PropertyAliases.txt.
+ *
+ * Important: If ICU is built with UCD files from Unicode versions below, e.g., 3.2,
+ * then properties marked with "new in Unicode 3.2" are not or not fully available.
+ * Check u_getUnicodeVersion to be sure.
+ *
+ * @see u_hasBinaryProperty
+ * @see u_getIntPropertyValue
+ * @see u_getUnicodeVersion
+ * @stable ICU 2.1
+ */
+typedef enum UProperty {
+ /* See note !!. Comments of the form "Binary property Dash",
+ "Enumerated property Script", "Double property Numeric_Value",
+ and "String property Age" are read by genpname. */
+
+ /* Note: Place UCHAR_ALPHABETIC before UCHAR_BINARY_START so that
+ debuggers display UCHAR_ALPHABETIC as the symbolic name for 0,
+ rather than UCHAR_BINARY_START. Likewise for other *_START
+ identifiers. */
+
+ /** Binary property Alphabetic. Same as u_isUAlphabetic, different from u_isalpha.
+ Lu+Ll+Lt+Lm+Lo+Nl+Other_Alphabetic @stable ICU 2.1 */
+ UCHAR_ALPHABETIC=0,
+ /** First constant for binary Unicode properties. @stable ICU 2.1 */
+ UCHAR_BINARY_START=UCHAR_ALPHABETIC,
+ /** Binary property ASCII_Hex_Digit. 0-9 A-F a-f @stable ICU 2.1 */
+ UCHAR_ASCII_HEX_DIGIT,
+ /** Binary property Bidi_Control.
+ Format controls which have specific functions
+ in the Bidi Algorithm. @stable ICU 2.1 */
+ UCHAR_BIDI_CONTROL,
+ /** Binary property Bidi_Mirrored.
+ Characters that may change display in RTL text.
+ Same as u_isMirrored.
+ See Bidi Algorithm, UTR 9. @stable ICU 2.1 */
+ UCHAR_BIDI_MIRRORED,
+ /** Binary property Dash. Variations of dashes. @stable ICU 2.1 */
+ UCHAR_DASH,
+ /** Binary property Default_Ignorable_Code_Point (new in Unicode 3.2).
+ Ignorable in most processing.
+ <2060..206F, FFF0..FFFB, E0000..E0FFF>+Other_Default_Ignorable_Code_Point+(Cf+Cc+Cs-White_Space) @stable ICU 2.1 */
+ UCHAR_DEFAULT_IGNORABLE_CODE_POINT,
+ /** Binary property Deprecated (new in Unicode 3.2).
+ The usage of deprecated characters is strongly discouraged. @stable ICU 2.1 */
+ UCHAR_DEPRECATED,
+ /** Binary property Diacritic. Characters that linguistically modify
+ the meaning of another character to which they apply. @stable ICU 2.1 */
+ UCHAR_DIACRITIC,
+ /** Binary property Extender.
+ Extend the value or shape of a preceding alphabetic character,
+ e.g., length and iteration marks. @stable ICU 2.1 */
+ UCHAR_EXTENDER,
+ /** Binary property Full_Composition_Exclusion.
+ CompositionExclusions.txt+Singleton Decompositions+
+ Non-Starter Decompositions. @stable ICU 2.1 */
+ UCHAR_FULL_COMPOSITION_EXCLUSION,
+ /** Binary property Grapheme_Base (new in Unicode 3.2).
+ For programmatic determination of grapheme cluster boundaries.
+ [0..10FFFF]-Cc-Cf-Cs-Co-Cn-Zl-Zp-Grapheme_Link-Grapheme_Extend-CGJ @stable ICU 2.1 */
+ UCHAR_GRAPHEME_BASE,
+ /** Binary property Grapheme_Extend (new in Unicode 3.2).
+ For programmatic determination of grapheme cluster boundaries.
+ Me+Mn+Mc+Other_Grapheme_Extend-Grapheme_Link-CGJ @stable ICU 2.1 */
+ UCHAR_GRAPHEME_EXTEND,
+ /** Binary property Grapheme_Link (new in Unicode 3.2).
+ For programmatic determination of grapheme cluster boundaries. @stable ICU 2.1 */
+ UCHAR_GRAPHEME_LINK,
+ /** Binary property Hex_Digit.
+ Characters commonly used for hexadecimal numbers. @stable ICU 2.1 */
+ UCHAR_HEX_DIGIT,
+ /** Binary property Hyphen. Dashes used to mark connections
+ between pieces of words, plus the Katakana middle dot. @stable ICU 2.1 */
+ UCHAR_HYPHEN,
+ /** Binary property ID_Continue.
+ Characters that can continue an identifier.
+ DerivedCoreProperties.txt also says "NOTE: Cf characters should be filtered out."
+ ID_Start+Mn+Mc+Nd+Pc @stable ICU 2.1 */
+ UCHAR_ID_CONTINUE,
+ /** Binary property ID_Start.
+ Characters that can start an identifier.
+ Lu+Ll+Lt+Lm+Lo+Nl @stable ICU 2.1 */
+ UCHAR_ID_START,
+ /** Binary property Ideographic.
+ CJKV ideographs. @stable ICU 2.1 */
+ UCHAR_IDEOGRAPHIC,
+ /** Binary property IDS_Binary_Operator (new in Unicode 3.2).
+ For programmatic determination of
+ Ideographic Description Sequences. @stable ICU 2.1 */
+ UCHAR_IDS_BINARY_OPERATOR,
+ /** Binary property IDS_Trinary_Operator (new in Unicode 3.2).
+ For programmatic determination of
+ Ideographic Description Sequences. @stable ICU 2.1 */
+ UCHAR_IDS_TRINARY_OPERATOR,
+ /** Binary property Join_Control.
+ Format controls for cursive joining and ligation. @stable ICU 2.1 */
+ UCHAR_JOIN_CONTROL,
+ /** Binary property Logical_Order_Exception (new in Unicode 3.2).
+ Characters that do not use logical order and
+ require special handling in most processing. @stable ICU 2.1 */
+ UCHAR_LOGICAL_ORDER_EXCEPTION,
+ /** Binary property Lowercase. Same as u_isULowercase, different from u_islower.
+ Ll+Other_Lowercase @stable ICU 2.1 */
+ UCHAR_LOWERCASE,
+ /** Binary property Math. Sm+Other_Math @stable ICU 2.1 */
+ UCHAR_MATH,
+ /** Binary property Noncharacter_Code_Point.
+ Code points that are explicitly defined as illegal
+ for the encoding of characters. @stable ICU 2.1 */
+ UCHAR_NONCHARACTER_CODE_POINT,
+ /** Binary property Quotation_Mark. @stable ICU 2.1 */
+ UCHAR_QUOTATION_MARK,
+ /** Binary property Radical (new in Unicode 3.2).
+ For programmatic determination of
+ Ideographic Description Sequences. @stable ICU 2.1 */
+ UCHAR_RADICAL,
+ /** Binary property Soft_Dotted (new in Unicode 3.2).
+ Characters with a "soft dot", like i or j.
+ An accent placed on these characters causes
+ the dot to disappear. @stable ICU 2.1 */
+ UCHAR_SOFT_DOTTED,
+ /** Binary property Terminal_Punctuation.
+ Punctuation characters that generally mark
+ the end of textual units. @stable ICU 2.1 */
+ UCHAR_TERMINAL_PUNCTUATION,
+ /** Binary property Unified_Ideograph (new in Unicode 3.2).
+ For programmatic determination of
+ Ideographic Description Sequences. @stable ICU 2.1 */
+ UCHAR_UNIFIED_IDEOGRAPH,
+ /** Binary property Uppercase. Same as u_isUUppercase, different from u_isupper.
+ Lu+Other_Uppercase @stable ICU 2.1 */
+ UCHAR_UPPERCASE,
+ /** Binary property White_Space.
+ Same as u_isUWhiteSpace, different from u_isspace and u_isWhitespace.
+ Space characters+TAB+CR+LF-ZWSP-ZWNBSP @stable ICU 2.1 */
+ UCHAR_WHITE_SPACE,
+ /** Binary property XID_Continue.
+ ID_Continue modified to allow closure under
+ normalization forms NFKC and NFKD. @stable ICU 2.1 */
+ UCHAR_XID_CONTINUE,
+ /** Binary property XID_Start. ID_Start modified to allow
+ closure under normalization forms NFKC and NFKD. @stable ICU 2.1 */
+ UCHAR_XID_START,
+ /** Binary property Case_Sensitive. Either the source of a case
+ mapping or _in_ the target of a case mapping. Not the same as
+ the general category Cased_Letter. @stable ICU 2.6 */
+ UCHAR_CASE_SENSITIVE,
+ /** Binary property STerm (new in Unicode 4.0.1).
+ Sentence Terminal. Used in UAX #29: Text Boundaries
+ (http://www.unicode.org/reports/tr29/)
+ @draft ICU 3.0 */
+ UCHAR_S_TERM,
+ /** Binary property Variation_Selector (new in Unicode 4.0.1).
+ Indicates all those characters that qualify as Variation Selectors.
+ For details on the behavior of these characters,
+ see StandardizedVariants.html and 15.6 Variation Selectors.
+ @draft ICU 3.0 */
+ UCHAR_VARIATION_SELECTOR,
+ /** Binary property NFD_Inert.
+ ICU-specific property for characters that are inert under NFD,
+ i.e., they do not interact with adjacent characters.
+ Used for example in normalizing transforms in incremental mode
+ to find the boundary of safely normalizable text despite possible
+ text additions.
+
+ There is one such property per normalization form.
+ These properties are computed as follows - an inert character is:
+ a) unassigned, or ALL of the following:
+ b) of combining class 0.
+ c) not decomposed by this normalization form.
+ AND if NFC or NFKC,
+ d) can never compose with a previous character.
+ e) can never compose with a following character.
+ f) can never change if another character is added.
+ Example: a-breve might satisfy all but f, but if you
+ add an ogonek it changes to a-ogonek + breve
+
+ See also com.ibm.text.UCD.NFSkippable in the ICU4J repository,
+ and icu/source/common/unormimp.h .
+ @draft ICU 3.0 */
+ UCHAR_NFD_INERT,
+ /** Binary property NFKD_Inert.
+ ICU-specific property for characters that are inert under NFKD,
+ i.e., they do not interact with adjacent characters.
+ Used for example in normalizing transforms in incremental mode
+ to find the boundary of safely normalizable text despite possible
+ text additions.
+ @see UCHAR_NFD_INERT
+ @draft ICU 3.0 */
+ UCHAR_NFKD_INERT,
+ /** Binary property NFC_Inert.
+ ICU-specific property for characters that are inert under NFC,
+ i.e., they do not interact with adjacent characters.
+ Used for example in normalizing transforms in incremental mode
+ to find the boundary of safely normalizable text despite possible
+ text additions.
+ @see UCHAR_NFD_INERT
+ @draft ICU 3.0 */
+ UCHAR_NFC_INERT,
+ /** Binary property NFKC_Inert.
+ ICU-specific property for characters that are inert under NFKC,
+ i.e., they do not interact with adjacent characters.
+ Used for example in normalizing transforms in incremental mode
+ to find the boundary of safely normalizable text despite possible
+ text additions.
+ @see UCHAR_NFD_INERT
+ @draft ICU 3.0 */
+ UCHAR_NFKC_INERT,
+ /** Binary Property Segment_Starter.
+ ICU-specific property for characters that are starters in terms of
+ Unicode normalization and combining character sequences.
+ They have ccc=0 and do not occur in non-initial position of the
+ canonical decomposition of any character
+ (like " in NFD(a-umlaut) and a Jamo T in an NFD(Hangul LVT)).
+ ICU uses this property for segmenting a string for generating a set of
+ canonically equivalent strings, e.g. for canonical closure while
+ processing collation tailoring rules.
+ @draft ICU 3.0 */
+ UCHAR_SEGMENT_STARTER,
+ /** One more than the last constant for binary Unicode properties. @stable ICU 2.1 */
+ UCHAR_BINARY_LIMIT,
+
+ /** Enumerated property Bidi_Class.
+ Same as u_charDirection, returns UCharDirection values. @stable ICU 2.2 */
+ UCHAR_BIDI_CLASS=0x1000,
+ /** First constant for enumerated/integer Unicode properties. @stable ICU 2.2 */
+ UCHAR_INT_START=UCHAR_BIDI_CLASS,
+ /** Enumerated property Block.
+ Same as ublock_getCode, returns UBlockCode values. @stable ICU 2.2 */
+ UCHAR_BLOCK,
+ /** Enumerated property Canonical_Combining_Class.
+ Same as u_getCombiningClass, returns 8-bit numeric values. @stable ICU 2.2 */
+ UCHAR_CANONICAL_COMBINING_CLASS,
+ /** Enumerated property Decomposition_Type.
+ Returns UDecompositionType values. @stable ICU 2.2 */
+ UCHAR_DECOMPOSITION_TYPE,
+ /** Enumerated property East_Asian_Width.
+ See http://www.unicode.org/reports/tr11/
+ Returns UEastAsianWidth values. @stable ICU 2.2 */
+ UCHAR_EAST_ASIAN_WIDTH,
+ /** Enumerated property General_Category.
+ Same as u_charType, returns UCharCategory values. @stable ICU 2.2 */
+ UCHAR_GENERAL_CATEGORY,
+ /** Enumerated property Joining_Group.
+ Returns UJoiningGroup values. @stable ICU 2.2 */
+ UCHAR_JOINING_GROUP,
+ /** Enumerated property Joining_Type.
+ Returns UJoiningType values. @stable ICU 2.2 */
+ UCHAR_JOINING_TYPE,
+ /** Enumerated property Line_Break.
+ Returns ULineBreak values. @stable ICU 2.2 */
+ UCHAR_LINE_BREAK,
+ /** Enumerated property Numeric_Type.
+ Returns UNumericType values. @stable ICU 2.2 */
+ UCHAR_NUMERIC_TYPE,
+ /** Enumerated property Script.
+ Same as uscript_getScript, returns UScriptCode values. @stable ICU 2.2 */
+ UCHAR_SCRIPT,
+ /** Enumerated property Hangul_Syllable_Type, new in Unicode 4.
+ Returns UHangulSyllableType values. @stable ICU 2.6 */
+ UCHAR_HANGUL_SYLLABLE_TYPE,
+ /** Enumerated property NFD_Quick_Check.
+ Returns UNormalizationCheckResult values. @draft ICU 3.0 */
+ UCHAR_NFD_QUICK_CHECK,
+ /** Enumerated property NFKD_Quick_Check.
+ Returns UNormalizationCheckResult values. @draft ICU 3.0 */
+ UCHAR_NFKD_QUICK_CHECK,
+ /** Enumerated property NFC_Quick_Check.
+ Returns UNormalizationCheckResult values. @draft ICU 3.0 */
+ UCHAR_NFC_QUICK_CHECK,
+ /** Enumerated property NFKC_Quick_Check.
+ Returns UNormalizationCheckResult values. @draft ICU 3.0 */
+ UCHAR_NFKC_QUICK_CHECK,
+ /** Enumerated property Lead_Canonical_Combining_Class.
+ ICU-specific property for the ccc of the first code point
+ of the decomposition, or lccc(c)=ccc(NFD(c)[0]).
+ Useful for checking for canonically ordered text;
+ see UNORM_FCD and http://www.unicode.org/notes/tn5/#FCD .
+ Returns 8-bit numeric values like UCHAR_CANONICAL_COMBINING_CLASS. @draft ICU 3.0 */
+ UCHAR_LEAD_CANONICAL_COMBINING_CLASS,
+ /** Enumerated property Trail_Canonical_Combining_Class.
+ ICU-specific property for the ccc of the last code point
+ of the decomposition, or tccc(c)=ccc(NFD(c)[last]).
+ Useful for checking for canonically ordered text;
+ see UNORM_FCD and http://www.unicode.org/notes/tn5/#FCD .
+ Returns 8-bit numeric values like UCHAR_CANONICAL_COMBINING_CLASS. @draft ICU 3.0 */
+ UCHAR_TRAIL_CANONICAL_COMBINING_CLASS,
+ /** One more than the last constant for enumerated/integer Unicode properties. @stable ICU 2.2 */
+ UCHAR_INT_LIMIT,
+
+ /** Bitmask property General_Category_Mask.
+ This is the General_Category property returned as a bit mask.
+ When used in u_getIntPropertyValue(c), same as U_MASK(u_charType(c)),
+ returns bit masks for UCharCategory values where exactly one bit is set.
+ When used with u_getPropertyValueName() and u_getPropertyValueEnum(),
+ a multi-bit mask is used for sets of categories like "Letters".
+ Mask values should be cast to uint32_t.
+ @stable ICU 2.4 */
+ UCHAR_GENERAL_CATEGORY_MASK=0x2000,
+ /** First constant for bit-mask Unicode properties. @stable ICU 2.4 */
+ UCHAR_MASK_START=UCHAR_GENERAL_CATEGORY_MASK,
+ /** One more than the last constant for bit-mask Unicode properties. @stable ICU 2.4 */
+ UCHAR_MASK_LIMIT,
+
+ /** Double property Numeric_Value.
+ Corresponds to u_getNumericValue. @stable ICU 2.4 */
+ UCHAR_NUMERIC_VALUE=0x3000,
+ /** First constant for double Unicode properties. @stable ICU 2.4 */
+ UCHAR_DOUBLE_START=UCHAR_NUMERIC_VALUE,
+ /** One more than the last constant for double Unicode properties. @stable ICU 2.4 */
+ UCHAR_DOUBLE_LIMIT,
+
+ /** String property Age.
+ Corresponds to u_charAge. @stable ICU 2.4 */
+ UCHAR_AGE=0x4000,
+ /** First constant for string Unicode properties. @stable ICU 2.4 */
+ UCHAR_STRING_START=UCHAR_AGE,
+ /** String property Bidi_Mirroring_Glyph.
+ Corresponds to u_charMirror. @stable ICU 2.4 */
+ UCHAR_BIDI_MIRRORING_GLYPH,
+ /** String property Case_Folding.
+ Corresponds to u_strFoldCase in ustring.h. @stable ICU 2.4 */
+ UCHAR_CASE_FOLDING,
+ /** String property ISO_Comment.
+ Corresponds to u_getISOComment. @stable ICU 2.4 */
+ UCHAR_ISO_COMMENT,
+ /** String property Lowercase_Mapping.
+ Corresponds to u_strToLower in ustring.h. @stable ICU 2.4 */
+ UCHAR_LOWERCASE_MAPPING,
+ /** String property Name.
+ Corresponds to u_charName. @stable ICU 2.4 */
+ UCHAR_NAME,
+ /** String property Simple_Case_Folding.
+ Corresponds to u_foldCase. @stable ICU 2.4 */
+ UCHAR_SIMPLE_CASE_FOLDING,
+ /** String property Simple_Lowercase_Mapping.
+ Corresponds to u_tolower. @stable ICU 2.4 */
+ UCHAR_SIMPLE_LOWERCASE_MAPPING,
+ /** String property Simple_Titlecase_Mapping.
+ Corresponds to u_totitle. @stable ICU 2.4 */
+ UCHAR_SIMPLE_TITLECASE_MAPPING,
+ /** String property Simple_Uppercase_Mapping.
+ Corresponds to u_toupper. @stable ICU 2.4 */
+ UCHAR_SIMPLE_UPPERCASE_MAPPING,
+ /** String property Titlecase_Mapping.
+ Corresponds to u_strToTitle in ustring.h. @stable ICU 2.4 */
+ UCHAR_TITLECASE_MAPPING,
+ /** String property Unicode_1_Name.
+ Corresponds to u_charName. @stable ICU 2.4 */
+ UCHAR_UNICODE_1_NAME,
+ /** String property Uppercase_Mapping.
+ Corresponds to u_strToUpper in ustring.h. @stable ICU 2.4 */
+ UCHAR_UPPERCASE_MAPPING,
+ /** One more than the last constant for string Unicode properties. @stable ICU 2.4 */
+ UCHAR_STRING_LIMIT,
+
+ /** Represents a nonexistent or invalid property or property value. @stable ICU 2.4 */
+ UCHAR_INVALID_CODE = -1
+} UProperty;
+
+/**
+ * Data for enumerated Unicode general category types.
+ * See http://www.unicode.org/Public/UNIDATA/UnicodeData.html .
+ * @stable ICU 2.0
+ */
+typedef enum UCharCategory
+{
+ /** See note !!. Comments of the form "Cn" are read by genpname. */
+
+ /** Non-category for unassigned and non-character code points. @stable ICU 2.0 */
+ U_UNASSIGNED = 0,
+ /** Cn "Other, Not Assigned (no characters in [UnicodeData.txt] have this property)" (same as U_UNASSIGNED!) @stable ICU 2.0 */
+ U_GENERAL_OTHER_TYPES = 0,
+ /** Lu @stable ICU 2.0 */
+ U_UPPERCASE_LETTER = 1,
+ /** Ll @stable ICU 2.0 */
+ U_LOWERCASE_LETTER = 2,
+ /** Lt @stable ICU 2.0 */
+ U_TITLECASE_LETTER = 3,
+ /** Lm @stable ICU 2.0 */
+ U_MODIFIER_LETTER = 4,
+ /** Lo @stable ICU 2.0 */
+ U_OTHER_LETTER = 5,
+ /** Mn @stable ICU 2.0 */
+ U_NON_SPACING_MARK = 6,
+ /** Me @stable ICU 2.0 */
+ U_ENCLOSING_MARK = 7,
+ /** Mc @stable ICU 2.0 */
+ U_COMBINING_SPACING_MARK = 8,
+ /** Nd @stable ICU 2.0 */
+ U_DECIMAL_DIGIT_NUMBER = 9,
+ /** Nl @stable ICU 2.0 */
+ U_LETTER_NUMBER = 10,
+ /** No @stable ICU 2.0 */
+ U_OTHER_NUMBER = 11,
+ /** Zs @stable ICU 2.0 */
+ U_SPACE_SEPARATOR = 12,
+ /** Zl @stable ICU 2.0 */
+ U_LINE_SEPARATOR = 13,
+ /** Zp @stable ICU 2.0 */
+ U_PARAGRAPH_SEPARATOR = 14,
+ /** Cc @stable ICU 2.0 */
+ U_CONTROL_CHAR = 15,
+ /** Cf @stable ICU 2.0 */
+ U_FORMAT_CHAR = 16,
+ /** Co @stable ICU 2.0 */
+ U_PRIVATE_USE_CHAR = 17,
+ /** Cs @stable ICU 2.0 */
+ U_SURROGATE = 18,
+ /** Pd @stable ICU 2.0 */
+ U_DASH_PUNCTUATION = 19,
+ /** Ps @stable ICU 2.0 */
+ U_START_PUNCTUATION = 20,
+ /** Pe @stable ICU 2.0 */
+ U_END_PUNCTUATION = 21,
+ /** Pc @stable ICU 2.0 */
+ U_CONNECTOR_PUNCTUATION = 22,
+ /** Po @stable ICU 2.0 */
+ U_OTHER_PUNCTUATION = 23,
+ /** Sm @stable ICU 2.0 */
+ U_MATH_SYMBOL = 24,
+ /** Sc @stable ICU 2.0 */
+ U_CURRENCY_SYMBOL = 25,
+ /** Sk @stable ICU 2.0 */
+ U_MODIFIER_SYMBOL = 26,
+ /** So @stable ICU 2.0 */
+ U_OTHER_SYMBOL = 27,
+ /** Pi @stable ICU 2.0 */
+ U_INITIAL_PUNCTUATION = 28,
+ /** Pf @stable ICU 2.0 */
+ U_FINAL_PUNCTUATION = 29,
+ /** One higher than the last enum UCharCategory constant. @stable ICU 2.0 */
+ U_CHAR_CATEGORY_COUNT
+} UCharCategory;
+
+/**
+ * U_GC_XX_MASK constants are bit flags corresponding to Unicode
+ * general category values.
+ * For each category, the nth bit is set if the numeric value of the
+ * corresponding UCharCategory constant is n.
+ *
+ * There are also some U_GC_Y_MASK constants for groups of general categories
+ * like L for all letter categories.
+ *
+ * @see u_charType
+ * @see U_GET_GC_MASK
+ * @see UCharCategory
+ * @stable ICU 2.1
+ */
+#define U_GC_CN_MASK U_MASK(U_GENERAL_OTHER_TYPES)
+
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_LU_MASK U_MASK(U_UPPERCASE_LETTER)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_LL_MASK U_MASK(U_LOWERCASE_LETTER)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_LT_MASK U_MASK(U_TITLECASE_LETTER)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_LM_MASK U_MASK(U_MODIFIER_LETTER)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_LO_MASK U_MASK(U_OTHER_LETTER)
+
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_MN_MASK U_MASK(U_NON_SPACING_MARK)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_ME_MASK U_MASK(U_ENCLOSING_MARK)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_MC_MASK U_MASK(U_COMBINING_SPACING_MARK)
+
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_ND_MASK U_MASK(U_DECIMAL_DIGIT_NUMBER)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_NL_MASK U_MASK(U_LETTER_NUMBER)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_NO_MASK U_MASK(U_OTHER_NUMBER)
+
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_ZS_MASK U_MASK(U_SPACE_SEPARATOR)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_ZL_MASK U_MASK(U_LINE_SEPARATOR)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_ZP_MASK U_MASK(U_PARAGRAPH_SEPARATOR)
+
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_CC_MASK U_MASK(U_CONTROL_CHAR)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_CF_MASK U_MASK(U_FORMAT_CHAR)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_CO_MASK U_MASK(U_PRIVATE_USE_CHAR)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_CS_MASK U_MASK(U_SURROGATE)
+
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_PD_MASK U_MASK(U_DASH_PUNCTUATION)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_PS_MASK U_MASK(U_START_PUNCTUATION)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_PE_MASK U_MASK(U_END_PUNCTUATION)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_PC_MASK U_MASK(U_CONNECTOR_PUNCTUATION)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_PO_MASK U_MASK(U_OTHER_PUNCTUATION)
+
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_SM_MASK U_MASK(U_MATH_SYMBOL)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_SC_MASK U_MASK(U_CURRENCY_SYMBOL)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_SK_MASK U_MASK(U_MODIFIER_SYMBOL)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_SO_MASK U_MASK(U_OTHER_SYMBOL)
+
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_PI_MASK U_MASK(U_INITIAL_PUNCTUATION)
+/** Mask constant for a UCharCategory. @stable ICU 2.1 */
+#define U_GC_PF_MASK U_MASK(U_FINAL_PUNCTUATION)
+
+
+/** Mask constant for multiple UCharCategory bits (L Letters). @stable ICU 2.1 */
+#define U_GC_L_MASK \
+ (U_GC_LU_MASK|U_GC_LL_MASK|U_GC_LT_MASK|U_GC_LM_MASK|U_GC_LO_MASK)
+
+/** Mask constant for multiple UCharCategory bits (LC Cased Letters). @stable ICU 2.1 */
+#define U_GC_LC_MASK \
+ (U_GC_LU_MASK|U_GC_LL_MASK|U_GC_LT_MASK)
+
+/** Mask constant for multiple UCharCategory bits (M Marks). @stable ICU 2.1 */
+#define U_GC_M_MASK (U_GC_MN_MASK|U_GC_ME_MASK|U_GC_MC_MASK)
+
+/** Mask constant for multiple UCharCategory bits (N Numbers). @stable ICU 2.1 */
+#define U_GC_N_MASK (U_GC_ND_MASK|U_GC_NL_MASK|U_GC_NO_MASK)
+
+/** Mask constant for multiple UCharCategory bits (Z Separators). @stable ICU 2.1 */
+#define U_GC_Z_MASK (U_GC_ZS_MASK|U_GC_ZL_MASK|U_GC_ZP_MASK)
+
+/** Mask constant for multiple UCharCategory bits (C Others). @stable ICU 2.1 */
+#define U_GC_C_MASK \
+ (U_GC_CN_MASK|U_GC_CC_MASK|U_GC_CF_MASK|U_GC_CO_MASK|U_GC_CS_MASK)
+
+/** Mask constant for multiple UCharCategory bits (P Punctuation). @stable ICU 2.1 */
+#define U_GC_P_MASK \
+ (U_GC_PD_MASK|U_GC_PS_MASK|U_GC_PE_MASK|U_GC_PC_MASK|U_GC_PO_MASK| \
+ U_GC_PI_MASK|U_GC_PF_MASK)
+
+/** Mask constant for multiple UCharCategory bits (S Symbols). @stable ICU 2.1 */
+#define U_GC_S_MASK (U_GC_SM_MASK|U_GC_SC_MASK|U_GC_SK_MASK|U_GC_SO_MASK)
+
+/**
+ * This specifies the language directional property of a character set.
+ * @stable ICU 2.0
+ */
+typedef enum UCharDirection {
+ /** See note !!. Comments of the form "EN" are read by genpname. */
+
+ /** L @stable ICU 2.0 */
+ U_LEFT_TO_RIGHT = 0,
+ /** R @stable ICU 2.0 */
+ U_RIGHT_TO_LEFT = 1,
+ /** EN @stable ICU 2.0 */
+ U_EUROPEAN_NUMBER = 2,
+ /** ES @stable ICU 2.0 */
+ U_EUROPEAN_NUMBER_SEPARATOR = 3,
+ /** ET @stable ICU 2.0 */
+ U_EUROPEAN_NUMBER_TERMINATOR = 4,
+ /** AN @stable ICU 2.0 */
+ U_ARABIC_NUMBER = 5,
+ /** CS @stable ICU 2.0 */
+ U_COMMON_NUMBER_SEPARATOR = 6,
+ /** B @stable ICU 2.0 */
+ U_BLOCK_SEPARATOR = 7,
+ /** S @stable ICU 2.0 */
+ U_SEGMENT_SEPARATOR = 8,
+ /** WS @stable ICU 2.0 */
+ U_WHITE_SPACE_NEUTRAL = 9,
+ /** ON @stable ICU 2.0 */
+ U_OTHER_NEUTRAL = 10,
+ /** LRE @stable ICU 2.0 */
+ U_LEFT_TO_RIGHT_EMBEDDING = 11,
+ /** LRO @stable ICU 2.0 */
+ U_LEFT_TO_RIGHT_OVERRIDE = 12,
+ /** AL @stable ICU 2.0 */
+ U_RIGHT_TO_LEFT_ARABIC = 13,
+ /** RLE @stable ICU 2.0 */
+ U_RIGHT_TO_LEFT_EMBEDDING = 14,
+ /** RLO @stable ICU 2.0 */
+ U_RIGHT_TO_LEFT_OVERRIDE = 15,
+ /** PDF @stable ICU 2.0 */
+ U_POP_DIRECTIONAL_FORMAT = 16,
+ /** NSM @stable ICU 2.0 */
+ U_DIR_NON_SPACING_MARK = 17,
+ /** BN @stable ICU 2.0 */
+ U_BOUNDARY_NEUTRAL = 18,
+ /** @stable ICU 2.0 */
+ U_CHAR_DIRECTION_COUNT
+} UCharDirection;
+
+/**
+ * Constants for Unicode blocks, see the Unicode Data file Blocks.txt
+ * @stable ICU 2.0
+ */
+enum UBlockCode {
+
+ /** New No_Block value in Unicode 4. @stable ICU 2.6 */
+ UBLOCK_NO_BLOCK = 0, /*[none]*/ /* Special range indicating No_Block */
+
+ /** @stable ICU 2.0 */
+ UBLOCK_BASIC_LATIN = 1, /*[0000]*/ /*See note !!*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_LATIN_1_SUPPLEMENT=2, /*[0080]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_LATIN_EXTENDED_A =3, /*[0100]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_LATIN_EXTENDED_B =4, /*[0180]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_IPA_EXTENSIONS =5, /*[0250]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_SPACING_MODIFIER_LETTERS =6, /*[02B0]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_COMBINING_DIACRITICAL_MARKS =7, /*[0300]*/
+
+ /**
+ * Unicode 3.2 renames this block to "Greek and Coptic".
+ * @stable ICU 2.0
+ */
+ UBLOCK_GREEK =8, /*[0370]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_CYRILLIC =9, /*[0400]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_ARMENIAN =10, /*[0530]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_HEBREW =11, /*[0590]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_ARABIC =12, /*[0600]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_SYRIAC =13, /*[0700]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_THAANA =14, /*[0780]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_DEVANAGARI =15, /*[0900]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_BENGALI =16, /*[0980]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_GURMUKHI =17, /*[0A00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_GUJARATI =18, /*[0A80]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_ORIYA =19, /*[0B00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_TAMIL =20, /*[0B80]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_TELUGU =21, /*[0C00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_KANNADA =22, /*[0C80]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_MALAYALAM =23, /*[0D00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_SINHALA =24, /*[0D80]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_THAI =25, /*[0E00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_LAO =26, /*[0E80]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_TIBETAN =27, /*[0F00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_MYANMAR =28, /*[1000]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_GEORGIAN =29, /*[10A0]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_HANGUL_JAMO =30, /*[1100]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_ETHIOPIC =31, /*[1200]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_CHEROKEE =32, /*[13A0]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_UNIFIED_CANADIAN_ABORIGINAL_SYLLABICS =33, /*[1400]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_OGHAM =34, /*[1680]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_RUNIC =35, /*[16A0]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_KHMER =36, /*[1780]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_MONGOLIAN =37, /*[1800]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_LATIN_EXTENDED_ADDITIONAL =38, /*[1E00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_GREEK_EXTENDED =39, /*[1F00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_GENERAL_PUNCTUATION =40, /*[2000]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_SUPERSCRIPTS_AND_SUBSCRIPTS =41, /*[2070]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_CURRENCY_SYMBOLS =42, /*[20A0]*/
+
+ /**
+ * Unicode 3.2 renames this block to "Combining Diacritical Marks for Symbols".
+ * @stable ICU 2.0
+ */
+ UBLOCK_COMBINING_MARKS_FOR_SYMBOLS =43, /*[20D0]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_LETTERLIKE_SYMBOLS =44, /*[2100]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_NUMBER_FORMS =45, /*[2150]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_ARROWS =46, /*[2190]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_MATHEMATICAL_OPERATORS =47, /*[2200]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_MISCELLANEOUS_TECHNICAL =48, /*[2300]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_CONTROL_PICTURES =49, /*[2400]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_OPTICAL_CHARACTER_RECOGNITION =50, /*[2440]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_ENCLOSED_ALPHANUMERICS =51, /*[2460]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_BOX_DRAWING =52, /*[2500]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_BLOCK_ELEMENTS =53, /*[2580]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_GEOMETRIC_SHAPES =54, /*[25A0]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_MISCELLANEOUS_SYMBOLS =55, /*[2600]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_DINGBATS =56, /*[2700]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_BRAILLE_PATTERNS =57, /*[2800]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_CJK_RADICALS_SUPPLEMENT =58, /*[2E80]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_KANGXI_RADICALS =59, /*[2F00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_IDEOGRAPHIC_DESCRIPTION_CHARACTERS =60, /*[2FF0]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_CJK_SYMBOLS_AND_PUNCTUATION =61, /*[3000]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_HIRAGANA =62, /*[3040]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_KATAKANA =63, /*[30A0]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_BOPOMOFO =64, /*[3100]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_HANGUL_COMPATIBILITY_JAMO =65, /*[3130]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_KANBUN =66, /*[3190]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_BOPOMOFO_EXTENDED =67, /*[31A0]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_ENCLOSED_CJK_LETTERS_AND_MONTHS =68, /*[3200]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_CJK_COMPATIBILITY =69, /*[3300]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_CJK_UNIFIED_IDEOGRAPHS_EXTENSION_A =70, /*[3400]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_CJK_UNIFIED_IDEOGRAPHS =71, /*[4E00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_YI_SYLLABLES =72, /*[A000]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_YI_RADICALS =73, /*[A490]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_HANGUL_SYLLABLES =74, /*[AC00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_HIGH_SURROGATES =75, /*[D800]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_HIGH_PRIVATE_USE_SURROGATES =76, /*[DB80]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_LOW_SURROGATES =77, /*[DC00]*/
+
+ /**
+ * Same as UBLOCK_PRIVATE_USE_AREA.
+ * Until Unicode 3.1.1, the corresponding block name was "Private Use",
+ * and multiple code point ranges had this block.
+ * Unicode 3.2 renames the block for the BMP PUA to "Private Use Area" and
+ * adds separate blocks for the supplementary PUAs.
+ *
+ * @stable ICU 2.0
+ */
+ UBLOCK_PRIVATE_USE = 78,
+ /**
+ * Same as UBLOCK_PRIVATE_USE.
+ * Until Unicode 3.1.1, the corresponding block name was "Private Use",
+ * and multiple code point ranges had this block.
+ * Unicode 3.2 renames the block for the BMP PUA to "Private Use Area" and
+ * adds separate blocks for the supplementary PUAs.
+ *
+ * @stable ICU 2.0
+ */
+ UBLOCK_PRIVATE_USE_AREA =UBLOCK_PRIVATE_USE, /*[E000]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_CJK_COMPATIBILITY_IDEOGRAPHS =79, /*[F900]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_ALPHABETIC_PRESENTATION_FORMS =80, /*[FB00]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_ARABIC_PRESENTATION_FORMS_A =81, /*[FB50]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_COMBINING_HALF_MARKS =82, /*[FE20]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_CJK_COMPATIBILITY_FORMS =83, /*[FE30]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_SMALL_FORM_VARIANTS =84, /*[FE50]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_ARABIC_PRESENTATION_FORMS_B =85, /*[FE70]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_SPECIALS =86, /*[FFF0]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_HALFWIDTH_AND_FULLWIDTH_FORMS =87, /*[FF00]*/
+
+ /* New blocks in Unicode 3.1 */
+
+ /** @stable ICU 2.0 */
+ UBLOCK_OLD_ITALIC = 88 , /*[10300]*/
+ /** @stable ICU 2.0 */
+ UBLOCK_GOTHIC = 89 , /*[10330]*/
+ /** @stable ICU 2.0 */
+ UBLOCK_DESERET = 90 , /*[10400]*/
+ /** @stable ICU 2.0 */
+ UBLOCK_BYZANTINE_MUSICAL_SYMBOLS = 91 , /*[1D000]*/
+ /** @stable ICU 2.0 */
+ UBLOCK_MUSICAL_SYMBOLS = 92 , /*[1D100]*/
+ /** @stable ICU 2.0 */
+ UBLOCK_MATHEMATICAL_ALPHANUMERIC_SYMBOLS = 93 , /*[1D400]*/
+ /** @stable ICU 2.0 */
+ UBLOCK_CJK_UNIFIED_IDEOGRAPHS_EXTENSION_B = 94 , /*[20000]*/
+ /** @stable ICU 2.0 */
+ UBLOCK_CJK_COMPATIBILITY_IDEOGRAPHS_SUPPLEMENT = 95 , /*[2F800]*/
+ /** @stable ICU 2.0 */
+ UBLOCK_TAGS = 96, /*[E0000]*/
+
+ /* New blocks in Unicode 3.2 */
+
+ /**
+ * Unicode 4.0.1 renames the "Cyrillic Supplementary" block to "Cyrillic Supplement".
+ * @stable ICU 2.2
+ */
+ UBLOCK_CYRILLIC_SUPPLEMENTARY = 97,
+ /** @draft ICU 3.0 */
+ UBLOCK_CYRILLIC_SUPPLEMENT = UBLOCK_CYRILLIC_SUPPLEMENTARY, /*[0500]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_TAGALOG = 98, /*[1700]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_HANUNOO = 99, /*[1720]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_BUHID = 100, /*[1740]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_TAGBANWA = 101, /*[1760]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_MISCELLANEOUS_MATHEMATICAL_SYMBOLS_A = 102, /*[27C0]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_SUPPLEMENTAL_ARROWS_A = 103, /*[27F0]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_SUPPLEMENTAL_ARROWS_B = 104, /*[2900]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_MISCELLANEOUS_MATHEMATICAL_SYMBOLS_B = 105, /*[2980]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_SUPPLEMENTAL_MATHEMATICAL_OPERATORS = 106, /*[2A00]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_KATAKANA_PHONETIC_EXTENSIONS = 107, /*[31F0]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_VARIATION_SELECTORS = 108, /*[FE00]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_SUPPLEMENTARY_PRIVATE_USE_AREA_A = 109, /*[F0000]*/
+ /** @stable ICU 2.2 */
+ UBLOCK_SUPPLEMENTARY_PRIVATE_USE_AREA_B = 110, /*[100000]*/
+
+ /* New blocks in Unicode 4 */
+
+ /** @stable ICU 2.6 */
+ UBLOCK_LIMBU = 111, /*[1900]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_TAI_LE = 112, /*[1950]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_KHMER_SYMBOLS = 113, /*[19E0]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_PHONETIC_EXTENSIONS = 114, /*[1D00]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_MISCELLANEOUS_SYMBOLS_AND_ARROWS = 115, /*[2B00]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_YIJING_HEXAGRAM_SYMBOLS = 116, /*[4DC0]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_LINEAR_B_SYLLABARY = 117, /*[10000]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_LINEAR_B_IDEOGRAMS = 118, /*[10080]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_AEGEAN_NUMBERS = 119, /*[10100]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_UGARITIC = 120, /*[10380]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_SHAVIAN = 121, /*[10450]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_OSMANYA = 122, /*[10480]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_CYPRIOT_SYLLABARY = 123, /*[10800]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_TAI_XUAN_JING_SYMBOLS = 124, /*[1D300]*/
+ /** @stable ICU 2.6 */
+ UBLOCK_VARIATION_SELECTORS_SUPPLEMENT = 125, /*[E0100]*/
+
+ /** @stable ICU 2.0 */
+ UBLOCK_COUNT,
+
+ /** @stable ICU 2.0 */
+ UBLOCK_INVALID_CODE=-1
+};
+
+/** @stable ICU 2.0 */
+typedef enum UBlockCode UBlockCode;
+
+/**
+ * East Asian Width constants.
+ *
+ * @see UCHAR_EAST_ASIAN_WIDTH
+ * @see u_getIntPropertyValue
+ * @stable ICU 2.2
+ */
+typedef enum UEastAsianWidth {
+ U_EA_NEUTRAL, /*[N]*/ /*See note !!*/
+ U_EA_AMBIGUOUS, /*[A]*/
+ U_EA_HALFWIDTH, /*[H]*/
+ U_EA_FULLWIDTH, /*[F]*/
+ U_EA_NARROW, /*[Na]*/
+ U_EA_WIDE, /*[W]*/
+ U_EA_COUNT
+} UEastAsianWidth;
+/*
+ * Implementation note:
+ * Keep UEastAsianWidth constant values in sync with names list in genprops/props2.c.
+ */
+
+/**
+ * Selector constants for u_charName().
+ * u_charName() returns the "modern" name of a
+ * Unicode character; or the name that was defined in
+ * Unicode version 1.0, before the Unicode standard merged
+ * with ISO-10646; or an "extended" name that gives each
+ * Unicode code point a unique name.
+ *
+ * @see u_charName
+ * @stable ICU 2.0
+ */
+typedef enum UCharNameChoice {
+ U_UNICODE_CHAR_NAME,
+ U_UNICODE_10_CHAR_NAME,
+ U_EXTENDED_CHAR_NAME,
+ U_CHAR_NAME_CHOICE_COUNT
+} UCharNameChoice;
+
+/**
+ * Selector constants for u_getPropertyName() and
+ * u_getPropertyValueName(). These selectors are used to choose which
+ * name is returned for a given property or value. All properties and
+ * values have a long name. Most have a short name, but some do not.
+ * Unicode allows for additional names, beyond the long and short
+ * name, which would be indicated by U_LONG_PROPERTY_NAME + i, where
+ * i=1, 2,...
+ *
+ * @see u_getPropertyName()
+ * @see u_getPropertyValueName()
+ * @stable ICU 2.4
+ */
+typedef enum UPropertyNameChoice {
+ U_SHORT_PROPERTY_NAME,
+ U_LONG_PROPERTY_NAME,
+ U_PROPERTY_NAME_CHOICE_COUNT
+} UPropertyNameChoice;
+
+/**
+ * Decomposition Type constants.
+ *
+ * @see UCHAR_DECOMPOSITION_TYPE
+ * @stable ICU 2.2
+ */
+typedef enum UDecompositionType {
+ U_DT_NONE, /*[none]*/ /*See note !!*/
+ U_DT_CANONICAL, /*[can]*/
+ U_DT_COMPAT, /*[com]*/
+ U_DT_CIRCLE, /*[enc]*/
+ U_DT_FINAL, /*[fin]*/
+ U_DT_FONT, /*[font]*/
+ U_DT_FRACTION, /*[fra]*/
+ U_DT_INITIAL, /*[init]*/
+ U_DT_ISOLATED, /*[iso]*/
+ U_DT_MEDIAL, /*[med]*/
+ U_DT_NARROW, /*[nar]*/
+ U_DT_NOBREAK, /*[nb]*/
+ U_DT_SMALL, /*[sml]*/
+ U_DT_SQUARE, /*[sqr]*/
+ U_DT_SUB, /*[sub]*/
+ U_DT_SUPER, /*[sup]*/
+ U_DT_VERTICAL, /*[vert]*/
+ U_DT_WIDE, /*[wide]*/
+ U_DT_COUNT /* 18 */
+} UDecompositionType;
+
+/**
+ * Joining Type constants.
+ *
+ * @see UCHAR_JOINING_TYPE
+ * @stable ICU 2.2
+ */
+typedef enum UJoiningType {
+ U_JT_NON_JOINING, /*[U]*/ /*See note !!*/
+ U_JT_JOIN_CAUSING, /*[C]*/
+ U_JT_DUAL_JOINING, /*[D]*/
+ U_JT_LEFT_JOINING, /*[L]*/
+ U_JT_RIGHT_JOINING, /*[R]*/
+ U_JT_TRANSPARENT, /*[T]*/
+ U_JT_COUNT /* 6 */
+} UJoiningType;
+
+/**
+ * Joining Group constants.
+ *
+ * @see UCHAR_JOINING_GROUP
+ * @stable ICU 2.2
+ */
+typedef enum UJoiningGroup {
+ U_JG_NO_JOINING_GROUP,
+ U_JG_AIN,
+ U_JG_ALAPH,
+ U_JG_ALEF,
+ U_JG_BEH,
+ U_JG_BETH,
+ U_JG_DAL,
+ U_JG_DALATH_RISH,
+ U_JG_E,
+ U_JG_FEH,
+ U_JG_FINAL_SEMKATH,
+ U_JG_GAF,
+ U_JG_GAMAL,
+ U_JG_HAH,
+ U_JG_HAMZA_ON_HEH_GOAL,
+ U_JG_HE,
+ U_JG_HEH,
+ U_JG_HEH_GOAL,
+ U_JG_HETH,
+ U_JG_KAF,
+ U_JG_KAPH,
+ U_JG_KNOTTED_HEH,
+ U_JG_LAM,
+ U_JG_LAMADH,
+ U_JG_MEEM,
+ U_JG_MIM,
+ U_JG_NOON,
+ U_JG_NUN,
+ U_JG_PE,
+ U_JG_QAF,
+ U_JG_QAPH,
+ U_JG_REH,
+ U_JG_REVERSED_PE,
+ U_JG_SAD,
+ U_JG_SADHE,
+ U_JG_SEEN,
+ U_JG_SEMKATH,
+ U_JG_SHIN,
+ U_JG_SWASH_KAF,
+ U_JG_SYRIAC_WAW,
+ U_JG_TAH,
+ U_JG_TAW,
+ U_JG_TEH_MARBUTA,
+ U_JG_TETH,
+ U_JG_WAW,
+ U_JG_YEH,
+ U_JG_YEH_BARREE,
+ U_JG_YEH_WITH_TAIL,
+ U_JG_YUDH,
+ U_JG_YUDH_HE,
+ U_JG_ZAIN,
+ U_JG_FE, /**< @stable ICU 2.6 */
+ U_JG_KHAPH, /**< @stable ICU 2.6 */
+ U_JG_ZHAIN, /**< @stable ICU 2.6 */
+ U_JG_COUNT
+} UJoiningGroup;
+
+/**
+ * Line Break constants.
+ *
+ * @see UCHAR_LINE_BREAK
+ * @stable ICU 2.2
+ */
+typedef enum ULineBreak {
+ U_LB_UNKNOWN, /*[XX]*/ /*See note !!*/
+ U_LB_AMBIGUOUS, /*[AI]*/
+ U_LB_ALPHABETIC, /*[AL]*/
+ U_LB_BREAK_BOTH, /*[B2]*/
+ U_LB_BREAK_AFTER, /*[BA]*/
+ U_LB_BREAK_BEFORE, /*[BB]*/
+ U_LB_MANDATORY_BREAK, /*[BK]*/
+ U_LB_CONTINGENT_BREAK, /*[CB]*/
+ U_LB_CLOSE_PUNCTUATION, /*[CL]*/
+ U_LB_COMBINING_MARK, /*[CM]*/
+ U_LB_CARRIAGE_RETURN, /*[CR]*/
+ U_LB_EXCLAMATION, /*[EX]*/
+ U_LB_GLUE, /*[GL]*/
+ U_LB_HYPHEN, /*[HY]*/
+ U_LB_IDEOGRAPHIC, /*[ID]*/
+ U_LB_INSEPERABLE,
+ /** Renamed from the misspelled "inseperable" in Unicode 4.0.1/ICU 3.0 @draft ICU 3.0 */
+ U_LB_INSEPARABLE=U_LB_INSEPERABLE,/*[IN]*/
+ U_LB_INFIX_NUMERIC, /*[IS]*/
+ U_LB_LINE_FEED, /*[LF]*/
+ U_LB_NONSTARTER, /*[NS]*/
+ U_LB_NUMERIC, /*[NU]*/
+ U_LB_OPEN_PUNCTUATION, /*[OP]*/
+ U_LB_POSTFIX_NUMERIC, /*[PO]*/
+ U_LB_PREFIX_NUMERIC, /*[PR]*/
+ U_LB_QUOTATION, /*[QU]*/
+ U_LB_COMPLEX_CONTEXT, /*[SA]*/
+ U_LB_SURROGATE, /*[SG]*/
+ U_LB_SPACE, /*[SP]*/
+ U_LB_BREAK_SYMBOLS, /*[SY]*/
+ U_LB_ZWSPACE, /*[ZW]*/
+ U_LB_NEXT_LINE, /*[NL]*/ /* from here on: new in Unicode 4/ICU 2.6 */
+ U_LB_WORD_JOINER, /*[WJ]*/
+ U_LB_COUNT
+} ULineBreak;
+
+/**
+ * Numeric Type constants.
+ *
+ * @see UCHAR_NUMERIC_TYPE
+ * @stable ICU 2.2
+ */
+typedef enum UNumericType {
+ U_NT_NONE, /*[None]*/ /*See note !!*/
+ U_NT_DECIMAL, /*[de]*/
+ U_NT_DIGIT, /*[di]*/
+ U_NT_NUMERIC, /*[nu]*/
+ U_NT_COUNT
+} UNumericType;
+
+/**
+ * Hangul Syllable Type constants.
+ *
+ * @see UCHAR_HANGUL_SYLLABLE_TYPE
+ * @stable ICU 2.6
+ */
+typedef enum UHangulSyllableType {
+ U_HST_NOT_APPLICABLE, /*[NA]*/ /*See note !!*/
+ U_HST_LEADING_JAMO, /*[L]*/
+ U_HST_VOWEL_JAMO, /*[V]*/
+ U_HST_TRAILING_JAMO, /*[T]*/
+ U_HST_LV_SYLLABLE, /*[LV]*/
+ U_HST_LVT_SYLLABLE, /*[LVT]*/
+ U_HST_COUNT
+} UHangulSyllableType;
+
+/**
+ * Check a binary Unicode property for a code point.
+ *
+ * Unicode, especially in version 3.2, defines many more properties than the
+ * original set in UnicodeData.txt.
+ *
+ * The properties APIs are intended to reflect Unicode properties as defined
+ * in the Unicode Character Database (UCD) and Unicode Technical Reports (UTR).
+ * For details about the properties see http://www.unicode.org/ucd/ .
+ * For names of Unicode properties see the UCD file PropertyAliases.txt.
+ *
+ * Important: If ICU is built with UCD files from Unicode versions below 3.2,
+ * then properties marked with "new in Unicode 3.2" are not or not fully available.
+ *
+ * @param c Code point to test.
+ * @param which UProperty selector constant, identifies which binary property to check.
+ * Must be UCHAR_BINARY_START<=which<UCHAR_BINARY_LIMIT.
+ * @return TRUE or FALSE according to the binary Unicode property value for c.
+ * Also FALSE if 'which' is out of bounds or if the Unicode version
+ * does not have data for the property at all, or not for this code point.
+ *
+ * @see UProperty
+ * @see u_getIntPropertyValue
+ * @see u_getUnicodeVersion
+ * @stable ICU 2.1
+ */
+U_STABLE UBool U_EXPORT2
+u_hasBinaryProperty(UChar32 c, UProperty which);
+
+/**
+ * Check if a code point has the Alphabetic Unicode property.
+ * Same as u_hasBinaryProperty(c, UCHAR_ALPHABETIC).
+ * This is different from u_isalpha!
+ * @param c Code point to test
+ * @return true if the code point has the Alphabetic Unicode property, false otherwise
+ *
+ * @see UCHAR_ALPHABETIC
+ * @see u_isalpha
+ * @see u_hasBinaryProperty
+ * @stable ICU 2.1
+ */
+U_STABLE UBool U_EXPORT2
+u_isUAlphabetic(UChar32 c);
+
+/**
+ * Check if a code point has the Lowercase Unicode property.
+ * Same as u_hasBinaryProperty(c, UCHAR_LOWERCASE).
+ * This is different from u_islower!
+ * @param c Code point to test
+ * @return true if the code point has the Lowercase Unicode property, false otherwise
+ *
+ * @see UCHAR_LOWERCASE
+ * @see u_islower
+ * @see u_hasBinaryProperty
+ * @stable ICU 2.1
+ */
+U_STABLE UBool U_EXPORT2
+u_isULowercase(UChar32 c);
+
+/**
+ * Check if a code point has the Uppercase Unicode property.
+ * Same as u_hasBinaryProperty(c, UCHAR_UPPERCASE).
+ * This is different from u_isupper!
+ * @param c Code point to test
+ * @return true if the code point has the Uppercase Unicode property, false otherwise
+ *
+ * @see UCHAR_UPPERCASE
+ * @see u_isupper
+ * @see u_hasBinaryProperty
+ * @stable ICU 2.1
+ */
+U_STABLE UBool U_EXPORT2
+u_isUUppercase(UChar32 c);
+
+/**
+ * Check if a code point has the White_Space Unicode property.
+ * Same as u_hasBinaryProperty(c, UCHAR_WHITE_SPACE).
+ * This is different from both u_isspace and u_isWhitespace!
+ *
+ * Note: There are several ICU whitespace functions; please see the uchar.h
+ * file documentation for a detailed comparison.
+ *
+ * @param c Code point to test
+ * @return true if the code point has the White_Space Unicode property, false otherwise.
+ *
+ * @see UCHAR_WHITE_SPACE
+ * @see u_isWhitespace
+ * @see u_isspace
+ * @see u_isJavaSpaceChar
+ * @see u_hasBinaryProperty
+ * @stable ICU 2.1
+ */
+U_STABLE UBool U_EXPORT2
+u_isUWhiteSpace(UChar32 c);
+
+/**
+ * Get the property value for an enumerated or integer Unicode property for a code point.
+ * Also returns binary and mask property values.
+ *
+ * Unicode, especially in version 3.2, defines many more properties than the
+ * original set in UnicodeData.txt.
+ *
+ * The properties APIs are intended to reflect Unicode properties as defined
+ * in the Unicode Character Database (UCD) and Unicode Technical Reports (UTR).
+ * For details about the properties see http://www.unicode.org/ .
+ * For names of Unicode properties see the UCD file PropertyAliases.txt.
+ *
+ * Sample usage:
+ * UEastAsianWidth ea=(UEastAsianWidth)u_getIntPropertyValue(c, UCHAR_EAST_ASIAN_WIDTH);
+ * UBool b=(UBool)u_getIntPropertyValue(c, UCHAR_IDEOGRAPHIC);
+ *
+ * @param c Code point to test.
+ * @param which UProperty selector constant, identifies which property to check.
+ * Must be UCHAR_BINARY_START<=which<UCHAR_BINARY_LIMIT
+ * or UCHAR_INT_START<=which<UCHAR_INT_LIMIT
+ * or UCHAR_MASK_START<=which<UCHAR_MASK_LIMIT.
+ * @return Numeric value that is directly the property value or,
+ * for enumerated properties, corresponds to the numeric value of the enumerated
+ * constant of the respective property value enumeration type
+ * (cast to enum type if necessary).
+ * Returns 0 or 1 (for FALSE/TRUE) for binary Unicode properties.
+ * Returns a bit-mask for mask properties.
+ * Returns 0 if 'which' is out of bounds or if the Unicode version
+ * does not have data for the property at all, or not for this code point.
+ *
+ * @see UProperty
+ * @see u_hasBinaryProperty
+ * @see u_getIntPropertyMinValue
+ * @see u_getIntPropertyMaxValue
+ * @see u_getUnicodeVersion
+ * @stable ICU 2.2
+ */
+U_STABLE int32_t U_EXPORT2
+u_getIntPropertyValue(UChar32 c, UProperty which);
+
+/**
+ * Get the minimum value for an enumerated/integer/binary Unicode property.
+ * Can be used together with u_getIntPropertyMaxValue
+ * to allocate arrays of UnicodeSet or similar.
+ *
+ * @param which UProperty selector constant, identifies which binary property to check.
+ * Must be UCHAR_BINARY_START<=which<UCHAR_BINARY_LIMIT
+ * or UCHAR_INT_START<=which<UCHAR_INT_LIMIT.
+ * @return Minimum value returned by u_getIntPropertyValue for a Unicode property.
+ * 0 if the property selector is out of range.
+ *
+ * @see UProperty
+ * @see u_hasBinaryProperty
+ * @see u_getUnicodeVersion
+ * @see u_getIntPropertyMaxValue
+ * @see u_getIntPropertyValue
+ * @stable ICU 2.2
+ */
+U_STABLE int32_t U_EXPORT2
+u_getIntPropertyMinValue(UProperty which);
+
+/**
+ * Get the maximum value for an enumerated/integer/binary Unicode property.
+ * Can be used together with u_getIntPropertyMinValue
+ * to allocate arrays of UnicodeSet or similar.
+ *
+ * Examples for min/max values (for Unicode 3.2):
+ *
+ * - UCHAR_BIDI_CLASS: 0/18 (U_LEFT_TO_RIGHT/U_BOUNDARY_NEUTRAL)
+ * - UCHAR_SCRIPT: 0/45 (USCRIPT_COMMON/USCRIPT_TAGBANWA)
+ * - UCHAR_IDEOGRAPHIC: 0/1 (FALSE/TRUE)
+ *
+ * For undefined UProperty constant values, min/max values will be 0/-1.
+ *
+ * @param which UProperty selector constant, identifies which binary property to check.
+ * Must be UCHAR_BINARY_START<=which<UCHAR_BINARY_LIMIT
+ * or UCHAR_INT_START<=which<UCHAR_INT_LIMIT.
+ * @return Maximum value returned by u_getIntPropertyValue for a Unicode property.
+ * <=0 if the property selector is out of range.
+ *
+ * @see UProperty
+ * @see u_hasBinaryProperty
+ * @see u_getUnicodeVersion
+ * @see u_getIntPropertyMaxValue
+ * @see u_getIntPropertyValue
+ * @stable ICU 2.2
+ */
+U_STABLE int32_t U_EXPORT2
+u_getIntPropertyMaxValue(UProperty which);
+
+/**
+ * Get the numeric value for a Unicode code point as defined in the
+ * Unicode Character Database.
+ *
+ * A "double" return type is necessary because
+ * some numeric values are fractions, negative, or too large for int32_t.
+ *
+ * For characters without any numeric values in the Unicode Character Database,
+ * this function will return U_NO_NUMERIC_VALUE.
+ *
+ * Similar to java.lang.Character.getNumericValue(), but u_getNumericValue()
+ * also supports negative values, large values, and fractions,
+ * while Java's getNumericValue() returns values 10..35 for ASCII letters.
+ *
+ * @param c Code point to get the numeric value for.
+ * @return Numeric value of c, or U_NO_NUMERIC_VALUE if none is defined.
+ *
+ * @see U_NO_NUMERIC_VALUE
+ * @stable ICU 2.2
+ */
+U_STABLE double U_EXPORT2
+u_getNumericValue(UChar32 c);
+
+/**
+ * Special value that is returned by u_getNumericValue when
+ * no numeric value is defined for a code point.
+ *
+ * @see u_getNumericValue
+ * @stable ICU 2.2
+ */
+#define U_NO_NUMERIC_VALUE ((double)-123456789.)
+
+/**
+ * Determines whether the specified code point has the general category "Ll"
+ * (lowercase letter).
+ *
+ * Same as java.lang.Character.isLowerCase().
+ *
+ * This misses some characters that are also lowercase but
+ * have a different general category value.
+ * In order to include those, use UCHAR_LOWERCASE.
+ *
+ * In addition to being equivalent to a Java function, this also serves
+ * as a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is an Ll lowercase letter
+ *
+ * @see UCHAR_LOWERCASE
+ * @see u_isupper
+ * @see u_istitle
+ * @see u_islower
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_islower(UChar32 c);
+
+/**
+ * Determines whether the specified code point has the general category "Lu"
+ * (uppercase letter).
+ *
+ * Same as java.lang.Character.isUpperCase().
+ *
+ * This misses some characters that are also uppercase but
+ * have a different general category value.
+ * In order to include those, use UCHAR_UPPERCASE.
+ *
+ * In addition to being equivalent to a Java function, this also serves
+ * as a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is an Lu uppercase letter
+ *
+ * @see UCHAR_UPPERCASE
+ * @see u_islower
+ * @see u_istitle
+ * @see u_tolower
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isupper(UChar32 c);
+
+/**
+ * Determines whether the specified code point is a titlecase letter.
+ * True for general category "Lt" (titlecase letter).
+ *
+ * Same as java.lang.Character.isTitleCase().
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is an Lt titlecase letter
+ *
+ * @see u_isupper
+ * @see u_islower
+ * @see u_totitle
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_istitle(UChar32 c);
+
+/**
+ * Determines whether the specified code point is a digit character according to Java.
+ * True for characters with general category "Nd" (decimal digit numbers).
+ * Beginning with Unicode 4, this is the same as
+ * testing for the Numeric_Type of Decimal.
+ *
+ * Same as java.lang.Character.isDigit().
+ *
+ * In addition to being equivalent to a Java function, this also serves
+ * as a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is a digit character according to Character.isDigit()
+ *
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isdigit(UChar32 c);
+
+/**
+ * Determines whether the specified code point is a letter character.
+ * True for general categories "L" (letters).
+ *
+ * Same as java.lang.Character.isLetter().
+ *
+ * In addition to being equivalent to a Java function, this also serves
+ * as a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is a letter character
+ *
+ * @see u_isdigit
+ * @see u_isalnum
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isalpha(UChar32 c);
+
+/**
+ * Determines whether the specified code point is an alphanumeric character
+ * (letter or digit) according to Java.
+ * True for characters with general categories
+ * "L" (letters) and "Nd" (decimal digit numbers).
+ *
+ * Same as java.lang.Character.isLetterOrDigit().
+ *
+ * In addition to being equivalent to a Java function, this also serves
+ * as a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is an alphanumeric character according to Character.isLetterOrDigit()
+ *
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isalnum(UChar32 c);
+
+/**
+ * Determines whether the specified code point is a hexadecimal digit.
+ * This is equivalent to u_digit(c, 16)>=0.
+ * True for characters with general category "Nd" (decimal digit numbers)
+ * as well as Latin letters a-f and A-F in both ASCII and Fullwidth ASCII.
+ * (That is, for letters with code points
+ * 0041..0046, 0061..0066, FF21..FF26, FF41..FF46.)
+ *
+ * In order to narrow the definition of hexadecimal digits to only ASCII
+ * characters, use (c<=0x7f && u_isxdigit(c)).
+ *
+ * This is a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is a hexadecimal digit
+ *
+ * @stable ICU 2.6
+ */
+U_STABLE UBool U_EXPORT2
+u_isxdigit(UChar32 c);
+
+/**
+ * Determines whether the specified code point is a punctuation character.
+ * True for characters with general categories "P" (punctuation).
+ *
+ * This is a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is a punctuation character
+ *
+ * @stable ICU 2.6
+ */
+U_STABLE UBool U_EXPORT2
+u_ispunct(UChar32 c);
+
+/**
+ * Determines whether the specified code point is a "graphic" character
+ * (printable, excluding spaces).
+ * TRUE for all characters except those with general categories
+ * "Cc" (control codes), "Cf" (format controls), "Cs" (surrogates),
+ * "Cn" (unassigned), and "Z" (separators).
+ *
+ * This is a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is a "graphic" character
+ *
+ * @stable ICU 2.6
+ */
+U_STABLE UBool U_EXPORT2
+u_isgraph(UChar32 c);
+
+/**
+ * Determines whether the specified code point is a "blank" or "horizontal space",
+ * a character that visibly separates words on a line.
+ * The following are equivalent definitions:
+ *
+ * TRUE for Unicode White_Space characters except for "vertical space controls"
+ * where "vertical space controls" are the following characters:
+ * U+000A (LF) U+000B (VT) U+000C (FF) U+000D (CR) U+0085 (NEL) U+2028 (LS) U+2029 (PS)
+ *
+ * same as
+ *
+ * TRUE for U+0009 (TAB) and characters with general category "Zs" (space separators)
+ * except Zero Width Space (ZWSP, U+200B).
+ *
+ * Note: There are several ICU whitespace functions; please see the uchar.h
+ * file documentation for a detailed comparison.
+ *
+ * This is a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is a "blank"
+ *
+ * @stable ICU 2.6
+ */
+U_STABLE UBool U_EXPORT2
+u_isblank(UChar32 c);
+
+/**
+ * Determines whether the specified code point is "defined",
+ * which usually means that it is assigned a character.
+ * True for general categories other than "Cn" (other, not assigned),
+ * i.e., true for all code points mentioned in UnicodeData.txt.
+ *
+ * Note that non-character code points (e.g., U+FDD0) are not "defined"
+ * (they are Cn), but surrogate code points are "defined" (Cs).
+ *
+ * Same as java.lang.Character.isDefined().
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is assigned a character
+ *
+ * @see u_isdigit
+ * @see u_isalpha
+ * @see u_isalnum
+ * @see u_isupper
+ * @see u_islower
+ * @see u_istitle
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isdefined(UChar32 c);
+
+/**
+ * Determines if the specified character is a space character or not.
+ *
+ * Note: There are several ICU whitespace functions; please see the uchar.h
+ * file documentation for a detailed comparison.
+ *
+ * This is a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the character to be tested
+ * @return true if the character is a space character; false otherwise.
+ *
+ * @see u_isJavaSpaceChar
+ * @see u_isWhitespace
+ * @see u_isUWhiteSpace
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isspace(UChar32 c);
+
+/**
+ * Determine if the specified code point is a space character according to Java.
+ * True for characters with general categories "Z" (separators),
+ * which does not include control codes (e.g., TAB or Line Feed).
+ *
+ * Same as java.lang.Character.isSpaceChar().
+ *
+ * Note: There are several ICU whitespace functions; please see the uchar.h
+ * file documentation for a detailed comparison.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is a space character according to Character.isSpaceChar()
+ *
+ * @see u_isspace
+ * @see u_isWhitespace
+ * @see u_isUWhiteSpace
+ * @stable ICU 2.6
+ */
+U_STABLE UBool U_EXPORT2
+u_isJavaSpaceChar(UChar32 c);
+
+/**
+ * Determines if the specified code point is a whitespace character according to Java/ICU.
+ * A character is considered to be a Java whitespace character if and only
+ * if it satisfies one of the following criteria:
+ *
+ * - It is a Unicode separator (categories "Z"), but is not
+ * a no-break space (U+00A0 NBSP or U+2007 Figure Space or U+202F Narrow NBSP).
+ * - It is U+0009 HORIZONTAL TABULATION.
+ * - It is U+000A LINE FEED.
+ * - It is U+000B VERTICAL TABULATION.
+ * - It is U+000C FORM FEED.
+ * - It is U+000D CARRIAGE RETURN.
+ * - It is U+001C FILE SEPARATOR.
+ * - It is U+001D GROUP SEPARATOR.
+ * - It is U+001E RECORD SEPARATOR.
+ * - It is U+001F UNIT SEPARATOR.
+ * - It is U+0085 NEXT LINE.
+ *
+ * Same as java.lang.Character.isWhitespace() except that Java omits U+0085.
+ *
+ * Note: There are several ICU whitespace functions; please see the uchar.h
+ * file documentation for a detailed comparison.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is a whitespace character according to Java/ICU
+ *
+ * @see u_isspace
+ * @see u_isJavaSpaceChar
+ * @see u_isUWhiteSpace
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isWhitespace(UChar32 c);
+
+/**
+ * Determines whether the specified code point is a control character
+ * (as defined by this function).
+ * A control character is one of the following:
+ * - ISO 8-bit control character (U+0000..U+001f and U+007f..U+009f)
+ * - U_CONTROL_CHAR (Cc)
+ * - U_FORMAT_CHAR (Cf)
+ * - U_LINE_SEPARATOR (Zl)
+ * - U_PARAGRAPH_SEPARATOR (Zp)
+ *
+ * This is a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is a control character
+ *
+ * @see UCHAR_DEFAULT_IGNORABLE_CODE_POINT
+ * @see u_isprint
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_iscntrl(UChar32 c);
+
+/**
+ * Determines whether the specified code point is an ISO control code.
+ * True for U+0000..U+001f and U+007f..U+009f (general category "Cc").
+ *
+ * Same as java.lang.Character.isISOControl().
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is an ISO control code
+ *
+ * @see u_iscntrl
+ * @stable ICU 2.6
+ */
+U_STABLE UBool U_EXPORT2
+u_isISOControl(UChar32 c);
+
+/**
+ * Determines whether the specified code point is a printable character.
+ * True for general categories <em>other</em> than "C" (controls).
+ *
+ * This is a C/POSIX migration function.
+ * See the comments about C/POSIX character classification functions in the
+ * documentation at the top of this header file.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is a printable character
+ *
+ * @see UCHAR_DEFAULT_IGNORABLE_CODE_POINT
+ * @see u_iscntrl
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isprint(UChar32 c);
+
+/**
+ * Determines whether the specified code point is a base character.
+ * True for general categories "L" (letters), "N" (numbers),
+ * "Mc" (spacing combining marks), and "Me" (enclosing marks).
+ *
+ * Note that this is different from the Unicode definition in
+ * chapter 3.5, conformance clause D13,
+ * which defines base characters to be all characters (not Cn)
+ * that do not graphically combine with preceding characters (M)
+ * and that are neither control (Cc) or format (Cf) characters.
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is a base character according to this function
+ *
+ * @see u_isalpha
+ * @see u_isdigit
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isbase(UChar32 c);
+
+/**
+ * Returns the bidirectional category value for the code point,
+ * which is used in the Unicode bidirectional algorithm
+ * (UAX #9 http://www.unicode.org/reports/tr9/).
+ * Note that some <em>unassigned</em> code points have bidi values
+ * of R or AL because they are in blocks that are reserved
+ * for Right-To-Left scripts.
+ *
+ * Same as java.lang.Character.getDirectionality()
+ *
+ * @param c the code point to be tested
+ * @return the bidirectional category (UCharDirection) value
+ *
+ * @see UCharDirection
+ * @stable ICU 2.0
+ */
+U_STABLE UCharDirection U_EXPORT2
+u_charDirection(UChar32 c);
+
+/**
+ * Determines whether the code point has the Bidi_Mirrored property.
+ * This property is set for characters that are commonly used in
+ * Right-To-Left contexts and need to be displayed with a "mirrored"
+ * glyph.
+ *
+ * Same as java.lang.Character.isMirrored().
+ * Same as UCHAR_BIDI_MIRRORED
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the character has the Bidi_Mirrored property
+ *
+ * @see UCHAR_BIDI_MIRRORED
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isMirrored(UChar32 c);
+
+/**
+ * Maps the specified character to a "mirror-image" character.
+ * For characters with the Bidi_Mirrored property, implementations
+ * sometimes need a "poor man's" mapping to another Unicode
+ * character (code point) such that the default glyph may serve
+ * as the mirror-image of the default glyph of the specified
+ * character. This is useful for text conversion to and from
+ * codepages with visual order, and for displays without glyph
+ * selecetion capabilities.
+ *
+ * @param c the code point to be mapped
+ * @return another Unicode code point that may serve as a mirror-image
+ * substitute, or c itself if there is no such mapping or c
+ * does not have the Bidi_Mirrored property
+ *
+ * @see UCHAR_BIDI_MIRRORED
+ * @see u_isMirrored
+ * @stable ICU 2.0
+ */
+U_STABLE UChar32 U_EXPORT2
+u_charMirror(UChar32 c);
+
+/**
+ * Returns the general category value for the code point.
+ *
+ * Same as java.lang.Character.getType().
+ *
+ * @param c the code point to be tested
+ * @return the general category (UCharCategory) value
+ *
+ * @see UCharCategory
+ * @stable ICU 2.0
+ */
+U_STABLE int8_t U_EXPORT2
+u_charType(UChar32 c);
+
+/**
+ * Get a single-bit bit set for the general category of a character.
+ * This bit set can be compared bitwise with U_GC_SM_MASK, U_GC_L_MASK, etc.
+ * Same as U_MASK(u_charType(c)).
+ *
+ * @param c the code point to be tested
+ * @return a single-bit mask corresponding to the general category (UCharCategory) value
+ *
+ * @see u_charType
+ * @see UCharCategory
+ * @see U_GC_CN_MASK
+ * @stable ICU 2.1
+ */
+#define U_GET_GC_MASK(c) U_MASK(u_charType(c))
+
+/**
+ * Callback from u_enumCharTypes(), is called for each contiguous range
+ * of code points c (where start<=c<limit)
+ * with the same Unicode general category ("character type").
+ *
+ * The callback function can stop the enumeration by returning FALSE.
+ *
+ * @param context an opaque pointer, as passed into utrie_enum()
+ * @param start the first code point in a contiguous range with value
+ * @param limit one past the last code point in a contiguous range with value
+ * @param type the general category for all code points in [start..limit[
+ * @return FALSE to stop the enumeration
+ *
+ * @stable ICU 2.1
+ * @see UCharCategory
+ * @see u_enumCharTypes
+ */
+typedef UBool U_CALLCONV
+UCharEnumTypeRange(const void *context, UChar32 start, UChar32 limit, UCharCategory type);
+
+/**
+ * Enumerate efficiently all code points with their Unicode general categories.
+ *
+ * This is useful for building data structures (e.g., UnicodeSet's),
+ * for enumerating all assigned code points (type!=U_UNASSIGNED), etc.
+ *
+ * For each contiguous range of code points with a given general category ("character type"),
+ * the UCharEnumTypeRange function is called.
+ * Adjacent ranges have different types.
+ * The Unicode Standard guarantees that the numeric value of the type is 0..31.
+ *
+ * @param enumRange a pointer to a function that is called for each contiguous range
+ * of code points with the same general category
+ * @param context an opaque pointer that is passed on to the callback function
+ *
+ * @stable ICU 2.1
+ * @see UCharCategory
+ * @see UCharEnumTypeRange
+ */
+U_STABLE void U_EXPORT2
+u_enumCharTypes(UCharEnumTypeRange *enumRange, const void *context);
+
+#if !UCONFIG_NO_NORMALIZATION
+
+/**
+ * Returns the combining class of the code point as specified in UnicodeData.txt.
+ *
+ * @param c the code point of the character
+ * @return the combining class of the character
+ * @stable ICU 2.0
+ */
+U_STABLE uint8_t U_EXPORT2
+u_getCombiningClass(UChar32 c);
+
+#endif
+
+/**
+ * Returns the decimal digit value of a decimal digit character.
+ * Such characters have the general category "Nd" (decimal digit numbers)
+ * and a Numeric_Type of Decimal.
+ *
+ * Unlike ICU releases before 2.6, no digit values are returned for any
+ * Han characters because Han number characters are often used with a special
+ * Chinese-style number format (with characters for powers of 10 in between)
+ * instead of in decimal-positional notation.
+ * Unicode 4 explicitly assigns Han number characters the Numeric_Type
+ * Numeric instead of Decimal.
+ * See Jitterbug 1483 for more details.
+ *
+ * Use u_getIntPropertyValue(c, UCHAR_NUMERIC_TYPE) and u_getNumericValue()
+ * for complete numeric Unicode properties.
+ *
+ * @param c the code point for which to get the decimal digit value
+ * @return the decimal digit value of c,
+ * or -1 if c is not a decimal digit character
+ *
+ * @see u_getNumericValue
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_charDigitValue(UChar32 c);
+
+/**
+ * Returns the Unicode allocation block that contains the character.
+ *
+ * @param c the code point to be tested
+ * @return the block value (UBlockCode) for c
+ *
+ * @see UBlockCode
+ * @stable ICU 2.0
+ */
+U_STABLE UBlockCode U_EXPORT2
+ublock_getCode(UChar32 c);
+
+/**
+ * Retrieve the name of a Unicode character.
+ * Depending on <code>nameChoice</code>, the character name written
+ * into the buffer is the "modern" name or the name that was defined
+ * in Unicode version 1.0.
+ * The name contains only "invariant" characters
+ * like A-Z, 0-9, space, and '-'.
+ * Unicode 1.0 names are only retrieved if they are different from the modern
+ * names and if the data file contains the data for them. gennames may or may
+ * not be called with a command line option to include 1.0 names in unames.dat.
+ *
+ * @param code The character (code point) for which to get the name.
+ * It must be <code>0<=code<=0x10ffff</code>.
+ * @param nameChoice Selector for which name to get.
+ * @param buffer Destination address for copying the name.
+ * The name will always be zero-terminated.
+ * If there is no name, then the buffer will be set to the empty string.
+ * @param bufferLength <code>==sizeof(buffer)</code>
+ * @param pErrorCode Pointer to a UErrorCode variable;
+ * check for <code>U_SUCCESS()</code> after <code>u_charName()</code>
+ * returns.
+ * @return The length of the name, or 0 if there is no name for this character.
+ * If the bufferLength is less than or equal to the length, then the buffer
+ * contains the truncated name and the returned length indicates the full
+ * length of the name.
+ * The length does not include the zero-termination.
+ *
+ * @see UCharNameChoice
+ * @see u_charFromName
+ * @see u_enumCharNames
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_charName(UChar32 code, UCharNameChoice nameChoice,
+ char *buffer, int32_t bufferLength,
+ UErrorCode *pErrorCode);
+
+/**
+ * Get the ISO 10646 comment for a character.
+ * The ISO 10646 comment is an informative field in the Unicode Character
+ * Database (UnicodeData.txt field 11) and is from the ISO 10646 names list.
+ *
+ * @param c The character (code point) for which to get the ISO comment.
+ * It must be <code>0<=c<=0x10ffff</code>.
+ * @param dest Destination address for copying the comment.
+ * The comment will be zero-terminated if possible.
+ * If there is no comment, then the buffer will be set to the empty string.
+ * @param destCapacity <code>==sizeof(dest)</code>
+ * @param pErrorCode Pointer to a UErrorCode variable;
+ * check for <code>U_SUCCESS()</code> after <code>u_getISOComment()</code>
+ * returns.
+ * @return The length of the comment, or 0 if there is no comment for this character.
+ * If the destCapacity is less than or equal to the length, then the buffer
+ * contains the truncated name and the returned length indicates the full
+ * length of the name.
+ * The length does not include the zero-termination.
+ *
+ * @stable ICU 2.2
+ */
+U_STABLE int32_t U_EXPORT2
+u_getISOComment(UChar32 c,
+ char *dest, int32_t destCapacity,
+ UErrorCode *pErrorCode);
+
+/**
+ * Find a Unicode character by its name and return its code point value.
+ * The name is matched exactly and completely.
+ * If the name does not correspond to a code point, <i>pErrorCode</i>
+ * is set to <code>U_INVALID_CHAR_FOUND</code>.
+ * A Unicode 1.0 name is matched only if it differs from the modern name.
+ * Unicode names are all uppercase. Extended names are lowercase followed
+ * by an uppercase hexadecimal number, and within angle brackets.
+ *
+ * @param nameChoice Selector for which name to match.
+ * @param name The name to match.
+ * @param pErrorCode Pointer to a UErrorCode variable
+ * @return The Unicode value of the code point with the given name,
+ * or an undefined value if there is no such code point.
+ *
+ * @see UCharNameChoice
+ * @see u_charName
+ * @see u_enumCharNames
+ * @stable ICU 1.7
+ */
+U_STABLE UChar32 U_EXPORT2
+u_charFromName(UCharNameChoice nameChoice,
+ const char *name,
+ UErrorCode *pErrorCode);
+
+/**
+ * Type of a callback function for u_enumCharNames() that gets called
+ * for each Unicode character with the code point value and
+ * the character name.
+ * If such a function returns FALSE, then the enumeration is stopped.
+ *
+ * @param context The context pointer that was passed to u_enumCharNames().
+ * @param code The Unicode code point for the character with this name.
+ * @param nameChoice Selector for which kind of names is enumerated.
+ * @param name The character's name, zero-terminated.
+ * @param length The length of the name.
+ * @return TRUE if the enumeration should continue, FALSE to stop it.
+ *
+ * @see UCharNameChoice
+ * @see u_enumCharNames
+ * @stable ICU 1.7
+ */
+typedef UBool UEnumCharNamesFn(void *context,
+ UChar32 code,
+ UCharNameChoice nameChoice,
+ const char *name,
+ int32_t length);
+
+/**
+ * Enumerate all assigned Unicode characters between the start and limit
+ * code points (start inclusive, limit exclusive) and call a function
+ * for each, passing the code point value and the character name.
+ * For Unicode 1.0 names, only those are enumerated that differ from the
+ * modern names.
+ *
+ * @param start The first code point in the enumeration range.
+ * @param limit One more than the last code point in the enumeration range
+ * (the first one after the range).
+ * @param fn The function that is to be called for each character name.
+ * @param context An arbitrary pointer that is passed to the function.
+ * @param nameChoice Selector for which kind of names to enumerate.
+ * @param pErrorCode Pointer to a UErrorCode variable
+ *
+ * @see UCharNameChoice
+ * @see UEnumCharNamesFn
+ * @see u_charName
+ * @see u_charFromName
+ * @stable ICU 1.7
+ */
+U_STABLE void U_EXPORT2
+u_enumCharNames(UChar32 start, UChar32 limit,
+ UEnumCharNamesFn *fn,
+ void *context,
+ UCharNameChoice nameChoice,
+ UErrorCode *pErrorCode);
+
+/**
+ * Return the Unicode name for a given property, as given in the
+ * Unicode database file PropertyAliases.txt.
+ *
+ * In addition, this function maps the property
+ * UCHAR_GENERAL_CATEGORY_MASK to the synthetic names "gcm" /
+ * "General_Category_Mask". These names are not in
+ * PropertyAliases.txt.
+ *
+ * @param property UProperty selector other than UCHAR_INVALID_CODE.
+ * If out of range, NULL is returned.
+ *
+ * @param nameChoice selector for which name to get. If out of range,
+ * NULL is returned. All properties have a long name. Most
+ * have a short name, but some do not. Unicode allows for
+ * additional names; if present these will be returned by
+ * U_LONG_PROPERTY_NAME + i, where i=1, 2,...
+ *
+ * @return a pointer to the name, or NULL if either the
+ * property or the nameChoice is out of range. If a given
+ * nameChoice returns NULL, then all larger values of
+ * nameChoice will return NULL, with one exception: if NULL is
+ * returned for U_SHORT_PROPERTY_NAME, then
+ * U_LONG_PROPERTY_NAME (and higher) may still return a
+ * non-NULL value. The returned pointer is valid until
+ * u_cleanup() is called.
+ *
+ * @see UProperty
+ * @see UPropertyNameChoice
+ * @stable ICU 2.4
+ */
+U_STABLE const char* U_EXPORT2
+u_getPropertyName(UProperty property,
+ UPropertyNameChoice nameChoice);
+
+/**
+ * Return the UProperty enum for a given property name, as specified
+ * in the Unicode database file PropertyAliases.txt. Short, long, and
+ * any other variants are recognized.
+ *
+ * In addition, this function maps the synthetic names "gcm" /
+ * "General_Category_Mask" to the property
+ * UCHAR_GENERAL_CATEGORY_MASK. These names are not in
+ * PropertyAliases.txt.
+ *
+ * @param alias the property name to be matched. The name is compared
+ * using "loose matching" as described in PropertyAliases.txt.
+ *
+ * @return a UProperty enum, or UCHAR_INVALID_CODE if the given name
+ * does not match any property.
+ *
+ * @see UProperty
+ * @stable ICU 2.4
+ */
+U_STABLE UProperty U_EXPORT2
+u_getPropertyEnum(const char* alias);
+
+/**
+ * Return the Unicode name for a given property value, as given in the
+ * Unicode database file PropertyValueAliases.txt.
+ *
+ * Note: Some of the names in PropertyValueAliases.txt can only be
+ * retrieved using UCHAR_GENERAL_CATEGORY_MASK, not
+ * UCHAR_GENERAL_CATEGORY. These include: "C" / "Other", "L" /
+ * "Letter", "LC" / "Cased_Letter", "M" / "Mark", "N" / "Number", "P"
+ * / "Punctuation", "S" / "Symbol", and "Z" / "Separator".
+ *
+ * @param property UProperty selector constant.
+ * Must be UCHAR_BINARY_START<=which<UCHAR_BINARY_LIMIT
+ * or UCHAR_INT_START<=which<UCHAR_INT_LIMIT
+ * or UCHAR_MASK_START<=which<UCHAR_MASK_LIMIT.
+ * If out of range, NULL is returned.
+ *
+ * @param value selector for a value for the given property. If out
+ * of range, NULL is returned. In general, valid values range
+ * from 0 up to some maximum. There are a few exceptions:
+ * (1.) UCHAR_BLOCK values begin at the non-zero value
+ * UBLOCK_BASIC_LATIN. (2.) UCHAR_CANONICAL_COMBINING_CLASS
+ * values are not contiguous and range from 0..240. (3.)
+ * UCHAR_GENERAL_CATEGORY_MASK values are not values of
+ * UCharCategory, but rather mask values produced by
+ * U_GET_GC_MASK(). This allows grouped categories such as
+ * [:L:] to be represented. Mask values range
+ * non-contiguously from 1..U_GC_P_MASK.
+ *
+ * @param nameChoice selector for which name to get. If out of range,
+ * NULL is returned. All values have a long name. Most have
+ * a short name, but some do not. Unicode allows for
+ * additional names; if present these will be returned by
+ * U_LONG_PROPERTY_NAME + i, where i=1, 2,...
+
+ * @return a pointer to the name, or NULL if either the
+ * property or the nameChoice is out of range. If a given
+ * nameChoice returns NULL, then all larger values of
+ * nameChoice will return NULL, with one exception: if NULL is
+ * returned for U_SHORT_PROPERTY_NAME, then
+ * U_LONG_PROPERTY_NAME (and higher) may still return a
+ * non-NULL value. The returned pointer is valid until
+ * u_cleanup() is called.
+ *
+ * @see UProperty
+ * @see UPropertyNameChoice
+ * @stable ICU 2.4
+ */
+U_STABLE const char* U_EXPORT2
+u_getPropertyValueName(UProperty property,
+ int32_t value,
+ UPropertyNameChoice nameChoice);
+
+/**
+ * Return the property value integer for a given value name, as
+ * specified in the Unicode database file PropertyValueAliases.txt.
+ * Short, long, and any other variants are recognized.
+ *
+ * Note: Some of the names in PropertyValueAliases.txt will only be
+ * recognized with UCHAR_GENERAL_CATEGORY_MASK, not
+ * UCHAR_GENERAL_CATEGORY. These include: "C" / "Other", "L" /
+ * "Letter", "LC" / "Cased_Letter", "M" / "Mark", "N" / "Number", "P"
+ * / "Punctuation", "S" / "Symbol", and "Z" / "Separator".
+ *
+ * @param property UProperty selector constant.
+ * Must be UCHAR_BINARY_START<=which<UCHAR_BINARY_LIMIT
+ * or UCHAR_INT_START<=which<UCHAR_INT_LIMIT
+ * or UCHAR_MASK_START<=which<UCHAR_MASK_LIMIT.
+ * If out of range, UCHAR_INVALID_CODE is returned.
+ *
+ * @param alias the value name to be matched. The name is compared
+ * using "loose matching" as described in
+ * PropertyValueAliases.txt.
+ *
+ * @return a value integer or UCHAR_INVALID_CODE if the given name
+ * does not match any value of the given property, or if the
+ * property is invalid. Note: U CHAR_GENERAL_CATEGORY values
+ * are not values of UCharCategory, but rather mask values
+ * produced by U_GET_GC_MASK(). This allows grouped
+ * categories such as [:L:] to be represented.
+ *
+ * @see UProperty
+ * @stable ICU 2.4
+ */
+U_STABLE int32_t U_EXPORT2
+u_getPropertyValueEnum(UProperty property,
+ const char* alias);
+
+/**
+ * Determines if the specified character is permissible as the
+ * first character in an identifier according to Unicode
+ * (The Unicode Standard, Version 3.0, chapter 5.16 Identifiers).
+ * True for characters with general categories "L" (letters) and "Nl" (letter numbers).
+ *
+ * Same as java.lang.Character.isUnicodeIdentifierStart().
+ * Same as UCHAR_ID_START
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point may start an identifier
+ *
+ * @see UCHAR_ID_START
+ * @see u_isalpha
+ * @see u_isIDPart
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isIDStart(UChar32 c);
+
+/**
+ * Determines if the specified character is permissible
+ * in an identifier according to Java.
+ * True for characters with general categories "L" (letters),
+ * "Nl" (letter numbers), "Nd" (decimal digits),
+ * "Mc" and "Mn" (combining marks), "Pc" (connecting punctuation), and
+ * u_isIDIgnorable(c).
+ *
+ * Same as java.lang.Character.isUnicodeIdentifierPart().
+ * Almost the same as Unicode's ID_Continue (UCHAR_ID_CONTINUE)
+ * except that Unicode recommends to ignore Cf which is less than
+ * u_isIDIgnorable(c).
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point may occur in an identifier according to Java
+ *
+ * @see UCHAR_ID_CONTINUE
+ * @see u_isIDStart
+ * @see u_isIDIgnorable
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isIDPart(UChar32 c);
+
+/**
+ * Determines if the specified character should be regarded
+ * as an ignorable character in an identifier,
+ * according to Java.
+ * True for characters with general category "Cf" (format controls) as well as
+ * non-whitespace ISO controls
+ * (U+0000..U+0008, U+000E..U+001B, U+007F..U+0084, U+0086..U+009F).
+ *
+ * Same as java.lang.Character.isIdentifierIgnorable()
+ * except that Java also returns TRUE for U+0085 Next Line
+ * (it omits U+0085 from whitespace ISO controls).
+ *
+ * Note that Unicode just recommends to ignore Cf (format controls).
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point is ignorable in identifiers according to Java
+ *
+ * @see UCHAR_DEFAULT_IGNORABLE_CODE_POINT
+ * @see u_isIDStart
+ * @see u_isIDPart
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isIDIgnorable(UChar32 c);
+
+/**
+ * Determines if the specified character is permissible as the
+ * first character in a Java identifier.
+ * In addition to u_isIDStart(c), true for characters with
+ * general categories "Sc" (currency symbols) and "Pc" (connecting punctuation).
+ *
+ * Same as java.lang.Character.isJavaIdentifierStart().
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point may start a Java identifier
+ *
+ * @see u_isJavaIDPart
+ * @see u_isalpha
+ * @see u_isIDStart
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isJavaIDStart(UChar32 c);
+
+/**
+ * Determines if the specified character is permissible
+ * in a Java identifier.
+ * In addition to u_isIDPart(c), true for characters with
+ * general category "Sc" (currency symbols).
+ *
+ * Same as java.lang.Character.isJavaIdentifierPart().
+ *
+ * @param c the code point to be tested
+ * @return TRUE if the code point may occur in a Java identifier
+ *
+ * @see u_isIDIgnorable
+ * @see u_isJavaIDStart
+ * @see u_isalpha
+ * @see u_isdigit
+ * @see u_isIDPart
+ * @stable ICU 2.0
+ */
+U_STABLE UBool U_EXPORT2
+u_isJavaIDPart(UChar32 c);
+
+/**
+ * The given character is mapped to its lowercase equivalent according to
+ * UnicodeData.txt; if the character has no lowercase equivalent, the character
+ * itself is returned.
+ *
+ * Same as java.lang.Character.toLowerCase().
+ *
+ * This function only returns the simple, single-code point case mapping.
+ * Full case mappings may result in zero, one or more code points and depend
+ * on context or language etc.
+ * Full case mappings are applied by the string case mapping functions,
+ * see ustring.h and the UnicodeString class.
+ *
+ * @param c the code point to be mapped
+ * @return the Simple_Lowercase_Mapping of the code point, if any;
+ * otherwise the code point itself.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar32 U_EXPORT2
+u_tolower(UChar32 c);
+
+/**
+ * The given character is mapped to its uppercase equivalent according to UnicodeData.txt;
+ * if the character has no uppercase equivalent, the character itself is
+ * returned.
+ *
+ * Same as java.lang.Character.toUpperCase().
+ *
+ * This function only returns the simple, single-code point case mapping.
+ * Full case mappings may result in zero, one or more code points and depend
+ * on context or language etc.
+ * Full case mappings are applied by the string case mapping functions,
+ * see ustring.h and the UnicodeString class.
+ *
+ * @param c the code point to be mapped
+ * @return the Simple_Uppercase_Mapping of the code point, if any;
+ * otherwise the code point itself.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar32 U_EXPORT2
+u_toupper(UChar32 c);
+
+/**
+ * The given character is mapped to its titlecase equivalent
+ * according to UnicodeData.txt;
+ * if none is defined, the character itself is returned.
+ *
+ * Same as java.lang.Character.toTitleCase().
+ *
+ * This function only returns the simple, single-code point case mapping.
+ * Full case mappings may result in zero, one or more code points and depend
+ * on context or language etc.
+ * Full case mappings are applied by the string case mapping functions,
+ * see ustring.h and the UnicodeString class.
+ *
+ * @param c the code point to be mapped
+ * @return the Simple_Titlecase_Mapping of the code point, if any;
+ * otherwise the code point itself.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar32 U_EXPORT2
+u_totitle(UChar32 c);
+
+/** Option value for case folding: use default mappings defined in CaseFolding.txt. @stable ICU 2.0 */
+#define U_FOLD_CASE_DEFAULT 0
+
+/**
+ * Option value for case folding:
+ *
+ * Use the modified set of mappings provided in CaseFolding.txt to handle dotted I
+ * and dotless i appropriately for Turkic languages (tr, az).
+ *
+ * Before Unicode 3.2, CaseFolding.txt contains mappings marked with 'I' that
+ * are to be included for default mappings and
+ * excluded for the Turkic-specific mappings.
+ *
+ * Unicode 3.2 CaseFolding.txt instead contains mappings marked with 'T' that
+ * are to be excluded for default mappings and
+ * included for the Turkic-specific mappings.
+ *
+ * @stable ICU 2.0
+ */
+#define U_FOLD_CASE_EXCLUDE_SPECIAL_I 1
+
+/**
+ * The given character is mapped to its case folding equivalent according to
+ * UnicodeData.txt and CaseFolding.txt;
+ * if the character has no case folding equivalent, the character
+ * itself is returned.
+ *
+ * This function only returns the simple, single-code point case mapping.
+ * Full case mappings may result in zero, one or more code points and depend
+ * on context or language etc.
+ * Full case mappings are applied by the string case mapping functions,
+ * see ustring.h and the UnicodeString class.
+ *
+ * @param c the code point to be mapped
+ * @param options Either U_FOLD_CASE_DEFAULT or U_FOLD_CASE_EXCLUDE_SPECIAL_I
+ * @return the Simple_Case_Folding of the code point, if any;
+ * otherwise the code point itself.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar32 U_EXPORT2
+u_foldCase(UChar32 c, uint32_t options);
+
+/**
+ * Returns the decimal digit value of the code point in the
+ * specified radix.
+ *
+ * If the radix is not in the range <code>2<=radix<=36</code> or if the
+ * value of <code>c</code> is not a valid digit in the specified
+ * radix, <code>-1</code> is returned. A character is a valid digit
+ * if at least one of the following is true:
+ * <ul>
+ * <li>The character has a decimal digit value.
+ * Such characters have the general category "Nd" (decimal digit numbers)
+ * and a Numeric_Type of Decimal.
+ * In this case the value is the character's decimal digit value.</li>
+ * <li>The character is one of the uppercase Latin letters
+ * <code>'A'</code> through <code>'Z'</code>.
+ * In this case the value is <code>c-'A'+10</code>.</li>
+ * <li>The character is one of the lowercase Latin letters
+ * <code>'a'</code> through <code>'z'</code>.
+ * In this case the value is <code>ch-'a'+10</code>.</li>
+ * <li>Latin letters from both the ASCII range (0061..007A, 0041..005A)
+ * as well as from the Fullwidth ASCII range (FF41..FF5A, FF21..FF3A)
+ * are recognized.</li>
+ * </ul>
+ *
+ * Same as java.lang.Character.digit().
+ *
+ * @param ch the code point to be tested.
+ * @param radix the radix.
+ * @return the numeric value represented by the character in the
+ * specified radix,
+ * or -1 if there is no value or if the value exceeds the radix.
+ *
+ * @see UCHAR_NUMERIC_TYPE
+ * @see u_forDigit
+ * @see u_charDigitValue
+ * @see u_isdigit
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_digit(UChar32 ch, int8_t radix);
+
+/**
+ * Determines the character representation for a specific digit in
+ * the specified radix. If the value of <code>radix</code> is not a
+ * valid radix, or the value of <code>digit</code> is not a valid
+ * digit in the specified radix, the null character
+ * (<code>U+0000</code>) is returned.
+ * <p>
+ * The <code>radix</code> argument is valid if it is greater than or
+ * equal to 2 and less than or equal to 36.
+ * The <code>digit</code> argument is valid if
+ * <code>0 <= digit < radix</code>.
+ * <p>
+ * If the digit is less than 10, then
+ * <code>'0' + digit</code> is returned. Otherwise, the value
+ * <code>'a' + digit - 10</code> is returned.
+ *
+ * Same as java.lang.Character.forDigit().
+ *
+ * @param digit the number to convert to a character.
+ * @param radix the radix.
+ * @return the <code>char</code> representation of the specified digit
+ * in the specified radix.
+ *
+ * @see u_digit
+ * @see u_charDigitValue
+ * @see u_isdigit
+ * @stable ICU 2.0
+ */
+U_STABLE UChar32 U_EXPORT2
+u_forDigit(int32_t digit, int8_t radix);
+
+/**
+ * Get the "age" of the code point.
+ * The "age" is the Unicode version when the code point was first
+ * designated (as a non-character or for Private Use)
+ * or assigned a character.
+ * This can be useful to avoid emitting code points to receiving
+ * processes that do not accept newer characters.
+ * The data is from the UCD file DerivedAge.txt.
+ *
+ * @param c The code point.
+ * @param versionArray The Unicode version number array, to be filled in.
+ *
+ * @stable ICU 2.1
+ */
+U_STABLE void U_EXPORT2
+u_charAge(UChar32 c, UVersionInfo versionArray);
+
+/**
+ * Gets the Unicode version information.
+ * The version array is filled in with the version information
+ * for the Unicode standard that is currently used by ICU.
+ * For example, Unicode version 3.1.1 is represented as an array with
+ * the values { 3, 1, 1, 0 }.
+ *
+ * @param versionArray an output array that will be filled in with
+ * the Unicode version number
+ * @stable ICU 2.0
+ */
+U_STABLE void U_EXPORT2
+u_getUnicodeVersion(UVersionInfo versionArray);
+
+/**
+ * Get the FC_NFKC_Closure property string for a character.
+ * See Unicode Standard Annex #15 for details, search for "FC_NFKC_Closure"
+ * or for "FNC": http://www.unicode.org/reports/tr15/
+ *
+ * @param c The character (code point) for which to get the FC_NFKC_Closure string.
+ * It must be <code>0<=c<=0x10ffff</code>.
+ * @param dest Destination address for copying the string.
+ * The string will be zero-terminated if possible.
+ * If there is no FC_NFKC_Closure string,
+ * then the buffer will be set to the empty string.
+ * @param destCapacity <code>==sizeof(dest)</code>
+ * @param pErrorCode Pointer to a UErrorCode variable.
+ * @return The length of the string, or 0 if there is no FC_NFKC_Closure string for this character.
+ * If the destCapacity is less than or equal to the length, then the buffer
+ * contains the truncated name and the returned length indicates the full
+ * length of the name.
+ * The length does not include the zero-termination.
+ *
+ * @stable ICU 2.2
+ */
+U_STABLE int32_t U_EXPORT2
+u_getFC_NFKC_Closure(UChar32 c, UChar *dest, int32_t destCapacity, UErrorCode *pErrorCode);
+
+U_CDECL_END
+
+#endif /*_UCHAR*/
+/*eof*/
diff --git a/WebKit/mac/icu/unicode/uconfig.h b/WebKit/mac/icu/unicode/uconfig.h
new file mode 100644
index 0000000..997cf68
--- /dev/null
+++ b/WebKit/mac/icu/unicode/uconfig.h
@@ -0,0 +1,186 @@
+/*
+**********************************************************************
+* Copyright (C) 2002-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+**********************************************************************
+* file name: uconfig.h
+* encoding: US-ASCII
+* tab size: 8 (not used)
+* indentation:4
+*
+* created on: 2002sep19
+* created by: Markus W. Scherer
+*/
+
+#ifndef __UCONFIG_H__
+#define __UCONFIG_H__
+
+/*!
+ * \file
+ * \brief Switches for excluding parts of ICU library code modules.
+ *
+ * Allows to build partial, smaller libraries for special purposes.
+ * By default, all modules are built.
+ * The switches are fairly coarse, controlling large modules.
+ * Basic services cannot be turned off.
+ *
+ * @stable ICU 2.4
+ */
+
+/**
+ * \def UCONFIG_ONLY_COLLATION
+ * This switch turns off modules that are not needed for collation.
+ *
+ * It does not turn off legacy conversion because that is necessary
+ * for ICU to work on EBCDIC platforms (for the default converter).
+ * If you want "only collation" and do not build for EBCDIC,
+ * then you can #define UCONFIG_NO_LEGACY_CONVERSION 1 as well.
+ *
+ * @stable ICU 2.4
+ */
+#ifndef UCONFIG_ONLY_COLLATION
+# define UCONFIG_ONLY_COLLATION 0
+#endif
+
+#if UCONFIG_ONLY_COLLATION
+ /* common library */
+# define UCONFIG_NO_BREAK_ITERATION 1
+# define UCONFIG_NO_IDNA 1
+
+ /* i18n library */
+# if UCONFIG_NO_COLLATION
+# error Contradictory collation switches in uconfig.h.
+# endif
+# define UCONFIG_NO_FORMATTING 1
+# define UCONFIG_NO_TRANSLITERATION 1
+# define UCONFIG_NO_REGULAR_EXPRESSIONS 1
+#endif
+
+/* common library switches -------------------------------------------------- */
+
+/**
+ * \def UCONFIG_NO_CONVERSION
+ * ICU will not completely build with this switch turned on.
+ * This switch turns off all converters.
+ *
+ * @draft ICU 3.2
+ */
+#ifndef UCONFIG_NO_CONVERSION
+# define UCONFIG_NO_CONVERSION 0
+#endif
+
+#if UCONFIG_NO_CONVERSION
+# define UCONFIG_NO_LEGACY_CONVERSION 1
+#endif
+
+/**
+ * \def UCONFIG_NO_LEGACY_CONVERSION
+ * This switch turns off all converters except for
+ * - Unicode charsets (UTF-7/8/16/32, CESU-8, SCSU, BOCU-1)
+ * - US-ASCII
+ * - ISO-8859-1
+ *
+ * Turning off legacy conversion is not possible on EBCDIC platforms
+ * because they need ibm-37 or ibm-1047 default converters.
+ *
+ * @stable ICU 2.4
+ */
+#ifndef UCONFIG_NO_LEGACY_CONVERSION
+# define UCONFIG_NO_LEGACY_CONVERSION 0
+#endif
+
+/**
+ * \def UCONFIG_NO_NORMALIZATION
+ * This switch turns off normalization.
+ * It implies turning off several other services as well, for example
+ * collation and IDNA.
+ *
+ * @stable ICU 2.6
+ */
+#ifndef UCONFIG_NO_NORMALIZATION
+# define UCONFIG_NO_NORMALIZATION 0
+#elif UCONFIG_NO_NORMALIZATION
+ /* common library */
+# define UCONFIG_NO_IDNA 1
+
+ /* i18n library */
+# if UCONFIG_ONLY_COLLATION
+# error Contradictory collation switches in uconfig.h.
+# endif
+# define UCONFIG_NO_COLLATION 1
+# define UCONFIG_NO_TRANSLITERATION 1
+#endif
+
+/**
+ * \def UCONFIG_NO_BREAK_ITERATION
+ * This switch turns off break iteration.
+ *
+ * @stable ICU 2.4
+ */
+#ifndef UCONFIG_NO_BREAK_ITERATION
+# define UCONFIG_NO_BREAK_ITERATION 0
+#endif
+
+/**
+ * \def UCONFIG_NO_IDNA
+ * This switch turns off IDNA.
+ *
+ * @stable ICU 2.6
+ */
+#ifndef UCONFIG_NO_IDNA
+# define UCONFIG_NO_IDNA 0
+#endif
+
+/* i18n library switches ---------------------------------------------------- */
+
+/**
+ * \def UCONFIG_NO_COLLATION
+ * This switch turns off collation and collation-based string search.
+ *
+ * @stable ICU 2.4
+ */
+#ifndef UCONFIG_NO_COLLATION
+# define UCONFIG_NO_COLLATION 0
+#endif
+
+/**
+ * \def UCONFIG_NO_FORMATTING
+ * This switch turns off formatting and calendar/timezone services.
+ *
+ * @stable ICU 2.4
+ */
+#ifndef UCONFIG_NO_FORMATTING
+# define UCONFIG_NO_FORMATTING 0
+#endif
+
+/**
+ * \def UCONFIG_NO_TRANSLITERATION
+ * This switch turns off transliteration.
+ *
+ * @stable ICU 2.4
+ */
+#ifndef UCONFIG_NO_TRANSLITERATION
+# define UCONFIG_NO_TRANSLITERATION 0
+#endif
+
+/**
+ * \def UCONFIG_NO_REGULAR_EXPRESSIONS
+ * This switch turns off regular expressions.
+ *
+ * @stable ICU 2.4
+ */
+#ifndef UCONFIG_NO_REGULAR_EXPRESSIONS
+# define UCONFIG_NO_REGULAR_EXPRESSIONS 0
+#endif
+
+/**
+ * \def UCONFIG_NO_SERVICE
+ * This switch turns off service registration.
+ *
+ * @draft ICU 3.2
+ */
+#ifndef UCONFIG_NO_SERVICE
+# define UCONFIG_NO_SERVICE 0
+#endif
+
+#endif
diff --git a/WebKit/mac/icu/unicode/uidna.h b/WebKit/mac/icu/unicode/uidna.h
new file mode 100644
index 0000000..7b1dd0b
--- /dev/null
+++ b/WebKit/mac/icu/unicode/uidna.h
@@ -0,0 +1,310 @@
+/*
+ *******************************************************************************
+ *
+ * Copyright (C) 2003-2004, International Business Machines
+ * Corporation and others. All Rights Reserved.
+ *
+ *******************************************************************************
+ * file name: uidna.h
+ * encoding: US-ASCII
+ * tab size: 8 (not used)
+ * indentation:4
+ *
+ * created on: 2003feb1
+ * created by: Ram Viswanadha
+ */
+
+#ifndef __UIDNA_H__
+#define __UIDNA_H__
+
+#include "unicode/utypes.h"
+
+#if !UCONFIG_NO_IDNA
+
+#include "unicode/parseerr.h"
+
+/**
+ *\file
+ * UIDNA API implements the IDNA protocol as defined in the IDNA RFC
+ * (http://www.ietf.org/rfc/rfc3490.txt).
+ * The RFC defines 2 operations: ToASCII and ToUnicode. Domain labels
+ * containing non-ASCII code points are required to be processed by
+ * ToASCII operation before passing it to resolver libraries. Domain names
+ * that are obtained from resolver libraries are required to be processed by
+ * ToUnicode operation before displaying the domain name to the user.
+ * IDNA requires that implementations process input strings with Nameprep
+ * (http://www.ietf.org/rfc/rfc3491.txt),
+ * which is a profile of Stringprep (http://www.ietf.org/rfc/rfc3454.txt),
+ * and then with Punycode (http://www.ietf.org/rfc/rfc3492.txt).
+ * Implementations of IDNA MUST fully implement Nameprep and Punycode;
+ * neither Nameprep nor Punycode are optional.
+ * The input and output of ToASCII and ToUnicode operations are Unicode
+ * and are designed to be chainable, i.e., applying ToASCII or ToUnicode operations
+ * multiple times to an input string will yield the same result as applying the operation
+ * once.
+ * ToUnicode(ToUnicode(ToUnicode...(ToUnicode(string)))) == ToUnicode(string)
+ * ToASCII(ToASCII(ToASCII...(ToASCII(string))) == ToASCII(string).
+ *
+ */
+
+#ifndef U_HIDE_DRAFT_API
+
+/**
+ * Option to prohibit processing of unassigned codepoints in the input and
+ * do not check if the input conforms to STD-3 ASCII rules.
+ *
+ * @see uidna_toASCII uidna_toUnicode
+ * @stable ICU 2.6
+ */
+#define UIDNA_DEFAULT 0x0000
+/**
+ * Option to allow processing of unassigned codepoints in the input
+ *
+ * @see uidna_toASCII uidna_toUnicode
+ * @stable ICU 2.6
+ */
+#define UIDNA_ALLOW_UNASSIGNED 0x0001
+/**
+ * Option to check if input conforms to STD-3 ASCII rules
+ *
+ * @see uidna_toASCII uidna_toUnicode
+ * @stable ICU 2.6
+ */
+#define UIDNA_USE_STD3_RULES 0x0002
+
+#endif /*U_HIDE_DRAFT_API*/
+
+/**
+ * This function implements the ToASCII operation as defined in the IDNA RFC.
+ * This operation is done on <b>single labels</b> before sending it to something that expects
+ * ASCII names. A label is an individual part of a domain name. Labels are usually
+ * separated by dots; e.g." "www.example.com" is composed of 3 labels
+ * "www","example", and "com".
+ *
+ *
+ * @param src Input UChar array containing label in Unicode.
+ * @param srcLength Number of UChars in src, or -1 if NUL-terminated.
+ * @param dest Output UChar array with ASCII (ACE encoded) label.
+ * @param destCapacity Size of dest.
+ * @param options A bit set of options:
+ *
+ * - UIDNA_DEFAULT Use default options, i.e., do not process unassigned code points
+ * and do not use STD3 ASCII rules
+ * If unassigned code points are found the operation fails with
+ * U_UNASSIGNED_ERROR error code.
+ *
+ * - UIDNA_ALLOW_UNASSIGNED Unassigned values can be converted to ASCII for query operations
+ * If this option is set, the unassigned code points are in the input
+ * are treated as normal Unicode code points.
+ *
+ * - UIDNA_USE_STD3_RULES Use STD3 ASCII rules for host name syntax restrictions
+ * If this option is set and the input does not satisfy STD3 rules,
+ * the operation will fail with U_IDNA_STD3_ASCII_RULES_ERROR
+ *
+ * @param parseError Pointer to UParseError struct to receive information on position
+ * of error if an error is encountered. Can be NULL.
+ * @param status ICU in/out error code parameter.
+ * U_INVALID_CHAR_FOUND if src contains
+ * unmatched single surrogates.
+ * U_INDEX_OUTOFBOUNDS_ERROR if src contains
+ * too many code points.
+ * U_BUFFER_OVERFLOW_ERROR if destCapacity is not enough
+ * @return Number of ASCII characters converted.
+ * @stable ICU 2.6
+ */
+U_STABLE int32_t U_EXPORT2
+uidna_toASCII(const UChar* src, int32_t srcLength,
+ UChar* dest, int32_t destCapacity,
+ int32_t options,
+ UParseError* parseError,
+ UErrorCode* status);
+
+
+/**
+ * This function implements the ToUnicode operation as defined in the IDNA RFC.
+ * This operation is done on <b>single labels</b> before sending it to something that expects
+ * Unicode names. A label is an individual part of a domain name. Labels are usually
+ * separated by dots; for e.g." "www.example.com" is composed of 3 labels
+ * "www","example", and "com".
+ *
+ * @param src Input UChar array containing ASCII (ACE encoded) label.
+ * @param srcLength Number of UChars in src, or -1 if NUL-terminated.
+ * @param dest Output Converted UChar array containing Unicode equivalent of label.
+ * @param destCapacity Size of dest.
+ * @param options A bit set of options:
+ *
+ * - UIDNA_DEFAULT Use default options, i.e., do not process unassigned code points
+ * and do not use STD3 ASCII rules
+ * If unassigned code points are found the operation fails with
+ * U_UNASSIGNED_ERROR error code.
+ *
+ * - UIDNA_ALLOW_UNASSIGNED Unassigned values can be converted to ASCII for query operations
+ * If this option is set, the unassigned code points are in the input
+ * are treated as normal Unicode code points. <b> Note: </b> This option is
+ * required on toUnicode operation because the RFC mandates
+ * verification of decoded ACE input by applying toASCII and comparing
+ * its output with source
+ *
+ *
+ *
+ * - UIDNA_USE_STD3_RULES Use STD3 ASCII rules for host name syntax restrictions
+ * If this option is set and the input does not satisfy STD3 rules,
+ * the operation will fail with U_IDNA_STD3_ASCII_RULES_ERROR
+ *
+ * @param parseError Pointer to UParseError struct to receive information on position
+ * of error if an error is encountered. Can be NULL.
+ * @param status ICU in/out error code parameter.
+ * U_INVALID_CHAR_FOUND if src contains
+ * unmatched single surrogates.
+ * U_INDEX_OUTOFBOUNDS_ERROR if src contains
+ * too many code points.
+ * U_BUFFER_OVERFLOW_ERROR if destCapacity is not enough
+ * @return Number of Unicode characters converted.
+ * @stable ICU 2.6
+ */
+U_STABLE int32_t U_EXPORT2
+uidna_toUnicode(const UChar* src, int32_t srcLength,
+ UChar* dest, int32_t destCapacity,
+ int32_t options,
+ UParseError* parseError,
+ UErrorCode* status);
+
+
+/**
+ * Convenience function that implements the IDNToASCII operation as defined in the IDNA RFC.
+ * This operation is done on complete domain names, e.g: "www.example.com".
+ * It is important to note that this operation can fail. If it fails, then the input
+ * domain name cannot be used as an Internationalized Domain Name and the application
+ * should have methods defined to deal with the failure.
+ *
+ * <b>Note:</b> IDNA RFC specifies that a conformant application should divide a domain name
+ * into separate labels, decide whether to apply allowUnassigned and useSTD3ASCIIRules on each,
+ * and then convert. This function does not offer that level of granularity. The options once
+ * set will apply to all labels in the domain name
+ *
+ * @param src Input UChar array containing IDN in Unicode.
+ * @param srcLength Number of UChars in src, or -1 if NUL-terminated.
+ * @param dest Output UChar array with ASCII (ACE encoded) IDN.
+ * @param destCapacity Size of dest.
+ * @param options A bit set of options:
+ *
+ * - UIDNA_DEFAULT Use default options, i.e., do not process unassigned code points
+ * and do not use STD3 ASCII rules
+ * If unassigned code points are found the operation fails with
+ * U_UNASSIGNED_CODE_POINT_FOUND error code.
+ *
+ * - UIDNA_ALLOW_UNASSIGNED Unassigned values can be converted to ASCII for query operations
+ * If this option is set, the unassigned code points are in the input
+ * are treated as normal Unicode code points.
+ *
+ * - UIDNA_USE_STD3_RULES Use STD3 ASCII rules for host name syntax restrictions
+ * If this option is set and the input does not satisfy STD3 rules,
+ * the operation will fail with U_IDNA_STD3_ASCII_RULES_ERROR
+ *
+ * @param parseError Pointer to UParseError struct to receive information on position
+ * of error if an error is encountered. Can be NULL.
+ * @param status ICU in/out error code parameter.
+ * U_INVALID_CHAR_FOUND if src contains
+ * unmatched single surrogates.
+ * U_INDEX_OUTOFBOUNDS_ERROR if src contains
+ * too many code points.
+ * U_BUFFER_OVERFLOW_ERROR if destCapacity is not enough
+ * @return Number of ASCII characters converted.
+ * @stable ICU 2.6
+ */
+U_STABLE int32_t U_EXPORT2
+uidna_IDNToASCII( const UChar* src, int32_t srcLength,
+ UChar* dest, int32_t destCapacity,
+ int32_t options,
+ UParseError* parseError,
+ UErrorCode* status);
+
+/**
+ * Convenience function that implements the IDNToUnicode operation as defined in the IDNA RFC.
+ * This operation is done on complete domain names, e.g: "www.example.com".
+ *
+ * <b>Note:</b> IDNA RFC specifies that a conformant application should divide a domain name
+ * into separate labels, decide whether to apply allowUnassigned and useSTD3ASCIIRules on each,
+ * and then convert. This function does not offer that level of granularity. The options once
+ * set will apply to all labels in the domain name
+ *
+ * @param src Input UChar array containing IDN in ASCII (ACE encoded) form.
+ * @param srcLength Number of UChars in src, or -1 if NUL-terminated.
+ * @param dest Output UChar array containing Unicode equivalent of source IDN.
+ * @param destCapacity Size of dest.
+ * @param options A bit set of options:
+ *
+ * - UIDNA_DEFAULT Use default options, i.e., do not process unassigned code points
+ * and do not use STD3 ASCII rules
+ * If unassigned code points are found the operation fails with
+ * U_UNASSIGNED_CODE_POINT_FOUND error code.
+ *
+ * - UIDNA_ALLOW_UNASSIGNED Unassigned values can be converted to ASCII for query operations
+ * If this option is set, the unassigned code points are in the input
+ * are treated as normal Unicode code points.
+ *
+ * - UIDNA_USE_STD3_RULES Use STD3 ASCII rules for host name syntax restrictions
+ * If this option is set and the input does not satisfy STD3 rules,
+ * the operation will fail with U_IDNA_STD3_ASCII_RULES_ERROR
+ *
+ * @param parseError Pointer to UParseError struct to receive information on position
+ * of error if an error is encountered. Can be NULL.
+ * @param status ICU in/out error code parameter.
+ * U_INVALID_CHAR_FOUND if src contains
+ * unmatched single surrogates.
+ * U_INDEX_OUTOFBOUNDS_ERROR if src contains
+ * too many code points.
+ * U_BUFFER_OVERFLOW_ERROR if destCapacity is not enough
+ * @return Number of ASCII characters converted.
+ * @stable ICU 2.6
+ */
+U_STABLE int32_t U_EXPORT2
+uidna_IDNToUnicode( const UChar* src, int32_t srcLength,
+ UChar* dest, int32_t destCapacity,
+ int32_t options,
+ UParseError* parseError,
+ UErrorCode* status);
+
+/**
+ * Compare two IDN strings for equivalence.
+ * This function splits the domain names into labels and compares them.
+ * According to IDN RFC, whenever two labels are compared, they are
+ * considered equal if and only if their ASCII forms (obtained by
+ * applying toASCII) match using an case-insensitive ASCII comparison.
+ * Two domain names are considered a match if and only if all labels
+ * match regardless of whether label separators match.
+ *
+ * @param s1 First source string.
+ * @param length1 Length of first source string, or -1 if NUL-terminated.
+ *
+ * @param s2 Second source string.
+ * @param length2 Length of second source string, or -1 if NUL-terminated.
+ * @param options A bit set of options:
+ *
+ * - UIDNA_DEFAULT Use default options, i.e., do not process unassigned code points
+ * and do not use STD3 ASCII rules
+ * If unassigned code points are found the operation fails with
+ * U_UNASSIGNED_CODE_POINT_FOUND error code.
+ *
+ * - UIDNA_ALLOW_UNASSIGNED Unassigned values can be converted to ASCII for query operations
+ * If this option is set, the unassigned code points are in the input
+ * are treated as normal Unicode code points.
+ *
+ * - UIDNA_USE_STD3_RULES Use STD3 ASCII rules for host name syntax restrictions
+ * If this option is set and the input does not satisfy STD3 rules,
+ * the operation will fail with U_IDNA_STD3_ASCII_RULES_ERROR
+ *
+ * @param status ICU error code in/out parameter.
+ * Must fulfill U_SUCCESS before the function call.
+ * @return <0 or 0 or >0 as usual for string comparisons
+ * @stable ICU 2.6
+ */
+U_STABLE int32_t U_EXPORT2
+uidna_compare( const UChar *s1, int32_t length1,
+ const UChar *s2, int32_t length2,
+ int32_t options,
+ UErrorCode* status);
+
+#endif /* #if !UCONFIG_NO_IDNA */
+
+#endif
diff --git a/WebKit/mac/icu/unicode/uiter.h b/WebKit/mac/icu/unicode/uiter.h
new file mode 100644
index 0000000..963df5c
--- /dev/null
+++ b/WebKit/mac/icu/unicode/uiter.h
@@ -0,0 +1,707 @@
+/*
+*******************************************************************************
+*
+* Copyright (C) 2002-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+*
+*******************************************************************************
+* file name: uiter.h
+* encoding: US-ASCII
+* tab size: 8 (not used)
+* indentation:4
+*
+* created on: 2002jan18
+* created by: Markus W. Scherer
+*/
+
+#ifndef __UITER_H__
+#define __UITER_H__
+
+/**
+ * \file
+ * \brief C API: Unicode Character Iteration
+ *
+ * @see UCharIterator
+ */
+
+#include "unicode/utypes.h"
+
+#ifdef XP_CPLUSPLUS
+ U_NAMESPACE_BEGIN
+
+ class CharacterIterator;
+ class Replaceable;
+
+ U_NAMESPACE_END
+#endif
+
+U_CDECL_BEGIN
+
+struct UCharIterator;
+typedef struct UCharIterator UCharIterator; /**< C typedef for struct UCharIterator. @stable ICU 2.1 */
+
+/**
+ * Origin constants for UCharIterator.getIndex() and UCharIterator.move().
+ * @see UCharIteratorMove
+ * @see UCharIterator
+ * @stable ICU 2.1
+ */
+typedef enum UCharIteratorOrigin {
+ UITER_START, UITER_CURRENT, UITER_LIMIT, UITER_ZERO, UITER_LENGTH
+} UCharIteratorOrigin;
+
+/** Constants for UCharIterator. @stable ICU 2.6 */
+enum {
+ /**
+ * Constant value that may be returned by UCharIteratorMove
+ * indicating that the final UTF-16 index is not known, but that the move succeeded.
+ * This can occur when moving relative to limit or length, or
+ * when moving relative to the current index after a setState()
+ * when the current UTF-16 index is not known.
+ *
+ * It would be very inefficient to have to count from the beginning of the text
+ * just to get the current/limit/length index after moving relative to it.
+ * The actual index can be determined with getIndex(UITER_CURRENT)
+ * which will count the UChars if necessary.
+ *
+ * @stable ICU 2.6
+ */
+ UITER_UNKNOWN_INDEX=-2
+};
+
+
+/**
+ * Constant for UCharIterator getState() indicating an error or
+ * an unknown state.
+ * Returned by uiter_getState()/UCharIteratorGetState
+ * when an error occurs.
+ * Also, some UCharIterator implementations may not be able to return
+ * a valid state for each position. This will be clearly documented
+ * for each such iterator (none of the public ones here).
+ *
+ * @stable ICU 2.6
+ */
+#define UITER_NO_STATE ((uint32_t)0xffffffff)
+
+/**
+ * Function type declaration for UCharIterator.getIndex().
+ *
+ * Gets the current position, or the start or limit of the
+ * iteration range.
+ *
+ * This function may perform slowly for UITER_CURRENT after setState() was called,
+ * or for UITER_LENGTH, because an iterator implementation may have to count
+ * UChars if the underlying storage is not UTF-16.
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @param origin get the 0, start, limit, length, or current index
+ * @return the requested index, or U_SENTINEL in an error condition
+ *
+ * @see UCharIteratorOrigin
+ * @see UCharIterator
+ * @stable ICU 2.1
+ */
+typedef int32_t U_CALLCONV
+UCharIteratorGetIndex(UCharIterator *iter, UCharIteratorOrigin origin);
+
+/**
+ * Function type declaration for UCharIterator.move().
+ *
+ * Use iter->move(iter, index, UITER_ZERO) like CharacterIterator::setIndex(index).
+ *
+ * Moves the current position relative to the start or limit of the
+ * iteration range, or relative to the current position itself.
+ * The movement is expressed in numbers of code units forward
+ * or backward by specifying a positive or negative delta.
+ * Out of bounds movement will be pinned to the start or limit.
+ *
+ * This function may perform slowly for moving relative to UITER_LENGTH
+ * because an iterator implementation may have to count the rest of the
+ * UChars if the native storage is not UTF-16.
+ *
+ * When moving relative to the limit or length, or
+ * relative to the current position after setState() was called,
+ * move() may return UITER_UNKNOWN_INDEX (-2) to avoid an inefficient
+ * determination of the actual UTF-16 index.
+ * The actual index can be determined with getIndex(UITER_CURRENT)
+ * which will count the UChars if necessary.
+ * See UITER_UNKNOWN_INDEX for details.
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @param delta can be positive, zero, or negative
+ * @param origin move relative to the 0, start, limit, length, or current index
+ * @return the new index, or U_SENTINEL on an error condition,
+ * or UITER_UNKNOWN_INDEX when the index is not known.
+ *
+ * @see UCharIteratorOrigin
+ * @see UCharIterator
+ * @see UITER_UNKNOWN_INDEX
+ * @stable ICU 2.1
+ */
+typedef int32_t U_CALLCONV
+UCharIteratorMove(UCharIterator *iter, int32_t delta, UCharIteratorOrigin origin);
+
+/**
+ * Function type declaration for UCharIterator.hasNext().
+ *
+ * Check if current() and next() can still
+ * return another code unit.
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @return boolean value for whether current() and next() can still return another code unit
+ *
+ * @see UCharIterator
+ * @stable ICU 2.1
+ */
+typedef UBool U_CALLCONV
+UCharIteratorHasNext(UCharIterator *iter);
+
+/**
+ * Function type declaration for UCharIterator.hasPrevious().
+ *
+ * Check if previous() can still return another code unit.
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @return boolean value for whether previous() can still return another code unit
+ *
+ * @see UCharIterator
+ * @stable ICU 2.1
+ */
+typedef UBool U_CALLCONV
+UCharIteratorHasPrevious(UCharIterator *iter);
+
+/**
+ * Function type declaration for UCharIterator.current().
+ *
+ * Return the code unit at the current position,
+ * or U_SENTINEL if there is none (index is at the limit).
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @return the current code unit
+ *
+ * @see UCharIterator
+ * @stable ICU 2.1
+ */
+typedef UChar32 U_CALLCONV
+UCharIteratorCurrent(UCharIterator *iter);
+
+/**
+ * Function type declaration for UCharIterator.next().
+ *
+ * Return the code unit at the current index and increment
+ * the index (post-increment, like s[i++]),
+ * or return U_SENTINEL if there is none (index is at the limit).
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @return the current code unit (and post-increment the current index)
+ *
+ * @see UCharIterator
+ * @stable ICU 2.1
+ */
+typedef UChar32 U_CALLCONV
+UCharIteratorNext(UCharIterator *iter);
+
+/**
+ * Function type declaration for UCharIterator.previous().
+ *
+ * Decrement the index and return the code unit from there
+ * (pre-decrement, like s[--i]),
+ * or return U_SENTINEL if there is none (index is at the start).
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @return the previous code unit (after pre-decrementing the current index)
+ *
+ * @see UCharIterator
+ * @stable ICU 2.1
+ */
+typedef UChar32 U_CALLCONV
+UCharIteratorPrevious(UCharIterator *iter);
+
+/**
+ * Function type declaration for UCharIterator.reservedFn().
+ * Reserved for future use.
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @param something some integer argument
+ * @return some integer
+ *
+ * @see UCharIterator
+ * @stable ICU 2.1
+ */
+typedef int32_t U_CALLCONV
+UCharIteratorReserved(UCharIterator *iter, int32_t something);
+
+/**
+ * Function type declaration for UCharIterator.getState().
+ *
+ * Get the "state" of the iterator in the form of a single 32-bit word.
+ * It is recommended that the state value be calculated to be as small as
+ * is feasible. For strings with limited lengths, fewer than 32 bits may
+ * be sufficient.
+ *
+ * This is used together with setState()/UCharIteratorSetState
+ * to save and restore the iterator position more efficiently than with
+ * getIndex()/move().
+ *
+ * The iterator state is defined as a uint32_t value because it is designed
+ * for use in ucol_nextSortKeyPart() which provides 32 bits to store the state
+ * of the character iterator.
+ *
+ * With some UCharIterator implementations (e.g., UTF-8),
+ * getting and setting the UTF-16 index with existing functions
+ * (getIndex(UITER_CURRENT) followed by move(pos, UITER_ZERO)) is possible but
+ * relatively slow because the iterator has to "walk" from a known index
+ * to the requested one.
+ * This takes more time the farther it needs to go.
+ *
+ * An opaque state value allows an iterator implementation to provide
+ * an internal index (UTF-8: the source byte array index) for
+ * fast, constant-time restoration.
+ *
+ * After calling setState(), a getIndex(UITER_CURRENT) may be slow because
+ * the UTF-16 index may not be restored as well, but the iterator can deliver
+ * the correct text contents and move relative to the current position
+ * without performance degradation.
+ *
+ * Some UCharIterator implementations may not be able to return
+ * a valid state for each position, in which case they return UITER_NO_STATE instead.
+ * This will be clearly documented for each such iterator (none of the public ones here).
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @return the state word
+ *
+ * @see UCharIterator
+ * @see UCharIteratorSetState
+ * @see UITER_NO_STATE
+ * @stable ICU 2.6
+ */
+typedef uint32_t U_CALLCONV
+UCharIteratorGetState(const UCharIterator *iter);
+
+/**
+ * Function type declaration for UCharIterator.setState().
+ *
+ * Restore the "state" of the iterator using a state word from a getState() call.
+ * The iterator object need not be the same one as for which getState() was called,
+ * but it must be of the same type (set up using the same uiter_setXYZ function)
+ * and it must iterate over the same string
+ * (binary identical regardless of memory address).
+ * For more about the state word see UCharIteratorGetState.
+ *
+ * After calling setState(), a getIndex(UITER_CURRENT) may be slow because
+ * the UTF-16 index may not be restored as well, but the iterator can deliver
+ * the correct text contents and move relative to the current position
+ * without performance degradation.
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @param state the state word from a getState() call
+ * on a same-type, same-string iterator
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ *
+ * @see UCharIterator
+ * @see UCharIteratorGetState
+ * @stable ICU 2.6
+ */
+typedef void U_CALLCONV
+UCharIteratorSetState(UCharIterator *iter, uint32_t state, UErrorCode *pErrorCode);
+
+
+/**
+ * C API for code unit iteration.
+ * This can be used as a C wrapper around
+ * CharacterIterator, Replaceable, or implemented using simple strings, etc.
+ *
+ * There are two roles for using UCharIterator:
+ *
+ * A "provider" sets the necessary function pointers and controls the "protected"
+ * fields of the UCharIterator structure. A "provider" passes a UCharIterator
+ * into C APIs that need a UCharIterator as an abstract, flexible string interface.
+ *
+ * Implementations of such C APIs are "callers" of UCharIterator functions;
+ * they only use the "public" function pointers and never access the "protected"
+ * fields directly.
+ *
+ * The current() and next() functions only check the current index against the
+ * limit, and previous() only checks the current index against the start,
+ * to see if the iterator already reached the end of the iteration range.
+ *
+ * The assumption - in all iterators - is that the index is moved via the API,
+ * which means it won't go out of bounds, or the index is modified by
+ * user code that knows enough about the iterator implementation to set valid
+ * index values.
+ *
+ * UCharIterator functions return code unit values 0..0xffff,
+ * or U_SENTINEL if the iteration bounds are reached.
+ *
+ * @stable ICU 2.1
+ */
+struct UCharIterator {
+ /**
+ * (protected) Pointer to string or wrapped object or similar.
+ * Not used by caller.
+ * @stable ICU 2.1
+ */
+ const void *context;
+
+ /**
+ * (protected) Length of string or similar.
+ * Not used by caller.
+ * @stable ICU 2.1
+ */
+ int32_t length;
+
+ /**
+ * (protected) Start index or similar.
+ * Not used by caller.
+ * @stable ICU 2.1
+ */
+ int32_t start;
+
+ /**
+ * (protected) Current index or similar.
+ * Not used by caller.
+ * @stable ICU 2.1
+ */
+ int32_t index;
+
+ /**
+ * (protected) Limit index or similar.
+ * Not used by caller.
+ * @stable ICU 2.1
+ */
+ int32_t limit;
+
+ /**
+ * (protected) Used by UTF-8 iterators and possibly others.
+ * @stable ICU 2.1
+ */
+ int32_t reservedField;
+
+ /**
+ * (public) Returns the current position or the
+ * start or limit index of the iteration range.
+ *
+ * @see UCharIteratorGetIndex
+ * @stable ICU 2.1
+ */
+ UCharIteratorGetIndex *getIndex;
+
+ /**
+ * (public) Moves the current position relative to the start or limit of the
+ * iteration range, or relative to the current position itself.
+ * The movement is expressed in numbers of code units forward
+ * or backward by specifying a positive or negative delta.
+ *
+ * @see UCharIteratorMove
+ * @stable ICU 2.1
+ */
+ UCharIteratorMove *move;
+
+ /**
+ * (public) Check if current() and next() can still
+ * return another code unit.
+ *
+ * @see UCharIteratorHasNext
+ * @stable ICU 2.1
+ */
+ UCharIteratorHasNext *hasNext;
+
+ /**
+ * (public) Check if previous() can still return another code unit.
+ *
+ * @see UCharIteratorHasPrevious
+ * @stable ICU 2.1
+ */
+ UCharIteratorHasPrevious *hasPrevious;
+
+ /**
+ * (public) Return the code unit at the current position,
+ * or U_SENTINEL if there is none (index is at the limit).
+ *
+ * @see UCharIteratorCurrent
+ * @stable ICU 2.1
+ */
+ UCharIteratorCurrent *current;
+
+ /**
+ * (public) Return the code unit at the current index and increment
+ * the index (post-increment, like s[i++]),
+ * or return U_SENTINEL if there is none (index is at the limit).
+ *
+ * @see UCharIteratorNext
+ * @stable ICU 2.1
+ */
+ UCharIteratorNext *next;
+
+ /**
+ * (public) Decrement the index and return the code unit from there
+ * (pre-decrement, like s[--i]),
+ * or return U_SENTINEL if there is none (index is at the start).
+ *
+ * @see UCharIteratorPrevious
+ * @stable ICU 2.1
+ */
+ UCharIteratorPrevious *previous;
+
+ /**
+ * (public) Reserved for future use. Currently NULL.
+ *
+ * @see UCharIteratorReserved
+ * @stable ICU 2.1
+ */
+ UCharIteratorReserved *reservedFn;
+
+ /**
+ * (public) Return the state of the iterator, to be restored later with setState().
+ * This function pointer is NULL if the iterator does not implement it.
+ *
+ * @see UCharIteratorGet
+ * @stable ICU 2.6
+ */
+ UCharIteratorGetState *getState;
+
+ /**
+ * (public) Restore the iterator state from the state word from a call
+ * to getState().
+ * This function pointer is NULL if the iterator does not implement it.
+ *
+ * @see UCharIteratorSet
+ * @stable ICU 2.6
+ */
+ UCharIteratorSetState *setState;
+};
+
+/**
+ * Helper function for UCharIterator to get the code point
+ * at the current index.
+ *
+ * Return the code point that includes the code unit at the current position,
+ * or U_SENTINEL if there is none (index is at the limit).
+ * If the current code unit is a lead or trail surrogate,
+ * then the following or preceding surrogate is used to form
+ * the code point value.
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @return the current code point
+ *
+ * @see UCharIterator
+ * @see U16_GET
+ * @see UnicodeString::char32At()
+ * @stable ICU 2.1
+ */
+U_STABLE UChar32 U_EXPORT2
+uiter_current32(UCharIterator *iter);
+
+/**
+ * Helper function for UCharIterator to get the next code point.
+ *
+ * Return the code point at the current index and increment
+ * the index (post-increment, like s[i++]),
+ * or return U_SENTINEL if there is none (index is at the limit).
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @return the current code point (and post-increment the current index)
+ *
+ * @see UCharIterator
+ * @see U16_NEXT
+ * @stable ICU 2.1
+ */
+U_STABLE UChar32 U_EXPORT2
+uiter_next32(UCharIterator *iter);
+
+/**
+ * Helper function for UCharIterator to get the previous code point.
+ *
+ * Decrement the index and return the code point from there
+ * (pre-decrement, like s[--i]),
+ * or return U_SENTINEL if there is none (index is at the start).
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @return the previous code point (after pre-decrementing the current index)
+ *
+ * @see UCharIterator
+ * @see U16_PREV
+ * @stable ICU 2.1
+ */
+U_STABLE UChar32 U_EXPORT2
+uiter_previous32(UCharIterator *iter);
+
+/**
+ * Get the "state" of the iterator in the form of a single 32-bit word.
+ * This is a convenience function that calls iter->getState(iter)
+ * if iter->getState is not NULL;
+ * if it is NULL or any other error occurs, then UITER_NO_STATE is returned.
+ *
+ * Some UCharIterator implementations may not be able to return
+ * a valid state for each position, in which case they return UITER_NO_STATE instead.
+ * This will be clearly documented for each such iterator (none of the public ones here).
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @return the state word
+ *
+ * @see UCharIterator
+ * @see UCharIteratorGetState
+ * @see UITER_NO_STATE
+ * @stable ICU 2.6
+ */
+U_STABLE uint32_t U_EXPORT2
+uiter_getState(const UCharIterator *iter);
+
+/**
+ * Restore the "state" of the iterator using a state word from a getState() call.
+ * This is a convenience function that calls iter->setState(iter, state, pErrorCode)
+ * if iter->setState is not NULL; if it is NULL, then U_UNSUPPORTED_ERROR is set.
+ *
+ * @param iter the UCharIterator structure ("this pointer")
+ * @param state the state word from a getState() call
+ * on a same-type, same-string iterator
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ *
+ * @see UCharIterator
+ * @see UCharIteratorSetState
+ * @stable ICU 2.6
+ */
+U_STABLE void U_EXPORT2
+uiter_setState(UCharIterator *iter, uint32_t state, UErrorCode *pErrorCode);
+
+/**
+ * Set up a UCharIterator to iterate over a string.
+ *
+ * Sets the UCharIterator function pointers for iteration over the string s
+ * with iteration boundaries start=index=0 and length=limit=string length.
+ * The "provider" may set the start, index, and limit values at any time
+ * within the range 0..length.
+ * The length field will be ignored.
+ *
+ * The string pointer s is set into UCharIterator.context without copying
+ * or reallocating the string contents.
+ *
+ * getState() simply returns the current index.
+ * move() will always return the final index.
+ *
+ * @param iter UCharIterator structure to be set for iteration
+ * @param s String to iterate over
+ * @param length Length of s, or -1 if NUL-terminated
+ *
+ * @see UCharIterator
+ * @stable ICU 2.1
+ */
+U_STABLE void U_EXPORT2
+uiter_setString(UCharIterator *iter, const UChar *s, int32_t length);
+
+/**
+ * Set up a UCharIterator to iterate over a UTF-16BE string
+ * (byte vector with a big-endian pair of bytes per UChar).
+ *
+ * Everything works just like with a normal UChar iterator (uiter_setString),
+ * except that UChars are assembled from byte pairs,
+ * and that the length argument here indicates an even number of bytes.
+ *
+ * getState() simply returns the current index.
+ * move() will always return the final index.
+ *
+ * @param iter UCharIterator structure to be set for iteration
+ * @param s UTF-16BE string to iterate over
+ * @param length Length of s as an even number of bytes, or -1 if NUL-terminated
+ * (NUL means pair of 0 bytes at even index from s)
+ *
+ * @see UCharIterator
+ * @see uiter_setString
+ * @stable ICU 2.6
+ */
+U_STABLE void U_EXPORT2
+uiter_setUTF16BE(UCharIterator *iter, const char *s, int32_t length);
+
+/**
+ * Set up a UCharIterator to iterate over a UTF-8 string.
+ *
+ * Sets the UCharIterator function pointers for iteration over the UTF-8 string s
+ * with UTF-8 iteration boundaries 0 and length.
+ * The implementation counts the UTF-16 index on the fly and
+ * lazily evaluates the UTF-16 length of the text.
+ *
+ * The start field is used as the UTF-8 offset, the limit field as the UTF-8 length.
+ * When the reservedField is not 0, then it contains a supplementary code point
+ * and the UTF-16 index is between the two corresponding surrogates.
+ * At that point, the UTF-8 index is behind that code point.
+ *
+ * The UTF-8 string pointer s is set into UCharIterator.context without copying
+ * or reallocating the string contents.
+ *
+ * getState() returns a state value consisting of
+ * - the current UTF-8 source byte index (bits 31..1)
+ * - a flag (bit 0) that indicates whether the UChar position is in the middle
+ * of a surrogate pair
+ * (from a 4-byte UTF-8 sequence for the corresponding supplementary code point)
+ *
+ * getState() cannot also encode the UTF-16 index in the state value.
+ * move(relative to limit or length), or
+ * move(relative to current) after setState(), may return UITER_UNKNOWN_INDEX.
+ *
+ * @param iter UCharIterator structure to be set for iteration
+ * @param s UTF-8 string to iterate over
+ * @param length Length of s in bytes, or -1 if NUL-terminated
+ *
+ * @see UCharIterator
+ * @stable ICU 2.6
+ */
+U_STABLE void U_EXPORT2
+uiter_setUTF8(UCharIterator *iter, const char *s, int32_t length);
+
+#ifdef XP_CPLUSPLUS
+
+/**
+ * Set up a UCharIterator to wrap around a C++ CharacterIterator.
+ *
+ * Sets the UCharIterator function pointers for iteration using the
+ * CharacterIterator charIter.
+ *
+ * The CharacterIterator pointer charIter is set into UCharIterator.context
+ * without copying or cloning the CharacterIterator object.
+ * The other "protected" UCharIterator fields are set to 0 and will be ignored.
+ * The iteration index and boundaries are controlled by the CharacterIterator.
+ *
+ * getState() simply returns the current index.
+ * move() will always return the final index.
+ *
+ * @param iter UCharIterator structure to be set for iteration
+ * @param charIter CharacterIterator to wrap
+ *
+ * @see UCharIterator
+ * @stable ICU 2.1
+ */
+U_STABLE void U_EXPORT2
+uiter_setCharacterIterator(UCharIterator *iter, CharacterIterator *charIter);
+
+/**
+ * Set up a UCharIterator to iterate over a C++ Replaceable.
+ *
+ * Sets the UCharIterator function pointers for iteration over the
+ * Replaceable rep with iteration boundaries start=index=0 and
+ * length=limit=rep->length().
+ * The "provider" may set the start, index, and limit values at any time
+ * within the range 0..length=rep->length().
+ * The length field will be ignored.
+ *
+ * The Replaceable pointer rep is set into UCharIterator.context without copying
+ * or cloning/reallocating the Replaceable object.
+ *
+ * getState() simply returns the current index.
+ * move() will always return the final index.
+ *
+ * @param iter UCharIterator structure to be set for iteration
+ * @param rep Replaceable to iterate over
+ *
+ * @see UCharIterator
+ * @stable ICU 2.1
+ */
+U_STABLE void U_EXPORT2
+uiter_setReplaceable(UCharIterator *iter, const Replaceable *rep);
+
+#endif
+
+U_CDECL_END
+
+#endif
diff --git a/WebKit/mac/icu/unicode/umachine.h b/WebKit/mac/icu/unicode/umachine.h
new file mode 100644
index 0000000..d841f53
--- /dev/null
+++ b/WebKit/mac/icu/unicode/umachine.h
@@ -0,0 +1,371 @@
+/*
+******************************************************************************
+*
+* Copyright (C) 1999-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+*
+******************************************************************************
+* file name: umachine.h
+* encoding: US-ASCII
+* tab size: 8 (not used)
+* indentation:4
+*
+* created on: 1999sep13
+* created by: Markus W. Scherer
+*
+* This file defines basic types and constants for utf.h to be
+* platform-independent. umachine.h and utf.h are included into
+* utypes.h to provide all the general definitions for ICU.
+* All of these definitions used to be in utypes.h before
+* the UTF-handling macros made this unmaintainable.
+*/
+
+#ifndef __UMACHINE_H__
+#define __UMACHINE_H__
+
+
+/**
+ * \file
+ * \brief Basic types and constants for UTF
+ *
+ * <h2> Basic types and constants for UTF </h2>
+ * This file defines basic types and constants for utf.h to be
+ * platform-independent. umachine.h and utf.h are included into
+ * utypes.h to provide all the general definitions for ICU.
+ * All of these definitions used to be in utypes.h before
+ * the UTF-handling macros made this unmaintainable.
+ *
+ */
+/*==========================================================================*/
+/* Include platform-dependent definitions */
+/* which are contained in the platform-specific file platform.h */
+/*==========================================================================*/
+
+#if defined(WIN32) || defined(_WIN32) || defined(WIN64) || defined(_WIN64)
+# include "unicode/pwin32.h"
+#else
+# include "unicode/platform.h"
+#endif
+
+/*
+ * ANSI C headers:
+ * stddef.h defines wchar_t
+ */
+#include <stddef.h>
+
+/*==========================================================================*/
+/* XP_CPLUSPLUS is a cross-platform symbol which should be defined when */
+/* using C++. It should not be defined when compiling under C. */
+/*==========================================================================*/
+
+#ifdef __cplusplus
+# ifndef XP_CPLUSPLUS
+# define XP_CPLUSPLUS
+# endif
+#else
+# undef XP_CPLUSPLUS
+#endif
+
+/*==========================================================================*/
+/* For C wrappers, we use the symbol U_STABLE. */
+/* This works properly if the includer is C or C++. */
+/* Functions are declared U_STABLE return-type U_EXPORT2 function-name()... */
+/*==========================================================================*/
+
+/**
+ * \def U_CFUNC
+ * This is used in a declaration of a library private ICU C function.
+ * @stable ICU 2.4
+ */
+
+/**
+ * \def U_CDECL_BEGIN
+ * This is used to begin a declaration of a library private ICU C API.
+ * @stable ICU 2.4
+ */
+
+/**
+ * \def U_CDECL_END
+ * This is used to end a declaration of a library private ICU C API
+ * @stable ICU 2.4
+ */
+
+#ifdef XP_CPLUSPLUS
+# define U_CFUNC extern "C"
+# define U_CDECL_BEGIN extern "C" {
+# define U_CDECL_END }
+#else
+# define U_CFUNC extern
+# define U_CDECL_BEGIN
+# define U_CDECL_END
+#endif
+
+/**
+ * \def U_NAMESPACE_BEGIN
+ * This is used to begin a declaration of a public ICU C++ API.
+ * If the compiler doesn't support namespaces, this does nothing.
+ * @stable ICU 2.4
+ */
+
+/**
+ * \def U_NAMESPACE_END
+ * This is used to end a declaration of a public ICU C++ API
+ * If the compiler doesn't support namespaces, this does nothing.
+ * @stable ICU 2.4
+ */
+
+/**
+ * \def U_NAMESPACE_USE
+ * This is used to specify that the rest of the code uses the
+ * public ICU C++ API namespace.
+ * If the compiler doesn't support namespaces, this does nothing.
+ * @stable ICU 2.4
+ */
+
+/**
+ * \def U_NAMESPACE_QUALIFIER
+ * This is used to qualify that a function or class is part of
+ * the public ICU C++ API namespace.
+ * If the compiler doesn't support namespaces, this does nothing.
+ * @stable ICU 2.4
+ */
+
+/* Define namespace symbols if the compiler supports it. */
+#if U_HAVE_NAMESPACE
+# define U_NAMESPACE_BEGIN namespace U_ICU_NAMESPACE {
+# define U_NAMESPACE_END }
+# define U_NAMESPACE_USE using namespace U_ICU_NAMESPACE;
+# define U_NAMESPACE_QUALIFIER U_ICU_NAMESPACE::
+#else
+# define U_NAMESPACE_BEGIN
+# define U_NAMESPACE_END
+# define U_NAMESPACE_USE
+# define U_NAMESPACE_QUALIFIER
+#endif
+
+/** This is used to declare a function as a public ICU C API @stable ICU 2.0*/
+#define U_CAPI U_CFUNC U_EXPORT
+#define U_STABLE U_CAPI
+#define U_DRAFT U_CAPI
+#define U_DEPRECATED U_CAPI
+#define U_OBSOLETE U_CAPI
+#define U_INTERNAL U_CAPI
+
+/*==========================================================================*/
+/* limits for int32_t etc., like in POSIX inttypes.h */
+/*==========================================================================*/
+
+#ifndef INT8_MIN
+/** The smallest value an 8 bit signed integer can hold @stable ICU 2.0 */
+# define INT8_MIN ((int8_t)(-128))
+#endif
+#ifndef INT16_MIN
+/** The smallest value a 16 bit signed integer can hold @stable ICU 2.0 */
+# define INT16_MIN ((int16_t)(-32767-1))
+#endif
+#ifndef INT32_MIN
+/** The smallest value a 32 bit signed integer can hold @stable ICU 2.0 */
+# define INT32_MIN ((int32_t)(-2147483647-1))
+#endif
+
+#ifndef INT8_MAX
+/** The largest value an 8 bit signed integer can hold @stable ICU 2.0 */
+# define INT8_MAX ((int8_t)(127))
+#endif
+#ifndef INT16_MAX
+/** The largest value a 16 bit signed integer can hold @stable ICU 2.0 */
+# define INT16_MAX ((int16_t)(32767))
+#endif
+#ifndef INT32_MAX
+/** The largest value a 32 bit signed integer can hold @stable ICU 2.0 */
+# define INT32_MAX ((int32_t)(2147483647))
+#endif
+
+#ifndef UINT8_MAX
+/** The largest value an 8 bit unsigned integer can hold @stable ICU 2.0 */
+# define UINT8_MAX ((uint8_t)(255U))
+#endif
+#ifndef UINT16_MAX
+/** The largest value a 16 bit unsigned integer can hold @stable ICU 2.0 */
+# define UINT16_MAX ((uint16_t)(65535U))
+#endif
+#ifndef UINT32_MAX
+/** The largest value a 32 bit unsigned integer can hold @stable ICU 2.0 */
+# define UINT32_MAX ((uint32_t)(4294967295U))
+#endif
+
+#if defined(U_INT64_T_UNAVAILABLE)
+# error int64_t is required for decimal format and rule-based number format.
+#else
+# ifndef INT64_C
+/**
+ * Provides a platform independent way to specify a signed 64-bit integer constant.
+ * note: may be wrong for some 64 bit platforms - ensure your compiler provides INT64_C
+ * @draft ICU 2.8
+ */
+# define INT64_C(c) c ## LL
+# endif
+# ifndef UINT64_C
+/**
+ * Provides a platform independent way to specify an unsigned 64-bit integer constant.
+ * note: may be wrong for some 64 bit platforms - ensure your compiler provides UINT64_C
+ * @draft ICU 2.8
+ */
+# define UINT64_C(c) c ## ULL
+# endif
+# ifndef U_INT64_MIN
+/** The smallest value a 64 bit signed integer can hold @stable ICU 2.8 */
+# define U_INT64_MIN ((int64_t)(INT64_C(-9223372036854775807)-1))
+# endif
+# ifndef U_INT64_MAX
+/** The largest value a 64 bit signed integer can hold @stable ICU 2.8 */
+# define U_INT64_MAX ((int64_t)(INT64_C(9223372036854775807)))
+# endif
+# ifndef U_UINT64_MAX
+/** The largest value a 64 bit unsigned integer can hold @stable ICU 2.8 */
+# define U_UINT64_MAX ((uint64_t)(UINT64_C(18446744073709551615)))
+# endif
+#endif
+
+/*==========================================================================*/
+/* Boolean data type */
+/*==========================================================================*/
+
+/** The ICU boolean type @stable ICU 2.0 */
+typedef int8_t UBool;
+
+#ifndef TRUE
+/** The TRUE value of a UBool @stable ICU 2.0 */
+# define TRUE 1
+#endif
+#ifndef FALSE
+/** The FALSE value of a UBool @stable ICU 2.0 */
+# define FALSE 0
+#endif
+
+
+/*==========================================================================*/
+/* Unicode data types */
+/*==========================================================================*/
+
+/* wchar_t-related definitions -------------------------------------------- */
+
+/**
+ * \def U_HAVE_WCHAR_H
+ * Indicates whether <wchar.h> is available (1) or not (0). Set to 1 by default.
+ *
+ * @stable ICU 2.0
+ */
+#ifndef U_HAVE_WCHAR_H
+# define U_HAVE_WCHAR_H 1
+#endif
+
+/**
+ * \def U_SIZEOF_WCHAR_T
+ * U_SIZEOF_WCHAR_T==sizeof(wchar_t) (0 means it is not defined or autoconf could not set it)
+ *
+ * @stable ICU 2.0
+ */
+#if U_SIZEOF_WCHAR_T==0
+# undef U_SIZEOF_WCHAR_T
+# define U_SIZEOF_WCHAR_T 4
+#endif
+
+/*
+ * \def U_WCHAR_IS_UTF16
+ * Defined if wchar_t uses UTF-16.
+ *
+ * @stable ICU 2.0
+ */
+/*
+ * \def U_WCHAR_IS_UTF32
+ * Defined if wchar_t uses UTF-32.
+ *
+ * @stable ICU 2.0
+ */
+#if !defined(U_WCHAR_IS_UTF16) && !defined(U_WCHAR_IS_UTF32)
+# ifdef __STDC_ISO_10646__
+# if (U_SIZEOF_WCHAR_T==2)
+# define U_WCHAR_IS_UTF16
+# elif (U_SIZEOF_WCHAR_T==4)
+# define U_WCHAR_IS_UTF32
+# endif
+# elif defined __UCS2__
+# if (__OS390__ || __OS400__) && (U_SIZEOF_WCHAR_T==2)
+# define U_WCHAR_IS_UTF16
+# endif
+# elif defined __UCS4__
+# if (U_SIZEOF_WCHAR_T==4)
+# define U_WCHAR_IS_UTF32
+# endif
+# elif defined(WIN32) || defined(_WIN32) || defined(WIN64) || defined(_WIN64)
+# define U_WCHAR_IS_UTF16
+# endif
+#endif
+
+/* UChar and UChar32 definitions -------------------------------------------- */
+
+/** Number of bytes in a UChar. @stable ICU 2.0 */
+#define U_SIZEOF_UCHAR 2
+
+/**
+ * \var UChar
+ * Define UChar to be wchar_t if that is 16 bits wide; always assumed to be unsigned.
+ * If wchar_t is not 16 bits wide, then define UChar to be uint16_t.
+ * This makes the definition of UChar platform-dependent
+ * but allows direct string type compatibility with platforms with
+ * 16-bit wchar_t types.
+ *
+ * @stable ICU 2.0
+ */
+
+/* Define UChar to be compatible with wchar_t if possible. */
+#if U_SIZEOF_WCHAR_T==2
+ typedef wchar_t UChar;
+#else
+ typedef uint16_t UChar;
+#endif
+
+/**
+ * Define UChar32 as a type for single Unicode code points.
+ * UChar32 is a signed 32-bit integer (same as int32_t).
+ *
+ * The Unicode code point range is 0..0x10ffff.
+ * All other values (negative or >=0x110000) are illegal as Unicode code points.
+ * They may be used as sentinel values to indicate "done", "error"
+ * or similar non-code point conditions.
+ *
+ * Before ICU 2.4 (Jitterbug 2146), UChar32 was defined
+ * to be wchar_t if that is 32 bits wide (wchar_t may be signed or unsigned)
+ * or else to be uint32_t.
+ * That is, the definition of UChar32 was platform-dependent.
+ *
+ * @see U_SENTINEL
+ * @stable ICU 2.4
+ */
+typedef int32_t UChar32;
+
+/*==========================================================================*/
+/* U_INLINE and U_ALIGN_CODE Set default values if these are not already */
+/* defined. Definitions normally are in */
+/* platform.h or the corresponding file for */
+/* the OS in use. */
+/*==========================================================================*/
+
+/**
+ * \def U_ALIGN_CODE
+ * This is used to align code fragments to a specific byte boundary.
+ * This is useful for getting consistent performance test results.
+ * @internal
+ */
+#ifndef U_ALIGN_CODE
+# define U_ALIGN_CODE(n)
+#endif
+
+#ifndef U_INLINE
+# define U_INLINE
+#endif
+
+#include "unicode/urename.h"
+
+#endif
diff --git a/WebKit/mac/icu/unicode/unorm.h b/WebKit/mac/icu/unicode/unorm.h
new file mode 100644
index 0000000..8bdbee7
--- /dev/null
+++ b/WebKit/mac/icu/unicode/unorm.h
@@ -0,0 +1,575 @@
+/*
+*******************************************************************************
+* Copyright (c) 1996-2004, International Business Machines Corporation
+* and others. All Rights Reserved.
+*******************************************************************************
+* File unorm.h
+*
+* Created by: Vladimir Weinstein 12052000
+*
+* Modification history :
+*
+* Date Name Description
+* 02/01/01 synwee Added normalization quickcheck enum and method.
+*/
+#ifndef UNORM_H
+#define UNORM_H
+
+#include "unicode/utypes.h"
+
+#if !UCONFIG_NO_NORMALIZATION
+
+#include "unicode/uiter.h"
+
+/**
+ * \file
+ * \brief C API: Unicode Normalization
+ *
+ * <h2>Unicode normalization API</h2>
+ *
+ * <code>unorm_normalize</code> transforms Unicode text into an equivalent composed or
+ * decomposed form, allowing for easier sorting and searching of text.
+ * <code>unorm_normalize</code> supports the standard normalization forms described in
+ * <a href="http://www.unicode.org/unicode/reports/tr15/" target="unicode">
+ * Unicode Standard Annex #15 &#8212; Unicode Normalization Forms</a>.
+ *
+ * Characters with accents or other adornments can be encoded in
+ * several different ways in Unicode. For example, take the character A-acute.
+ * In Unicode, this can be encoded as a single character (the
+ * "composed" form):
+ *
+ * \code
+ * 00C1 LATIN CAPITAL LETTER A WITH ACUTE
+ * \endcode
+ *
+ * or as two separate characters (the "decomposed" form):
+ *
+ * \code
+ * 0041 LATIN CAPITAL LETTER A
+ * 0301 COMBINING ACUTE ACCENT
+ * \endcode
+ *
+ * To a user of your program, however, both of these sequences should be
+ * treated as the same "user-level" character "A with acute accent". When you are searching or
+ * comparing text, you must ensure that these two sequences are treated
+ * equivalently. In addition, you must handle characters with more than one
+ * accent. Sometimes the order of a character's combining accents is
+ * significant, while in other cases accent sequences in different orders are
+ * really equivalent.
+ *
+ * Similarly, the string "ffi" can be encoded as three separate letters:
+ *
+ * \code
+ * 0066 LATIN SMALL LETTER F
+ * 0066 LATIN SMALL LETTER F
+ * 0069 LATIN SMALL LETTER I
+ * \endcode
+ *
+ * or as the single character
+ *
+ * \code
+ * FB03 LATIN SMALL LIGATURE FFI
+ * \endcode
+ *
+ * The ffi ligature is not a distinct semantic character, and strictly speaking
+ * it shouldn't be in Unicode at all, but it was included for compatibility
+ * with existing character sets that already provided it. The Unicode standard
+ * identifies such characters by giving them "compatibility" decompositions
+ * into the corresponding semantic characters. When sorting and searching, you
+ * will often want to use these mappings.
+ *
+ * <code>unorm_normalize</code> helps solve these problems by transforming text into the
+ * canonical composed and decomposed forms as shown in the first example above.
+ * In addition, you can have it perform compatibility decompositions so that
+ * you can treat compatibility characters the same as their equivalents.
+ * Finally, <code>unorm_normalize</code> rearranges accents into the proper canonical
+ * order, so that you do not have to worry about accent rearrangement on your
+ * own.
+ *
+ * Form FCD, "Fast C or D", is also designed for collation.
+ * It allows to work on strings that are not necessarily normalized
+ * with an algorithm (like in collation) that works under "canonical closure", i.e., it treats precomposed
+ * characters and their decomposed equivalents the same.
+ *
+ * It is not a normalization form because it does not provide for uniqueness of representation. Multiple strings
+ * may be canonically equivalent (their NFDs are identical) and may all conform to FCD without being identical
+ * themselves.
+ *
+ * The form is defined such that the "raw decomposition", the recursive canonical decomposition of each character,
+ * results in a string that is canonically ordered. This means that precomposed characters are allowed for as long
+ * as their decompositions do not need canonical reordering.
+ *
+ * Its advantage for a process like collation is that all NFD and most NFC texts - and many unnormalized texts -
+ * already conform to FCD and do not need to be normalized (NFD) for such a process. The FCD quick check will
+ * return UNORM_YES for most strings in practice.
+ *
+ * unorm_normalize(UNORM_FCD) may be implemented with UNORM_NFD.
+ *
+ * For more details on FCD see the collation design document:
+ * http://oss.software.ibm.com/cvs/icu/~checkout~/icuhtml/design/collation/ICU_collation_design.htm
+ *
+ * ICU collation performs either NFD or FCD normalization automatically if normalization
+ * is turned on for the collator object.
+ * Beyond collation and string search, normalized strings may be useful for string equivalence comparisons,
+ * transliteration/transcription, unique representations, etc.
+ *
+ * The W3C generally recommends to exchange texts in NFC.
+ * Note also that most legacy character encodings use only precomposed forms and often do not
+ * encode any combining marks by themselves. For conversion to such character encodings the
+ * Unicode text needs to be normalized to NFC.
+ * For more usage examples, see the Unicode Standard Annex.
+ */
+
+/**
+ * Constants for normalization modes.
+ * @stable ICU 2.0
+ */
+typedef enum {
+ /** No decomposition/composition. @stable ICU 2.0 */
+ UNORM_NONE = 1,
+ /** Canonical decomposition. @stable ICU 2.0 */
+ UNORM_NFD = 2,
+ /** Compatibility decomposition. @stable ICU 2.0 */
+ UNORM_NFKD = 3,
+ /** Canonical decomposition followed by canonical composition. @stable ICU 2.0 */
+ UNORM_NFC = 4,
+ /** Default normalization. @stable ICU 2.0 */
+ UNORM_DEFAULT = UNORM_NFC,
+ /** Compatibility decomposition followed by canonical composition. @stable ICU 2.0 */
+ UNORM_NFKC =5,
+ /** "Fast C or D" form. @stable ICU 2.0 */
+ UNORM_FCD = 6,
+
+ /** One more than the highest normalization mode constant. @stable ICU 2.0 */
+ UNORM_MODE_COUNT
+} UNormalizationMode;
+
+/**
+ * Constants for options flags for normalization.
+ * Use 0 for default options,
+ * including normalization according to the Unicode version
+ * that is currently supported by ICU (see u_getUnicodeVersion).
+ * @stable ICU 2.6
+ */
+enum {
+ /**
+ * Options bit set value to select Unicode 3.2 normalization
+ * (except NormalizationCorrections).
+ * At most one Unicode version can be selected at a time.
+ * @stable ICU 2.6
+ */
+ UNORM_UNICODE_3_2=0x20
+};
+
+/**
+ * Lowest-order bit number of unorm_compare() options bits corresponding to
+ * normalization options bits.
+ *
+ * The options parameter for unorm_compare() uses most bits for
+ * itself and for various comparison and folding flags.
+ * The most significant bits, however, are shifted down and passed on
+ * to the normalization implementation.
+ * (That is, from unorm_compare(..., options, ...),
+ * options>>UNORM_COMPARE_NORM_OPTIONS_SHIFT will be passed on to the
+ * internal normalization functions.)
+ *
+ * @see unorm_compare
+ * @stable ICU 2.6
+ */
+#define UNORM_COMPARE_NORM_OPTIONS_SHIFT 20
+
+/**
+ * Normalize a string.
+ * The string will be normalized according the specified normalization mode
+ * and options.
+ *
+ * @param source The string to normalize.
+ * @param sourceLength The length of source, or -1 if NUL-terminated.
+ * @param mode The normalization mode; one of UNORM_NONE,
+ * UNORM_NFD, UNORM_NFC, UNORM_NFKC, UNORM_NFKD, UNORM_DEFAULT.
+ * @param options The normalization options, ORed together (0 for no options).
+ * @param result A pointer to a buffer to receive the result string.
+ * The result string is NUL-terminated if possible.
+ * @param resultLength The maximum size of result.
+ * @param status A pointer to a UErrorCode to receive any errors.
+ * @return The total buffer size needed; if greater than resultLength,
+ * the output was truncated, and the error code is set to U_BUFFER_OVERFLOW_ERROR.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+unorm_normalize(const UChar *source, int32_t sourceLength,
+ UNormalizationMode mode, int32_t options,
+ UChar *result, int32_t resultLength,
+ UErrorCode *status);
+#endif
+/**
+ * Result values for unorm_quickCheck().
+ * For details see Unicode Technical Report 15.
+ * @stable ICU 2.0
+ */
+typedef enum UNormalizationCheckResult {
+ /**
+ * Indicates that string is not in the normalized format
+ */
+ UNORM_NO,
+ /**
+ * Indicates that string is in the normalized format
+ */
+ UNORM_YES,
+ /**
+ * Indicates that string cannot be determined if it is in the normalized
+ * format without further thorough checks.
+ */
+ UNORM_MAYBE
+} UNormalizationCheckResult;
+#if !UCONFIG_NO_NORMALIZATION
+/**
+ * Performing quick check on a string, to quickly determine if the string is
+ * in a particular normalization format.
+ * Three types of result can be returned UNORM_YES, UNORM_NO or
+ * UNORM_MAYBE. Result UNORM_YES indicates that the argument
+ * string is in the desired normalized format, UNORM_NO determines that
+ * argument string is not in the desired normalized format. A
+ * UNORM_MAYBE result indicates that a more thorough check is required,
+ * the user may have to put the string in its normalized form and compare the
+ * results.
+ *
+ * @param source string for determining if it is in a normalized format
+ * @param sourcelength length of source to test, or -1 if NUL-terminated
+ * @param mode which normalization form to test for
+ * @param status a pointer to a UErrorCode to receive any errors
+ * @return UNORM_YES, UNORM_NO or UNORM_MAYBE
+ *
+ * @see unorm_isNormalized
+ * @stable ICU 2.0
+ */
+U_STABLE UNormalizationCheckResult U_EXPORT2
+unorm_quickCheck(const UChar *source, int32_t sourcelength,
+ UNormalizationMode mode,
+ UErrorCode *status);
+
+/**
+ * Performing quick check on a string; same as unorm_quickCheck but
+ * takes an extra options parameter like most normalization functions.
+ *
+ * @param src String that is to be tested if it is in a normalization format.
+ * @param srcLength Length of source to test, or -1 if NUL-terminated.
+ * @param mode Which normalization form to test for.
+ * @param options The normalization options, ORed together (0 for no options).
+ * @param pErrorCode ICU error code in/out parameter.
+ * Must fulfill U_SUCCESS before the function call.
+ * @return UNORM_YES, UNORM_NO or UNORM_MAYBE
+ *
+ * @see unorm_quickCheck
+ * @see unorm_isNormalized
+ * @stable ICU 2.6
+ */
+U_STABLE UNormalizationCheckResult U_EXPORT2
+unorm_quickCheckWithOptions(const UChar *src, int32_t srcLength,
+ UNormalizationMode mode, int32_t options,
+ UErrorCode *pErrorCode);
+
+/**
+ * Test if a string is in a given normalization form.
+ * This is semantically equivalent to source.equals(normalize(source, mode)) .
+ *
+ * Unlike unorm_quickCheck(), this function returns a definitive result,
+ * never a "maybe".
+ * For NFD, NFKD, and FCD, both functions work exactly the same.
+ * For NFC and NFKC where quickCheck may return "maybe", this function will
+ * perform further tests to arrive at a TRUE/FALSE result.
+ *
+ * @param src String that is to be tested if it is in a normalization format.
+ * @param srcLength Length of source to test, or -1 if NUL-terminated.
+ * @param mode Which normalization form to test for.
+ * @param pErrorCode ICU error code in/out parameter.
+ * Must fulfill U_SUCCESS before the function call.
+ * @return Boolean value indicating whether the source string is in the
+ * "mode" normalization form.
+ *
+ * @see unorm_quickCheck
+ * @stable ICU 2.2
+ */
+U_STABLE UBool U_EXPORT2
+unorm_isNormalized(const UChar *src, int32_t srcLength,
+ UNormalizationMode mode,
+ UErrorCode *pErrorCode);
+
+/**
+ * Test if a string is in a given normalization form; same as unorm_isNormalized but
+ * takes an extra options parameter like most normalization functions.
+ *
+ * @param src String that is to be tested if it is in a normalization format.
+ * @param srcLength Length of source to test, or -1 if NUL-terminated.
+ * @param mode Which normalization form to test for.
+ * @param options The normalization options, ORed together (0 for no options).
+ * @param pErrorCode ICU error code in/out parameter.
+ * Must fulfill U_SUCCESS before the function call.
+ * @return Boolean value indicating whether the source string is in the
+ * "mode/options" normalization form.
+ *
+ * @see unorm_quickCheck
+ * @see unorm_isNormalized
+ * @stable ICU 2.6
+ */
+U_STABLE UBool U_EXPORT2
+unorm_isNormalizedWithOptions(const UChar *src, int32_t srcLength,
+ UNormalizationMode mode, int32_t options,
+ UErrorCode *pErrorCode);
+
+/**
+ * Iterative normalization forward.
+ * This function (together with unorm_previous) is somewhat
+ * similar to the C++ Normalizer class (see its non-static functions).
+ *
+ * Iterative normalization is useful when only a small portion of a longer
+ * string/text needs to be processed.
+ *
+ * For example, the likelihood may be high that processing the first 10% of some
+ * text will be sufficient to find certain data.
+ * Another example: When one wants to concatenate two normalized strings and get a
+ * normalized result, it is much more efficient to normalize just a small part of
+ * the result around the concatenation place instead of re-normalizing everything.
+ *
+ * The input text is an instance of the C character iteration API UCharIterator.
+ * It may wrap around a simple string, a CharacterIterator, a Replaceable, or any
+ * other kind of text object.
+ *
+ * If a buffer overflow occurs, then the caller needs to reset the iterator to the
+ * old index and call the function again with a larger buffer - if the caller cares
+ * for the actual output.
+ * Regardless of the output buffer, the iterator will always be moved to the next
+ * normalization boundary.
+ *
+ * This function (like unorm_previous) serves two purposes:
+ *
+ * 1) To find the next boundary so that the normalization of the part of the text
+ * from the current position to that boundary does not affect and is not affected
+ * by the part of the text beyond that boundary.
+ *
+ * 2) To normalize the text up to the boundary.
+ *
+ * The second step is optional, per the doNormalize parameter.
+ * It is omitted for operations like string concatenation, where the two adjacent
+ * string ends need to be normalized together.
+ * In such a case, the output buffer will just contain a copy of the text up to the
+ * boundary.
+ *
+ * pNeededToNormalize is an output-only parameter. Its output value is only defined
+ * if normalization was requested (doNormalize) and successful (especially, no
+ * buffer overflow).
+ * It is useful for operations like a normalizing transliterator, where one would
+ * not want to replace a piece of text if it is not modified.
+ *
+ * If doNormalize==TRUE and pNeededToNormalize!=NULL then *pNeeded... is set TRUE
+ * if the normalization was necessary.
+ *
+ * If doNormalize==FALSE then *pNeededToNormalize will be set to FALSE.
+ *
+ * If the buffer overflows, then *pNeededToNormalize will be undefined;
+ * essentially, whenever U_FAILURE is true (like in buffer overflows), this result
+ * will be undefined.
+ *
+ * @param src The input text in the form of a C character iterator.
+ * @param dest The output buffer; can be NULL if destCapacity==0 for pure preflighting.
+ * @param destCapacity The number of UChars that fit into dest.
+ * @param mode The normalization mode.
+ * @param options The normalization options, ORed together (0 for no options).
+ * @param doNormalize Indicates if the source text up to the next boundary
+ * is to be normalized (TRUE) or just copied (FALSE).
+ * @param pNeededToNormalize Output flag indicating if the normalization resulted in
+ * different text from the input.
+ * Not defined if an error occurs including buffer overflow.
+ * Always FALSE if !doNormalize.
+ * @param pErrorCode ICU error code in/out parameter.
+ * Must fulfill U_SUCCESS before the function call.
+ * @return Length of output (number of UChars) when successful or buffer overflow.
+ *
+ * @see unorm_previous
+ * @see unorm_normalize
+ *
+ * @stable ICU 2.1
+ */
+U_STABLE int32_t U_EXPORT2
+unorm_next(UCharIterator *src,
+ UChar *dest, int32_t destCapacity,
+ UNormalizationMode mode, int32_t options,
+ UBool doNormalize, UBool *pNeededToNormalize,
+ UErrorCode *pErrorCode);
+
+/**
+ * Iterative normalization backward.
+ * This function (together with unorm_next) is somewhat
+ * similar to the C++ Normalizer class (see its non-static functions).
+ * For all details see unorm_next.
+ *
+ * @param src The input text in the form of a C character iterator.
+ * @param dest The output buffer; can be NULL if destCapacity==0 for pure preflighting.
+ * @param destCapacity The number of UChars that fit into dest.
+ * @param mode The normalization mode.
+ * @param options The normalization options, ORed together (0 for no options).
+ * @param doNormalize Indicates if the source text up to the next boundary
+ * is to be normalized (TRUE) or just copied (FALSE).
+ * @param pNeededToNormalize Output flag indicating if the normalization resulted in
+ * different text from the input.
+ * Not defined if an error occurs including buffer overflow.
+ * Always FALSE if !doNormalize.
+ * @param pErrorCode ICU error code in/out parameter.
+ * Must fulfill U_SUCCESS before the function call.
+ * @return Length of output (number of UChars) when successful or buffer overflow.
+ *
+ * @see unorm_next
+ * @see unorm_normalize
+ *
+ * @stable ICU 2.1
+ */
+U_STABLE int32_t U_EXPORT2
+unorm_previous(UCharIterator *src,
+ UChar *dest, int32_t destCapacity,
+ UNormalizationMode mode, int32_t options,
+ UBool doNormalize, UBool *pNeededToNormalize,
+ UErrorCode *pErrorCode);
+
+/**
+ * Concatenate normalized strings, making sure that the result is normalized as well.
+ *
+ * If both the left and the right strings are in
+ * the normalization form according to "mode/options",
+ * then the result will be
+ *
+ * \code
+ * dest=normalize(left+right, mode, options)
+ * \endcode
+ *
+ * With the input strings already being normalized,
+ * this function will use unorm_next() and unorm_previous()
+ * to find the adjacent end pieces of the input strings.
+ * Only the concatenation of these end pieces will be normalized and
+ * then concatenated with the remaining parts of the input strings.
+ *
+ * It is allowed to have dest==left to avoid copying the entire left string.
+ *
+ * @param left Left source string, may be same as dest.
+ * @param leftLength Length of left source string, or -1 if NUL-terminated.
+ * @param right Right source string.
+ * @param rightLength Length of right source string, or -1 if NUL-terminated.
+ * @param dest The output buffer; can be NULL if destCapacity==0 for pure preflighting.
+ * @param destCapacity The number of UChars that fit into dest.
+ * @param mode The normalization mode.
+ * @param options The normalization options, ORed together (0 for no options).
+ * @param pErrorCode ICU error code in/out parameter.
+ * Must fulfill U_SUCCESS before the function call.
+ * @return Length of output (number of UChars) when successful or buffer overflow.
+ *
+ * @see unorm_normalize
+ * @see unorm_next
+ * @see unorm_previous
+ *
+ * @stable ICU 2.1
+ */
+U_STABLE int32_t U_EXPORT2
+unorm_concatenate(const UChar *left, int32_t leftLength,
+ const UChar *right, int32_t rightLength,
+ UChar *dest, int32_t destCapacity,
+ UNormalizationMode mode, int32_t options,
+ UErrorCode *pErrorCode);
+
+/**
+ * Option bit for unorm_compare:
+ * Both input strings are assumed to fulfill FCD conditions.
+ * @stable ICU 2.2
+ */
+#define UNORM_INPUT_IS_FCD 0x20000
+
+/**
+ * Option bit for unorm_compare:
+ * Perform case-insensitive comparison.
+ * @stable ICU 2.2
+ */
+#define U_COMPARE_IGNORE_CASE 0x10000
+
+#ifndef U_COMPARE_CODE_POINT_ORDER
+/* see also unistr.h and ustring.h */
+/**
+ * Option bit for u_strCaseCompare, u_strcasecmp, unorm_compare, etc:
+ * Compare strings in code point order instead of code unit order.
+ * @stable ICU 2.2
+ */
+#define U_COMPARE_CODE_POINT_ORDER 0x8000
+#endif
+
+/**
+ * Compare two strings for canonical equivalence.
+ * Further options include case-insensitive comparison and
+ * code point order (as opposed to code unit order).
+ *
+ * Canonical equivalence between two strings is defined as their normalized
+ * forms (NFD or NFC) being identical.
+ * This function compares strings incrementally instead of normalizing
+ * (and optionally case-folding) both strings entirely,
+ * improving performance significantly.
+ *
+ * Bulk normalization is only necessary if the strings do not fulfill the FCD
+ * conditions. Only in this case, and only if the strings are relatively long,
+ * is memory allocated temporarily.
+ * For FCD strings and short non-FCD strings there is no memory allocation.
+ *
+ * Semantically, this is equivalent to
+ * strcmp[CodePointOrder](NFD(foldCase(NFD(s1))), NFD(foldCase(NFD(s2))))
+ * where code point order and foldCase are all optional.
+ *
+ * UAX 21 2.5 Caseless Matching specifies that for a canonical caseless match
+ * the case folding must be performed first, then the normalization.
+ *
+ * @param s1 First source string.
+ * @param length1 Length of first source string, or -1 if NUL-terminated.
+ *
+ * @param s2 Second source string.
+ * @param length2 Length of second source string, or -1 if NUL-terminated.
+ *
+ * @param options A bit set of options:
+ * - U_FOLD_CASE_DEFAULT or 0 is used for default options:
+ * Case-sensitive comparison in code unit order, and the input strings
+ * are quick-checked for FCD.
+ *
+ * - UNORM_INPUT_IS_FCD
+ * Set if the caller knows that both s1 and s2 fulfill the FCD conditions.
+ * If not set, the function will quickCheck for FCD
+ * and normalize if necessary.
+ *
+ * - U_COMPARE_CODE_POINT_ORDER
+ * Set to choose code point order instead of code unit order
+ * (see u_strCompare for details).
+ *
+ * - U_COMPARE_IGNORE_CASE
+ * Set to compare strings case-insensitively using case folding,
+ * instead of case-sensitively.
+ * If set, then the following case folding options are used.
+ *
+ * - Options as used with case-insensitive comparisons, currently:
+ *
+ * - U_FOLD_CASE_EXCLUDE_SPECIAL_I
+ * (see u_strCaseCompare for details)
+ *
+ * - regular normalization options shifted left by UNORM_COMPARE_NORM_OPTIONS_SHIFT
+ *
+ * @param pErrorCode ICU error code in/out parameter.
+ * Must fulfill U_SUCCESS before the function call.
+ * @return <0 or 0 or >0 as usual for string comparisons
+ *
+ * @see unorm_normalize
+ * @see UNORM_FCD
+ * @see u_strCompare
+ * @see u_strCaseCompare
+ *
+ * @stable ICU 2.2
+ */
+U_STABLE int32_t U_EXPORT2
+unorm_compare(const UChar *s1, int32_t length1,
+ const UChar *s2, int32_t length2,
+ uint32_t options,
+ UErrorCode *pErrorCode);
+
+#endif /* #if !UCONFIG_NO_NORMALIZATION */
+
+#endif
diff --git a/WebKit/mac/icu/unicode/urename.h b/WebKit/mac/icu/unicode/urename.h
new file mode 100644
index 0000000..5562592
--- /dev/null
+++ b/WebKit/mac/icu/unicode/urename.h
@@ -0,0 +1,1468 @@
+/*
+*******************************************************************************
+* Copyright (C) 2002-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+*******************************************************************************
+*
+* file name: urename.h
+* encoding: US-ASCII
+* tab size: 8 (not used)
+* indentation:4
+*
+* Created by: Perl script written by Vladimir Weinstein
+*
+* Contains data for renaming ICU exports.
+* Gets included by umachine.h
+*
+* THIS FILE IS MACHINE-GENERATED, DON'T PLAY WITH IT IF YOU DON'T KNOW WHAT
+* YOU ARE DOING, OTHERWISE VERY BAD THINGS WILL HAPPEN!
+*/
+
+#ifndef URENAME_H
+#define URENAME_H
+
+/* Uncomment the following line to disable renaming on platforms
+ that do not use Autoconf. */
+/* #define U_DISABLE_RENAMING 1 */
+
+#if !U_DISABLE_RENAMING
+
+/* C exports renaming data */
+
+#define T_CString_int64ToString T_CString_int64ToString_3_2
+#define T_CString_integerToString T_CString_integerToString_3_2
+#define T_CString_stricmp T_CString_stricmp_3_2
+#define T_CString_stringToInteger T_CString_stringToInteger_3_2
+#define T_CString_strnicmp T_CString_strnicmp_3_2
+#define T_CString_toLowerCase T_CString_toLowerCase_3_2
+#define T_CString_toUpperCase T_CString_toUpperCase_3_2
+#define T_FileStream_close T_FileStream_close_3_2
+#define T_FileStream_eof T_FileStream_eof_3_2
+#define T_FileStream_error T_FileStream_error_3_2
+#define T_FileStream_file_exists T_FileStream_file_exists_3_2
+#define T_FileStream_getc T_FileStream_getc_3_2
+#define T_FileStream_open T_FileStream_open_3_2
+#define T_FileStream_peek T_FileStream_peek_3_2
+#define T_FileStream_putc T_FileStream_putc_3_2
+#define T_FileStream_read T_FileStream_read_3_2
+#define T_FileStream_readLine T_FileStream_readLine_3_2
+#define T_FileStream_remove T_FileStream_remove_3_2
+#define T_FileStream_rewind T_FileStream_rewind_3_2
+#define T_FileStream_size T_FileStream_size_3_2
+#define T_FileStream_stderr T_FileStream_stderr_3_2
+#define T_FileStream_stdin T_FileStream_stdin_3_2
+#define T_FileStream_stdout T_FileStream_stdout_3_2
+#define T_FileStream_ungetc T_FileStream_ungetc_3_2
+#define T_FileStream_write T_FileStream_write_3_2
+#define T_FileStream_writeLine T_FileStream_writeLine_3_2
+#define UCNV_FROM_U_CALLBACK_ESCAPE UCNV_FROM_U_CALLBACK_ESCAPE_3_2
+#define UCNV_FROM_U_CALLBACK_SKIP UCNV_FROM_U_CALLBACK_SKIP_3_2
+#define UCNV_FROM_U_CALLBACK_STOP UCNV_FROM_U_CALLBACK_STOP_3_2
+#define UCNV_FROM_U_CALLBACK_SUBSTITUTE UCNV_FROM_U_CALLBACK_SUBSTITUTE_3_2
+#define UCNV_TO_U_CALLBACK_ESCAPE UCNV_TO_U_CALLBACK_ESCAPE_3_2
+#define UCNV_TO_U_CALLBACK_SKIP UCNV_TO_U_CALLBACK_SKIP_3_2
+#define UCNV_TO_U_CALLBACK_STOP UCNV_TO_U_CALLBACK_STOP_3_2
+#define UCNV_TO_U_CALLBACK_SUBSTITUTE UCNV_TO_U_CALLBACK_SUBSTITUTE_3_2
+#define UDataMemory_createNewInstance UDataMemory_createNewInstance_3_2
+#define UDataMemory_init UDataMemory_init_3_2
+#define UDataMemory_isLoaded UDataMemory_isLoaded_3_2
+#define UDataMemory_normalizeDataPointer UDataMemory_normalizeDataPointer_3_2
+#define UDataMemory_setData UDataMemory_setData_3_2
+#define UDatamemory_assign UDatamemory_assign_3_2
+#define _ASCIIData _ASCIIData_3_2
+#define _Bocu1Data _Bocu1Data_3_2
+#define _CESU8Data _CESU8Data_3_2
+#define _HZData _HZData_3_2
+#define _IMAPData _IMAPData_3_2
+#define _ISCIIData _ISCIIData_3_2
+#define _ISO2022Data _ISO2022Data_3_2
+#define _LMBCSData1 _LMBCSData1_3_2
+#define _LMBCSData11 _LMBCSData11_3_2
+#define _LMBCSData16 _LMBCSData16_3_2
+#define _LMBCSData17 _LMBCSData17_3_2
+#define _LMBCSData18 _LMBCSData18_3_2
+#define _LMBCSData19 _LMBCSData19_3_2
+#define _LMBCSData2 _LMBCSData2_3_2
+#define _LMBCSData3 _LMBCSData3_3_2
+#define _LMBCSData4 _LMBCSData4_3_2
+#define _LMBCSData5 _LMBCSData5_3_2
+#define _LMBCSData6 _LMBCSData6_3_2
+#define _LMBCSData8 _LMBCSData8_3_2
+#define _Latin1Data _Latin1Data_3_2
+#define _MBCSData _MBCSData_3_2
+#define _SCSUData _SCSUData_3_2
+#define _UTF16BEData _UTF16BEData_3_2
+#define _UTF16Data _UTF16Data_3_2
+#define _UTF16LEData _UTF16LEData_3_2
+#define _UTF32BEData _UTF32BEData_3_2
+#define _UTF32Data _UTF32Data_3_2
+#define _UTF32LEData _UTF32LEData_3_2
+#define _UTF7Data _UTF7Data_3_2
+#define _UTF8Data _UTF8Data_3_2
+#define cmemory_cleanup cmemory_cleanup_3_2
+#define cmemory_inUse cmemory_inUse_3_2
+#define locale_getKeywords locale_getKeywords_3_2
+#define locale_get_default locale_get_default_3_2
+#define locale_set_default locale_set_default_3_2
+#define res_countArrayItems res_countArrayItems_3_2
+#define res_findResource res_findResource_3_2
+#define res_getAlias res_getAlias_3_2
+#define res_getArrayItem res_getArrayItem_3_2
+#define res_getBinary res_getBinary_3_2
+#define res_getIntVector res_getIntVector_3_2
+#define res_getResource res_getResource_3_2
+#define res_getString res_getString_3_2
+#define res_getTableItemByIndex res_getTableItemByIndex_3_2
+#define res_getTableItemByKey res_getTableItemByKey_3_2
+#define res_load res_load_3_2
+#define res_unload res_unload_3_2
+#define transliterator_cleanup transliterator_cleanup_3_2
+#define u_UCharsToChars u_UCharsToChars_3_2
+#define u_austrcpy u_austrcpy_3_2
+#define u_austrncpy u_austrncpy_3_2
+#define u_catclose u_catclose_3_2
+#define u_catgets u_catgets_3_2
+#define u_catopen u_catopen_3_2
+#define u_charAge u_charAge_3_2
+#define u_charDigitValue u_charDigitValue_3_2
+#define u_charDirection u_charDirection_3_2
+#define u_charFromName u_charFromName_3_2
+#define u_charMirror u_charMirror_3_2
+#define u_charName u_charName_3_2
+#define u_charType u_charType_3_2
+#define u_charsToUChars u_charsToUChars_3_2
+#define u_cleanup u_cleanup_3_2
+#define u_countChar32 u_countChar32_3_2
+#define u_digit u_digit_3_2
+#define u_enumCharNames u_enumCharNames_3_2
+#define u_enumCharTypes u_enumCharTypes_3_2
+#define u_errorName u_errorName_3_2
+#define u_fclose u_fclose_3_2
+#define u_feof u_feof_3_2
+#define u_fflush u_fflush_3_2
+#define u_fgetConverter u_fgetConverter_3_2
+#define u_fgetc u_fgetc_3_2
+#define u_fgetcodepage u_fgetcodepage_3_2
+#define u_fgetcx u_fgetcx_3_2
+#define u_fgetfile u_fgetfile_3_2
+#define u_fgetlocale u_fgetlocale_3_2
+#define u_fgets u_fgets_3_2
+#define u_file_read u_file_read_3_2
+#define u_file_write u_file_write_3_2
+#define u_file_write_flush u_file_write_flush_3_2
+#define u_finit u_finit_3_2
+#define u_foldCase u_foldCase_3_2
+#define u_fopen u_fopen_3_2
+#define u_forDigit u_forDigit_3_2
+#define u_formatMessage u_formatMessage_3_2
+#define u_formatMessageWithError u_formatMessageWithError_3_2
+#define u_fprintf u_fprintf_3_2
+#define u_fprintf_u u_fprintf_u_3_2
+#define u_fputc u_fputc_3_2
+#define u_fputs u_fputs_3_2
+#define u_frewind u_frewind_3_2
+#define u_fscanf u_fscanf_3_2
+#define u_fscanf_u u_fscanf_u_3_2
+#define u_fsetcodepage u_fsetcodepage_3_2
+#define u_fsetlocale u_fsetlocale_3_2
+#define u_fsettransliterator u_fsettransliterator_3_2
+#define u_fstropen u_fstropen_3_2
+#define u_fungetc u_fungetc_3_2
+#define u_getCombiningClass u_getCombiningClass_3_2
+#define u_getDataDirectory u_getDataDirectory_3_2
+#define u_getDefaultConverter u_getDefaultConverter_3_2
+#define u_getFC_NFKC_Closure u_getFC_NFKC_Closure_3_2
+#define u_getISOComment u_getISOComment_3_2
+#define u_getIntPropertyMaxValue u_getIntPropertyMaxValue_3_2
+#define u_getIntPropertyMinValue u_getIntPropertyMinValue_3_2
+#define u_getIntPropertyValue u_getIntPropertyValue_3_2
+#define u_getNumericValue u_getNumericValue_3_2
+#define u_getPropertyEnum u_getPropertyEnum_3_2
+#define u_getPropertyName u_getPropertyName_3_2
+#define u_getPropertyValueEnum u_getPropertyValueEnum_3_2
+#define u_getPropertyValueName u_getPropertyValueName_3_2
+#define u_getUnicodeProperties u_getUnicodeProperties_3_2
+#define u_getUnicodeVersion u_getUnicodeVersion_3_2
+#define u_getVersion u_getVersion_3_2
+#define u_growBufferFromStatic u_growBufferFromStatic_3_2
+#define u_hasBinaryProperty u_hasBinaryProperty_3_2
+#define u_init u_init_3_2
+#define u_isIDIgnorable u_isIDIgnorable_3_2
+#define u_isIDPart u_isIDPart_3_2
+#define u_isIDStart u_isIDStart_3_2
+#define u_isISOControl u_isISOControl_3_2
+#define u_isJavaIDPart u_isJavaIDPart_3_2
+#define u_isJavaIDStart u_isJavaIDStart_3_2
+#define u_isJavaSpaceChar u_isJavaSpaceChar_3_2
+#define u_isMirrored u_isMirrored_3_2
+#define u_isUAlphabetic u_isUAlphabetic_3_2
+#define u_isULowercase u_isULowercase_3_2
+#define u_isUUppercase u_isUUppercase_3_2
+#define u_isUWhiteSpace u_isUWhiteSpace_3_2
+#define u_isWhitespace u_isWhitespace_3_2
+#define u_isalnum u_isalnum_3_2
+#define u_isalpha u_isalpha_3_2
+#define u_isbase u_isbase_3_2
+#define u_isblank u_isblank_3_2
+#define u_iscntrl u_iscntrl_3_2
+#define u_isdefined u_isdefined_3_2
+#define u_isdigit u_isdigit_3_2
+#define u_isgraph u_isgraph_3_2
+#define u_islower u_islower_3_2
+#define u_isprint u_isprint_3_2
+#define u_ispunct u_ispunct_3_2
+#define u_isspace u_isspace_3_2
+#define u_istitle u_istitle_3_2
+#define u_isupper u_isupper_3_2
+#define u_isxdigit u_isxdigit_3_2
+#define u_lengthOfIdenticalLevelRun u_lengthOfIdenticalLevelRun_3_2
+#define u_locbund_close u_locbund_close_3_2
+#define u_locbund_getNumberFormat u_locbund_getNumberFormat_3_2
+#define u_locbund_init u_locbund_init_3_2
+#define u_memcasecmp u_memcasecmp_3_2
+#define u_memchr u_memchr_3_2
+#define u_memchr32 u_memchr32_3_2
+#define u_memcmp u_memcmp_3_2
+#define u_memcmpCodePointOrder u_memcmpCodePointOrder_3_2
+#define u_memcpy u_memcpy_3_2
+#define u_memmove u_memmove_3_2
+#define u_memrchr u_memrchr_3_2
+#define u_memrchr32 u_memrchr32_3_2
+#define u_memset u_memset_3_2
+#define u_parseMessage u_parseMessage_3_2
+#define u_parseMessageWithError u_parseMessageWithError_3_2
+#define u_printf_parse u_printf_parse_3_2
+#define u_releaseDefaultConverter u_releaseDefaultConverter_3_2
+#define u_scanf_parse u_scanf_parse_3_2
+#define u_setAtomicIncDecFunctions u_setAtomicIncDecFunctions_3_2
+#define u_setDataDirectory u_setDataDirectory_3_2
+#define u_setMemoryFunctions u_setMemoryFunctions_3_2
+#define u_setMutexFunctions u_setMutexFunctions_3_2
+#define u_shapeArabic u_shapeArabic_3_2
+#define u_snprintf u_snprintf_3_2
+#define u_snprintf_u u_snprintf_u_3_2
+#define u_sprintf u_sprintf_3_2
+#define u_sprintf_u u_sprintf_u_3_2
+#define u_sscanf u_sscanf_3_2
+#define u_sscanf_u u_sscanf_u_3_2
+#define u_strCaseCompare u_strCaseCompare_3_2
+#define u_strCompare u_strCompare_3_2
+#define u_strCompareIter u_strCompareIter_3_2
+#define u_strFindFirst u_strFindFirst_3_2
+#define u_strFindLast u_strFindLast_3_2
+#define u_strFoldCase u_strFoldCase_3_2
+#define u_strFromPunycode u_strFromPunycode_3_2
+#define u_strFromUTF32 u_strFromUTF32_3_2
+#define u_strFromUTF8 u_strFromUTF8_3_2
+#define u_strFromWCS u_strFromWCS_3_2
+#define u_strHasMoreChar32Than u_strHasMoreChar32Than_3_2
+#define u_strToLower u_strToLower_3_2
+#define u_strToPunycode u_strToPunycode_3_2
+#define u_strToTitle u_strToTitle_3_2
+#define u_strToUTF32 u_strToUTF32_3_2
+#define u_strToUTF8 u_strToUTF8_3_2
+#define u_strToUpper u_strToUpper_3_2
+#define u_strToWCS u_strToWCS_3_2
+#define u_strcasecmp u_strcasecmp_3_2
+#define u_strcat u_strcat_3_2
+#define u_strchr u_strchr_3_2
+#define u_strchr32 u_strchr32_3_2
+#define u_strcmp u_strcmp_3_2
+#define u_strcmpCodePointOrder u_strcmpCodePointOrder_3_2
+#define u_strcmpFold u_strcmpFold_3_2
+#define u_strcpy u_strcpy_3_2
+#define u_strcspn u_strcspn_3_2
+#define u_strlen u_strlen_3_2
+#define u_strncasecmp u_strncasecmp_3_2
+#define u_strncat u_strncat_3_2
+#define u_strncmp u_strncmp_3_2
+#define u_strncmpCodePointOrder u_strncmpCodePointOrder_3_2
+#define u_strncpy u_strncpy_3_2
+#define u_strpbrk u_strpbrk_3_2
+#define u_strrchr u_strrchr_3_2
+#define u_strrchr32 u_strrchr32_3_2
+#define u_strrstr u_strrstr_3_2
+#define u_strspn u_strspn_3_2
+#define u_strstr u_strstr_3_2
+#define u_strtok_r u_strtok_r_3_2
+#define u_terminateChars u_terminateChars_3_2
+#define u_terminateUChar32s u_terminateUChar32s_3_2
+#define u_terminateUChars u_terminateUChars_3_2
+#define u_terminateWChars u_terminateWChars_3_2
+#define u_tolower u_tolower_3_2
+#define u_totitle u_totitle_3_2
+#define u_toupper u_toupper_3_2
+#define u_uastrcpy u_uastrcpy_3_2
+#define u_uastrncpy u_uastrncpy_3_2
+#define u_unescape u_unescape_3_2
+#define u_unescapeAt u_unescapeAt_3_2
+#define u_versionFromString u_versionFromString_3_2
+#define u_versionToString u_versionToString_3_2
+#define u_vformatMessage u_vformatMessage_3_2
+#define u_vformatMessageWithError u_vformatMessageWithError_3_2
+#define u_vfprintf u_vfprintf_3_2
+#define u_vfprintf_u u_vfprintf_u_3_2
+#define u_vfscanf u_vfscanf_3_2
+#define u_vfscanf_u u_vfscanf_u_3_2
+#define u_vparseMessage u_vparseMessage_3_2
+#define u_vparseMessageWithError u_vparseMessageWithError_3_2
+#define u_vsnprintf u_vsnprintf_3_2
+#define u_vsnprintf_u u_vsnprintf_u_3_2
+#define u_vsprintf u_vsprintf_3_2
+#define u_vsprintf_u u_vsprintf_u_3_2
+#define u_vsscanf u_vsscanf_3_2
+#define u_vsscanf_u u_vsscanf_u_3_2
+#define u_writeDiff u_writeDiff_3_2
+#define u_writeIdenticalLevelRun u_writeIdenticalLevelRun_3_2
+#define u_writeIdenticalLevelRunTwoChars u_writeIdenticalLevelRunTwoChars_3_2
+#define ubidi_close ubidi_close_3_2
+#define ubidi_countRuns ubidi_countRuns_3_2
+#define ubidi_getDirection ubidi_getDirection_3_2
+#define ubidi_getLength ubidi_getLength_3_2
+#define ubidi_getLevelAt ubidi_getLevelAt_3_2
+#define ubidi_getLevels ubidi_getLevels_3_2
+#define ubidi_getLogicalIndex ubidi_getLogicalIndex_3_2
+#define ubidi_getLogicalMap ubidi_getLogicalMap_3_2
+#define ubidi_getLogicalRun ubidi_getLogicalRun_3_2
+#define ubidi_getMemory ubidi_getMemory_3_2
+#define ubidi_getParaLevel ubidi_getParaLevel_3_2
+#define ubidi_getRuns ubidi_getRuns_3_2
+#define ubidi_getText ubidi_getText_3_2
+#define ubidi_getVisualIndex ubidi_getVisualIndex_3_2
+#define ubidi_getVisualMap ubidi_getVisualMap_3_2
+#define ubidi_getVisualRun ubidi_getVisualRun_3_2
+#define ubidi_invertMap ubidi_invertMap_3_2
+#define ubidi_isInverse ubidi_isInverse_3_2
+#define ubidi_open ubidi_open_3_2
+#define ubidi_openSized ubidi_openSized_3_2
+#define ubidi_reorderLogical ubidi_reorderLogical_3_2
+#define ubidi_reorderVisual ubidi_reorderVisual_3_2
+#define ubidi_setInverse ubidi_setInverse_3_2
+#define ubidi_setLine ubidi_setLine_3_2
+#define ubidi_setPara ubidi_setPara_3_2
+#define ubidi_writeReordered ubidi_writeReordered_3_2
+#define ubidi_writeReverse ubidi_writeReverse_3_2
+#define ublock_getCode ublock_getCode_3_2
+#define ubrk_close ubrk_close_3_2
+#define ubrk_countAvailable ubrk_countAvailable_3_2
+#define ubrk_current ubrk_current_3_2
+#define ubrk_first ubrk_first_3_2
+#define ubrk_following ubrk_following_3_2
+#define ubrk_getAvailable ubrk_getAvailable_3_2
+#define ubrk_getLocaleByType ubrk_getLocaleByType_3_2
+#define ubrk_getRuleStatus ubrk_getRuleStatus_3_2
+#define ubrk_getRuleStatusVec ubrk_getRuleStatusVec_3_2
+#define ubrk_isBoundary ubrk_isBoundary_3_2
+#define ubrk_last ubrk_last_3_2
+#define ubrk_next ubrk_next_3_2
+#define ubrk_open ubrk_open_3_2
+#define ubrk_openRules ubrk_openRules_3_2
+#define ubrk_preceding ubrk_preceding_3_2
+#define ubrk_previous ubrk_previous_3_2
+#define ubrk_safeClone ubrk_safeClone_3_2
+#define ubrk_setText ubrk_setText_3_2
+#define ubrk_swap ubrk_swap_3_2
+#define ucal_add ucal_add_3_2
+#define ucal_clear ucal_clear_3_2
+#define ucal_clearField ucal_clearField_3_2
+#define ucal_close ucal_close_3_2
+#define ucal_countAvailable ucal_countAvailable_3_2
+#define ucal_equivalentTo ucal_equivalentTo_3_2
+#define ucal_get ucal_get_3_2
+#define ucal_getAttribute ucal_getAttribute_3_2
+#define ucal_getAvailable ucal_getAvailable_3_2
+#define ucal_getDSTSavings ucal_getDSTSavings_3_2
+#define ucal_getDefaultTimeZone ucal_getDefaultTimeZone_3_2
+#define ucal_getLimit ucal_getLimit_3_2
+#define ucal_getLocaleByType ucal_getLocaleByType_3_2
+#define ucal_getMillis ucal_getMillis_3_2
+#define ucal_getNow ucal_getNow_3_2
+#define ucal_getTimeZoneDisplayName ucal_getTimeZoneDisplayName_3_2
+#define ucal_inDaylightTime ucal_inDaylightTime_3_2
+#define ucal_isSet ucal_isSet_3_2
+#define ucal_open ucal_open_3_2
+#define ucal_openCountryTimeZones ucal_openCountryTimeZones_3_2
+#define ucal_openTimeZones ucal_openTimeZones_3_2
+#define ucal_roll ucal_roll_3_2
+#define ucal_set ucal_set_3_2
+#define ucal_setAttribute ucal_setAttribute_3_2
+#define ucal_setDate ucal_setDate_3_2
+#define ucal_setDateTime ucal_setDateTime_3_2
+#define ucal_setDefaultTimeZone ucal_setDefaultTimeZone_3_2
+#define ucal_setMillis ucal_setMillis_3_2
+#define ucal_setTimeZone ucal_setTimeZone_3_2
+#define ucase_addPropertyStarts ucase_addPropertyStarts_3_2
+#define ucase_close ucase_close_3_2
+#define ucase_fold ucase_fold_3_2
+#define ucase_getSingleton ucase_getSingleton_3_2
+#define ucase_getType ucase_getType_3_2
+#define ucase_getTypeOrIgnorable ucase_getTypeOrIgnorable_3_2
+#define ucase_isCaseSensitive ucase_isCaseSensitive_3_2
+#define ucase_isSoftDotted ucase_isSoftDotted_3_2
+#define ucase_open ucase_open_3_2
+#define ucase_openBinary ucase_openBinary_3_2
+#define ucase_swap ucase_swap_3_2
+#define ucase_toFullFolding ucase_toFullFolding_3_2
+#define ucase_toFullLower ucase_toFullLower_3_2
+#define ucase_toFullTitle ucase_toFullTitle_3_2
+#define ucase_toFullUpper ucase_toFullUpper_3_2
+#define ucase_tolower ucase_tolower_3_2
+#define ucase_totitle ucase_totitle_3_2
+#define ucase_toupper ucase_toupper_3_2
+#define uchar_addPropertyStarts uchar_addPropertyStarts_3_2
+#define uchar_getHST uchar_getHST_3_2
+#define uchar_swapNames uchar_swapNames_3_2
+#define ucln_common_lib_cleanup ucln_common_lib_cleanup_3_2
+#define ucln_common_registerCleanup ucln_common_registerCleanup_3_2
+#define ucln_i18n_registerCleanup ucln_i18n_registerCleanup_3_2
+#define ucln_registerCleanup ucln_registerCleanup_3_2
+#define ucmp8_close ucmp8_close_3_2
+#define ucmp8_compact ucmp8_compact_3_2
+#define ucmp8_expand ucmp8_expand_3_2
+#define ucmp8_flattenMem ucmp8_flattenMem_3_2
+#define ucmp8_getArray ucmp8_getArray_3_2
+#define ucmp8_getCount ucmp8_getCount_3_2
+#define ucmp8_getIndex ucmp8_getIndex_3_2
+#define ucmp8_getkBlockCount ucmp8_getkBlockCount_3_2
+#define ucmp8_getkUnicodeCount ucmp8_getkUnicodeCount_3_2
+#define ucmp8_init ucmp8_init_3_2
+#define ucmp8_initAdopt ucmp8_initAdopt_3_2
+#define ucmp8_initAlias ucmp8_initAlias_3_2
+#define ucmp8_initBogus ucmp8_initBogus_3_2
+#define ucmp8_initFromData ucmp8_initFromData_3_2
+#define ucmp8_isBogus ucmp8_isBogus_3_2
+#define ucmp8_open ucmp8_open_3_2
+#define ucmp8_openAdopt ucmp8_openAdopt_3_2
+#define ucmp8_openAlias ucmp8_openAlias_3_2
+#define ucmp8_set ucmp8_set_3_2
+#define ucmp8_setRange ucmp8_setRange_3_2
+#define ucnv_MBCSFromUChar32 ucnv_MBCSFromUChar32_3_2
+#define ucnv_MBCSFromUnicodeWithOffsets ucnv_MBCSFromUnicodeWithOffsets_3_2
+#define ucnv_MBCSGetType ucnv_MBCSGetType_3_2
+#define ucnv_MBCSGetUnicodeSetForBytes ucnv_MBCSGetUnicodeSetForBytes_3_2
+#define ucnv_MBCSGetUnicodeSetForUnicode ucnv_MBCSGetUnicodeSetForUnicode_3_2
+#define ucnv_MBCSIsLeadByte ucnv_MBCSIsLeadByte_3_2
+#define ucnv_MBCSSimpleGetNextUChar ucnv_MBCSSimpleGetNextUChar_3_2
+#define ucnv_MBCSToUnicodeWithOffsets ucnv_MBCSToUnicodeWithOffsets_3_2
+#define ucnv_cbFromUWriteBytes ucnv_cbFromUWriteBytes_3_2
+#define ucnv_cbFromUWriteSub ucnv_cbFromUWriteSub_3_2
+#define ucnv_cbFromUWriteUChars ucnv_cbFromUWriteUChars_3_2
+#define ucnv_cbToUWriteSub ucnv_cbToUWriteSub_3_2
+#define ucnv_cbToUWriteUChars ucnv_cbToUWriteUChars_3_2
+#define ucnv_close ucnv_close_3_2
+#define ucnv_compareNames ucnv_compareNames_3_2
+#define ucnv_convert ucnv_convert_3_2
+#define ucnv_convertEx ucnv_convertEx_3_2
+#define ucnv_copyPlatformString ucnv_copyPlatformString_3_2
+#define ucnv_countAliases ucnv_countAliases_3_2
+#define ucnv_countAvailable ucnv_countAvailable_3_2
+#define ucnv_countStandards ucnv_countStandards_3_2
+#define ucnv_createAlgorithmicConverter ucnv_createAlgorithmicConverter_3_2
+#define ucnv_createConverter ucnv_createConverter_3_2
+#define ucnv_createConverterFromPackage ucnv_createConverterFromPackage_3_2
+#define ucnv_createConverterFromSharedData ucnv_createConverterFromSharedData_3_2
+#define ucnv_detectUnicodeSignature ucnv_detectUnicodeSignature_3_2
+#define ucnv_extContinueMatchFromU ucnv_extContinueMatchFromU_3_2
+#define ucnv_extContinueMatchToU ucnv_extContinueMatchToU_3_2
+#define ucnv_extGetUnicodeSet ucnv_extGetUnicodeSet_3_2
+#define ucnv_extInitialMatchFromU ucnv_extInitialMatchFromU_3_2
+#define ucnv_extInitialMatchToU ucnv_extInitialMatchToU_3_2
+#define ucnv_extSimpleMatchFromU ucnv_extSimpleMatchFromU_3_2
+#define ucnv_extSimpleMatchToU ucnv_extSimpleMatchToU_3_2
+#define ucnv_fixFileSeparator ucnv_fixFileSeparator_3_2
+#define ucnv_flushCache ucnv_flushCache_3_2
+#define ucnv_fromAlgorithmic ucnv_fromAlgorithmic_3_2
+#define ucnv_fromUChars ucnv_fromUChars_3_2
+#define ucnv_fromUWriteBytes ucnv_fromUWriteBytes_3_2
+#define ucnv_fromUnicode ucnv_fromUnicode_3_2
+#define ucnv_fromUnicode_UTF8 ucnv_fromUnicode_UTF8_3_2
+#define ucnv_fromUnicode_UTF8_OFFSETS_LOGIC ucnv_fromUnicode_UTF8_OFFSETS_LOGIC_3_2
+#define ucnv_getAlias ucnv_getAlias_3_2
+#define ucnv_getAliases ucnv_getAliases_3_2
+#define ucnv_getAvailableName ucnv_getAvailableName_3_2
+#define ucnv_getCCSID ucnv_getCCSID_3_2
+#define ucnv_getCanonicalName ucnv_getCanonicalName_3_2
+#define ucnv_getCompleteUnicodeSet ucnv_getCompleteUnicodeSet_3_2
+#define ucnv_getDefaultName ucnv_getDefaultName_3_2
+#define ucnv_getDisplayName ucnv_getDisplayName_3_2
+#define ucnv_getFromUCallBack ucnv_getFromUCallBack_3_2
+#define ucnv_getInvalidChars ucnv_getInvalidChars_3_2
+#define ucnv_getInvalidUChars ucnv_getInvalidUChars_3_2
+#define ucnv_getMaxCharSize ucnv_getMaxCharSize_3_2
+#define ucnv_getMinCharSize ucnv_getMinCharSize_3_2
+#define ucnv_getName ucnv_getName_3_2
+#define ucnv_getNextUChar ucnv_getNextUChar_3_2
+#define ucnv_getNonSurrogateUnicodeSet ucnv_getNonSurrogateUnicodeSet_3_2
+#define ucnv_getPlatform ucnv_getPlatform_3_2
+#define ucnv_getStandard ucnv_getStandard_3_2
+#define ucnv_getStandardName ucnv_getStandardName_3_2
+#define ucnv_getStarters ucnv_getStarters_3_2
+#define ucnv_getSubstChars ucnv_getSubstChars_3_2
+#define ucnv_getToUCallBack ucnv_getToUCallBack_3_2
+#define ucnv_getType ucnv_getType_3_2
+#define ucnv_getUnicodeSet ucnv_getUnicodeSet_3_2
+#define ucnv_incrementRefCount ucnv_incrementRefCount_3_2
+#define ucnv_io_countAliases ucnv_io_countAliases_3_2
+#define ucnv_io_countAvailableAliases ucnv_io_countAvailableAliases_3_2
+#define ucnv_io_countAvailableConverters ucnv_io_countAvailableConverters_3_2
+#define ucnv_io_countStandards ucnv_io_countStandards_3_2
+#define ucnv_io_flushAvailableConverterCache ucnv_io_flushAvailableConverterCache_3_2
+#define ucnv_io_getAlias ucnv_io_getAlias_3_2
+#define ucnv_io_getAliases ucnv_io_getAliases_3_2
+#define ucnv_io_getAvailableConverter ucnv_io_getAvailableConverter_3_2
+#define ucnv_io_getConverterName ucnv_io_getConverterName_3_2
+#define ucnv_io_getDefaultConverterName ucnv_io_getDefaultConverterName_3_2
+#define ucnv_io_setDefaultConverterName ucnv_io_setDefaultConverterName_3_2
+#define ucnv_io_stripASCIIForCompare ucnv_io_stripASCIIForCompare_3_2
+#define ucnv_io_stripEBCDICForCompare ucnv_io_stripEBCDICForCompare_3_2
+#define ucnv_isAmbiguous ucnv_isAmbiguous_3_2
+#define ucnv_load ucnv_load_3_2
+#define ucnv_loadSharedData ucnv_loadSharedData_3_2
+#define ucnv_open ucnv_open_3_2
+#define ucnv_openAllNames ucnv_openAllNames_3_2
+#define ucnv_openCCSID ucnv_openCCSID_3_2
+#define ucnv_openPackage ucnv_openPackage_3_2
+#define ucnv_openStandardNames ucnv_openStandardNames_3_2
+#define ucnv_openU ucnv_openU_3_2
+#define ucnv_reset ucnv_reset_3_2
+#define ucnv_resetFromUnicode ucnv_resetFromUnicode_3_2
+#define ucnv_resetToUnicode ucnv_resetToUnicode_3_2
+#define ucnv_safeClone ucnv_safeClone_3_2
+#define ucnv_setDefaultName ucnv_setDefaultName_3_2
+#define ucnv_setFallback ucnv_setFallback_3_2
+#define ucnv_setFromUCallBack ucnv_setFromUCallBack_3_2
+#define ucnv_setSubstChars ucnv_setSubstChars_3_2
+#define ucnv_setToUCallBack ucnv_setToUCallBack_3_2
+#define ucnv_swap ucnv_swap_3_2
+#define ucnv_swapAliases ucnv_swapAliases_3_2
+#define ucnv_toAlgorithmic ucnv_toAlgorithmic_3_2
+#define ucnv_toUChars ucnv_toUChars_3_2
+#define ucnv_toUWriteCodePoint ucnv_toUWriteCodePoint_3_2
+#define ucnv_toUWriteUChars ucnv_toUWriteUChars_3_2
+#define ucnv_toUnicode ucnv_toUnicode_3_2
+#define ucnv_unload ucnv_unload_3_2
+#define ucnv_unloadSharedDataIfReady ucnv_unloadSharedDataIfReady_3_2
+#define ucnv_usesFallback ucnv_usesFallback_3_2
+#define ucol_allocWeights ucol_allocWeights_3_2
+#define ucol_assembleTailoringTable ucol_assembleTailoringTable_3_2
+#define ucol_calcSortKey ucol_calcSortKey_3_2
+#define ucol_calcSortKeySimpleTertiary ucol_calcSortKeySimpleTertiary_3_2
+#define ucol_cloneBinary ucol_cloneBinary_3_2
+#define ucol_cloneRuleData ucol_cloneRuleData_3_2
+#define ucol_close ucol_close_3_2
+#define ucol_closeElements ucol_closeElements_3_2
+#define ucol_collatorToIdentifier ucol_collatorToIdentifier_3_2
+#define ucol_countAvailable ucol_countAvailable_3_2
+#define ucol_createElements ucol_createElements_3_2
+#define ucol_doCE ucol_doCE_3_2
+#define ucol_equal ucol_equal_3_2
+#define ucol_equals ucol_equals_3_2
+#define ucol_getAttribute ucol_getAttribute_3_2
+#define ucol_getAttributeOrDefault ucol_getAttributeOrDefault_3_2
+#define ucol_getAvailable ucol_getAvailable_3_2
+#define ucol_getBound ucol_getBound_3_2
+#define ucol_getCEGenerator ucol_getCEGenerator_3_2
+#define ucol_getCEStrengthDifference ucol_getCEStrengthDifference_3_2
+#define ucol_getContractions ucol_getContractions_3_2
+#define ucol_getDisplayName ucol_getDisplayName_3_2
+#define ucol_getFirstCE ucol_getFirstCE_3_2
+#define ucol_getFunctionalEquivalent ucol_getFunctionalEquivalent_3_2
+#define ucol_getKeywordValues ucol_getKeywordValues_3_2
+#define ucol_getKeywords ucol_getKeywords_3_2
+#define ucol_getLocale ucol_getLocale_3_2
+#define ucol_getLocaleByType ucol_getLocaleByType_3_2
+#define ucol_getMaxExpansion ucol_getMaxExpansion_3_2
+#define ucol_getNextCE ucol_getNextCE_3_2
+#define ucol_getNextGenerated ucol_getNextGenerated_3_2
+#define ucol_getOffset ucol_getOffset_3_2
+#define ucol_getPrevCE ucol_getPrevCE_3_2
+#define ucol_getRules ucol_getRules_3_2
+#define ucol_getRulesEx ucol_getRulesEx_3_2
+#define ucol_getShortDefinitionString ucol_getShortDefinitionString_3_2
+#define ucol_getSimpleCEGenerator ucol_getSimpleCEGenerator_3_2
+#define ucol_getSortKey ucol_getSortKey_3_2
+#define ucol_getSortKeySize ucol_getSortKeySize_3_2
+#define ucol_getSortKeyWithAllocation ucol_getSortKeyWithAllocation_3_2
+#define ucol_getStrength ucol_getStrength_3_2
+#define ucol_getTailoredSet ucol_getTailoredSet_3_2
+#define ucol_getUCAVersion ucol_getUCAVersion_3_2
+#define ucol_getUnsafeSet ucol_getUnsafeSet_3_2
+#define ucol_getVariableTop ucol_getVariableTop_3_2
+#define ucol_getVersion ucol_getVersion_3_2
+#define ucol_greater ucol_greater_3_2
+#define ucol_greaterOrEqual ucol_greaterOrEqual_3_2
+#define ucol_identifierToShortString ucol_identifierToShortString_3_2
+#define ucol_initBuffers ucol_initBuffers_3_2
+#define ucol_initCollator ucol_initCollator_3_2
+#define ucol_initInverseUCA ucol_initInverseUCA_3_2
+#define ucol_initUCA ucol_initUCA_3_2
+#define ucol_inv_getGapPositions ucol_inv_getGapPositions_3_2
+#define ucol_inv_getNextCE ucol_inv_getNextCE_3_2
+#define ucol_inv_getPrevCE ucol_inv_getPrevCE_3_2
+#define ucol_isTailored ucol_isTailored_3_2
+#define ucol_keyHashCode ucol_keyHashCode_3_2
+#define ucol_mergeSortkeys ucol_mergeSortkeys_3_2
+#define ucol_next ucol_next_3_2
+#define ucol_nextSortKeyPart ucol_nextSortKeyPart_3_2
+#define ucol_nextWeight ucol_nextWeight_3_2
+#define ucol_normalizeShortDefinitionString ucol_normalizeShortDefinitionString_3_2
+#define ucol_open ucol_open_3_2
+#define ucol_openAvailableLocales ucol_openAvailableLocales_3_2
+#define ucol_openBinary ucol_openBinary_3_2
+#define ucol_openElements ucol_openElements_3_2
+#define ucol_openFromIdentifier ucol_openFromIdentifier_3_2
+#define ucol_openFromShortString ucol_openFromShortString_3_2
+#define ucol_openRules ucol_openRules_3_2
+#define ucol_open_internal ucol_open_internal_3_2
+#define ucol_previous ucol_previous_3_2
+#define ucol_primaryOrder ucol_primaryOrder_3_2
+#define ucol_prv_getSpecialCE ucol_prv_getSpecialCE_3_2
+#define ucol_prv_getSpecialPrevCE ucol_prv_getSpecialPrevCE_3_2
+#define ucol_reset ucol_reset_3_2
+#define ucol_restoreVariableTop ucol_restoreVariableTop_3_2
+#define ucol_safeClone ucol_safeClone_3_2
+#define ucol_secondaryOrder ucol_secondaryOrder_3_2
+#define ucol_setAttribute ucol_setAttribute_3_2
+#define ucol_setOffset ucol_setOffset_3_2
+#define ucol_setOptionsFromHeader ucol_setOptionsFromHeader_3_2
+#define ucol_setReqValidLocales ucol_setReqValidLocales_3_2
+#define ucol_setStrength ucol_setStrength_3_2
+#define ucol_setText ucol_setText_3_2
+#define ucol_setVariableTop ucol_setVariableTop_3_2
+#define ucol_shortStringToIdentifier ucol_shortStringToIdentifier_3_2
+#define ucol_sortKeyToString ucol_sortKeyToString_3_2
+#define ucol_strcoll ucol_strcoll_3_2
+#define ucol_strcollIter ucol_strcollIter_3_2
+#define ucol_swap ucol_swap_3_2
+#define ucol_swapBinary ucol_swapBinary_3_2
+#define ucol_swapInverseUCA ucol_swapInverseUCA_3_2
+#define ucol_tertiaryOrder ucol_tertiaryOrder_3_2
+#define ucol_tok_assembleTokenList ucol_tok_assembleTokenList_3_2
+#define ucol_tok_closeTokenList ucol_tok_closeTokenList_3_2
+#define ucol_tok_getNextArgument ucol_tok_getNextArgument_3_2
+#define ucol_tok_initTokenList ucol_tok_initTokenList_3_2
+#define ucol_tok_parseNextToken ucol_tok_parseNextToken_3_2
+#define ucol_updateInternalState ucol_updateInternalState_3_2
+#define ucurr_forLocale ucurr_forLocale_3_2
+#define ucurr_getDefaultFractionDigits ucurr_getDefaultFractionDigits_3_2
+#define ucurr_getName ucurr_getName_3_2
+#define ucurr_getRoundingIncrement ucurr_getRoundingIncrement_3_2
+#define ucurr_register ucurr_register_3_2
+#define ucurr_unregister ucurr_unregister_3_2
+#define udat_applyPattern udat_applyPattern_3_2
+#define udat_clone udat_clone_3_2
+#define udat_close udat_close_3_2
+#define udat_countAvailable udat_countAvailable_3_2
+#define udat_countSymbols udat_countSymbols_3_2
+#define udat_format udat_format_3_2
+#define udat_get2DigitYearStart udat_get2DigitYearStart_3_2
+#define udat_getAvailable udat_getAvailable_3_2
+#define udat_getCalendar udat_getCalendar_3_2
+#define udat_getLocaleByType udat_getLocaleByType_3_2
+#define udat_getNumberFormat udat_getNumberFormat_3_2
+#define udat_getSymbols udat_getSymbols_3_2
+#define udat_isLenient udat_isLenient_3_2
+#define udat_open udat_open_3_2
+#define udat_parse udat_parse_3_2
+#define udat_parseCalendar udat_parseCalendar_3_2
+#define udat_set2DigitYearStart udat_set2DigitYearStart_3_2
+#define udat_setCalendar udat_setCalendar_3_2
+#define udat_setLenient udat_setLenient_3_2
+#define udat_setNumberFormat udat_setNumberFormat_3_2
+#define udat_setSymbols udat_setSymbols_3_2
+#define udat_toPattern udat_toPattern_3_2
+#define udata_checkCommonData udata_checkCommonData_3_2
+#define udata_close udata_close_3_2
+#define udata_closeSwapper udata_closeSwapper_3_2
+#define udata_getHeaderSize udata_getHeaderSize_3_2
+#define udata_getInfo udata_getInfo_3_2
+#define udata_getInfoSize udata_getInfoSize_3_2
+#define udata_getLength udata_getLength_3_2
+#define udata_getMemory udata_getMemory_3_2
+#define udata_getRawMemory udata_getRawMemory_3_2
+#define udata_open udata_open_3_2
+#define udata_openChoice udata_openChoice_3_2
+#define udata_openSwapper udata_openSwapper_3_2
+#define udata_openSwapperForInputData udata_openSwapperForInputData_3_2
+#define udata_printError udata_printError_3_2
+#define udata_readInt16 udata_readInt16_3_2
+#define udata_readInt32 udata_readInt32_3_2
+#define udata_setAppData udata_setAppData_3_2
+#define udata_setCommonData udata_setCommonData_3_2
+#define udata_swapDataHeader udata_swapDataHeader_3_2
+#define udata_swapInvStringBlock udata_swapInvStringBlock_3_2
+#define uenum_close uenum_close_3_2
+#define uenum_count uenum_count_3_2
+#define uenum_next uenum_next_3_2
+#define uenum_nextDefault uenum_nextDefault_3_2
+#define uenum_openCharStringsEnumeration uenum_openCharStringsEnumeration_3_2
+#define uenum_openStringEnumeration uenum_openStringEnumeration_3_2
+#define uenum_reset uenum_reset_3_2
+#define uenum_unext uenum_unext_3_2
+#define uenum_unextDefault uenum_unextDefault_3_2
+#define ufile_close_translit ufile_close_translit_3_2
+#define ufile_fill_uchar_buffer ufile_fill_uchar_buffer_3_2
+#define ufile_flush_translit ufile_flush_translit_3_2
+#define ufile_getch ufile_getch_3_2
+#define ufile_getch32 ufile_getch32_3_2
+#define ufmt_64tou ufmt_64tou_3_2
+#define ufmt_defaultCPToUnicode ufmt_defaultCPToUnicode_3_2
+#define ufmt_digitvalue ufmt_digitvalue_3_2
+#define ufmt_isdigit ufmt_isdigit_3_2
+#define ufmt_ptou ufmt_ptou_3_2
+#define ufmt_uto64 ufmt_uto64_3_2
+#define ufmt_utop ufmt_utop_3_2
+#define uhash_close uhash_close_3_2
+#define uhash_compareCaselessUnicodeString uhash_compareCaselessUnicodeString_3_2
+#define uhash_compareChars uhash_compareChars_3_2
+#define uhash_compareIChars uhash_compareIChars_3_2
+#define uhash_compareLong uhash_compareLong_3_2
+#define uhash_compareUChars uhash_compareUChars_3_2
+#define uhash_compareUnicodeString uhash_compareUnicodeString_3_2
+#define uhash_count uhash_count_3_2
+#define uhash_deleteHashtable uhash_deleteHashtable_3_2
+#define uhash_deleteUVector uhash_deleteUVector_3_2
+#define uhash_deleteUnicodeString uhash_deleteUnicodeString_3_2
+#define uhash_find uhash_find_3_2
+#define uhash_freeBlock uhash_freeBlock_3_2
+#define uhash_get uhash_get_3_2
+#define uhash_geti uhash_geti_3_2
+#define uhash_hashCaselessUnicodeString uhash_hashCaselessUnicodeString_3_2
+#define uhash_hashChars uhash_hashChars_3_2
+#define uhash_hashIChars uhash_hashIChars_3_2
+#define uhash_hashLong uhash_hashLong_3_2
+#define uhash_hashUChars uhash_hashUChars_3_2
+#define uhash_hashUCharsN uhash_hashUCharsN_3_2
+#define uhash_hashUnicodeString uhash_hashUnicodeString_3_2
+#define uhash_iget uhash_iget_3_2
+#define uhash_igeti uhash_igeti_3_2
+#define uhash_iput uhash_iput_3_2
+#define uhash_iputi uhash_iputi_3_2
+#define uhash_iremove uhash_iremove_3_2
+#define uhash_iremovei uhash_iremovei_3_2
+#define uhash_nextElement uhash_nextElement_3_2
+#define uhash_open uhash_open_3_2
+#define uhash_openSize uhash_openSize_3_2
+#define uhash_put uhash_put_3_2
+#define uhash_puti uhash_puti_3_2
+#define uhash_remove uhash_remove_3_2
+#define uhash_removeAll uhash_removeAll_3_2
+#define uhash_removeElement uhash_removeElement_3_2
+#define uhash_removei uhash_removei_3_2
+#define uhash_setKeyComparator uhash_setKeyComparator_3_2
+#define uhash_setKeyDeleter uhash_setKeyDeleter_3_2
+#define uhash_setKeyHasher uhash_setKeyHasher_3_2
+#define uhash_setResizePolicy uhash_setResizePolicy_3_2
+#define uhash_setValueDeleter uhash_setValueDeleter_3_2
+#define uhash_toki uhash_toki_3_2
+#define uhash_tokp uhash_tokp_3_2
+#define uhst_addPropertyStarts uhst_addPropertyStarts_3_2
+#define uidna_IDNToASCII uidna_IDNToASCII_3_2
+#define uidna_IDNToUnicode uidna_IDNToUnicode_3_2
+#define uidna_compare uidna_compare_3_2
+#define uidna_toASCII uidna_toASCII_3_2
+#define uidna_toUnicode uidna_toUnicode_3_2
+#define uiter_current32 uiter_current32_3_2
+#define uiter_getState uiter_getState_3_2
+#define uiter_next32 uiter_next32_3_2
+#define uiter_previous32 uiter_previous32_3_2
+#define uiter_setCharacterIterator uiter_setCharacterIterator_3_2
+#define uiter_setReplaceable uiter_setReplaceable_3_2
+#define uiter_setState uiter_setState_3_2
+#define uiter_setString uiter_setString_3_2
+#define uiter_setUTF16BE uiter_setUTF16BE_3_2
+#define uiter_setUTF8 uiter_setUTF8_3_2
+#define uloc_acceptLanguage uloc_acceptLanguage_3_2
+#define uloc_acceptLanguageFromHTTP uloc_acceptLanguageFromHTTP_3_2
+#define uloc_canonicalize uloc_canonicalize_3_2
+#define uloc_countAvailable uloc_countAvailable_3_2
+#define uloc_getAvailable uloc_getAvailable_3_2
+#define uloc_getBaseName uloc_getBaseName_3_2
+#define uloc_getCountry uloc_getCountry_3_2
+#define uloc_getDefault uloc_getDefault_3_2
+#define uloc_getDisplayCountry uloc_getDisplayCountry_3_2
+#define uloc_getDisplayKeyword uloc_getDisplayKeyword_3_2
+#define uloc_getDisplayKeywordValue uloc_getDisplayKeywordValue_3_2
+#define uloc_getDisplayLanguage uloc_getDisplayLanguage_3_2
+#define uloc_getDisplayName uloc_getDisplayName_3_2
+#define uloc_getDisplayScript uloc_getDisplayScript_3_2
+#define uloc_getDisplayVariant uloc_getDisplayVariant_3_2
+#define uloc_getISO3Country uloc_getISO3Country_3_2
+#define uloc_getISO3Language uloc_getISO3Language_3_2
+#define uloc_getISOCountries uloc_getISOCountries_3_2
+#define uloc_getISOLanguages uloc_getISOLanguages_3_2
+#define uloc_getKeywordValue uloc_getKeywordValue_3_2
+#define uloc_getLCID uloc_getLCID_3_2
+#define uloc_getLanguage uloc_getLanguage_3_2
+#define uloc_getName uloc_getName_3_2
+#define uloc_getParent uloc_getParent_3_2
+#define uloc_getScript uloc_getScript_3_2
+#define uloc_getVariant uloc_getVariant_3_2
+#define uloc_openKeywordList uloc_openKeywordList_3_2
+#define uloc_openKeywords uloc_openKeywords_3_2
+#define uloc_setDefault uloc_setDefault_3_2
+#define uloc_setKeywordValue uloc_setKeywordValue_3_2
+#define ulocdata_getExemplarSet ulocdata_getExemplarSet_3_2
+#define ulocdata_getMeasurementSystem ulocdata_getMeasurementSystem_3_2
+#define ulocdata_getPaperSize ulocdata_getPaperSize_3_2
+#define umsg_applyPattern umsg_applyPattern_3_2
+#define umsg_clone umsg_clone_3_2
+#define umsg_close umsg_close_3_2
+#define umsg_format umsg_format_3_2
+#define umsg_getLocale umsg_getLocale_3_2
+#define umsg_getLocaleByType umsg_getLocaleByType_3_2
+#define umsg_open umsg_open_3_2
+#define umsg_parse umsg_parse_3_2
+#define umsg_setLocale umsg_setLocale_3_2
+#define umsg_toPattern umsg_toPattern_3_2
+#define umsg_vformat umsg_vformat_3_2
+#define umsg_vparse umsg_vparse_3_2
+#define umtx_atomic_dec umtx_atomic_dec_3_2
+#define umtx_atomic_inc umtx_atomic_inc_3_2
+#define umtx_cleanup umtx_cleanup_3_2
+#define umtx_destroy umtx_destroy_3_2
+#define umtx_init umtx_init_3_2
+#define umtx_lock umtx_lock_3_2
+#define umtx_unlock umtx_unlock_3_2
+#define unorm_addPropertyStarts unorm_addPropertyStarts_3_2
+#define unorm_closeIter unorm_closeIter_3_2
+#define unorm_compare unorm_compare_3_2
+#define unorm_compose unorm_compose_3_2
+#define unorm_concatenate unorm_concatenate_3_2
+#define unorm_decompose unorm_decompose_3_2
+#define unorm_getCanonStartSet unorm_getCanonStartSet_3_2
+#define unorm_getCanonicalDecomposition unorm_getCanonicalDecomposition_3_2
+#define unorm_getDecomposition unorm_getDecomposition_3_2
+#define unorm_getFCD16FromCodePoint unorm_getFCD16FromCodePoint_3_2
+#define unorm_getFCDTrie unorm_getFCDTrie_3_2
+#define unorm_getNX unorm_getNX_3_2
+#define unorm_getQuickCheck unorm_getQuickCheck_3_2
+#define unorm_getUnicodeVersion unorm_getUnicodeVersion_3_2
+#define unorm_haveData unorm_haveData_3_2
+#define unorm_internalIsFullCompositionExclusion unorm_internalIsFullCompositionExclusion_3_2
+#define unorm_internalNormalize unorm_internalNormalize_3_2
+#define unorm_internalNormalizeWithNX unorm_internalNormalizeWithNX_3_2
+#define unorm_internalQuickCheck unorm_internalQuickCheck_3_2
+#define unorm_isCanonSafeStart unorm_isCanonSafeStart_3_2
+#define unorm_isNFSkippable unorm_isNFSkippable_3_2
+#define unorm_isNormalized unorm_isNormalized_3_2
+#define unorm_isNormalizedWithOptions unorm_isNormalizedWithOptions_3_2
+#define unorm_next unorm_next_3_2
+#define unorm_normalize unorm_normalize_3_2
+#define unorm_openIter unorm_openIter_3_2
+#define unorm_previous unorm_previous_3_2
+#define unorm_quickCheck unorm_quickCheck_3_2
+#define unorm_quickCheckWithOptions unorm_quickCheckWithOptions_3_2
+#define unorm_setIter unorm_setIter_3_2
+#define unorm_swap unorm_swap_3_2
+#define unum_applyPattern unum_applyPattern_3_2
+#define unum_clone unum_clone_3_2
+#define unum_close unum_close_3_2
+#define unum_countAvailable unum_countAvailable_3_2
+#define unum_format unum_format_3_2
+#define unum_formatDouble unum_formatDouble_3_2
+#define unum_formatDoubleCurrency unum_formatDoubleCurrency_3_2
+#define unum_formatInt64 unum_formatInt64_3_2
+#define unum_getAttribute unum_getAttribute_3_2
+#define unum_getAvailable unum_getAvailable_3_2
+#define unum_getDoubleAttribute unum_getDoubleAttribute_3_2
+#define unum_getLocaleByType unum_getLocaleByType_3_2
+#define unum_getSymbol unum_getSymbol_3_2
+#define unum_getTextAttribute unum_getTextAttribute_3_2
+#define unum_open unum_open_3_2
+#define unum_parse unum_parse_3_2
+#define unum_parseDouble unum_parseDouble_3_2
+#define unum_parseDoubleCurrency unum_parseDoubleCurrency_3_2
+#define unum_parseInt64 unum_parseInt64_3_2
+#define unum_setAttribute unum_setAttribute_3_2
+#define unum_setDoubleAttribute unum_setDoubleAttribute_3_2
+#define unum_setSymbol unum_setSymbol_3_2
+#define unum_setTextAttribute unum_setTextAttribute_3_2
+#define unum_toPattern unum_toPattern_3_2
+#define upname_swap upname_swap_3_2
+#define uprops_getSource uprops_getSource_3_2
+#define uprops_swap uprops_swap_3_2
+#define uprv_asciiFromEbcdic uprv_asciiFromEbcdic_3_2
+#define uprv_asciitolower uprv_asciitolower_3_2
+#define uprv_ceil uprv_ceil_3_2
+#define uprv_cnttab_addContraction uprv_cnttab_addContraction_3_2
+#define uprv_cnttab_changeContraction uprv_cnttab_changeContraction_3_2
+#define uprv_cnttab_changeLastCE uprv_cnttab_changeLastCE_3_2
+#define uprv_cnttab_clone uprv_cnttab_clone_3_2
+#define uprv_cnttab_close uprv_cnttab_close_3_2
+#define uprv_cnttab_constructTable uprv_cnttab_constructTable_3_2
+#define uprv_cnttab_findCE uprv_cnttab_findCE_3_2
+#define uprv_cnttab_findCP uprv_cnttab_findCP_3_2
+#define uprv_cnttab_getCE uprv_cnttab_getCE_3_2
+#define uprv_cnttab_insertContraction uprv_cnttab_insertContraction_3_2
+#define uprv_cnttab_isTailored uprv_cnttab_isTailored_3_2
+#define uprv_cnttab_open uprv_cnttab_open_3_2
+#define uprv_cnttab_setContraction uprv_cnttab_setContraction_3_2
+#define uprv_compareASCIIPropertyNames uprv_compareASCIIPropertyNames_3_2
+#define uprv_compareEBCDICPropertyNames uprv_compareEBCDICPropertyNames_3_2
+#define uprv_compareInvAscii uprv_compareInvAscii_3_2
+#define uprv_compareInvEbcdic uprv_compareInvEbcdic_3_2
+#define uprv_convertToLCID uprv_convertToLCID_3_2
+#define uprv_convertToPosix uprv_convertToPosix_3_2
+#define uprv_copyAscii uprv_copyAscii_3_2
+#define uprv_copyEbcdic uprv_copyEbcdic_3_2
+#define uprv_dtostr uprv_dtostr_3_2
+#define uprv_ebcdicFromAscii uprv_ebcdicFromAscii_3_2
+#define uprv_ebcdictolower uprv_ebcdictolower_3_2
+#define uprv_fabs uprv_fabs_3_2
+#define uprv_floor uprv_floor_3_2
+#define uprv_fmax uprv_fmax_3_2
+#define uprv_fmin uprv_fmin_3_2
+#define uprv_fmod uprv_fmod_3_2
+#define uprv_free uprv_free_3_2
+#define uprv_getCharNameCharacters uprv_getCharNameCharacters_3_2
+#define uprv_getDefaultCodepage uprv_getDefaultCodepage_3_2
+#define uprv_getDefaultLocaleID uprv_getDefaultLocaleID_3_2
+#define uprv_getInfinity uprv_getInfinity_3_2
+#define uprv_getMaxCharNameLength uprv_getMaxCharNameLength_3_2
+#define uprv_getMaxValues uprv_getMaxValues_3_2
+#define uprv_getNaN uprv_getNaN_3_2
+#define uprv_getStaticCurrencyName uprv_getStaticCurrencyName_3_2
+#define uprv_getUTCtime uprv_getUTCtime_3_2
+#define uprv_haveProperties uprv_haveProperties_3_2
+#define uprv_init_collIterate uprv_init_collIterate_3_2
+#define uprv_int32Comparator uprv_int32Comparator_3_2
+#define uprv_isInfinite uprv_isInfinite_3_2
+#define uprv_isInvariantString uprv_isInvariantString_3_2
+#define uprv_isInvariantUString uprv_isInvariantUString_3_2
+#define uprv_isNaN uprv_isNaN_3_2
+#define uprv_isNegativeInfinity uprv_isNegativeInfinity_3_2
+#define uprv_isPositiveInfinity uprv_isPositiveInfinity_3_2
+#define uprv_isRuleWhiteSpace uprv_isRuleWhiteSpace_3_2
+#define uprv_itou uprv_itou_3_2
+#define uprv_loadPropsData uprv_loadPropsData_3_2
+#define uprv_log uprv_log_3_2
+#define uprv_log10 uprv_log10_3_2
+#define uprv_malloc uprv_malloc_3_2
+#define uprv_mapFile uprv_mapFile_3_2
+#define uprv_max uprv_max_3_2
+#define uprv_maxMantissa uprv_maxMantissa_3_2
+#define uprv_min uprv_min_3_2
+#define uprv_modf uprv_modf_3_2
+#define uprv_openRuleWhiteSpaceSet uprv_openRuleWhiteSpaceSet_3_2
+#define uprv_pathIsAbsolute uprv_pathIsAbsolute_3_2
+#define uprv_pow uprv_pow_3_2
+#define uprv_pow10 uprv_pow10_3_2
+#define uprv_realloc uprv_realloc_3_2
+#define uprv_round uprv_round_3_2
+#define uprv_sortArray uprv_sortArray_3_2
+#define uprv_strCompare uprv_strCompare_3_2
+#define uprv_strdup uprv_strdup_3_2
+#define uprv_strndup uprv_strndup_3_2
+#define uprv_syntaxError uprv_syntaxError_3_2
+#define uprv_timezone uprv_timezone_3_2
+#define uprv_toupper uprv_toupper_3_2
+#define uprv_trunc uprv_trunc_3_2
+#define uprv_tzname uprv_tzname_3_2
+#define uprv_tzset uprv_tzset_3_2
+#define uprv_uca_addAnElement uprv_uca_addAnElement_3_2
+#define uprv_uca_assembleTable uprv_uca_assembleTable_3_2
+#define uprv_uca_canonicalClosure uprv_uca_canonicalClosure_3_2
+#define uprv_uca_cloneTempTable uprv_uca_cloneTempTable_3_2
+#define uprv_uca_closeTempTable uprv_uca_closeTempTable_3_2
+#define uprv_uca_getCodePointFromRaw uprv_uca_getCodePointFromRaw_3_2
+#define uprv_uca_getImplicitFromRaw uprv_uca_getImplicitFromRaw_3_2
+#define uprv_uca_getImplicitPrimary uprv_uca_getImplicitPrimary_3_2
+#define uprv_uca_getRawFromCodePoint uprv_uca_getRawFromCodePoint_3_2
+#define uprv_uca_getRawFromImplicit uprv_uca_getRawFromImplicit_3_2
+#define uprv_uca_initImplicitConstants uprv_uca_initImplicitConstants_3_2
+#define uprv_uca_initTempTable uprv_uca_initTempTable_3_2
+#define uprv_uint16Comparator uprv_uint16Comparator_3_2
+#define uprv_uint32Comparator uprv_uint32Comparator_3_2
+#define uprv_unmapFile uprv_unmapFile_3_2
+#define uregex_appendReplacement uregex_appendReplacement_3_2
+#define uregex_appendTail uregex_appendTail_3_2
+#define uregex_clone uregex_clone_3_2
+#define uregex_close uregex_close_3_2
+#define uregex_end uregex_end_3_2
+#define uregex_find uregex_find_3_2
+#define uregex_findNext uregex_findNext_3_2
+#define uregex_flags uregex_flags_3_2
+#define uregex_getText uregex_getText_3_2
+#define uregex_group uregex_group_3_2
+#define uregex_groupCount uregex_groupCount_3_2
+#define uregex_lookingAt uregex_lookingAt_3_2
+#define uregex_matches uregex_matches_3_2
+#define uregex_open uregex_open_3_2
+#define uregex_openC uregex_openC_3_2
+#define uregex_pattern uregex_pattern_3_2
+#define uregex_replaceAll uregex_replaceAll_3_2
+#define uregex_replaceFirst uregex_replaceFirst_3_2
+#define uregex_reset uregex_reset_3_2
+#define uregex_setText uregex_setText_3_2
+#define uregex_split uregex_split_3_2
+#define uregex_start uregex_start_3_2
+#define ures_appendResPath ures_appendResPath_3_2
+#define ures_close ures_close_3_2
+#define ures_copyResb ures_copyResb_3_2
+#define ures_countArrayItems ures_countArrayItems_3_2
+#define ures_findResource ures_findResource_3_2
+#define ures_findSubResource ures_findSubResource_3_2
+#define ures_freeResPath ures_freeResPath_3_2
+#define ures_getBinary ures_getBinary_3_2
+#define ures_getByIndex ures_getByIndex_3_2
+#define ures_getByKey ures_getByKey_3_2
+#define ures_getByKeyWithFallback ures_getByKeyWithFallback_3_2
+#define ures_getFunctionalEquivalent ures_getFunctionalEquivalent_3_2
+#define ures_getInt ures_getInt_3_2
+#define ures_getIntVector ures_getIntVector_3_2
+#define ures_getKey ures_getKey_3_2
+#define ures_getKeywordValues ures_getKeywordValues_3_2
+#define ures_getLocale ures_getLocale_3_2
+#define ures_getLocaleByType ures_getLocaleByType_3_2
+#define ures_getName ures_getName_3_2
+#define ures_getNextResource ures_getNextResource_3_2
+#define ures_getNextString ures_getNextString_3_2
+#define ures_getPath ures_getPath_3_2
+#define ures_getSize ures_getSize_3_2
+#define ures_getString ures_getString_3_2
+#define ures_getStringByIndex ures_getStringByIndex_3_2
+#define ures_getStringByKey ures_getStringByKey_3_2
+#define ures_getType ures_getType_3_2
+#define ures_getUInt ures_getUInt_3_2
+#define ures_getVersion ures_getVersion_3_2
+#define ures_getVersionNumber ures_getVersionNumber_3_2
+#define ures_hasNext ures_hasNext_3_2
+#define ures_initStackObject ures_initStackObject_3_2
+#define ures_open ures_open_3_2
+#define ures_openAvailableLocales ures_openAvailableLocales_3_2
+#define ures_openDirect ures_openDirect_3_2
+#define ures_openFillIn ures_openFillIn_3_2
+#define ures_openU ures_openU_3_2
+#define ures_resetIterator ures_resetIterator_3_2
+#define ures_swap ures_swap_3_2
+#define uscript_closeRun uscript_closeRun_3_2
+#define uscript_getCode uscript_getCode_3_2
+#define uscript_getName uscript_getName_3_2
+#define uscript_getScript uscript_getScript_3_2
+#define uscript_getShortName uscript_getShortName_3_2
+#define uscript_nextRun uscript_nextRun_3_2
+#define uscript_openRun uscript_openRun_3_2
+#define uscript_resetRun uscript_resetRun_3_2
+#define uscript_setRunText uscript_setRunText_3_2
+#define usearch_close usearch_close_3_2
+#define usearch_first usearch_first_3_2
+#define usearch_following usearch_following_3_2
+#define usearch_getAttribute usearch_getAttribute_3_2
+#define usearch_getBreakIterator usearch_getBreakIterator_3_2
+#define usearch_getCollator usearch_getCollator_3_2
+#define usearch_getMatchedLength usearch_getMatchedLength_3_2
+#define usearch_getMatchedStart usearch_getMatchedStart_3_2
+#define usearch_getMatchedText usearch_getMatchedText_3_2
+#define usearch_getOffset usearch_getOffset_3_2
+#define usearch_getPattern usearch_getPattern_3_2
+#define usearch_getText usearch_getText_3_2
+#define usearch_handleNextCanonical usearch_handleNextCanonical_3_2
+#define usearch_handleNextExact usearch_handleNextExact_3_2
+#define usearch_handlePreviousCanonical usearch_handlePreviousCanonical_3_2
+#define usearch_handlePreviousExact usearch_handlePreviousExact_3_2
+#define usearch_last usearch_last_3_2
+#define usearch_next usearch_next_3_2
+#define usearch_open usearch_open_3_2
+#define usearch_openFromCollator usearch_openFromCollator_3_2
+#define usearch_preceding usearch_preceding_3_2
+#define usearch_previous usearch_previous_3_2
+#define usearch_reset usearch_reset_3_2
+#define usearch_setAttribute usearch_setAttribute_3_2
+#define usearch_setBreakIterator usearch_setBreakIterator_3_2
+#define usearch_setCollator usearch_setCollator_3_2
+#define usearch_setOffset usearch_setOffset_3_2
+#define usearch_setPattern usearch_setPattern_3_2
+#define usearch_setText usearch_setText_3_2
+#define userv_deleteStringPair userv_deleteStringPair_3_2
+#define uset_add uset_add_3_2
+#define uset_addAll uset_addAll_3_2
+#define uset_addRange uset_addRange_3_2
+#define uset_addString uset_addString_3_2
+#define uset_applyIntPropertyValue uset_applyIntPropertyValue_3_2
+#define uset_applyPattern uset_applyPattern_3_2
+#define uset_applyPropertyAlias uset_applyPropertyAlias_3_2
+#define uset_charAt uset_charAt_3_2
+#define uset_clear uset_clear_3_2
+#define uset_close uset_close_3_2
+#define uset_compact uset_compact_3_2
+#define uset_complement uset_complement_3_2
+#define uset_complementAll uset_complementAll_3_2
+#define uset_contains uset_contains_3_2
+#define uset_containsAll uset_containsAll_3_2
+#define uset_containsNone uset_containsNone_3_2
+#define uset_containsRange uset_containsRange_3_2
+#define uset_containsSome uset_containsSome_3_2
+#define uset_containsString uset_containsString_3_2
+#define uset_equals uset_equals_3_2
+#define uset_getItem uset_getItem_3_2
+#define uset_getItemCount uset_getItemCount_3_2
+#define uset_getSerializedRange uset_getSerializedRange_3_2
+#define uset_getSerializedRangeCount uset_getSerializedRangeCount_3_2
+#define uset_getSerializedSet uset_getSerializedSet_3_2
+#define uset_indexOf uset_indexOf_3_2
+#define uset_isEmpty uset_isEmpty_3_2
+#define uset_open uset_open_3_2
+#define uset_openPattern uset_openPattern_3_2
+#define uset_openPatternOptions uset_openPatternOptions_3_2
+#define uset_remove uset_remove_3_2
+#define uset_removeAll uset_removeAll_3_2
+#define uset_removeRange uset_removeRange_3_2
+#define uset_removeString uset_removeString_3_2
+#define uset_resemblesPattern uset_resemblesPattern_3_2
+#define uset_retain uset_retain_3_2
+#define uset_retainAll uset_retainAll_3_2
+#define uset_serialize uset_serialize_3_2
+#define uset_serializedContains uset_serializedContains_3_2
+#define uset_set uset_set_3_2
+#define uset_setSerializedToOne uset_setSerializedToOne_3_2
+#define uset_size uset_size_3_2
+#define uset_toPattern uset_toPattern_3_2
+#define usprep_close usprep_close_3_2
+#define usprep_open usprep_open_3_2
+#define usprep_prepare usprep_prepare_3_2
+#define usprep_swap usprep_swap_3_2
+#define ustr_foldCase ustr_foldCase_3_2
+#define ustr_toLower ustr_toLower_3_2
+#define ustr_toTitle ustr_toTitle_3_2
+#define ustr_toUpper ustr_toUpper_3_2
+#define utf8_appendCharSafeBody utf8_appendCharSafeBody_3_2
+#define utf8_back1SafeBody utf8_back1SafeBody_3_2
+#define utf8_countTrailBytes utf8_countTrailBytes_3_2
+#define utf8_nextCharSafeBody utf8_nextCharSafeBody_3_2
+#define utf8_prevCharSafeBody utf8_prevCharSafeBody_3_2
+#define utmscale_fromInt64 utmscale_fromInt64_3_2
+#define utmscale_getTimeScaleValue utmscale_getTimeScaleValue_3_2
+#define utmscale_toInt64 utmscale_toInt64_3_2
+#define utrace_cleanup utrace_cleanup_3_2
+#define utrace_data utrace_data_3_2
+#define utrace_entry utrace_entry_3_2
+#define utrace_exit utrace_exit_3_2
+#define utrace_format utrace_format_3_2
+#define utrace_functionName utrace_functionName_3_2
+#define utrace_getFunctions utrace_getFunctions_3_2
+#define utrace_getLevel utrace_getLevel_3_2
+#define utrace_level utrace_level_3_2
+#define utrace_setFunctions utrace_setFunctions_3_2
+#define utrace_setLevel utrace_setLevel_3_2
+#define utrace_vformat utrace_vformat_3_2
+#define utrans_clone utrans_clone_3_2
+#define utrans_close utrans_close_3_2
+#define utrans_countAvailableIDs utrans_countAvailableIDs_3_2
+#define utrans_getAvailableID utrans_getAvailableID_3_2
+#define utrans_getID utrans_getID_3_2
+#define utrans_getUnicodeID utrans_getUnicodeID_3_2
+#define utrans_open utrans_open_3_2
+#define utrans_openIDs utrans_openIDs_3_2
+#define utrans_openInverse utrans_openInverse_3_2
+#define utrans_openU utrans_openU_3_2
+#define utrans_register utrans_register_3_2
+#define utrans_rep_caseContextIterator utrans_rep_caseContextIterator_3_2
+#define utrans_setFilter utrans_setFilter_3_2
+#define utrans_trans utrans_trans_3_2
+#define utrans_transIncremental utrans_transIncremental_3_2
+#define utrans_transIncrementalUChars utrans_transIncrementalUChars_3_2
+#define utrans_transUChars utrans_transUChars_3_2
+#define utrans_unregister utrans_unregister_3_2
+#define utrans_unregisterID utrans_unregisterID_3_2
+#define utrie_clone utrie_clone_3_2
+#define utrie_close utrie_close_3_2
+#define utrie_enum utrie_enum_3_2
+#define utrie_get32 utrie_get32_3_2
+#define utrie_getData utrie_getData_3_2
+#define utrie_open utrie_open_3_2
+#define utrie_serialize utrie_serialize_3_2
+#define utrie_set32 utrie_set32_3_2
+#define utrie_setRange32 utrie_setRange32_3_2
+#define utrie_swap utrie_swap_3_2
+#define utrie_unserialize utrie_unserialize_3_2
+/* C++ class names renaming defines */
+
+#ifdef XP_CPLUSPLUS
+#if !U_HAVE_NAMESPACE
+
+#define AbsoluteValueSubstitution AbsoluteValueSubstitution_3_2
+#define AlternateSubstitutionSubtable AlternateSubstitutionSubtable_3_2
+#define AnchorTable AnchorTable_3_2
+#define AnyTransliterator AnyTransliterator_3_2
+#define ArabicOpenTypeLayoutEngine ArabicOpenTypeLayoutEngine_3_2
+#define ArabicShaping ArabicShaping_3_2
+#define BasicCalendarFactory BasicCalendarFactory_3_2
+#define BinarySearchLookupTable BinarySearchLookupTable_3_2
+#define BreakDictionary BreakDictionary_3_2
+#define BreakIterator BreakIterator_3_2
+#define BuddhistCalendar BuddhistCalendar_3_2
+#define CFactory CFactory_3_2
+#define Calendar Calendar_3_2
+#define CalendarAstronomer CalendarAstronomer_3_2
+#define CalendarCache CalendarCache_3_2
+#define CalendarData CalendarData_3_2
+#define CalendarService CalendarService_3_2
+#define CanonShaping CanonShaping_3_2
+#define CanonicalIterator CanonicalIterator_3_2
+#define CaseMapTransliterator CaseMapTransliterator_3_2
+#define ChainingContextualSubstitutionFormat1Subtable ChainingContextualSubstitutionFormat1Subtable_3_2
+#define ChainingContextualSubstitutionFormat2Subtable ChainingContextualSubstitutionFormat2Subtable_3_2
+#define ChainingContextualSubstitutionFormat3Subtable ChainingContextualSubstitutionFormat3Subtable_3_2
+#define ChainingContextualSubstitutionSubtable ChainingContextualSubstitutionSubtable_3_2
+#define CharSubstitutionFilter CharSubstitutionFilter_3_2
+#define CharacterIterator CharacterIterator_3_2
+#define ChoiceFormat ChoiceFormat_3_2
+#define ClassDefFormat1Table ClassDefFormat1Table_3_2
+#define ClassDefFormat2Table ClassDefFormat2Table_3_2
+#define ClassDefinitionTable ClassDefinitionTable_3_2
+#define CollationElementIterator CollationElementIterator_3_2
+#define CollationKey CollationKey_3_2
+#define Collator Collator_3_2
+#define CollatorFactory CollatorFactory_3_2
+#define CompoundTransliterator CompoundTransliterator_3_2
+#define ContextualGlyphSubstitutionProcessor ContextualGlyphSubstitutionProcessor_3_2
+#define ContextualSubstitutionBase ContextualSubstitutionBase_3_2
+#define ContextualSubstitutionFormat1Subtable ContextualSubstitutionFormat1Subtable_3_2
+#define ContextualSubstitutionFormat2Subtable ContextualSubstitutionFormat2Subtable_3_2
+#define ContextualSubstitutionFormat3Subtable ContextualSubstitutionFormat3Subtable_3_2
+#define ContextualSubstitutionSubtable ContextualSubstitutionSubtable_3_2
+#define CoverageFormat1Table CoverageFormat1Table_3_2
+#define CoverageFormat2Table CoverageFormat2Table_3_2
+#define CoverageTable CoverageTable_3_2
+#define CurrencyAmount CurrencyAmount_3_2
+#define CurrencyFormat CurrencyFormat_3_2
+#define CurrencyUnit CurrencyUnit_3_2
+#define CursiveAttachmentSubtable CursiveAttachmentSubtable_3_2
+#define DateFormat DateFormat_3_2
+#define DateFormatSymbols DateFormatSymbols_3_2
+#define DecimalFormat DecimalFormat_3_2
+#define DecimalFormatSymbols DecimalFormatSymbols_3_2
+#define DefaultCalendarFactory DefaultCalendarFactory_3_2
+#define DefaultCharMapper DefaultCharMapper_3_2
+#define DeviceTable DeviceTable_3_2
+#define DictionaryBasedBreakIterator DictionaryBasedBreakIterator_3_2
+#define DictionaryBasedBreakIteratorTables DictionaryBasedBreakIteratorTables_3_2
+#define DigitList DigitList_3_2
+#define Entry Entry_3_2
+#define EnumToOffset EnumToOffset_3_2
+#define EscapeTransliterator EscapeTransliterator_3_2
+#define EventListener EventListener_3_2
+#define ExtensionSubtable ExtensionSubtable_3_2
+#define FeatureListTable FeatureListTable_3_2
+#define FieldPosition FieldPosition_3_2
+#define FontRuns FontRuns_3_2
+#define Format Format_3_2
+#define Format1AnchorTable Format1AnchorTable_3_2
+#define Format2AnchorTable Format2AnchorTable_3_2
+#define Format3AnchorTable Format3AnchorTable_3_2
+#define Formattable Formattable_3_2
+#define ForwardCharacterIterator ForwardCharacterIterator_3_2
+#define FractionalPartSubstitution FractionalPartSubstitution_3_2
+#define FunctionReplacer FunctionReplacer_3_2
+#define GDEFMarkFilter GDEFMarkFilter_3_2
+#define GXLayoutEngine GXLayoutEngine_3_2
+#define GlyphDefinitionTableHeader GlyphDefinitionTableHeader_3_2
+#define GlyphIterator GlyphIterator_3_2
+#define GlyphLookupTableHeader GlyphLookupTableHeader_3_2
+#define GlyphPositioningLookupProcessor GlyphPositioningLookupProcessor_3_2
+#define GlyphPositioningTableHeader GlyphPositioningTableHeader_3_2
+#define GlyphSubstitutionLookupProcessor GlyphSubstitutionLookupProcessor_3_2
+#define GlyphSubstitutionTableHeader GlyphSubstitutionTableHeader_3_2
+#define Grego Grego_3_2
+#define GregorianCalendar GregorianCalendar_3_2
+#define HanOpenTypeLayoutEngine HanOpenTypeLayoutEngine_3_2
+#define HebrewCalendar HebrewCalendar_3_2
+#define ICUBreakIteratorFactory ICUBreakIteratorFactory_3_2
+#define ICUBreakIteratorService ICUBreakIteratorService_3_2
+#define ICUCollatorFactory ICUCollatorFactory_3_2
+#define ICUCollatorService ICUCollatorService_3_2
+#define ICULayoutEngine ICULayoutEngine_3_2
+#define ICULocaleService ICULocaleService_3_2
+#define ICUNotifier ICUNotifier_3_2
+#define ICUNumberFormatFactory ICUNumberFormatFactory_3_2
+#define ICUNumberFormatService ICUNumberFormatService_3_2
+#define ICUResourceBundleFactory ICUResourceBundleFactory_3_2
+#define ICUService ICUService_3_2
+#define ICUServiceFactory ICUServiceFactory_3_2
+#define ICUServiceKey ICUServiceKey_3_2
+#define ICU_Utility ICU_Utility_3_2
+#define IndicClassTable IndicClassTable_3_2
+#define IndicOpenTypeLayoutEngine IndicOpenTypeLayoutEngine_3_2
+#define IndicRearrangementProcessor IndicRearrangementProcessor_3_2
+#define IndicReordering IndicReordering_3_2
+#define IntegralPartSubstitution IntegralPartSubstitution_3_2
+#define IslamicCalendar IslamicCalendar_3_2
+#define JapaneseCalendar JapaneseCalendar_3_2
+#define KeywordEnumeration KeywordEnumeration_3_2
+#define LECharMapper LECharMapper_3_2
+#define LEFontInstance LEFontInstance_3_2
+#define LEGlyphFilter LEGlyphFilter_3_2
+#define LEGlyphStorage LEGlyphStorage_3_2
+#define LEInsertionCallback LEInsertionCallback_3_2
+#define LEInsertionList LEInsertionList_3_2
+#define LXUtilities LXUtilities_3_2
+#define LayoutEngine LayoutEngine_3_2
+#define LigatureSubstitutionProcessor LigatureSubstitutionProcessor_3_2
+#define LigatureSubstitutionSubtable LigatureSubstitutionSubtable_3_2
+#define LocDataParser LocDataParser_3_2
+#define Locale Locale_3_2
+#define LocaleBased LocaleBased_3_2
+#define LocaleKey LocaleKey_3_2
+#define LocaleKeyFactory LocaleKeyFactory_3_2
+#define LocaleRuns LocaleRuns_3_2
+#define LocaleUtility LocaleUtility_3_2
+#define LocalizationInfo LocalizationInfo_3_2
+#define LookupListTable LookupListTable_3_2
+#define LookupProcessor LookupProcessor_3_2
+#define LookupSubtable LookupSubtable_3_2
+#define LookupTable LookupTable_3_2
+#define LowercaseTransliterator LowercaseTransliterator_3_2
+#define MPreFixups MPreFixups_3_2
+#define MarkArray MarkArray_3_2
+#define MarkToBasePositioningSubtable MarkToBasePositioningSubtable_3_2
+#define MarkToLigaturePositioningSubtable MarkToLigaturePositioningSubtable_3_2
+#define MarkToMarkPositioningSubtable MarkToMarkPositioningSubtable_3_2
+#define Math Math_3_2
+#define Measure Measure_3_2
+#define MeasureFormat MeasureFormat_3_2
+#define MeasureUnit MeasureUnit_3_2
+#define MessageFormat MessageFormat_3_2
+#define MessageFormatAdapter MessageFormatAdapter_3_2
+#define ModulusSubstitution ModulusSubstitution_3_2
+#define MoonRiseSetCoordFunc MoonRiseSetCoordFunc_3_2
+#define MoonTimeAngleFunc MoonTimeAngleFunc_3_2
+#define MorphSubtableHeader MorphSubtableHeader_3_2
+#define MorphTableHeader MorphTableHeader_3_2
+#define MultipleSubstitutionSubtable MultipleSubstitutionSubtable_3_2
+#define MultiplierSubstitution MultiplierSubstitution_3_2
+#define NFFactory NFFactory_3_2
+#define NFRule NFRule_3_2
+#define NFRuleSet NFRuleSet_3_2
+#define NFSubstitution NFSubstitution_3_2
+#define NameToEnum NameToEnum_3_2
+#define NameUnicodeTransliterator NameUnicodeTransliterator_3_2
+#define NonContextualGlyphSubstitutionProcessor NonContextualGlyphSubstitutionProcessor_3_2
+#define NonContiguousEnumToOffset NonContiguousEnumToOffset_3_2
+#define NormalizationTransliterator NormalizationTransliterator_3_2
+#define Normalizer Normalizer_3_2
+#define NullSubstitution NullSubstitution_3_2
+#define NullTransliterator NullTransliterator_3_2
+#define NumberFormat NumberFormat_3_2
+#define NumberFormatFactory NumberFormatFactory_3_2
+#define NumeratorSubstitution NumeratorSubstitution_3_2
+#define OlsonTimeZone OlsonTimeZone_3_2
+#define OpenTypeLayoutEngine OpenTypeLayoutEngine_3_2
+#define OpenTypeUtilities OpenTypeUtilities_3_2
+#define PairPositioningFormat1Subtable PairPositioningFormat1Subtable_3_2
+#define PairPositioningFormat2Subtable PairPositioningFormat2Subtable_3_2
+#define PairPositioningSubtable PairPositioningSubtable_3_2
+#define ParagraphLayout ParagraphLayout_3_2
+#define ParseData ParseData_3_2
+#define ParsePosition ParsePosition_3_2
+#define PropertyAliases PropertyAliases_3_2
+#define Quantifier Quantifier_3_2
+#define RBBIDataWrapper RBBIDataWrapper_3_2
+#define RBBINode RBBINode_3_2
+#define RBBIRuleBuilder RBBIRuleBuilder_3_2
+#define RBBIRuleScanner RBBIRuleScanner_3_2
+#define RBBISetBuilder RBBISetBuilder_3_2
+#define RBBIStateDescriptor RBBIStateDescriptor_3_2
+#define RBBISymbolTable RBBISymbolTable_3_2
+#define RBBISymbolTableEntry RBBISymbolTableEntry_3_2
+#define RBBITableBuilder RBBITableBuilder_3_2
+#define RangeDescriptor RangeDescriptor_3_2
+#define RegexCompile RegexCompile_3_2
+#define RegexMatcher RegexMatcher_3_2
+#define RegexPattern RegexPattern_3_2
+#define RegexStaticSets RegexStaticSets_3_2
+#define RemoveTransliterator RemoveTransliterator_3_2
+#define Replaceable Replaceable_3_2
+#define ReplaceableGlue ReplaceableGlue_3_2
+#define ResourceBundle ResourceBundle_3_2
+#define RiseSetCoordFunc RiseSetCoordFunc_3_2
+#define RuleBasedBreakIterator RuleBasedBreakIterator_3_2
+#define RuleBasedCollator RuleBasedCollator_3_2
+#define RuleBasedNumberFormat RuleBasedNumberFormat_3_2
+#define RuleBasedTransliterator RuleBasedTransliterator_3_2
+#define RuleCharacterIterator RuleCharacterIterator_3_2
+#define RuleHalf RuleHalf_3_2
+#define RunArray RunArray_3_2
+#define SameValueSubstitution SameValueSubstitution_3_2
+#define ScriptListTable ScriptListTable_3_2
+#define ScriptRunIterator ScriptRunIterator_3_2
+#define ScriptTable ScriptTable_3_2
+#define SearchIterator SearchIterator_3_2
+#define SegmentArrayProcessor SegmentArrayProcessor_3_2
+#define SegmentSingleProcessor SegmentSingleProcessor_3_2
+#define ServiceEnumeration ServiceEnumeration_3_2
+#define ServiceListener ServiceListener_3_2
+#define SimpleArrayProcessor SimpleArrayProcessor_3_2
+#define SimpleDateFormat SimpleDateFormat_3_2
+#define SimpleFactory SimpleFactory_3_2
+#define SimpleLocaleKeyFactory SimpleLocaleKeyFactory_3_2
+#define SimpleNumberFormatFactory SimpleNumberFormatFactory_3_2
+#define SimpleTimeZone SimpleTimeZone_3_2
+#define SinglePositioningFormat1Subtable SinglePositioningFormat1Subtable_3_2
+#define SinglePositioningFormat2Subtable SinglePositioningFormat2Subtable_3_2
+#define SinglePositioningSubtable SinglePositioningSubtable_3_2
+#define SingleSubstitutionFormat1Subtable SingleSubstitutionFormat1Subtable_3_2
+#define SingleSubstitutionFormat2Subtable SingleSubstitutionFormat2Subtable_3_2
+#define SingleSubstitutionSubtable SingleSubstitutionSubtable_3_2
+#define SingleTableProcessor SingleTableProcessor_3_2
+#define Spec Spec_3_2
+#define StateTableProcessor StateTableProcessor_3_2
+#define StringCharacterIterator StringCharacterIterator_3_2
+#define StringEnumeration StringEnumeration_3_2
+#define StringLocalizationInfo StringLocalizationInfo_3_2
+#define StringMatcher StringMatcher_3_2
+#define StringPair StringPair_3_2
+#define StringReplacer StringReplacer_3_2
+#define StringSearch StringSearch_3_2
+#define StyleRuns StyleRuns_3_2
+#define SubstitutionLookup SubstitutionLookup_3_2
+#define SubtableProcessor SubtableProcessor_3_2
+#define SunTimeAngleFunc SunTimeAngleFunc_3_2
+#define SymbolTable SymbolTable_3_2
+#define TZEnumeration TZEnumeration_3_2
+#define ThaiLayoutEngine ThaiLayoutEngine_3_2
+#define ThaiShaping ThaiShaping_3_2
+#define TimeZone TimeZone_3_2
+#define TitlecaseTransliterator TitlecaseTransliterator_3_2
+#define TransliterationRule TransliterationRule_3_2
+#define TransliterationRuleData TransliterationRuleData_3_2
+#define TransliterationRuleSet TransliterationRuleSet_3_2
+#define Transliterator Transliterator_3_2
+#define TransliteratorAlias TransliteratorAlias_3_2
+#define TransliteratorIDParser TransliteratorIDParser_3_2
+#define TransliteratorParser TransliteratorParser_3_2
+#define TransliteratorRegistry TransliteratorRegistry_3_2
+#define TrimmedArrayProcessor TrimmedArrayProcessor_3_2
+#define UCharCharacterIterator UCharCharacterIterator_3_2
+#define UMemory UMemory_3_2
+#define UObject UObject_3_2
+#define UStack UStack_3_2
+#define UStringEnumeration UStringEnumeration_3_2
+#define UVector UVector_3_2
+#define UVector32 UVector32_3_2
+#define UnescapeTransliterator UnescapeTransliterator_3_2
+#define UnicodeArabicOpenTypeLayoutEngine UnicodeArabicOpenTypeLayoutEngine_3_2
+#define UnicodeFilter UnicodeFilter_3_2
+#define UnicodeFunctor UnicodeFunctor_3_2
+#define UnicodeMatcher UnicodeMatcher_3_2
+#define UnicodeNameTransliterator UnicodeNameTransliterator_3_2
+#define UnicodeReplacer UnicodeReplacer_3_2
+#define UnicodeSet UnicodeSet_3_2
+#define UnicodeSetIterator UnicodeSetIterator_3_2
+#define UnicodeString UnicodeString_3_2
+#define UppercaseTransliterator UppercaseTransliterator_3_2
+#define ValueRecord ValueRecord_3_2
+#define ValueRuns ValueRuns_3_2
+#define locale_set_default_internal locale_set_default_internal_3_2
+#define uprv_parseCurrency uprv_parseCurrency_3_2
+#define util64_fromDouble util64_fromDouble_3_2
+#define util64_pow util64_pow_3_2
+#define util64_tou util64_tou_3_2
+#define util64_utoi util64_utoi_3_2
+
+#endif
+#endif
+
+#endif
+
+#endif
diff --git a/WebKit/mac/icu/unicode/uscript.h b/WebKit/mac/icu/unicode/uscript.h
new file mode 100644
index 0000000..f31d748
--- /dev/null
+++ b/WebKit/mac/icu/unicode/uscript.h
@@ -0,0 +1,148 @@
+/*
+**********************************************************************
+* Copyright (C) 1997-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+**********************************************************************
+*
+* File USCRIPT.H
+*
+* Modification History:
+*
+* Date Name Description
+* 07/06/2001 Ram Creation.
+******************************************************************************
+*/
+#ifndef USCRIPT_H
+#define USCRIPT_H
+#include "unicode/utypes.h"
+
+/**
+ * Constants for Unicode script values from ScriptNames.txt .
+ *
+ * @stable ICU 2.2
+ */
+typedef enum UScriptCode {
+ USCRIPT_INVALID_CODE = -1,
+ USCRIPT_COMMON = 0 , /* Zyyy */
+ USCRIPT_INHERITED = 1, /* Qaai */
+ USCRIPT_ARABIC = 2, /* Arab */
+ USCRIPT_ARMENIAN = 3, /* Armn */
+ USCRIPT_BENGALI = 4, /* Beng */
+ USCRIPT_BOPOMOFO = 5, /* Bopo */
+ USCRIPT_CHEROKEE = 6, /* Cher */
+ USCRIPT_COPTIC = 7, /* Copt */
+ USCRIPT_CYRILLIC = 8, /* Cyrl (Cyrs) */
+ USCRIPT_DESERET = 9, /* Dsrt */
+ USCRIPT_DEVANAGARI = 10, /* Deva */
+ USCRIPT_ETHIOPIC = 11, /* Ethi */
+ USCRIPT_GEORGIAN = 12, /* Geor (Geon, Geoa) */
+ USCRIPT_GOTHIC = 13, /* Goth */
+ USCRIPT_GREEK = 14, /* Grek */
+ USCRIPT_GUJARATI = 15, /* Gujr */
+ USCRIPT_GURMUKHI = 16, /* Guru */
+ USCRIPT_HAN = 17, /* Hani */
+ USCRIPT_HANGUL = 18, /* Hang */
+ USCRIPT_HEBREW = 19, /* Hebr */
+ USCRIPT_HIRAGANA = 20, /* Hira */
+ USCRIPT_KANNADA = 21, /* Knda */
+ USCRIPT_KATAKANA = 22, /* Kana */
+ USCRIPT_KHMER = 23, /* Khmr */
+ USCRIPT_LAO = 24, /* Laoo */
+ USCRIPT_LATIN = 25, /* Latn (Latf, Latg) */
+ USCRIPT_MALAYALAM = 26, /* Mlym */
+ USCRIPT_MONGOLIAN = 27, /* Mong */
+ USCRIPT_MYANMAR = 28, /* Mymr */
+ USCRIPT_OGHAM = 29, /* Ogam */
+ USCRIPT_OLD_ITALIC = 30, /* Ital */
+ USCRIPT_ORIYA = 31, /* Orya */
+ USCRIPT_RUNIC = 32, /* Runr */
+ USCRIPT_SINHALA = 33, /* Sinh */
+ USCRIPT_SYRIAC = 34, /* Syrc (Syrj, Syrn, Syre) */
+ USCRIPT_TAMIL = 35, /* Taml */
+ USCRIPT_TELUGU = 36, /* Telu */
+ USCRIPT_THAANA = 37, /* Thaa */
+ USCRIPT_THAI = 38, /* Thai */
+ USCRIPT_TIBETAN = 39, /* Tibt */
+ /** Canadian_Aboriginal script. @stable ICU 2.6 */
+ USCRIPT_CANADIAN_ABORIGINAL = 40, /* Cans */
+ /** Canadian_Aboriginal script (alias). @stable ICU 2.2 */
+ USCRIPT_UCAS = USCRIPT_CANADIAN_ABORIGINAL,
+ USCRIPT_YI = 41, /* Yiii */
+ USCRIPT_TAGALOG = 42, /* Tglg */
+ USCRIPT_HANUNOO = 43, /* Hano */
+ USCRIPT_BUHID = 44, /* Buhd */
+ USCRIPT_TAGBANWA = 45, /* Tagb */
+
+ /* New scripts in Unicode 4 @stable ICU 2.6 */
+ USCRIPT_BRAILLE, /* Brai */
+ USCRIPT_CYPRIOT, /* Cprt */
+ USCRIPT_LIMBU, /* Limb */
+ USCRIPT_LINEAR_B, /* Linb */
+ USCRIPT_OSMANYA, /* Osma */
+ USCRIPT_SHAVIAN, /* Shaw */
+ USCRIPT_TAI_LE, /* Tale */
+ USCRIPT_UGARITIC, /* Ugar */
+
+ /** New script code in Unicode 4.0.1 @draft ICU 3.0 */
+ USCRIPT_KATAKANA_OR_HIRAGANA,/*Hrkt */
+
+ USCRIPT_CODE_LIMIT
+} UScriptCode;
+
+/**
+ * Gets script codes associated with the given locale or ISO 15924 abbreviation or name.
+ * Fills in USCRIPT_MALAYALAM given "Malayam" OR "Mlym".
+ * Fills in USCRIPT_LATIN given "en" OR "en_US"
+ * If required capacity is greater than capacity of the destination buffer then the error code
+ * is set to U_BUFFER_OVERFLOW_ERROR and the required capacity is returned
+ *
+ * <p>Note: To search by short or long script alias only, use
+ * u_getPropertyValueEnum(UCHAR_SCRIPT, alias) instead. This does
+ * a fast lookup with no access of the locale data.
+ * @param nameOrAbbrOrLocale name of the script, as given in
+ * PropertyValueAliases.txt, or ISO 15924 code or locale
+ * @param fillIn the UScriptCode buffer to fill in the script code
+ * @param capacity the capacity (size) fo UScriptCode buffer passed in.
+ * @param err the error status code.
+ * @return The number of script codes filled in the buffer passed in
+ * @stable ICU 2.4
+ */
+U_STABLE int32_t U_EXPORT2
+uscript_getCode(const char* nameOrAbbrOrLocale,UScriptCode* fillIn,int32_t capacity,UErrorCode *err);
+
+/**
+ * Gets a script name associated with the given script code.
+ * Returns "Malayam" given USCRIPT_MALAYALAM
+ * @param scriptCode UScriptCode enum
+ * @return script long name as given in
+ * PropertyValueAliases.txt, or NULL if scriptCode is invalid
+ * @stable ICU 2.4
+ */
+U_STABLE const char* U_EXPORT2
+uscript_getName(UScriptCode scriptCode);
+
+/**
+ * Gets a script name associated with the given script code.
+ * Returns "Mlym" given USCRIPT_MALAYALAM
+ * @param scriptCode UScriptCode enum
+ * @return script abbreviated name as given in
+ * PropertyValueAliases.txt, or NULL if scriptCode is invalid
+ * @stable ICU 2.4
+ */
+U_STABLE const char* U_EXPORT2
+uscript_getShortName(UScriptCode scriptCode);
+
+/**
+ * Gets the script code associated with the given codepoint.
+ * Returns USCRIPT_MALAYALAM given 0x0D02
+ * @param codepoint UChar32 codepoint
+ * @param err the error status code.
+ * @return The UScriptCode, or 0 if codepoint is invalid
+ * @stable ICU 2.4
+ */
+U_STABLE UScriptCode U_EXPORT2
+uscript_getScript(UChar32 codepoint, UErrorCode *err);
+
+#endif
+
+
diff --git a/WebKit/mac/icu/unicode/ustring.h b/WebKit/mac/icu/unicode/ustring.h
new file mode 100644
index 0000000..6ebb6fb
--- /dev/null
+++ b/WebKit/mac/icu/unicode/ustring.h
@@ -0,0 +1,1320 @@
+/*
+**********************************************************************
+* Copyright (C) 1998-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+**********************************************************************
+*
+* File ustring.h
+*
+* Modification History:
+*
+* Date Name Description
+* 12/07/98 bertrand Creation.
+******************************************************************************
+*/
+
+#ifndef USTRING_H
+#define USTRING_H
+
+#include "unicode/utypes.h"
+#include "unicode/putil.h"
+#include "unicode/uiter.h"
+
+/** Simple declaration for u_strToTitle() to avoid including unicode/ubrk.h. @stable ICU 2.1*/
+#ifndef UBRK_TYPEDEF_UBREAK_ITERATOR
+# define UBRK_TYPEDEF_UBREAK_ITERATOR
+ typedef void UBreakIterator;
+#endif
+
+/**
+ * \file
+ * \brief C API: Unicode string handling functions
+ *
+ * These C API functions provide general Unicode string handling.
+ *
+ * Some functions are equivalent in name, signature, and behavior to the ANSI C <string.h>
+ * functions. (For example, they do not check for bad arguments like NULL string pointers.)
+ * In some cases, only the thread-safe variant of such a function is implemented here
+ * (see u_strtok_r()).
+ *
+ * Other functions provide more Unicode-specific functionality like locale-specific
+ * upper/lower-casing and string comparison in code point order.
+ *
+ * ICU uses 16-bit Unicode (UTF-16) in the form of arrays of UChar code units.
+ * UTF-16 encodes each Unicode code point with either one or two UChar code units.
+ * (This is the default form of Unicode, and a forward-compatible extension of the original,
+ * fixed-width form that was known as UCS-2. UTF-16 superseded UCS-2 with Unicode 2.0
+ * in 1996.)
+ *
+ * Some APIs accept a 32-bit UChar32 value for a single code point.
+ *
+ * ICU also handles 16-bit Unicode text with unpaired surrogates.
+ * Such text is not well-formed UTF-16.
+ * Code-point-related functions treat unpaired surrogates as surrogate code points,
+ * i.e., as separate units.
+ *
+ * Although UTF-16 is a variable-width encoding form (like some legacy multi-byte encodings),
+ * it is much more efficient even for random access because the code unit values
+ * for single-unit characters vs. lead units vs. trail units are completely disjoint.
+ * This means that it is easy to determine character (code point) boundaries from
+ * random offsets in the string.
+ *
+ * Unicode (UTF-16) string processing is optimized for the single-unit case.
+ * Although it is important to support supplementary characters
+ * (which use pairs of lead/trail code units called "surrogates"),
+ * their occurrence is rare. Almost all characters in modern use require only
+ * a single UChar code unit (i.e., their code point values are <=0xffff).
+ *
+ * For more details see the User Guide Strings chapter (http://oss.software.ibm.com/icu/userguide/strings.html).
+ * For a discussion of the handling of unpaired surrogates see also
+ * Jitterbug 2145 and its icu mailing list proposal on 2002-sep-18.
+ */
+
+/**
+ * Determine the length of an array of UChar.
+ *
+ * @param s The array of UChars, NULL (U+0000) terminated.
+ * @return The number of UChars in <code>chars</code>, minus the terminator.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strlen(const UChar *s);
+
+/**
+ * Count Unicode code points in the length UChar code units of the string.
+ * A code point may occupy either one or two UChar code units.
+ * Counting code points involves reading all code units.
+ *
+ * This functions is basically the inverse of the U16_FWD_N() macro (see utf.h).
+ *
+ * @param s The input string.
+ * @param length The number of UChar code units to be checked, or -1 to count all
+ * code points before the first NUL (U+0000).
+ * @return The number of code points in the specified code units.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_countChar32(const UChar *s, int32_t length);
+
+/**
+ * Check if the string contains more Unicode code points than a certain number.
+ * This is more efficient than counting all code points in the entire string
+ * and comparing that number with a threshold.
+ * This function may not need to scan the string at all if the length is known
+ * (not -1 for NUL-termination) and falls within a certain range, and
+ * never needs to count more than 'number+1' code points.
+ * Logically equivalent to (u_countChar32(s, length)>number).
+ * A Unicode code point may occupy either one or two UChar code units.
+ *
+ * @param s The input string.
+ * @param length The length of the string, or -1 if it is NUL-terminated.
+ * @param number The number of code points in the string is compared against
+ * the 'number' parameter.
+ * @return Boolean value for whether the string contains more Unicode code points
+ * than 'number'. Same as (u_countChar32(s, length)>number).
+ * @stable ICU 2.4
+ */
+U_STABLE UBool U_EXPORT2
+u_strHasMoreChar32Than(const UChar *s, int32_t length, int32_t number);
+
+/**
+ * Concatenate two ustrings. Appends a copy of <code>src</code>,
+ * including the null terminator, to <code>dst</code>. The initial copied
+ * character from <code>src</code> overwrites the null terminator in <code>dst</code>.
+ *
+ * @param dst The destination string.
+ * @param src The source string.
+ * @return A pointer to <code>dst</code>.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2
+u_strcat(UChar *dst,
+ const UChar *src);
+
+/**
+ * Concatenate two ustrings.
+ * Appends at most <code>n</code> characters from <code>src</code> to <code>dst</code>.
+ * Adds a terminating NUL.
+ * If src is too long, then only <code>n-1</code> characters will be copied
+ * before the terminating NUL.
+ * If <code>n&lt;=0</code> then dst is not modified.
+ *
+ * @param dst The destination string.
+ * @param src The source string.
+ * @param n The maximum number of characters to compare.
+ * @return A pointer to <code>dst</code>.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2
+u_strncat(UChar *dst,
+ const UChar *src,
+ int32_t n);
+
+/**
+ * Find the first occurrence of a substring in a string.
+ * The substring is found at code point boundaries.
+ * That means that if the substring begins with
+ * a trail surrogate or ends with a lead surrogate,
+ * then it is found only if these surrogates stand alone in the text.
+ * Otherwise, the substring edge units would be matched against
+ * halves of surrogate pairs.
+ *
+ * @param s The string to search (NUL-terminated).
+ * @param substring The substring to find (NUL-terminated).
+ * @return A pointer to the first occurrence of <code>substring</code> in <code>s</code>,
+ * or <code>s</code> itself if the <code>substring</code> is empty,
+ * or <code>NULL</code> if <code>substring</code> is not in <code>s</code>.
+ * @stable ICU 2.0
+ *
+ * @see u_strrstr
+ * @see u_strFindFirst
+ * @see u_strFindLast
+ */
+U_STABLE UChar * U_EXPORT2
+u_strstr(const UChar *s, const UChar *substring);
+
+/**
+ * Find the first occurrence of a substring in a string.
+ * The substring is found at code point boundaries.
+ * That means that if the substring begins with
+ * a trail surrogate or ends with a lead surrogate,
+ * then it is found only if these surrogates stand alone in the text.
+ * Otherwise, the substring edge units would be matched against
+ * halves of surrogate pairs.
+ *
+ * @param s The string to search.
+ * @param length The length of s (number of UChars), or -1 if it is NUL-terminated.
+ * @param substring The substring to find (NUL-terminated).
+ * @param subLength The length of substring (number of UChars), or -1 if it is NUL-terminated.
+ * @return A pointer to the first occurrence of <code>substring</code> in <code>s</code>,
+ * or <code>s</code> itself if the <code>substring</code> is empty,
+ * or <code>NULL</code> if <code>substring</code> is not in <code>s</code>.
+ * @stable ICU 2.4
+ *
+ * @see u_strstr
+ * @see u_strFindLast
+ */
+U_STABLE UChar * U_EXPORT2
+u_strFindFirst(const UChar *s, int32_t length, const UChar *substring, int32_t subLength);
+
+/**
+ * Find the first occurrence of a BMP code point in a string.
+ * A surrogate code point is found only if its match in the text is not
+ * part of a surrogate pair.
+ * A NUL character is found at the string terminator.
+ *
+ * @param s The string to search (NUL-terminated).
+ * @param c The BMP code point to find.
+ * @return A pointer to the first occurrence of <code>c</code> in <code>s</code>
+ * or <code>NULL</code> if <code>c</code> is not in <code>s</code>.
+ * @stable ICU 2.0
+ *
+ * @see u_strchr32
+ * @see u_memchr
+ * @see u_strstr
+ * @see u_strFindFirst
+ */
+U_STABLE UChar * U_EXPORT2
+u_strchr(const UChar *s, UChar c);
+
+/**
+ * Find the first occurrence of a code point in a string.
+ * A surrogate code point is found only if its match in the text is not
+ * part of a surrogate pair.
+ * A NUL character is found at the string terminator.
+ *
+ * @param s The string to search (NUL-terminated).
+ * @param c The code point to find.
+ * @return A pointer to the first occurrence of <code>c</code> in <code>s</code>
+ * or <code>NULL</code> if <code>c</code> is not in <code>s</code>.
+ * @stable ICU 2.0
+ *
+ * @see u_strchr
+ * @see u_memchr32
+ * @see u_strstr
+ * @see u_strFindFirst
+ */
+U_STABLE UChar * U_EXPORT2
+u_strchr32(const UChar *s, UChar32 c);
+
+/**
+ * Find the last occurrence of a substring in a string.
+ * The substring is found at code point boundaries.
+ * That means that if the substring begins with
+ * a trail surrogate or ends with a lead surrogate,
+ * then it is found only if these surrogates stand alone in the text.
+ * Otherwise, the substring edge units would be matched against
+ * halves of surrogate pairs.
+ *
+ * @param s The string to search (NUL-terminated).
+ * @param substring The substring to find (NUL-terminated).
+ * @return A pointer to the last occurrence of <code>substring</code> in <code>s</code>,
+ * or <code>s</code> itself if the <code>substring</code> is empty,
+ * or <code>NULL</code> if <code>substring</code> is not in <code>s</code>.
+ * @stable ICU 2.4
+ *
+ * @see u_strstr
+ * @see u_strFindFirst
+ * @see u_strFindLast
+ */
+U_STABLE UChar * U_EXPORT2
+u_strrstr(const UChar *s, const UChar *substring);
+
+/**
+ * Find the last occurrence of a substring in a string.
+ * The substring is found at code point boundaries.
+ * That means that if the substring begins with
+ * a trail surrogate or ends with a lead surrogate,
+ * then it is found only if these surrogates stand alone in the text.
+ * Otherwise, the substring edge units would be matched against
+ * halves of surrogate pairs.
+ *
+ * @param s The string to search.
+ * @param length The length of s (number of UChars), or -1 if it is NUL-terminated.
+ * @param substring The substring to find (NUL-terminated).
+ * @param subLength The length of substring (number of UChars), or -1 if it is NUL-terminated.
+ * @return A pointer to the last occurrence of <code>substring</code> in <code>s</code>,
+ * or <code>s</code> itself if the <code>substring</code> is empty,
+ * or <code>NULL</code> if <code>substring</code> is not in <code>s</code>.
+ * @stable ICU 2.4
+ *
+ * @see u_strstr
+ * @see u_strFindLast
+ */
+U_STABLE UChar * U_EXPORT2
+u_strFindLast(const UChar *s, int32_t length, const UChar *substring, int32_t subLength);
+
+/**
+ * Find the last occurrence of a BMP code point in a string.
+ * A surrogate code point is found only if its match in the text is not
+ * part of a surrogate pair.
+ * A NUL character is found at the string terminator.
+ *
+ * @param s The string to search (NUL-terminated).
+ * @param c The BMP code point to find.
+ * @return A pointer to the last occurrence of <code>c</code> in <code>s</code>
+ * or <code>NULL</code> if <code>c</code> is not in <code>s</code>.
+ * @stable ICU 2.4
+ *
+ * @see u_strrchr32
+ * @see u_memrchr
+ * @see u_strrstr
+ * @see u_strFindLast
+ */
+U_STABLE UChar * U_EXPORT2
+u_strrchr(const UChar *s, UChar c);
+
+/**
+ * Find the last occurrence of a code point in a string.
+ * A surrogate code point is found only if its match in the text is not
+ * part of a surrogate pair.
+ * A NUL character is found at the string terminator.
+ *
+ * @param s The string to search (NUL-terminated).
+ * @param c The code point to find.
+ * @return A pointer to the last occurrence of <code>c</code> in <code>s</code>
+ * or <code>NULL</code> if <code>c</code> is not in <code>s</code>.
+ * @stable ICU 2.4
+ *
+ * @see u_strrchr
+ * @see u_memchr32
+ * @see u_strrstr
+ * @see u_strFindLast
+ */
+U_STABLE UChar * U_EXPORT2
+u_strrchr32(const UChar *s, UChar32 c);
+
+/**
+ * Locates the first occurrence in the string <code>string</code> of any of the characters
+ * in the string <code>matchSet</code>.
+ * Works just like C's strpbrk but with Unicode.
+ *
+ * @param string The string in which to search, NUL-terminated.
+ * @param matchSet A NUL-terminated string defining a set of code points
+ * for which to search in the text string.
+ * @return A pointer to the character in <code>string</code> that matches one of the
+ * characters in <code>matchSet</code>, or NULL if no such character is found.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar * U_EXPORT2
+u_strpbrk(const UChar *string, const UChar *matchSet);
+
+/**
+ * Returns the number of consecutive characters in <code>string</code>,
+ * beginning with the first, that do not occur somewhere in <code>matchSet</code>.
+ * Works just like C's strcspn but with Unicode.
+ *
+ * @param string The string in which to search, NUL-terminated.
+ * @param matchSet A NUL-terminated string defining a set of code points
+ * for which to search in the text string.
+ * @return The number of initial characters in <code>string</code> that do not
+ * occur in <code>matchSet</code>.
+ * @see u_strspn
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strcspn(const UChar *string, const UChar *matchSet);
+
+/**
+ * Returns the number of consecutive characters in <code>string</code>,
+ * beginning with the first, that occur somewhere in <code>matchSet</code>.
+ * Works just like C's strspn but with Unicode.
+ *
+ * @param string The string in which to search, NUL-terminated.
+ * @param matchSet A NUL-terminated string defining a set of code points
+ * for which to search in the text string.
+ * @return The number of initial characters in <code>string</code> that do
+ * occur in <code>matchSet</code>.
+ * @see u_strcspn
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strspn(const UChar *string, const UChar *matchSet);
+
+/**
+ * The string tokenizer API allows an application to break a string into
+ * tokens. Unlike strtok(), the saveState (the current pointer within the
+ * original string) is maintained in saveState. In the first call, the
+ * argument src is a pointer to the string. In subsequent calls to
+ * return successive tokens of that string, src must be specified as
+ * NULL. The value saveState is set by this function to maintain the
+ * function's position within the string, and on each subsequent call
+ * you must give this argument the same variable. This function does
+ * handle surrogate pairs. This function is similar to the strtok_r()
+ * the POSIX Threads Extension (1003.1c-1995) version.
+ *
+ * @param src String containing token(s). This string will be modified.
+ * After the first call to u_strtok_r(), this argument must
+ * be NULL to get to the next token.
+ * @param delim Set of delimiter characters (Unicode code points).
+ * @param saveState The current pointer within the original string,
+ * which is set by this function. The saveState
+ * parameter should the address of a local variable of type
+ * UChar *. (i.e. defined "Uhar *myLocalSaveState" and use
+ * &myLocalSaveState for this parameter).
+ * @return A pointer to the next token found in src, or NULL
+ * when there are no more tokens.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar * U_EXPORT2
+u_strtok_r(UChar *src,
+ const UChar *delim,
+ UChar **saveState);
+
+/**
+ * Compare two Unicode strings for bitwise equality (code unit order).
+ *
+ * @param s1 A string to compare.
+ * @param s2 A string to compare.
+ * @return 0 if <code>s1</code> and <code>s2</code> are bitwise equal; a negative
+ * value if <code>s1</code> is bitwise less than <code>s2,</code>; a positive
+ * value if <code>s1</code> is bitwise greater than <code>s2</code>.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strcmp(const UChar *s1,
+ const UChar *s2);
+
+/**
+ * Compare two Unicode strings in code point order.
+ * See u_strCompare for details.
+ *
+ * @param s1 A string to compare.
+ * @param s2 A string to compare.
+ * @return a negative/zero/positive integer corresponding to whether
+ * the first string is less than/equal to/greater than the second one
+ * in code point order
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strcmpCodePointOrder(const UChar *s1, const UChar *s2);
+
+/**
+ * Compare two Unicode strings (binary order).
+ *
+ * The comparison can be done in code unit order or in code point order.
+ * They differ only in UTF-16 when
+ * comparing supplementary code points (U+10000..U+10ffff)
+ * to BMP code points near the end of the BMP (i.e., U+e000..U+ffff).
+ * In code unit order, high BMP code points sort after supplementary code points
+ * because they are stored as pairs of surrogates which are at U+d800..U+dfff.
+ *
+ * This functions works with strings of different explicitly specified lengths
+ * unlike the ANSI C-like u_strcmp() and u_memcmp() etc.
+ * NUL-terminated strings are possible with length arguments of -1.
+ *
+ * @param s1 First source string.
+ * @param length1 Length of first source string, or -1 if NUL-terminated.
+ *
+ * @param s2 Second source string.
+ * @param length2 Length of second source string, or -1 if NUL-terminated.
+ *
+ * @param codePointOrder Choose between code unit order (FALSE)
+ * and code point order (TRUE).
+ *
+ * @return <0 or 0 or >0 as usual for string comparisons
+ *
+ * @stable ICU 2.2
+ */
+U_STABLE int32_t U_EXPORT2
+u_strCompare(const UChar *s1, int32_t length1,
+ const UChar *s2, int32_t length2,
+ UBool codePointOrder);
+
+/**
+ * Compare two Unicode strings (binary order)
+ * as presented by UCharIterator objects.
+ * Works otherwise just like u_strCompare().
+ *
+ * Both iterators are reset to their start positions.
+ * When the function returns, it is undefined where the iterators
+ * have stopped.
+ *
+ * @param iter1 First source string iterator.
+ * @param iter2 Second source string iterator.
+ * @param codePointOrder Choose between code unit order (FALSE)
+ * and code point order (TRUE).
+ *
+ * @return <0 or 0 or >0 as usual for string comparisons
+ *
+ * @see u_strCompare
+ *
+ * @stable ICU 2.6
+ */
+U_STABLE int32_t U_EXPORT2
+u_strCompareIter(UCharIterator *iter1, UCharIterator *iter2, UBool codePointOrder);
+
+#ifndef U_COMPARE_CODE_POINT_ORDER
+/* see also unistr.h and unorm.h */
+/**
+ * Option bit for u_strCaseCompare, u_strcasecmp, unorm_compare, etc:
+ * Compare strings in code point order instead of code unit order.
+ * @stable ICU 2.2
+ */
+#define U_COMPARE_CODE_POINT_ORDER 0x8000
+#endif
+
+/**
+ * Compare two strings case-insensitively using full case folding.
+ * This is equivalent to
+ * u_strCompare(u_strFoldCase(s1, options),
+ * u_strFoldCase(s2, options),
+ * (options&U_COMPARE_CODE_POINT_ORDER)!=0).
+ *
+ * The comparison can be done in UTF-16 code unit order or in code point order.
+ * They differ only when comparing supplementary code points (U+10000..U+10ffff)
+ * to BMP code points near the end of the BMP (i.e., U+e000..U+ffff).
+ * In code unit order, high BMP code points sort after supplementary code points
+ * because they are stored as pairs of surrogates which are at U+d800..U+dfff.
+ *
+ * This functions works with strings of different explicitly specified lengths
+ * unlike the ANSI C-like u_strcmp() and u_memcmp() etc.
+ * NUL-terminated strings are possible with length arguments of -1.
+ *
+ * @param s1 First source string.
+ * @param length1 Length of first source string, or -1 if NUL-terminated.
+ *
+ * @param s2 Second source string.
+ * @param length2 Length of second source string, or -1 if NUL-terminated.
+ *
+ * @param options A bit set of options:
+ * - U_FOLD_CASE_DEFAULT or 0 is used for default options:
+ * Comparison in code unit order with default case folding.
+ *
+ * - U_COMPARE_CODE_POINT_ORDER
+ * Set to choose code point order instead of code unit order
+ * (see u_strCompare for details).
+ *
+ * - U_FOLD_CASE_EXCLUDE_SPECIAL_I
+ *
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ *
+ * @return <0 or 0 or >0 as usual for string comparisons
+ *
+ * @stable ICU 2.2
+ */
+U_STABLE int32_t U_EXPORT2
+u_strCaseCompare(const UChar *s1, int32_t length1,
+ const UChar *s2, int32_t length2,
+ uint32_t options,
+ UErrorCode *pErrorCode);
+
+/**
+ * Compare two ustrings for bitwise equality.
+ * Compares at most <code>n</code> characters.
+ *
+ * @param ucs1 A string to compare.
+ * @param ucs2 A string to compare.
+ * @param n The maximum number of characters to compare.
+ * @return 0 if <code>s1</code> and <code>s2</code> are bitwise equal; a negative
+ * value if <code>s1</code> is bitwise less than <code>s2</code>; a positive
+ * value if <code>s1</code> is bitwise greater than <code>s2</code>.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strncmp(const UChar *ucs1,
+ const UChar *ucs2,
+ int32_t n);
+
+/**
+ * Compare two Unicode strings in code point order.
+ * This is different in UTF-16 from u_strncmp() if supplementary characters are present.
+ * For details, see u_strCompare().
+ *
+ * @param s1 A string to compare.
+ * @param s2 A string to compare.
+ * @param n The maximum number of characters to compare.
+ * @return a negative/zero/positive integer corresponding to whether
+ * the first string is less than/equal to/greater than the second one
+ * in code point order
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strncmpCodePointOrder(const UChar *s1, const UChar *s2, int32_t n);
+
+/**
+ * Compare two strings case-insensitively using full case folding.
+ * This is equivalent to u_strcmp(u_strFoldCase(s1, options), u_strFoldCase(s2, options)).
+ *
+ * @param s1 A string to compare.
+ * @param s2 A string to compare.
+ * @param options A bit set of options:
+ * - U_FOLD_CASE_DEFAULT or 0 is used for default options:
+ * Comparison in code unit order with default case folding.
+ *
+ * - U_COMPARE_CODE_POINT_ORDER
+ * Set to choose code point order instead of code unit order
+ * (see u_strCompare for details).
+ *
+ * - U_FOLD_CASE_EXCLUDE_SPECIAL_I
+ *
+ * @return A negative, zero, or positive integer indicating the comparison result.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strcasecmp(const UChar *s1, const UChar *s2, uint32_t options);
+
+/**
+ * Compare two strings case-insensitively using full case folding.
+ * This is equivalent to u_strcmp(u_strFoldCase(s1, at most n, options),
+ * u_strFoldCase(s2, at most n, options)).
+ *
+ * @param s1 A string to compare.
+ * @param s2 A string to compare.
+ * @param n The maximum number of characters each string to case-fold and then compare.
+ * @param options A bit set of options:
+ * - U_FOLD_CASE_DEFAULT or 0 is used for default options:
+ * Comparison in code unit order with default case folding.
+ *
+ * - U_COMPARE_CODE_POINT_ORDER
+ * Set to choose code point order instead of code unit order
+ * (see u_strCompare for details).
+ *
+ * - U_FOLD_CASE_EXCLUDE_SPECIAL_I
+ *
+ * @return A negative, zero, or positive integer indicating the comparison result.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strncasecmp(const UChar *s1, const UChar *s2, int32_t n, uint32_t options);
+
+/**
+ * Compare two strings case-insensitively using full case folding.
+ * This is equivalent to u_strcmp(u_strFoldCase(s1, n, options),
+ * u_strFoldCase(s2, n, options)).
+ *
+ * @param s1 A string to compare.
+ * @param s2 A string to compare.
+ * @param length The number of characters in each string to case-fold and then compare.
+ * @param options A bit set of options:
+ * - U_FOLD_CASE_DEFAULT or 0 is used for default options:
+ * Comparison in code unit order with default case folding.
+ *
+ * - U_COMPARE_CODE_POINT_ORDER
+ * Set to choose code point order instead of code unit order
+ * (see u_strCompare for details).
+ *
+ * - U_FOLD_CASE_EXCLUDE_SPECIAL_I
+ *
+ * @return A negative, zero, or positive integer indicating the comparison result.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_memcasecmp(const UChar *s1, const UChar *s2, int32_t length, uint32_t options);
+
+/**
+ * Copy a ustring. Adds a null terminator.
+ *
+ * @param dst The destination string.
+ * @param src The source string.
+ * @return A pointer to <code>dst</code>.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2
+u_strcpy(UChar *dst,
+ const UChar *src);
+
+/**
+ * Copy a ustring.
+ * Copies at most <code>n</code> characters. The result will be null terminated
+ * if the length of <code>src</code> is less than <code>n</code>.
+ *
+ * @param dst The destination string.
+ * @param src The source string.
+ * @param n The maximum number of characters to copy.
+ * @return A pointer to <code>dst</code>.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2
+u_strncpy(UChar *dst,
+ const UChar *src,
+ int32_t n);
+
+#if !UCONFIG_NO_CONVERSION
+
+/**
+ * Copy a byte string encoded in the default codepage to a ustring.
+ * Adds a null terminator.
+ * Performs a host byte to UChar conversion
+ *
+ * @param dst The destination string.
+ * @param src The source string.
+ * @return A pointer to <code>dst</code>.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2 u_uastrcpy(UChar *dst,
+ const char *src );
+
+/**
+ * Copy a byte string encoded in the default codepage to a ustring.
+ * Copies at most <code>n</code> characters. The result will be null terminated
+ * if the length of <code>src</code> is less than <code>n</code>.
+ * Performs a host byte to UChar conversion
+ *
+ * @param dst The destination string.
+ * @param src The source string.
+ * @param n The maximum number of characters to copy.
+ * @return A pointer to <code>dst</code>.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2 u_uastrncpy(UChar *dst,
+ const char *src,
+ int32_t n);
+
+/**
+ * Copy ustring to a byte string encoded in the default codepage.
+ * Adds a null terminator.
+ * Performs a UChar to host byte conversion
+ *
+ * @param dst The destination string.
+ * @param src The source string.
+ * @return A pointer to <code>dst</code>.
+ * @stable ICU 2.0
+ */
+U_STABLE char* U_EXPORT2 u_austrcpy(char *dst,
+ const UChar *src );
+
+/**
+ * Copy ustring to a byte string encoded in the default codepage.
+ * Copies at most <code>n</code> characters. The result will be null terminated
+ * if the length of <code>src</code> is less than <code>n</code>.
+ * Performs a UChar to host byte conversion
+ *
+ * @param dst The destination string.
+ * @param src The source string.
+ * @param n The maximum number of characters to copy.
+ * @return A pointer to <code>dst</code>.
+ * @stable ICU 2.0
+ */
+U_STABLE char* U_EXPORT2 u_austrncpy(char *dst,
+ const UChar *src,
+ int32_t n );
+
+#endif
+
+/**
+ * Synonym for memcpy(), but with UChars only.
+ * @param dest The destination string
+ * @param src The source string
+ * @param count The number of characters to copy
+ * @return A pointer to <code>dest</code>
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2
+u_memcpy(UChar *dest, const UChar *src, int32_t count);
+
+/**
+ * Synonym for memmove(), but with UChars only.
+ * @param dest The destination string
+ * @param src The source string
+ * @param count The number of characters to move
+ * @return A pointer to <code>dest</code>
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2
+u_memmove(UChar *dest, const UChar *src, int32_t count);
+
+/**
+ * Initialize <code>count</code> characters of <code>dest</code> to <code>c</code>.
+ *
+ * @param dest The destination string.
+ * @param c The character to initialize the string.
+ * @param count The maximum number of characters to set.
+ * @return A pointer to <code>dest</code>.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2
+u_memset(UChar *dest, UChar c, int32_t count);
+
+/**
+ * Compare the first <code>count</code> UChars of each buffer.
+ *
+ * @param buf1 The first string to compare.
+ * @param buf2 The second string to compare.
+ * @param count The maximum number of UChars to compare.
+ * @return When buf1 < buf2, a negative number is returned.
+ * When buf1 == buf2, 0 is returned.
+ * When buf1 > buf2, a positive number is returned.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_memcmp(const UChar *buf1, const UChar *buf2, int32_t count);
+
+/**
+ * Compare two Unicode strings in code point order.
+ * This is different in UTF-16 from u_memcmp() if supplementary characters are present.
+ * For details, see u_strCompare().
+ *
+ * @param s1 A string to compare.
+ * @param s2 A string to compare.
+ * @param count The maximum number of characters to compare.
+ * @return a negative/zero/positive integer corresponding to whether
+ * the first string is less than/equal to/greater than the second one
+ * in code point order
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_memcmpCodePointOrder(const UChar *s1, const UChar *s2, int32_t count);
+
+/**
+ * Find the first occurrence of a BMP code point in a string.
+ * A surrogate code point is found only if its match in the text is not
+ * part of a surrogate pair.
+ * A NUL character is found at the string terminator.
+ *
+ * @param s The string to search (contains <code>count</code> UChars).
+ * @param c The BMP code point to find.
+ * @param count The length of the string.
+ * @return A pointer to the first occurrence of <code>c</code> in <code>s</code>
+ * or <code>NULL</code> if <code>c</code> is not in <code>s</code>.
+ * @stable ICU 2.0
+ *
+ * @see u_strchr
+ * @see u_memchr32
+ * @see u_strFindFirst
+ */
+U_STABLE UChar* U_EXPORT2
+u_memchr(const UChar *s, UChar c, int32_t count);
+
+/**
+ * Find the first occurrence of a code point in a string.
+ * A surrogate code point is found only if its match in the text is not
+ * part of a surrogate pair.
+ * A NUL character is found at the string terminator.
+ *
+ * @param s The string to search (contains <code>count</code> UChars).
+ * @param c The code point to find.
+ * @param count The length of the string.
+ * @return A pointer to the first occurrence of <code>c</code> in <code>s</code>
+ * or <code>NULL</code> if <code>c</code> is not in <code>s</code>.
+ * @stable ICU 2.0
+ *
+ * @see u_strchr32
+ * @see u_memchr
+ * @see u_strFindFirst
+ */
+U_STABLE UChar* U_EXPORT2
+u_memchr32(const UChar *s, UChar32 c, int32_t count);
+
+/**
+ * Find the last occurrence of a BMP code point in a string.
+ * A surrogate code point is found only if its match in the text is not
+ * part of a surrogate pair.
+ * A NUL character is found at the string terminator.
+ *
+ * @param s The string to search (contains <code>count</code> UChars).
+ * @param c The BMP code point to find.
+ * @param count The length of the string.
+ * @return A pointer to the last occurrence of <code>c</code> in <code>s</code>
+ * or <code>NULL</code> if <code>c</code> is not in <code>s</code>.
+ * @stable ICU 2.4
+ *
+ * @see u_strrchr
+ * @see u_memrchr32
+ * @see u_strFindLast
+ */
+U_STABLE UChar* U_EXPORT2
+u_memrchr(const UChar *s, UChar c, int32_t count);
+
+/**
+ * Find the last occurrence of a code point in a string.
+ * A surrogate code point is found only if its match in the text is not
+ * part of a surrogate pair.
+ * A NUL character is found at the string terminator.
+ *
+ * @param s The string to search (contains <code>count</code> UChars).
+ * @param c The code point to find.
+ * @param count The length of the string.
+ * @return A pointer to the last occurrence of <code>c</code> in <code>s</code>
+ * or <code>NULL</code> if <code>c</code> is not in <code>s</code>.
+ * @stable ICU 2.4
+ *
+ * @see u_strrchr32
+ * @see u_memrchr
+ * @see u_strFindLast
+ */
+U_STABLE UChar* U_EXPORT2
+u_memrchr32(const UChar *s, UChar32 c, int32_t count);
+
+/**
+ * Unicode String literals in C.
+ * We need one macro to declare a variable for the string
+ * and to statically preinitialize it if possible,
+ * and a second macro to dynamically intialize such a string variable if necessary.
+ *
+ * The macros are defined for maximum performance.
+ * They work only for strings that contain "invariant characters", i.e.,
+ * only latin letters, digits, and some punctuation.
+ * See utypes.h for details.
+ *
+ * A pair of macros for a single string must be used with the same
+ * parameters.
+ * The string parameter must be a C string literal.
+ * The length of the string, not including the terminating
+ * <code>NUL</code>, must be specified as a constant.
+ * The U_STRING_DECL macro should be invoked exactly once for one
+ * such string variable before it is used.
+ *
+ * Usage:
+ * <pre>
+ * &#32; U_STRING_DECL(ustringVar1, "Quick-Fox 2", 11);
+ * &#32; U_STRING_DECL(ustringVar2, "jumps 5%", 8);
+ * &#32; static UBool didInit=FALSE;
+ * &#32;
+ * &#32; int32_t function() {
+ * &#32; if(!didInit) {
+ * &#32; U_STRING_INIT(ustringVar1, "Quick-Fox 2", 11);
+ * &#32; U_STRING_INIT(ustringVar2, "jumps 5%", 8);
+ * &#32; didInit=TRUE;
+ * &#32; }
+ * &#32; return u_strcmp(ustringVar1, ustringVar2);
+ * &#32; }
+ * </pre>
+ * @stable ICU 2.0
+ */
+#if U_SIZEOF_WCHAR_T==U_SIZEOF_UCHAR && U_CHARSET_FAMILY==U_ASCII_FAMILY
+# define U_STRING_DECL(var, cs, length) static const wchar_t var[(length)+1]={ L ## cs }
+ /**@stable ICU 2.0 */
+# define U_STRING_INIT(var, cs, length)
+#elif U_SIZEOF_UCHAR==1 && U_CHARSET_FAMILY==U_ASCII_FAMILY
+# define U_STRING_DECL(var, cs, length) static const UChar var[(length)+1]={ (const UChar *)cs }
+ /**@stable ICU 2.0 */
+# define U_STRING_INIT(var, cs, length)
+#else
+# define U_STRING_DECL(var, cs, length) static UChar var[(length)+1]
+ /**@stable ICU 2.0 */
+# define U_STRING_INIT(var, cs, length) u_charsToUChars(cs, var, length+1)
+#endif
+
+/**
+ * Unescape a string of characters and write the resulting
+ * Unicode characters to the destination buffer. The following escape
+ * sequences are recognized:
+ *
+ * \\uhhhh 4 hex digits; h in [0-9A-Fa-f]
+ * \\Uhhhhhhhh 8 hex digits
+ * \\xhh 1-2 hex digits
+ * \\x{h...} 1-8 hex digits
+ * \\ooo 1-3 octal digits; o in [0-7]
+ * \\cX control-X; X is masked with 0x1F
+ *
+ * as well as the standard ANSI C escapes:
+ *
+ * \\a => U+0007, \\b => U+0008, \\t => U+0009, \\n => U+000A,
+ * \\v => U+000B, \\f => U+000C, \\r => U+000D, \\e => U+001B,
+ * \\" => U+0022, \\' => U+0027, \\? => U+003F, \\\\ => U+005C
+ *
+ * Anything else following a backslash is generically escaped. For
+ * example, "[a\\-z]" returns "[a-z]".
+ *
+ * If an escape sequence is ill-formed, this method returns an empty
+ * string. An example of an ill-formed sequence is "\\u" followed by
+ * fewer than 4 hex digits.
+ *
+ * The above characters are recognized in the compiler's codepage,
+ * that is, they are coded as 'u', '\\', etc. Characters that are
+ * not parts of escape sequences are converted using u_charsToUChars().
+ *
+ * This function is similar to UnicodeString::unescape() but not
+ * identical to it. The latter takes a source UnicodeString, so it
+ * does escape recognition but no conversion.
+ *
+ * @param src a zero-terminated string of invariant characters
+ * @param dest pointer to buffer to receive converted and unescaped
+ * text and, if there is room, a zero terminator. May be NULL for
+ * preflighting, in which case no UChars will be written, but the
+ * return value will still be valid. On error, an empty string is
+ * stored here (if possible).
+ * @param destCapacity the number of UChars that may be written at
+ * dest. Ignored if dest == NULL.
+ * @return the length of unescaped string.
+ * @see u_unescapeAt
+ * @see UnicodeString#unescape()
+ * @see UnicodeString#unescapeAt()
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_unescape(const char *src,
+ UChar *dest, int32_t destCapacity);
+
+U_CDECL_BEGIN
+/**
+ * Callback function for u_unescapeAt() that returns a character of
+ * the source text given an offset and a context pointer. The context
+ * pointer will be whatever is passed into u_unescapeAt().
+ *
+ * @param offset pointer to the offset that will be passed to u_unescapeAt().
+ * @param context an opaque pointer passed directly into u_unescapeAt()
+ * @return the character represented by the escape sequence at
+ * offset
+ * @see u_unescapeAt
+ * @stable ICU 2.0
+ */
+typedef UChar (U_CALLCONV *UNESCAPE_CHAR_AT)(int32_t offset, void *context);
+U_CDECL_END
+
+/**
+ * Unescape a single sequence. The character at offset-1 is assumed
+ * (without checking) to be a backslash. This method takes a callback
+ * pointer to a function that returns the UChar at a given offset. By
+ * varying this callback, ICU functions are able to unescape char*
+ * strings, UnicodeString objects, and UFILE pointers.
+ *
+ * If offset is out of range, or if the escape sequence is ill-formed,
+ * (UChar32)0xFFFFFFFF is returned. See documentation of u_unescape()
+ * for a list of recognized sequences.
+ *
+ * @param charAt callback function that returns a UChar of the source
+ * text given an offset and a context pointer.
+ * @param offset pointer to the offset that will be passed to charAt.
+ * The offset value will be updated upon return to point after the
+ * last parsed character of the escape sequence. On error the offset
+ * is unchanged.
+ * @param length the number of characters in the source text. The
+ * last character of the source text is considered to be at offset
+ * length-1.
+ * @param context an opaque pointer passed directly into charAt.
+ * @return the character represented by the escape sequence at
+ * offset, or (UChar32)0xFFFFFFFF on error.
+ * @see u_unescape()
+ * @see UnicodeString#unescape()
+ * @see UnicodeString#unescapeAt()
+ * @stable ICU 2.0
+ */
+U_STABLE UChar32 U_EXPORT2
+u_unescapeAt(UNESCAPE_CHAR_AT charAt,
+ int32_t *offset,
+ int32_t length,
+ void *context);
+
+/**
+ * Uppercase the characters in a string.
+ * Casing is locale-dependent and context-sensitive.
+ * The result may be longer or shorter than the original.
+ * The source string and the destination buffer are allowed to overlap.
+ *
+ * @param dest A buffer for the result string. The result will be zero-terminated if
+ * the buffer is large enough.
+ * @param destCapacity The size of the buffer (number of UChars). If it is 0, then
+ * dest may be NULL and the function will only return the length of the result
+ * without writing any of the result string.
+ * @param src The original string
+ * @param srcLength The length of the original string. If -1, then src must be zero-terminated.
+ * @param locale The locale to consider, or "" for the root locale or NULL for the default locale.
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ * @return The length of the result string. It may be greater than destCapacity. In that case,
+ * only some of the result was written to the destination buffer.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strToUpper(UChar *dest, int32_t destCapacity,
+ const UChar *src, int32_t srcLength,
+ const char *locale,
+ UErrorCode *pErrorCode);
+
+/**
+ * Lowercase the characters in a string.
+ * Casing is locale-dependent and context-sensitive.
+ * The result may be longer or shorter than the original.
+ * The source string and the destination buffer are allowed to overlap.
+ *
+ * @param dest A buffer for the result string. The result will be zero-terminated if
+ * the buffer is large enough.
+ * @param destCapacity The size of the buffer (number of UChars). If it is 0, then
+ * dest may be NULL and the function will only return the length of the result
+ * without writing any of the result string.
+ * @param src The original string
+ * @param srcLength The length of the original string. If -1, then src must be zero-terminated.
+ * @param locale The locale to consider, or "" for the root locale or NULL for the default locale.
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ * @return The length of the result string. It may be greater than destCapacity. In that case,
+ * only some of the result was written to the destination buffer.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strToLower(UChar *dest, int32_t destCapacity,
+ const UChar *src, int32_t srcLength,
+ const char *locale,
+ UErrorCode *pErrorCode);
+
+#if !UCONFIG_NO_BREAK_ITERATION
+
+/**
+ * Titlecase a string.
+ * Casing is locale-dependent and context-sensitive.
+ * Titlecasing uses a break iterator to find the first characters of words
+ * that are to be titlecased. It titlecases those characters and lowercases
+ * all others.
+ *
+ * The titlecase break iterator can be provided to customize for arbitrary
+ * styles, using rules and dictionaries beyond the standard iterators.
+ * It may be more efficient to always provide an iterator to avoid
+ * opening and closing one for each string.
+ * The standard titlecase iterator for the root locale implements the
+ * algorithm of Unicode TR 21.
+ *
+ * This function uses only the first() and next() methods of the
+ * provided break iterator.
+ *
+ * The result may be longer or shorter than the original.
+ * The source string and the destination buffer are allowed to overlap.
+ *
+ * @param dest A buffer for the result string. The result will be zero-terminated if
+ * the buffer is large enough.
+ * @param destCapacity The size of the buffer (number of UChars). If it is 0, then
+ * dest may be NULL and the function will only return the length of the result
+ * without writing any of the result string.
+ * @param src The original string
+ * @param srcLength The length of the original string. If -1, then src must be zero-terminated.
+ * @param titleIter A break iterator to find the first characters of words
+ * that are to be titlecased.
+ * If none is provided (NULL), then a standard titlecase
+ * break iterator is opened.
+ * @param locale The locale to consider, or "" for the root locale or NULL for the default locale.
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ * @return The length of the result string. It may be greater than destCapacity. In that case,
+ * only some of the result was written to the destination buffer.
+ * @stable ICU 2.1
+ */
+U_STABLE int32_t U_EXPORT2
+u_strToTitle(UChar *dest, int32_t destCapacity,
+ const UChar *src, int32_t srcLength,
+ UBreakIterator *titleIter,
+ const char *locale,
+ UErrorCode *pErrorCode);
+
+#endif
+
+/**
+ * Case-fold the characters in a string.
+ * Case-folding is locale-independent and not context-sensitive,
+ * but there is an option for whether to include or exclude mappings for dotted I
+ * and dotless i that are marked with 'I' in CaseFolding.txt.
+ * The result may be longer or shorter than the original.
+ * The source string and the destination buffer are allowed to overlap.
+ *
+ * @param dest A buffer for the result string. The result will be zero-terminated if
+ * the buffer is large enough.
+ * @param destCapacity The size of the buffer (number of UChars). If it is 0, then
+ * dest may be NULL and the function will only return the length of the result
+ * without writing any of the result string.
+ * @param src The original string
+ * @param srcLength The length of the original string. If -1, then src must be zero-terminated.
+ * @param options Either U_FOLD_CASE_DEFAULT or U_FOLD_CASE_EXCLUDE_SPECIAL_I
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ * @return The length of the result string. It may be greater than destCapacity. In that case,
+ * only some of the result was written to the destination buffer.
+ * @stable ICU 2.0
+ */
+U_STABLE int32_t U_EXPORT2
+u_strFoldCase(UChar *dest, int32_t destCapacity,
+ const UChar *src, int32_t srcLength,
+ uint32_t options,
+ UErrorCode *pErrorCode);
+
+/**
+ * Converts a sequence of UChars to wchar_t units.
+ *
+ * @param dest A buffer for the result string. The result will be zero-terminated if
+ * the buffer is large enough.
+ * @param destCapacity The size of the buffer (number of wchar_t's). If it is 0, then
+ * dest may be NULL and the function will only return the length of the
+ * result without writing any of the result string (pre-flighting).
+ * @param pDestLength A pointer to receive the number of units written to the destination. If
+ * pDestLength!=NULL then *pDestLength is always set to the
+ * number of output units corresponding to the transformation of
+ * all the input units, even in case of a buffer overflow.
+ * @param src The original source string
+ * @param srcLength The length of the original string. If -1, then src must be zero-terminated.
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ * @return The pointer to destination buffer.
+ * @stable ICU 2.0
+ */
+U_STABLE wchar_t* U_EXPORT2
+u_strToWCS(wchar_t *dest,
+ int32_t destCapacity,
+ int32_t *pDestLength,
+ const UChar *src,
+ int32_t srcLength,
+ UErrorCode *pErrorCode);
+/**
+ * Converts a sequence of wchar_t units to UChars
+ *
+ * @param dest A buffer for the result string. The result will be zero-terminated if
+ * the buffer is large enough.
+ * @param destCapacity The size of the buffer (number of UChars). If it is 0, then
+ * dest may be NULL and the function will only return the length of the
+ * result without writing any of the result string (pre-flighting).
+ * @param pDestLength A pointer to receive the number of units written to the destination. If
+ * pDestLength!=NULL then *pDestLength is always set to the
+ * number of output units corresponding to the transformation of
+ * all the input units, even in case of a buffer overflow.
+ * @param src The original source string
+ * @param srcLength The length of the original string. If -1, then src must be zero-terminated.
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ * @return The pointer to destination buffer.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2
+u_strFromWCS(UChar *dest,
+ int32_t destCapacity,
+ int32_t *pDestLength,
+ const wchar_t *src,
+ int32_t srcLength,
+ UErrorCode *pErrorCode);
+/**
+ * Converts a sequence of UChars (UTF-16) to UTF-8 bytes
+ *
+ * @param dest A buffer for the result string. The result will be zero-terminated if
+ * the buffer is large enough.
+ * @param destCapacity The size of the buffer (number of chars). If it is 0, then
+ * dest may be NULL and the function will only return the length of the
+ * result without writing any of the result string (pre-flighting).
+ * @param pDestLength A pointer to receive the number of units written to the destination. If
+ * pDestLength!=NULL then *pDestLength is always set to the
+ * number of output units corresponding to the transformation of
+ * all the input units, even in case of a buffer overflow.
+ * @param src The original source string
+ * @param srcLength The length of the original string. If -1, then src must be zero-terminated.
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ * @return The pointer to destination buffer.
+ * @stable ICU 2.0
+ */
+U_STABLE char* U_EXPORT2
+u_strToUTF8(char *dest,
+ int32_t destCapacity,
+ int32_t *pDestLength,
+ const UChar *src,
+ int32_t srcLength,
+ UErrorCode *pErrorCode);
+
+/**
+ * Converts a sequence of UTF-8 bytes to UChars (UTF-16).
+ *
+ * @param dest A buffer for the result string. The result will be zero-terminated if
+ * the buffer is large enough.
+ * @param destCapacity The size of the buffer (number of UChars). If it is 0, then
+ * dest may be NULL and the function will only return the length of the
+ * result without writing any of the result string (pre-flighting).
+ * @param pDestLength A pointer to receive the number of units written to the destination. If
+ * pDestLength!=NULL then *pDestLength is always set to the
+ * number of output units corresponding to the transformation of
+ * all the input units, even in case of a buffer overflow.
+ * @param src The original source string
+ * @param srcLength The length of the original string. If -1, then src must be zero-terminated.
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ * @return The pointer to destination buffer.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2
+u_strFromUTF8(UChar *dest,
+ int32_t destCapacity,
+ int32_t *pDestLength,
+ const char *src,
+ int32_t srcLength,
+ UErrorCode *pErrorCode);
+
+/**
+ * Converts a sequence of UChars (UTF-16) to UTF32 units.
+ *
+ * @param dest A buffer for the result string. The result will be zero-terminated if
+ * the buffer is large enough.
+ * @param destCapacity The size of the buffer (number of UChar32s). If it is 0, then
+ * dest may be NULL and the function will only return the length of the
+ * result without writing any of the result string (pre-flighting).
+ * @param pDestLength A pointer to receive the number of units written to the destination. If
+ * pDestLength!=NULL then *pDestLength is always set to the
+ * number of output units corresponding to the transformation of
+ * all the input units, even in case of a buffer overflow.
+ * @param src The original source string
+ * @param srcLength The length of the original string. If -1, then src must be zero-terminated.
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ * @return The pointer to destination buffer.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar32* U_EXPORT2
+u_strToUTF32(UChar32 *dest,
+ int32_t destCapacity,
+ int32_t *pDestLength,
+ const UChar *src,
+ int32_t srcLength,
+ UErrorCode *pErrorCode);
+
+/**
+ * Converts a sequence of UTF32 units to UChars (UTF-16)
+ *
+ * @param dest A buffer for the result string. The result will be zero-terminated if
+ * the buffer is large enough.
+ * @param destCapacity The size of the buffer (number of UChars). If it is 0, then
+ * dest may be NULL and the function will only return the length of the
+ * result without writing any of the result string (pre-flighting).
+ * @param pDestLength A pointer to receive the number of units written to the destination. If
+ * pDestLength!=NULL then *pDestLength is always set to the
+ * number of output units corresponding to the transformation of
+ * all the input units, even in case of a buffer overflow.
+ * @param src The original source string
+ * @param srcLength The length of the original string. If -1, then src must be zero-terminated.
+ * @param pErrorCode Must be a valid pointer to an error code value,
+ * which must not indicate a failure before the function call.
+ * @return The pointer to destination buffer.
+ * @stable ICU 2.0
+ */
+U_STABLE UChar* U_EXPORT2
+u_strFromUTF32(UChar *dest,
+ int32_t destCapacity,
+ int32_t *pDestLength,
+ const UChar32 *src,
+ int32_t srcLength,
+ UErrorCode *pErrorCode);
+
+#endif
diff --git a/WebKit/mac/icu/unicode/utf.h b/WebKit/mac/icu/unicode/utf.h
new file mode 100644
index 0000000..201691d
--- /dev/null
+++ b/WebKit/mac/icu/unicode/utf.h
@@ -0,0 +1,221 @@
+/*
+*******************************************************************************
+*
+* Copyright (C) 1999-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+*
+*******************************************************************************
+* file name: utf.h
+* encoding: US-ASCII
+* tab size: 8 (not used)
+* indentation:4
+*
+* created on: 1999sep09
+* created by: Markus W. Scherer
+*/
+
+/**
+ * \file
+ * \brief C API: Code point macros
+ *
+ * This file defines macros for checking whether a code point is
+ * a surrogate or a non-character etc.
+ *
+ * The UChar and UChar32 data types for Unicode code units and code points
+ * are defined in umachines.h because they can be machine-dependent.
+ *
+ * utf.h is included by utypes.h and itself includes utf8.h and utf16.h after some
+ * common definitions. Those files define macros for efficiently getting code points
+ * in and out of UTF-8/16 strings.
+ * utf16.h macros have "U16_" prefixes.
+ * utf8.h defines similar macros with "U8_" prefixes for UTF-8 string handling.
+ *
+ * ICU processes 16-bit Unicode strings.
+ * Most of the time, such strings are well-formed UTF-16.
+ * Single, unpaired surrogates must be handled as well, and are treated in ICU
+ * like regular code points where possible.
+ * (Pairs of surrogate code points are indistinguishable from supplementary
+ * code points encoded as pairs of supplementary code units.)
+ *
+ * In fact, almost all Unicode code points in normal text (>99%)
+ * are on the BMP (<=U+ffff) and even <=U+d7ff.
+ * ICU functions handle supplementary code points (U+10000..U+10ffff)
+ * but are optimized for the much more frequently occurring BMP code points.
+ *
+ * utf.h defines UChar to be an unsigned 16-bit integer. If this matches wchar_t, then
+ * UChar is defined to be exactly wchar_t, otherwise uint16_t.
+ *
+ * UChar32 is defined to be a signed 32-bit integer (int32_t), large enough for a 21-bit
+ * Unicode code point (Unicode scalar value, 0..0x10ffff).
+ * Before ICU 2.4, the definition of UChar32 was similarly platform-dependent as
+ * the definition of UChar. For details see the documentation for UChar32 itself.
+ *
+ * utf.h also defines a small number of C macros for single Unicode code points.
+ * These are simple checks for surrogates and non-characters.
+ * For actual Unicode character properties see uchar.h.
+ *
+ * By default, string operations must be done with error checking in case
+ * a string is not well-formed UTF-16.
+ * The macros will detect if a surrogate code unit is unpaired
+ * (lead unit without trail unit or vice versa) and just return the unit itself
+ * as the code point.
+ * (It is an accidental property of Unicode and UTF-16 that all
+ * malformed sequences can be expressed unambiguously with a distinct subrange
+ * of Unicode code points.)
+ *
+ * When it is safe to assume that text is well-formed UTF-16
+ * (does not contain single, unpaired surrogates), then one can use
+ * U16_..._UNSAFE macros.
+ * These do not check for proper code unit sequences or truncated text and may
+ * yield wrong results or even cause a crash if they are used with "malformed"
+ * text.
+ * In practice, U16_..._UNSAFE macros will produce slightly less code but
+ * should not be faster because the processing is only different when a
+ * surrogate code unit is detected, which will be rare.
+ *
+ * Similarly for UTF-8, there are "safe" macros without a suffix,
+ * and U8_..._UNSAFE versions.
+ * The performance differences are much larger here because UTF-8 provides so
+ * many opportunities for malformed sequences.
+ * The unsafe UTF-8 macros are entirely implemented inside the macro definitions
+ * and are fast, while the safe UTF-8 macros call functions for all but the
+ * trivial (ASCII) cases.
+ *
+ * Unlike with UTF-16, malformed sequences cannot be expressed with distinct
+ * code point values (0..U+10ffff). They are indicated with negative values instead.
+ *
+ * For more information see the ICU User Guide Strings chapter
+ * (http://oss.software.ibm.com/icu/userguide/).
+ *
+ * <em>Usage:</em>
+ * ICU coding guidelines for if() statements should be followed when using these macros.
+ * Compound statements (curly braces {}) must be used for if-else-while...
+ * bodies and all macro statements should be terminated with semicolon.
+ *
+ * @stable ICU 2.4
+ */
+
+#ifndef __UTF_H__
+#define __UTF_H__
+
+#include "unicode/utypes.h"
+/* include the utfXX.h after the following definitions */
+
+/* single-code point definitions -------------------------------------------- */
+
+/**
+ * This value is intended for sentinel values for APIs that
+ * (take or) return single code points (UChar32).
+ * It is outside of the Unicode code point range 0..0x10ffff.
+ *
+ * For example, a "done" or "error" value in a new API
+ * could be indicated with U_SENTINEL.
+ *
+ * ICU APIs designed before ICU 2.4 usually define service-specific "done"
+ * values, mostly 0xffff.
+ * Those may need to be distinguished from
+ * actual U+ffff text contents by calling functions like
+ * CharacterIterator::hasNext() or UnicodeString::length().
+ *
+ * @return -1
+ * @see UChar32
+ * @stable ICU 2.4
+ */
+#define U_SENTINEL (-1)
+
+/**
+ * Is this code point a Unicode noncharacter?
+ * @param c 32-bit code point
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U_IS_UNICODE_NONCHAR(c) \
+ ((c)>=0xfdd0 && \
+ ((uint32_t)(c)<=0xfdef || ((c)&0xfffe)==0xfffe) && \
+ (uint32_t)(c)<=0x10ffff)
+
+/**
+ * Is c a Unicode code point value (0..U+10ffff)
+ * that can be assigned a character?
+ *
+ * Code points that are not characters include:
+ * - single surrogate code points (U+d800..U+dfff, 2048 code points)
+ * - the last two code points on each plane (U+__fffe and U+__ffff, 34 code points)
+ * - U+fdd0..U+fdef (new with Unicode 3.1, 32 code points)
+ * - the highest Unicode code point value is U+10ffff
+ *
+ * This means that all code points below U+d800 are character code points,
+ * and that boundary is tested first for performance.
+ *
+ * @param c 32-bit code point
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U_IS_UNICODE_CHAR(c) \
+ ((uint32_t)(c)<0xd800 || \
+ ((uint32_t)(c)>0xdfff && \
+ (uint32_t)(c)<=0x10ffff && \
+ !U_IS_UNICODE_NONCHAR(c)))
+
+#ifndef U_HIDE_DRAFT_API
+
+/**
+ * Is this code point a BMP code point (U+0000..U+ffff)?
+ * @param c 32-bit code point
+ * @return TRUE or FALSE
+ * @draft ICU 2.8
+ */
+#define U_IS_BMP(c) ((uint32_t)(c)<=0xffff)
+
+/**
+ * Is this code point a supplementary code point (U+10000..U+10ffff)?
+ * @param c 32-bit code point
+ * @return TRUE or FALSE
+ * @draft ICU 2.8
+ */
+#define U_IS_SUPPLEMENTARY(c) ((uint32_t)((c)-0x10000)<=0xfffff)
+
+#endif /*U_HIDE_DRAFT_API*/
+
+/**
+ * Is this code point a lead surrogate (U+d800..U+dbff)?
+ * @param c 32-bit code point
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U_IS_LEAD(c) (((c)&0xfffffc00)==0xd800)
+
+/**
+ * Is this code point a trail surrogate (U+dc00..U+dfff)?
+ * @param c 32-bit code point
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U_IS_TRAIL(c) (((c)&0xfffffc00)==0xdc00)
+
+/**
+ * Is this code point a surrogate (U+d800..U+dfff)?
+ * @param c 32-bit code point
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U_IS_SURROGATE(c) (((c)&0xfffff800)==0xd800)
+
+/**
+ * Assuming c is a surrogate code point (U_IS_SURROGATE(c)),
+ * is it a lead surrogate?
+ * @param c 32-bit code point
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U_IS_SURROGATE_LEAD(c) (((c)&0x400)==0)
+
+/* include the utfXX.h ------------------------------------------------------ */
+
+#include "unicode/utf8.h"
+#include "unicode/utf16.h"
+
+/* utf_old.h contains deprecated, pre-ICU 2.4 definitions */
+#include "unicode/utf_old.h"
+
+#endif
diff --git a/WebKit/mac/icu/unicode/utf16.h b/WebKit/mac/icu/unicode/utf16.h
new file mode 100644
index 0000000..7bf3872
--- /dev/null
+++ b/WebKit/mac/icu/unicode/utf16.h
@@ -0,0 +1,605 @@
+/*
+*******************************************************************************
+*
+* Copyright (C) 1999-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+*
+*******************************************************************************
+* file name: utf16.h
+* encoding: US-ASCII
+* tab size: 8 (not used)
+* indentation:4
+*
+* created on: 1999sep09
+* created by: Markus W. Scherer
+*/
+
+/**
+ * \file
+ * \brief C API: 16-bit Unicode handling macros
+ *
+ * This file defines macros to deal with 16-bit Unicode (UTF-16) code units and strings.
+ * utf16.h is included by utf.h after unicode/umachine.h
+ * and some common definitions.
+ *
+ * For more information see utf.h and the ICU User Guide Strings chapter
+ * (http://oss.software.ibm.com/icu/userguide/).
+ *
+ * <em>Usage:</em>
+ * ICU coding guidelines for if() statements should be followed when using these macros.
+ * Compound statements (curly braces {}) must be used for if-else-while...
+ * bodies and all macro statements should be terminated with semicolon.
+ */
+
+#ifndef __UTF16_H__
+#define __UTF16_H__
+
+/* utf.h must be included first. */
+#ifndef __UTF_H__
+# include "unicode/utf.h"
+#endif
+
+/* single-code point definitions -------------------------------------------- */
+
+/**
+ * Does this code unit alone encode a code point (BMP, not a surrogate)?
+ * @param c 16-bit code unit
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U16_IS_SINGLE(c) !U_IS_SURROGATE(c)
+
+/**
+ * Is this code unit a lead surrogate (U+d800..U+dbff)?
+ * @param c 16-bit code unit
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U16_IS_LEAD(c) (((c)&0xfffffc00)==0xd800)
+
+/**
+ * Is this code unit a trail surrogate (U+dc00..U+dfff)?
+ * @param c 16-bit code unit
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U16_IS_TRAIL(c) (((c)&0xfffffc00)==0xdc00)
+
+/**
+ * Is this code unit a surrogate (U+d800..U+dfff)?
+ * @param c 16-bit code unit
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U16_IS_SURROGATE(c) U_IS_SURROGATE(c)
+
+/**
+ * Assuming c is a surrogate code point (U16_IS_SURROGATE(c)),
+ * is it a lead surrogate?
+ * @param c 16-bit code unit
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U16_IS_SURROGATE_LEAD(c) (((c)&0x400)==0)
+
+/**
+ * Helper constant for U16_GET_SUPPLEMENTARY.
+ * @internal
+ */
+#define U16_SURROGATE_OFFSET ((0xd800<<10UL)+0xdc00-0x10000)
+
+/**
+ * Get a supplementary code point value (U+10000..U+10ffff)
+ * from its lead and trail surrogates.
+ * The result is undefined if the input values are not
+ * lead and trail surrogates.
+ *
+ * @param lead lead surrogate (U+d800..U+dbff)
+ * @param trail trail surrogate (U+dc00..U+dfff)
+ * @return supplementary code point (U+10000..U+10ffff)
+ * @stable ICU 2.4
+ */
+#define U16_GET_SUPPLEMENTARY(lead, trail) \
+ (((UChar32)(lead)<<10UL)+(UChar32)(trail)-U16_SURROGATE_OFFSET)
+
+
+/**
+ * Get the lead surrogate (0xd800..0xdbff) for a
+ * supplementary code point (0x10000..0x10ffff).
+ * @param supplementary 32-bit code point (U+10000..U+10ffff)
+ * @return lead surrogate (U+d800..U+dbff) for supplementary
+ * @stable ICU 2.4
+ */
+#define U16_LEAD(supplementary) (UChar)(((supplementary)>>10)+0xd7c0)
+
+/**
+ * Get the trail surrogate (0xdc00..0xdfff) for a
+ * supplementary code point (0x10000..0x10ffff).
+ * @param supplementary 32-bit code point (U+10000..U+10ffff)
+ * @return trail surrogate (U+dc00..U+dfff) for supplementary
+ * @stable ICU 2.4
+ */
+#define U16_TRAIL(supplementary) (UChar)(((supplementary)&0x3ff)|0xdc00)
+
+/**
+ * How many 16-bit code units are used to encode this Unicode code point? (1 or 2)
+ * The result is not defined if c is not a Unicode code point (U+0000..U+10ffff).
+ * @param c 32-bit code point
+ * @return 1 or 2
+ * @stable ICU 2.4
+ */
+#define U16_LENGTH(c) ((uint32_t)(c)<=0xffff ? 1 : 2)
+
+/**
+ * The maximum number of 16-bit code units per Unicode code point (U+0000..U+10ffff).
+ * @return 2
+ * @stable ICU 2.4
+ */
+#define U16_MAX_LENGTH 2
+
+/**
+ * Get a code point from a string at a random-access offset,
+ * without changing the offset.
+ * "Unsafe" macro, assumes well-formed UTF-16.
+ *
+ * The offset may point to either the lead or trail surrogate unit
+ * for a supplementary code point, in which case the macro will read
+ * the adjacent matching surrogate as well.
+ * The result is undefined if the offset points to a single, unpaired surrogate.
+ * Iteration through a string is more efficient with U16_NEXT_UNSAFE or U16_NEXT.
+ *
+ * @param s const UChar * string
+ * @param i string offset
+ * @param c output UChar32 variable
+ * @see U16_GET
+ * @stable ICU 2.4
+ */
+#define U16_GET_UNSAFE(s, i, c) { \
+ (c)=(s)[i]; \
+ if(U16_IS_SURROGATE(c)) { \
+ if(U16_IS_SURROGATE_LEAD(c)) { \
+ (c)=U16_GET_SUPPLEMENTARY((c), (s)[(i)+1]); \
+ } else { \
+ (c)=U16_GET_SUPPLEMENTARY((s)[(i)-1], (c)); \
+ } \
+ } \
+}
+
+/**
+ * Get a code point from a string at a random-access offset,
+ * without changing the offset.
+ * "Safe" macro, handles unpaired surrogates and checks for string boundaries.
+ *
+ * The offset may point to either the lead or trail surrogate unit
+ * for a supplementary code point, in which case the macro will read
+ * the adjacent matching surrogate as well.
+ * If the offset points to a single, unpaired surrogate, then that itself
+ * will be returned as the code point.
+ * Iteration through a string is more efficient with U16_NEXT_UNSAFE or U16_NEXT.
+ *
+ * @param s const UChar * string
+ * @param start starting string offset (usually 0)
+ * @param i string offset, start<=i<length
+ * @param length string length
+ * @param c output UChar32 variable
+ * @see U16_GET_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U16_GET(s, start, i, length, c) { \
+ (c)=(s)[i]; \
+ if(U16_IS_SURROGATE(c)) { \
+ uint16_t __c2; \
+ if(U16_IS_SURROGATE_LEAD(c)) { \
+ if((i)+1<(length) && U16_IS_TRAIL(__c2=(s)[(i)+1])) { \
+ (c)=U16_GET_SUPPLEMENTARY((c), __c2); \
+ } \
+ } else { \
+ if((i)-1>=(start) && U16_IS_LEAD(__c2=(s)[(i)-1])) { \
+ (c)=U16_GET_SUPPLEMENTARY(__c2, (c)); \
+ } \
+ } \
+ } \
+}
+
+/* definitions with forward iteration --------------------------------------- */
+
+/**
+ * Get a code point from a string at a code point boundary offset,
+ * and advance the offset to the next code point boundary.
+ * (Post-incrementing forward iteration.)
+ * "Unsafe" macro, assumes well-formed UTF-16.
+ *
+ * The offset may point to the lead surrogate unit
+ * for a supplementary code point, in which case the macro will read
+ * the following trail surrogate as well.
+ * If the offset points to a trail surrogate, then that itself
+ * will be returned as the code point.
+ * The result is undefined if the offset points to a single, unpaired lead surrogate.
+ *
+ * @param s const UChar * string
+ * @param i string offset
+ * @param c output UChar32 variable
+ * @see U16_NEXT
+ * @stable ICU 2.4
+ */
+#define U16_NEXT_UNSAFE(s, i, c) { \
+ (c)=(s)[(i)++]; \
+ if(U16_IS_LEAD(c)) { \
+ (c)=U16_GET_SUPPLEMENTARY((c), (s)[(i)++]); \
+ } \
+}
+
+/**
+ * Get a code point from a string at a code point boundary offset,
+ * and advance the offset to the next code point boundary.
+ * (Post-incrementing forward iteration.)
+ * "Safe" macro, handles unpaired surrogates and checks for string boundaries.
+ *
+ * The offset may point to the lead surrogate unit
+ * for a supplementary code point, in which case the macro will read
+ * the following trail surrogate as well.
+ * If the offset points to a trail surrogate or
+ * to a single, unpaired lead surrogate, then that itself
+ * will be returned as the code point.
+ *
+ * @param s const UChar * string
+ * @param i string offset, i<length
+ * @param length string length
+ * @param c output UChar32 variable
+ * @see U16_NEXT_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U16_NEXT(s, i, length, c) { \
+ (c)=(s)[(i)++]; \
+ if(U16_IS_LEAD(c)) { \
+ uint16_t __c2; \
+ if((i)<(length) && U16_IS_TRAIL(__c2=(s)[(i)])) { \
+ ++(i); \
+ (c)=U16_GET_SUPPLEMENTARY((c), __c2); \
+ } \
+ } \
+}
+
+/**
+ * Append a code point to a string, overwriting 1 or 2 code units.
+ * The offset points to the current end of the string contents
+ * and is advanced (post-increment).
+ * "Unsafe" macro, assumes a valid code point and sufficient space in the string.
+ * Otherwise, the result is undefined.
+ *
+ * @param s const UChar * string buffer
+ * @param i string offset
+ * @param c code point to append
+ * @see U16_APPEND
+ * @stable ICU 2.4
+ */
+#define U16_APPEND_UNSAFE(s, i, c) { \
+ if((uint32_t)(c)<=0xffff) { \
+ (s)[(i)++]=(uint16_t)(c); \
+ } else { \
+ (s)[(i)++]=(uint16_t)(((c)>>10)+0xd7c0); \
+ (s)[(i)++]=(uint16_t)(((c)&0x3ff)|0xdc00); \
+ } \
+}
+
+/**
+ * Append a code point to a string, overwriting 1 or 2 code units.
+ * The offset points to the current end of the string contents
+ * and is advanced (post-increment).
+ * "Safe" macro, checks for a valid code point.
+ * If a surrogate pair is written, checks for sufficient space in the string.
+ * If the code point is not valid or a trail surrogate does not fit,
+ * then isError is set to TRUE.
+ *
+ * @param s const UChar * string buffer
+ * @param i string offset, i<length
+ * @param capacity size of the string buffer
+ * @param c code point to append
+ * @param isError output UBool set to TRUE if an error occurs, otherwise not modified
+ * @see U16_APPEND_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U16_APPEND(s, i, capacity, c, isError) { \
+ if((uint32_t)(c)<=0xffff) { \
+ (s)[(i)++]=(uint16_t)(c); \
+ } else if((uint32_t)(c)<=0x10ffff && (i)+1<(capacity)) { \
+ (s)[(i)++]=(uint16_t)(((c)>>10)+0xd7c0); \
+ (s)[(i)++]=(uint16_t)(((c)&0x3ff)|0xdc00); \
+ } else /* c>0x10ffff or not enough space */ { \
+ (isError)=TRUE; \
+ } \
+}
+
+/**
+ * Advance the string offset from one code point boundary to the next.
+ * (Post-incrementing iteration.)
+ * "Unsafe" macro, assumes well-formed UTF-16.
+ *
+ * @param s const UChar * string
+ * @param i string offset
+ * @see U16_FWD_1
+ * @stable ICU 2.4
+ */
+#define U16_FWD_1_UNSAFE(s, i) { \
+ if(U16_IS_LEAD((s)[(i)++])) { \
+ ++(i); \
+ } \
+}
+
+/**
+ * Advance the string offset from one code point boundary to the next.
+ * (Post-incrementing iteration.)
+ * "Safe" macro, handles unpaired surrogates and checks for string boundaries.
+ *
+ * @param s const UChar * string
+ * @param i string offset, i<length
+ * @param length string length
+ * @see U16_FWD_1_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U16_FWD_1(s, i, length) { \
+ if(U16_IS_LEAD((s)[(i)++]) && (i)<(length) && U16_IS_TRAIL((s)[i])) { \
+ ++(i); \
+ } \
+}
+
+/**
+ * Advance the string offset from one code point boundary to the n-th next one,
+ * i.e., move forward by n code points.
+ * (Post-incrementing iteration.)
+ * "Unsafe" macro, assumes well-formed UTF-16.
+ *
+ * @param s const UChar * string
+ * @param i string offset
+ * @param n number of code points to skip
+ * @see U16_FWD_N
+ * @stable ICU 2.4
+ */
+#define U16_FWD_N_UNSAFE(s, i, n) { \
+ int32_t __N=(n); \
+ while(__N>0) { \
+ U16_FWD_1_UNSAFE(s, i); \
+ --__N; \
+ } \
+}
+
+/**
+ * Advance the string offset from one code point boundary to the n-th next one,
+ * i.e., move forward by n code points.
+ * (Post-incrementing iteration.)
+ * "Safe" macro, handles unpaired surrogates and checks for string boundaries.
+ *
+ * @param s const UChar * string
+ * @param i string offset, i<length
+ * @param length string length
+ * @param n number of code points to skip
+ * @see U16_FWD_N_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U16_FWD_N(s, i, length, n) { \
+ int32_t __N=(n); \
+ while(__N>0 && (i)<(length)) { \
+ U16_FWD_1(s, i, length); \
+ --__N; \
+ } \
+}
+
+/**
+ * Adjust a random-access offset to a code point boundary
+ * at the start of a code point.
+ * If the offset points to the trail surrogate of a surrogate pair,
+ * then the offset is decremented.
+ * Otherwise, it is not modified.
+ * "Unsafe" macro, assumes well-formed UTF-16.
+ *
+ * @param s const UChar * string
+ * @param i string offset
+ * @see U16_SET_CP_START
+ * @stable ICU 2.4
+ */
+#define U16_SET_CP_START_UNSAFE(s, i) { \
+ if(U16_IS_TRAIL((s)[i])) { \
+ --(i); \
+ } \
+}
+
+/**
+ * Adjust a random-access offset to a code point boundary
+ * at the start of a code point.
+ * If the offset points to the trail surrogate of a surrogate pair,
+ * then the offset is decremented.
+ * Otherwise, it is not modified.
+ * "Safe" macro, handles unpaired surrogates and checks for string boundaries.
+ *
+ * @param s const UChar * string
+ * @param start starting string offset (usually 0)
+ * @param i string offset, start<=i
+ * @see U16_SET_CP_START_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U16_SET_CP_START(s, start, i) { \
+ if(U16_IS_TRAIL((s)[i]) && (i)>(start) && U16_IS_LEAD((s)[(i)-1])) { \
+ --(i); \
+ } \
+}
+
+/* definitions with backward iteration -------------------------------------- */
+
+/**
+ * Move the string offset from one code point boundary to the previous one
+ * and get the code point between them.
+ * (Pre-decrementing backward iteration.)
+ * "Unsafe" macro, assumes well-formed UTF-16.
+ *
+ * The input offset may be the same as the string length.
+ * If the offset is behind a trail surrogate unit
+ * for a supplementary code point, then the macro will read
+ * the preceding lead surrogate as well.
+ * If the offset is behind a lead surrogate, then that itself
+ * will be returned as the code point.
+ * The result is undefined if the offset is behind a single, unpaired trail surrogate.
+ *
+ * @param s const UChar * string
+ * @param i string offset
+ * @param c output UChar32 variable
+ * @see U16_PREV
+ * @stable ICU 2.4
+ */
+#define U16_PREV_UNSAFE(s, i, c) { \
+ (c)=(s)[--(i)]; \
+ if(U16_IS_TRAIL(c)) { \
+ (c)=U16_GET_SUPPLEMENTARY((s)[--(i)], (c)); \
+ } \
+}
+
+/**
+ * Move the string offset from one code point boundary to the previous one
+ * and get the code point between them.
+ * (Pre-decrementing backward iteration.)
+ * "Safe" macro, handles unpaired surrogates and checks for string boundaries.
+ *
+ * The input offset may be the same as the string length.
+ * If the offset is behind a trail surrogate unit
+ * for a supplementary code point, then the macro will read
+ * the preceding lead surrogate as well.
+ * If the offset is behind a lead surrogate or behind a single, unpaired
+ * trail surrogate, then that itself
+ * will be returned as the code point.
+ *
+ * @param s const UChar * string
+ * @param start starting string offset (usually 0)
+ * @param i string offset, start<=i
+ * @param c output UChar32 variable
+ * @see U16_PREV_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U16_PREV(s, start, i, c) { \
+ (c)=(s)[--(i)]; \
+ if(U16_IS_TRAIL(c)) { \
+ uint16_t __c2; \
+ if((i)>(start) && U16_IS_LEAD(__c2=(s)[(i)-1])) { \
+ --(i); \
+ (c)=U16_GET_SUPPLEMENTARY(__c2, (c)); \
+ } \
+ } \
+}
+
+/**
+ * Move the string offset from one code point boundary to the previous one.
+ * (Pre-decrementing backward iteration.)
+ * The input offset may be the same as the string length.
+ * "Unsafe" macro, assumes well-formed UTF-16.
+ *
+ * @param s const UChar * string
+ * @param i string offset
+ * @see U16_BACK_1
+ * @stable ICU 2.4
+ */
+#define U16_BACK_1_UNSAFE(s, i) { \
+ if(U16_IS_TRAIL((s)[--(i)])) { \
+ --(i); \
+ } \
+}
+
+/**
+ * Move the string offset from one code point boundary to the previous one.
+ * (Pre-decrementing backward iteration.)
+ * The input offset may be the same as the string length.
+ * "Safe" macro, handles unpaired surrogates and checks for string boundaries.
+ *
+ * @param s const UChar * string
+ * @param start starting string offset (usually 0)
+ * @param i string offset, start<=i
+ * @see U16_BACK_1_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U16_BACK_1(s, start, i) { \
+ if(U16_IS_TRAIL((s)[--(i)]) && (i)>(start) && U16_IS_LEAD((s)[(i)-1])) { \
+ --(i); \
+ } \
+}
+
+/**
+ * Move the string offset from one code point boundary to the n-th one before it,
+ * i.e., move backward by n code points.
+ * (Pre-decrementing backward iteration.)
+ * The input offset may be the same as the string length.
+ * "Unsafe" macro, assumes well-formed UTF-16.
+ *
+ * @param s const UChar * string
+ * @param i string offset
+ * @param n number of code points to skip
+ * @see U16_BACK_N
+ * @stable ICU 2.4
+ */
+#define U16_BACK_N_UNSAFE(s, i, n) { \
+ int32_t __N=(n); \
+ while(__N>0) { \
+ U16_BACK_1_UNSAFE(s, i); \
+ --__N; \
+ } \
+}
+
+/**
+ * Move the string offset from one code point boundary to the n-th one before it,
+ * i.e., move backward by n code points.
+ * (Pre-decrementing backward iteration.)
+ * The input offset may be the same as the string length.
+ * "Safe" macro, handles unpaired surrogates and checks for string boundaries.
+ *
+ * @param s const UChar * string
+ * @param start start of string
+ * @param i string offset, i<length
+ * @param n number of code points to skip
+ * @see U16_BACK_N_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U16_BACK_N(s, start, i, n) { \
+ int32_t __N=(n); \
+ while(__N>0 && (i)>(start)) { \
+ U16_BACK_1(s, start, i); \
+ --__N; \
+ } \
+}
+
+/**
+ * Adjust a random-access offset to a code point boundary after a code point.
+ * If the offset is behind the lead surrogate of a surrogate pair,
+ * then the offset is incremented.
+ * Otherwise, it is not modified.
+ * The input offset may be the same as the string length.
+ * "Unsafe" macro, assumes well-formed UTF-16.
+ *
+ * @param s const UChar * string
+ * @param i string offset
+ * @see U16_SET_CP_LIMIT
+ * @stable ICU 2.4
+ */
+#define U16_SET_CP_LIMIT_UNSAFE(s, i) { \
+ if(U16_IS_LEAD((s)[(i)-1])) { \
+ ++(i); \
+ } \
+}
+
+/**
+ * Adjust a random-access offset to a code point boundary after a code point.
+ * If the offset is behind the lead surrogate of a surrogate pair,
+ * then the offset is incremented.
+ * Otherwise, it is not modified.
+ * The input offset may be the same as the string length.
+ * "Safe" macro, handles unpaired surrogates and checks for string boundaries.
+ *
+ * @param s const UChar * string
+ * @param start starting string offset (usually 0)
+ * @param i string offset, start<=i<=length
+ * @param length string length
+ * @see U16_SET_CP_LIMIT_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U16_SET_CP_LIMIT(s, start, i, length) { \
+ if((start)<(i) && (i)<(length) && U16_IS_LEAD((s)[(i)-1]) && U16_IS_TRAIL((s)[i])) { \
+ ++(i); \
+ } \
+}
+
+#endif
diff --git a/WebKit/mac/icu/unicode/utf8.h b/WebKit/mac/icu/unicode/utf8.h
new file mode 100644
index 0000000..f83662b
--- /dev/null
+++ b/WebKit/mac/icu/unicode/utf8.h
@@ -0,0 +1,627 @@
+/*
+*******************************************************************************
+*
+* Copyright (C) 1999-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+*
+*******************************************************************************
+* file name: utf8.h
+* encoding: US-ASCII
+* tab size: 8 (not used)
+* indentation:4
+*
+* created on: 1999sep13
+* created by: Markus W. Scherer
+*/
+
+/**
+ * \file
+ * \brief C API: 8-bit Unicode handling macros
+ *
+ * This file defines macros to deal with 8-bit Unicode (UTF-8) code units (bytes) and strings.
+ * utf8.h is included by utf.h after unicode/umachine.h
+ * and some common definitions.
+ *
+ * For more information see utf.h and the ICU User Guide Strings chapter
+ * (http://oss.software.ibm.com/icu/userguide/).
+ *
+ * <em>Usage:</em>
+ * ICU coding guidelines for if() statements should be followed when using these macros.
+ * Compound statements (curly braces {}) must be used for if-else-while...
+ * bodies and all macro statements should be terminated with semicolon.
+ */
+
+#ifndef __UTF8_H__
+#define __UTF8_H__
+
+/* utf.h must be included first. */
+#ifndef __UTF_H__
+# include "unicode/utf.h"
+#endif
+
+/* internal definitions ----------------------------------------------------- */
+
+/**
+ * \var utf8_countTrailBytes
+ * Internal array with numbers of trail bytes for any given byte used in
+ * lead byte position.
+ * @internal
+ */
+#ifdef U_UTF8_IMPL
+U_INTERNAL const uint8_t
+#elif defined(U_STATIC_IMPLEMENTATION)
+U_CFUNC const uint8_t
+#else
+U_CFUNC U_IMPORT const uint8_t /* U_IMPORT2? */ /*U_IMPORT*/
+#endif
+utf8_countTrailBytes[256];
+
+/**
+ * Count the trail bytes for a UTF-8 lead byte.
+ * @internal
+ */
+#define U8_COUNT_TRAIL_BYTES(leadByte) (utf8_countTrailBytes[(uint8_t)leadByte])
+
+/**
+ * Mask a UTF-8 lead byte, leave only the lower bits that form part of the code point value.
+ * @internal
+ */
+#define U8_MASK_LEAD_BYTE(leadByte, countTrailBytes) ((leadByte)&=(1<<(6-(countTrailBytes)))-1)
+
+/**
+ * Function for handling "next code point" with error-checking.
+ * @internal
+ */
+U_INTERNAL UChar32 U_EXPORT2
+utf8_nextCharSafeBody(const uint8_t *s, int32_t *pi, int32_t length, UChar32 c, UBool strict);
+
+/**
+ * Function for handling "append code point" with error-checking.
+ * @internal
+ */
+U_INTERNAL int32_t U_EXPORT2
+utf8_appendCharSafeBody(uint8_t *s, int32_t i, int32_t length, UChar32 c, UBool *pIsError);
+
+/**
+ * Function for handling "previous code point" with error-checking.
+ * @internal
+ */
+U_INTERNAL UChar32 U_EXPORT2
+utf8_prevCharSafeBody(const uint8_t *s, int32_t start, int32_t *pi, UChar32 c, UBool strict);
+
+/**
+ * Function for handling "skip backward one code point" with error-checking.
+ * @internal
+ */
+U_INTERNAL int32_t U_EXPORT2
+utf8_back1SafeBody(const uint8_t *s, int32_t start, int32_t i);
+
+/* single-code point definitions -------------------------------------------- */
+
+/**
+ * Does this code unit (byte) encode a code point by itself (US-ASCII 0..0x7f)?
+ * @param c 8-bit code unit (byte)
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U8_IS_SINGLE(c) (((c)&0x80)==0)
+
+/**
+ * Is this code unit (byte) a UTF-8 lead byte?
+ * @param c 8-bit code unit (byte)
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U8_IS_LEAD(c) ((uint8_t)((c)-0xc0)<0x3e)
+
+/**
+ * Is this code unit (byte) a UTF-8 trail byte?
+ * @param c 8-bit code unit (byte)
+ * @return TRUE or FALSE
+ * @stable ICU 2.4
+ */
+#define U8_IS_TRAIL(c) (((c)&0xc0)==0x80)
+
+/**
+ * How many code units (bytes) are used for the UTF-8 encoding
+ * of this Unicode code point?
+ * @param c 32-bit code point
+ * @return 1..4, or 0 if c is a surrogate or not a Unicode code point
+ * @stable ICU 2.4
+ */
+#define U8_LENGTH(c) \
+ ((uint32_t)(c)<=0x7f ? 1 : \
+ ((uint32_t)(c)<=0x7ff ? 2 : \
+ ((uint32_t)(c)<=0xd7ff ? 3 : \
+ ((uint32_t)(c)<=0xdfff || (uint32_t)(c)>0x10ffff ? 0 : \
+ ((uint32_t)(c)<=0xffff ? 3 : 4)\
+ ) \
+ ) \
+ ) \
+ )
+
+/**
+ * The maximum number of UTF-8 code units (bytes) per Unicode code point (U+0000..U+10ffff).
+ * @return 4
+ * @stable ICU 2.4
+ */
+#define U8_MAX_LENGTH 4
+
+/**
+ * Get a code point from a string at a random-access offset,
+ * without changing the offset.
+ * The offset may point to either the lead byte or one of the trail bytes
+ * for a code point, in which case the macro will read all of the bytes
+ * for the code point.
+ * The result is undefined if the offset points to an illegal UTF-8
+ * byte sequence.
+ * Iteration through a string is more efficient with U8_NEXT_UNSAFE or U8_NEXT.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset
+ * @param c output UChar32 variable
+ * @see U8_GET
+ * @stable ICU 2.4
+ */
+#define U8_GET_UNSAFE(s, i, c) { \
+ int32_t _u8_get_unsafe_index=(int32_t)(i); \
+ U8_SET_CP_START_UNSAFE(s, _u8_get_unsafe_index); \
+ U8_NEXT_UNSAFE(s, _u8_get_unsafe_index, c); \
+}
+
+/**
+ * Get a code point from a string at a random-access offset,
+ * without changing the offset.
+ * The offset may point to either the lead byte or one of the trail bytes
+ * for a code point, in which case the macro will read all of the bytes
+ * for the code point.
+ * If the offset points to an illegal UTF-8 byte sequence, then
+ * c is set to a negative value.
+ * Iteration through a string is more efficient with U8_NEXT_UNSAFE or U8_NEXT.
+ *
+ * @param s const uint8_t * string
+ * @param start starting string offset
+ * @param i string offset, start<=i<length
+ * @param length string length
+ * @param c output UChar32 variable, set to <0 in case of an error
+ * @see U8_GET_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U8_GET(s, start, i, length, c) { \
+ int32_t _u8_get_index=(int32_t)(i); \
+ U8_SET_CP_START(s, start, _u8_get_index); \
+ U8_NEXT(s, _u8_get_index, length, c); \
+}
+
+/* definitions with forward iteration --------------------------------------- */
+
+/**
+ * Get a code point from a string at a code point boundary offset,
+ * and advance the offset to the next code point boundary.
+ * (Post-incrementing forward iteration.)
+ * "Unsafe" macro, assumes well-formed UTF-8.
+ *
+ * The offset may point to the lead byte of a multi-byte sequence,
+ * in which case the macro will read the whole sequence.
+ * The result is undefined if the offset points to a trail byte
+ * or an illegal UTF-8 sequence.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset
+ * @param c output UChar32 variable
+ * @see U8_NEXT
+ * @stable ICU 2.4
+ */
+#define U8_NEXT_UNSAFE(s, i, c) { \
+ (c)=(s)[(i)++]; \
+ if((uint8_t)((c)-0xc0)<0x35) { \
+ uint8_t __count=U8_COUNT_TRAIL_BYTES(c); \
+ U8_MASK_LEAD_BYTE(c, __count); \
+ switch(__count) { \
+ /* each following branch falls through to the next one */ \
+ case 3: \
+ (c)=((c)<<6)|((s)[(i)++]&0x3f); \
+ case 2: \
+ (c)=((c)<<6)|((s)[(i)++]&0x3f); \
+ case 1: \
+ (c)=((c)<<6)|((s)[(i)++]&0x3f); \
+ /* no other branches to optimize switch() */ \
+ break; \
+ } \
+ } \
+}
+
+/**
+ * Get a code point from a string at a code point boundary offset,
+ * and advance the offset to the next code point boundary.
+ * (Post-incrementing forward iteration.)
+ * "Safe" macro, checks for illegal sequences and for string boundaries.
+ *
+ * The offset may point to the lead byte of a multi-byte sequence,
+ * in which case the macro will read the whole sequence.
+ * If the offset points to a trail byte or an illegal UTF-8 sequence, then
+ * c is set to a negative value.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset, i<length
+ * @param length string length
+ * @param c output UChar32 variable, set to <0 in case of an error
+ * @see U8_NEXT_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U8_NEXT(s, i, length, c) { \
+ (c)=(s)[(i)++]; \
+ if(((uint8_t)(c))>=0x80) { \
+ if(U8_IS_LEAD(c)) { \
+ (c)=utf8_nextCharSafeBody((const uint8_t *)s, &(i), (int32_t)(length), c, -1); \
+ } else { \
+ (c)=U_SENTINEL; \
+ } \
+ } \
+}
+
+/**
+ * Append a code point to a string, overwriting 1 to 4 bytes.
+ * The offset points to the current end of the string contents
+ * and is advanced (post-increment).
+ * "Unsafe" macro, assumes a valid code point and sufficient space in the string.
+ * Otherwise, the result is undefined.
+ *
+ * @param s const uint8_t * string buffer
+ * @param i string offset
+ * @param c code point to append
+ * @see U8_APPEND
+ * @stable ICU 2.4
+ */
+#define U8_APPEND_UNSAFE(s, i, c) { \
+ if((uint32_t)(c)<=0x7f) { \
+ (s)[(i)++]=(uint8_t)(c); \
+ } else { \
+ if((uint32_t)(c)<=0x7ff) { \
+ (s)[(i)++]=(uint8_t)(((c)>>6)|0xc0); \
+ } else { \
+ if((uint32_t)(c)<=0xffff) { \
+ (s)[(i)++]=(uint8_t)(((c)>>12)|0xe0); \
+ } else { \
+ (s)[(i)++]=(uint8_t)(((c)>>18)|0xf0); \
+ (s)[(i)++]=(uint8_t)((((c)>>12)&0x3f)|0x80); \
+ } \
+ (s)[(i)++]=(uint8_t)((((c)>>6)&0x3f)|0x80); \
+ } \
+ (s)[(i)++]=(uint8_t)(((c)&0x3f)|0x80); \
+ } \
+}
+
+/**
+ * Append a code point to a string, overwriting 1 or 2 code units.
+ * The offset points to the current end of the string contents
+ * and is advanced (post-increment).
+ * "Safe" macro, checks for a valid code point.
+ * If a non-ASCII code point is written, checks for sufficient space in the string.
+ * If the code point is not valid or trail bytes do not fit,
+ * then isError is set to TRUE.
+ *
+ * @param s const uint8_t * string buffer
+ * @param i string offset, i<length
+ * @param length size of the string buffer
+ * @param c code point to append
+ * @param isError output UBool set to TRUE if an error occurs, otherwise not modified
+ * @see U8_APPEND_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U8_APPEND(s, i, length, c, isError) { \
+ if((uint32_t)(c)<=0x7f) { \
+ (s)[(i)++]=(uint8_t)(c); \
+ } else { \
+ (i)=utf8_appendCharSafeBody(s, (int32_t)(i), (int32_t)(length), c, &(isError)); \
+ } \
+}
+
+/**
+ * Advance the string offset from one code point boundary to the next.
+ * (Post-incrementing iteration.)
+ * "Unsafe" macro, assumes well-formed UTF-8.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset
+ * @see U8_FWD_1
+ * @stable ICU 2.4
+ */
+#define U8_FWD_1_UNSAFE(s, i) { \
+ (i)+=1+U8_COUNT_TRAIL_BYTES((s)[i]); \
+}
+
+/**
+ * Advance the string offset from one code point boundary to the next.
+ * (Post-incrementing iteration.)
+ * "Safe" macro, checks for illegal sequences and for string boundaries.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset, i<length
+ * @param length string length
+ * @see U8_FWD_1_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U8_FWD_1(s, i, length) { \
+ uint8_t __b=(s)[(i)++]; \
+ if(U8_IS_LEAD(__b)) { \
+ uint8_t __count=U8_COUNT_TRAIL_BYTES(__b); \
+ if((i)+__count>(length)) { \
+ __count=(uint8_t)((length)-(i)); \
+ } \
+ while(__count>0 && U8_IS_TRAIL((s)[i])) { \
+ ++(i); \
+ --__count; \
+ } \
+ } \
+}
+
+/**
+ * Advance the string offset from one code point boundary to the n-th next one,
+ * i.e., move forward by n code points.
+ * (Post-incrementing iteration.)
+ * "Unsafe" macro, assumes well-formed UTF-8.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset
+ * @param n number of code points to skip
+ * @see U8_FWD_N
+ * @stable ICU 2.4
+ */
+#define U8_FWD_N_UNSAFE(s, i, n) { \
+ int32_t __N=(n); \
+ while(__N>0) { \
+ U8_FWD_1_UNSAFE(s, i); \
+ --__N; \
+ } \
+}
+
+/**
+ * Advance the string offset from one code point boundary to the n-th next one,
+ * i.e., move forward by n code points.
+ * (Post-incrementing iteration.)
+ * "Safe" macro, checks for illegal sequences and for string boundaries.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset, i<length
+ * @param length string length
+ * @param n number of code points to skip
+ * @see U8_FWD_N_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U8_FWD_N(s, i, length, n) { \
+ int32_t __N=(n); \
+ while(__N>0 && (i)<(length)) { \
+ U8_FWD_1(s, i, length); \
+ --__N; \
+ } \
+}
+
+/**
+ * Adjust a random-access offset to a code point boundary
+ * at the start of a code point.
+ * If the offset points to a UTF-8 trail byte,
+ * then the offset is moved backward to the corresponding lead byte.
+ * Otherwise, it is not modified.
+ * "Unsafe" macro, assumes well-formed UTF-8.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset
+ * @see U8_SET_CP_START
+ * @stable ICU 2.4
+ */
+#define U8_SET_CP_START_UNSAFE(s, i) { \
+ while(U8_IS_TRAIL((s)[i])) { --(i); } \
+}
+
+/**
+ * Adjust a random-access offset to a code point boundary
+ * at the start of a code point.
+ * If the offset points to a UTF-8 trail byte,
+ * then the offset is moved backward to the corresponding lead byte.
+ * Otherwise, it is not modified.
+ * "Safe" macro, checks for illegal sequences and for string boundaries.
+ *
+ * @param s const uint8_t * string
+ * @param start starting string offset (usually 0)
+ * @param i string offset, start<=i
+ * @see U8_SET_CP_START_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U8_SET_CP_START(s, start, i) { \
+ if(U8_IS_TRAIL((s)[(i)])) { \
+ (i)=utf8_back1SafeBody(s, start, (int32_t)(i)); \
+ } \
+}
+
+/* definitions with backward iteration -------------------------------------- */
+
+/**
+ * Move the string offset from one code point boundary to the previous one
+ * and get the code point between them.
+ * (Pre-decrementing backward iteration.)
+ * "Unsafe" macro, assumes well-formed UTF-8.
+ *
+ * The input offset may be the same as the string length.
+ * If the offset is behind a multi-byte sequence, then the macro will read
+ * the whole sequence.
+ * If the offset is behind a lead byte, then that itself
+ * will be returned as the code point.
+ * The result is undefined if the offset is behind an illegal UTF-8 sequence.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset
+ * @param c output UChar32 variable
+ * @see U8_PREV
+ * @stable ICU 2.4
+ */
+#define U8_PREV_UNSAFE(s, i, c) { \
+ (c)=(s)[--(i)]; \
+ if(U8_IS_TRAIL(c)) { \
+ uint8_t __b, __count=1, __shift=6; \
+\
+ /* c is a trail byte */ \
+ (c)&=0x3f; \
+ for(;;) { \
+ __b=(s)[--(i)]; \
+ if(__b>=0xc0) { \
+ U8_MASK_LEAD_BYTE(__b, __count); \
+ (c)|=(UChar32)__b<<__shift; \
+ break; \
+ } else { \
+ (c)|=(UChar32)(__b&0x3f)<<__shift; \
+ ++__count; \
+ __shift+=6; \
+ } \
+ } \
+ } \
+}
+
+/**
+ * Move the string offset from one code point boundary to the previous one
+ * and get the code point between them.
+ * (Pre-decrementing backward iteration.)
+ * "Safe" macro, checks for illegal sequences and for string boundaries.
+ *
+ * The input offset may be the same as the string length.
+ * If the offset is behind a multi-byte sequence, then the macro will read
+ * the whole sequence.
+ * If the offset is behind a lead byte, then that itself
+ * will be returned as the code point.
+ * If the offset is behind an illegal UTF-8 sequence, then c is set to a negative value.
+ *
+ * @param s const uint8_t * string
+ * @param start starting string offset (usually 0)
+ * @param i string offset, start<=i
+ * @param c output UChar32 variable, set to <0 in case of an error
+ * @see U8_PREV_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U8_PREV(s, start, i, c) { \
+ (c)=(s)[--(i)]; \
+ if((c)>=0x80) { \
+ if((c)<=0xbf) { \
+ (c)=utf8_prevCharSafeBody(s, start, &(i), c, -1); \
+ } else { \
+ (c)=U_SENTINEL; \
+ } \
+ } \
+}
+
+/**
+ * Move the string offset from one code point boundary to the previous one.
+ * (Pre-decrementing backward iteration.)
+ * The input offset may be the same as the string length.
+ * "Unsafe" macro, assumes well-formed UTF-8.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset
+ * @see U8_BACK_1
+ * @stable ICU 2.4
+ */
+#define U8_BACK_1_UNSAFE(s, i) { \
+ while(U8_IS_TRAIL((s)[--(i)])) {} \
+}
+
+/**
+ * Move the string offset from one code point boundary to the previous one.
+ * (Pre-decrementing backward iteration.)
+ * The input offset may be the same as the string length.
+ * "Safe" macro, checks for illegal sequences and for string boundaries.
+ *
+ * @param s const uint8_t * string
+ * @param start starting string offset (usually 0)
+ * @param i string offset, start<=i
+ * @see U8_BACK_1_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U8_BACK_1(s, start, i) { \
+ if(U8_IS_TRAIL((s)[--(i)])) { \
+ (i)=utf8_back1SafeBody(s, start, (int32_t)(i)); \
+ } \
+}
+
+/**
+ * Move the string offset from one code point boundary to the n-th one before it,
+ * i.e., move backward by n code points.
+ * (Pre-decrementing backward iteration.)
+ * The input offset may be the same as the string length.
+ * "Unsafe" macro, assumes well-formed UTF-8.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset
+ * @param n number of code points to skip
+ * @see U8_BACK_N
+ * @stable ICU 2.4
+ */
+#define U8_BACK_N_UNSAFE(s, i, n) { \
+ int32_t __N=(n); \
+ while(__N>0) { \
+ U8_BACK_1_UNSAFE(s, i); \
+ --__N; \
+ } \
+}
+
+/**
+ * Move the string offset from one code point boundary to the n-th one before it,
+ * i.e., move backward by n code points.
+ * (Pre-decrementing backward iteration.)
+ * The input offset may be the same as the string length.
+ * "Safe" macro, checks for illegal sequences and for string boundaries.
+ *
+ * @param s const uint8_t * string
+ * @param start index of the start of the string
+ * @param i string offset, i<length
+ * @param n number of code points to skip
+ * @see U8_BACK_N_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U8_BACK_N(s, start, i, n) { \
+ int32_t __N=(n); \
+ while(__N>0 && (i)>(start)) { \
+ U8_BACK_1(s, start, i); \
+ --__N; \
+ } \
+}
+
+/**
+ * Adjust a random-access offset to a code point boundary after a code point.
+ * If the offset is behind a partial multi-byte sequence,
+ * then the offset is incremented to behind the whole sequence.
+ * Otherwise, it is not modified.
+ * The input offset may be the same as the string length.
+ * "Unsafe" macro, assumes well-formed UTF-8.
+ *
+ * @param s const uint8_t * string
+ * @param i string offset
+ * @see U8_SET_CP_LIMIT
+ * @stable ICU 2.4
+ */
+#define U8_SET_CP_LIMIT_UNSAFE(s, i) { \
+ U8_BACK_1_UNSAFE(s, i); \
+ U8_FWD_1_UNSAFE(s, i); \
+}
+
+/**
+ * Adjust a random-access offset to a code point boundary after a code point.
+ * If the offset is behind a partial multi-byte sequence,
+ * then the offset is incremented to behind the whole sequence.
+ * Otherwise, it is not modified.
+ * The input offset may be the same as the string length.
+ * "Safe" macro, checks for illegal sequences and for string boundaries.
+ *
+ * @param s const uint8_t * string
+ * @param start starting string offset (usually 0)
+ * @param i string offset, start<=i<=length
+ * @param length string length
+ * @see U8_SET_CP_LIMIT_UNSAFE
+ * @stable ICU 2.4
+ */
+#define U8_SET_CP_LIMIT(s, start, i, length) { \
+ if((start)<(i) && (i)<(length)) { \
+ U8_BACK_1(s, start, i); \
+ U8_FWD_1(s, i, length); \
+ } \
+}
+
+#endif
diff --git a/WebKit/mac/icu/unicode/utf_old.h b/WebKit/mac/icu/unicode/utf_old.h
new file mode 100644
index 0000000..e69de29
--- /dev/null
+++ b/WebKit/mac/icu/unicode/utf_old.h
diff --git a/WebKit/mac/icu/unicode/utypes.h b/WebKit/mac/icu/unicode/utypes.h
new file mode 100644
index 0000000..e20cd79
--- /dev/null
+++ b/WebKit/mac/icu/unicode/utypes.h
@@ -0,0 +1,745 @@
+/*
+**********************************************************************
+* Copyright (C) 1996-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+**********************************************************************
+*
+* FILE NAME : UTYPES.H (formerly ptypes.h)
+*
+* Date Name Description
+* 12/11/96 helena Creation.
+* 02/27/97 aliu Added typedefs for UClassID, int8, int16, int32,
+* uint8, uint16, and uint32.
+* 04/01/97 aliu Added XP_CPLUSPLUS and modified to work under C as
+* well as C++.
+* Modified to use memcpy() for uprv_arrayCopy() fns.
+* 04/14/97 aliu Added TPlatformUtilities.
+* 05/07/97 aliu Added import/export specifiers (replacing the old
+* broken EXT_CLASS). Added version number for our
+* code. Cleaned up header.
+* 6/20/97 helena Java class name change.
+* 08/11/98 stephen UErrorCode changed from typedef to enum
+* 08/12/98 erm Changed T_ANALYTIC_PACKAGE_VERSION to 3
+* 08/14/98 stephen Added uprv_arrayCopy() for int8_t, int16_t, int32_t
+* 12/09/98 jfitz Added BUFFER_OVERFLOW_ERROR (bug 1100066)
+* 04/20/99 stephen Cleaned up & reworked for autoconf.
+* Renamed to utypes.h.
+* 05/05/99 stephen Changed to use <inttypes.h>
+* 12/07/99 helena Moved copyright notice string from ucnv_bld.h here.
+*******************************************************************************
+*/
+
+#ifndef UTYPES_H
+#define UTYPES_H
+
+
+#include "unicode/umachine.h"
+#include "unicode/utf.h"
+#include "unicode/uversion.h"
+#include "unicode/uconfig.h"
+
+#ifdef U_HIDE_DRAFT_API
+#include "unicode/udraft.h"
+#endif
+
+#ifdef U_HIDE_DEPRECATED_API
+#include "unicode/udeprctd.h"
+#endif
+
+#ifdef U_HIDE_DEPRECATED_API
+#include "unicode/uobslete.h"
+#endif
+
+
+/*!
+ * \file
+ * \brief Basic definitions for ICU, for both C and C++ APIs
+ *
+ * This file defines basic types, constants, and enumerations directly or
+ * indirectly by including other header files, especially utf.h for the
+ * basic character and string definitions and umachine.h for consistent
+ * integer and other types.
+ */
+
+/*===========================================================================*/
+/* char Character set family */
+/*===========================================================================*/
+
+/**
+ * U_CHARSET_FAMILY is equal to this value when the platform is an ASCII based platform.
+ * @stable ICU 2.0
+ */
+#define U_ASCII_FAMILY 0
+
+/**
+ * U_CHARSET_FAMILY is equal to this value when the platform is an EBCDIC based platform.
+ * @stable ICU 2.0
+ */
+#define U_EBCDIC_FAMILY 1
+
+/**
+ * \def U_CHARSET_FAMILY
+ *
+ * <p>These definitions allow to specify the encoding of text
+ * in the char data type as defined by the platform and the compiler.
+ * It is enough to determine the code point values of "invariant characters",
+ * which are the ones shared by all encodings that are in use
+ * on a given platform.</p>
+ *
+ * <p>Those "invariant characters" should be all the uppercase and lowercase
+ * latin letters, the digits, the space, and "basic punctuation".
+ * Also, '\\n', '\\r', '\\t' should be available.</p>
+ *
+ * <p>The list of "invariant characters" is:<br>
+ * \code
+ * A-Z a-z 0-9 SPACE " % &amp; ' ( ) * + , - . / : ; < = > ? _
+ * \endcode
+ * <br>
+ * (52 letters + 10 numbers + 20 punc/sym/space = 82 total)</p>
+ *
+ * <p>This matches the IBM Syntactic Character Set (CS 640).</p>
+ *
+ * <p>In other words, all the graphic characters in 7-bit ASCII should
+ * be safely accessible except the following:</p>
+ *
+ * \code
+ * '\' <backslash>
+ * '[' <left bracket>
+ * ']' <right bracket>
+ * '{' <left brace>
+ * '}' <right brace>
+ * '^' <circumflex>
+ * '~' <tilde>
+ * '!' <exclamation mark>
+ * '#' <number sign>
+ * '|' <vertical line>
+ * '$' <dollar sign>
+ * '@' <commercial at>
+ * '`' <grave accent>
+ * \endcode
+ * @stable ICU 2.0
+ */
+
+#ifndef U_CHARSET_FAMILY
+# define U_CHARSET_FAMILY 0
+#endif
+
+/*===========================================================================*/
+/* ICUDATA naming scheme */
+/*===========================================================================*/
+
+/**
+ * \def U_ICUDATA_TYPE_LETTER
+ *
+ * This is a platform-dependent string containing one letter:
+ * - b for big-endian, ASCII-family platforms
+ * - l for little-endian, ASCII-family platforms
+ * - e for big-endian, EBCDIC-family platforms
+ * This letter is part of the common data file name.
+ * @stable ICU 2.0
+ */
+
+/**
+ * \def U_ICUDATA_TYPE_LITLETTER
+ * The non-string form of U_ICUDATA_TYPE_LETTER
+ * @stable ICU 2.0
+ */
+#if U_CHARSET_FAMILY
+# if U_IS_BIG_ENDIAN
+ /* EBCDIC - should always be BE */
+# define U_ICUDATA_TYPE_LETTER "e"
+# define U_ICUDATA_TYPE_LITLETTER e
+# else
+# error "Don't know what to do with little endian EBCDIC!"
+# define U_ICUDATA_TYPE_LETTER "x"
+# define U_ICUDATA_TYPE_LITLETTER x
+# endif
+#else
+# if U_IS_BIG_ENDIAN
+ /* Big-endian ASCII */
+# define U_ICUDATA_TYPE_LETTER "b"
+# define U_ICUDATA_TYPE_LITLETTER b
+# else
+ /* Little-endian ASCII */
+# define U_ICUDATA_TYPE_LETTER "l"
+# define U_ICUDATA_TYPE_LITLETTER l
+# endif
+#endif
+
+/**
+ * A single string literal containing the icudata stub name. i.e. 'icudt18e' for
+ * ICU 1.8.x on EBCDIC, etc..
+ * @stable ICU 2.0
+ */
+#define U_ICUDATA_NAME "icudt" U_ICU_VERSION_SHORT U_ICUDATA_TYPE_LETTER
+
+
+/**
+ * U_ICU_ENTRY_POINT is the name of the DLL entry point to the ICU data library.
+ * Defined as a literal, not a string.
+ * Tricky Preprocessor use - ## operator replaces macro paramters with the literal string
+ * from the corresponding macro invocation, _before_ other macro substitutions.
+ * Need a nested #defines to get the actual version numbers rather than
+ * the literal text U_ICU_VERSION_MAJOR_NUM into the name.
+ * The net result will be something of the form
+ * #define U_ICU_ENTRY_POINT icudt19_dat
+ * @stable ICU 2.4
+ */
+#define U_ICUDATA_ENTRY_POINT U_DEF2_ICUDATA_ENTRY_POINT(U_ICU_VERSION_MAJOR_NUM, U_ICU_VERSION_MINOR_NUM)
+/**
+ * @internal
+ */
+#define U_DEF2_ICUDATA_ENTRY_POINT(major, minor) U_DEF_ICUDATA_ENTRY_POINT(major, minor)
+/**
+ * @internal
+ */
+#define U_DEF_ICUDATA_ENTRY_POINT(major, minor) icudt##major##minor##_dat
+
+/**
+ * \def U_CALLCONV
+ * Similar to U_CDECL_BEGIN/U_CDECL_END, this qualifier is necessary
+ * in callback function typedefs to make sure that the calling convention
+ * is compatible.
+ *
+ * This is only used for non-ICU-API functions.
+ * When a function is a public ICU API,
+ * you must use the U_CAPI and U_EXPORT2 qualifiers.
+ * @stable ICU 2.0
+ */
+#if defined(OS390) && (__COMPILER_VER__ < 0x41020000) && defined(XP_CPLUSPLUS)
+# define U_CALLCONV __cdecl
+#else
+# define U_CALLCONV U_EXPORT2
+#endif
+
+/**
+ * \def NULL
+ * Define NULL if necessary, to 0 for C++ and to ((void *)0) for C.
+ * @stable ICU 2.0
+ */
+#ifndef NULL
+#ifdef XP_CPLUSPLUS
+#define NULL 0
+#else
+#define NULL ((void *)0)
+#endif
+#endif
+
+/*===========================================================================*/
+/* Calendar/TimeZone data types */
+/*===========================================================================*/
+
+/**
+ * Date and Time data type.
+ * This is a primitive data type that holds the date and time
+ * as the number of milliseconds since 1970-jan-01, 00:00 UTC.
+ * UTC leap seconds are ignored.
+ * @stable ICU 2.0
+ */
+typedef double UDate;
+
+/** The number of milliseconds per second @stable ICU 2.0 */
+#define U_MILLIS_PER_SECOND (1000)
+/** The number of milliseconds per minute @stable ICU 2.0 */
+#define U_MILLIS_PER_MINUTE (60000)
+/** The number of milliseconds per hour @stable ICU 2.0 */
+#define U_MILLIS_PER_HOUR (3600000)
+/** The number of milliseconds per day @stable ICU 2.0 */
+#define U_MILLIS_PER_DAY (86400000)
+
+
+/*===========================================================================*/
+/* UClassID-based RTTI */
+/*===========================================================================*/
+
+/**
+ * UClassID is used to identify classes without using RTTI, since RTTI
+ * is not yet supported by all C++ compilers. Each class hierarchy which needs
+ * to implement polymorphic clone() or operator==() defines two methods,
+ * described in detail below. UClassID values can be compared using
+ * operator==(). Nothing else should be done with them.
+ *
+ * \par
+ * getDynamicClassID() is declared in the base class of the hierarchy as
+ * a pure virtual. Each concrete subclass implements it in the same way:
+ *
+ * \code
+ * class Base {
+ * public:
+ * virtual UClassID getDynamicClassID() const = 0;
+ * }
+ *
+ * class Derived {
+ * public:
+ * virtual UClassID getDynamicClassID() const
+ * { return Derived::getStaticClassID(); }
+ * }
+ * \endcode
+ *
+ * Each concrete class implements getStaticClassID() as well, which allows
+ * clients to test for a specific type.
+ *
+ * \code
+ * class Derived {
+ * public:
+ * static UClassID U_EXPORT2 getStaticClassID();
+ * private:
+ * static char fgClassID;
+ * }
+ *
+ * // In Derived.cpp:
+ * UClassID Derived::getStaticClassID()
+ * { return (UClassID)&Derived::fgClassID; }
+ * char Derived::fgClassID = 0; // Value is irrelevant
+ * \endcode
+ * @stable ICU 2.0
+ */
+typedef void* UClassID;
+
+/*===========================================================================*/
+/* Shared library/DLL import-export API control */
+/*===========================================================================*/
+
+/*
+ * Control of symbol import/export.
+ * ICU is separated into three libraries.
+ */
+
+/*
+ * \def U_COMBINED_IMPLEMENTATION
+ * Set to export library symbols from inside the ICU library
+ * when all of ICU is in a single library.
+ * This can be set as a compiler option while building ICU, and it
+ * needs to be the first one tested to override U_COMMON_API, U_I18N_API, etc.
+ * @stable ICU 2.0
+ */
+
+/**
+ * \def U_DATA_API
+ * Set to export library symbols from inside the stubdata library,
+ * and to import them from outside.
+ * @draft ICU 3.0
+ */
+
+/**
+ * \def U_COMMON_API
+ * Set to export library symbols from inside the common library,
+ * and to import them from outside.
+ * @stable ICU 2.0
+ */
+
+/**
+ * \def U_I18N_API
+ * Set to export library symbols from inside the i18n library,
+ * and to import them from outside.
+ * @stable ICU 2.0
+ */
+
+/**
+ * \def U_LAYOUT_API
+ * Set to export library symbols from inside the layout engine library,
+ * and to import them from outside.
+ * @stable ICU 2.0
+ */
+
+/**
+ * \def U_LAYOUTEX_API
+ * Set to export library symbols from inside the layout extensions library,
+ * and to import them from outside.
+ * @stable ICU 2.6
+ */
+
+/**
+ * \def U_IO_API
+ * Set to export library symbols from inside the ustdio library,
+ * and to import them from outside.
+ * @stable ICU 2.0
+ */
+
+#if defined(U_COMBINED_IMPLEMENTATION)
+#define U_DATA_API U_EXPORT
+#define U_COMMON_API U_EXPORT
+#define U_I18N_API U_EXPORT
+#define U_LAYOUT_API U_EXPORT
+#define U_LAYOUTEX_API U_EXPORT
+#define U_IO_API U_EXPORT
+#elif defined(U_STATIC_IMPLEMENTATION)
+#define U_DATA_API
+#define U_COMMON_API
+#define U_I18N_API
+#define U_LAYOUT_API
+#define U_LAYOUTEX_API
+#define U_IO_API
+#elif defined(U_COMMON_IMPLEMENTATION)
+#define U_DATA_API U_IMPORT
+#define U_COMMON_API U_EXPORT
+#define U_I18N_API U_IMPORT
+#define U_LAYOUT_API U_IMPORT
+#define U_LAYOUTEX_API U_IMPORT
+#define U_IO_API U_IMPORT
+#elif defined(U_I18N_IMPLEMENTATION)
+#define U_DATA_API U_IMPORT
+#define U_COMMON_API U_IMPORT
+#define U_I18N_API U_EXPORT
+#define U_LAYOUT_API U_IMPORT
+#define U_LAYOUTEX_API U_IMPORT
+#define U_IO_API U_IMPORT
+#elif defined(U_LAYOUT_IMPLEMENTATION)
+#define U_DATA_API U_IMPORT
+#define U_COMMON_API U_IMPORT
+#define U_I18N_API U_IMPORT
+#define U_LAYOUT_API U_EXPORT
+#define U_LAYOUTEX_API U_IMPORT
+#define U_IO_API U_IMPORT
+#elif defined(U_LAYOUTEX_IMPLEMENTATION)
+#define U_DATA_API U_IMPORT
+#define U_COMMON_API U_IMPORT
+#define U_I18N_API U_IMPORT
+#define U_LAYOUT_API U_IMPORT
+#define U_LAYOUTEX_API U_EXPORT
+#define U_IO_API U_IMPORT
+#elif defined(U_IO_IMPLEMENTATION)
+#define U_DATA_API U_IMPORT
+#define U_COMMON_API U_IMPORT
+#define U_I18N_API U_IMPORT
+#define U_LAYOUT_API U_IMPORT
+#define U_LAYOUTEX_API U_IMPORT
+#define U_IO_API U_EXPORT
+#else
+#define U_DATA_API U_IMPORT
+#define U_COMMON_API U_IMPORT
+#define U_I18N_API U_IMPORT
+#define U_LAYOUT_API U_IMPORT
+#define U_LAYOUTEX_API U_IMPORT
+#define U_IO_API U_IMPORT
+#endif
+
+/**
+ * \def U_STANDARD_CPP_NAMESPACE
+ * Control of C++ Namespace
+ * @stable ICU 2.0
+ */
+#ifdef __cplusplus
+#define U_STANDARD_CPP_NAMESPACE ::
+#else
+#define U_STANDARD_CPP_NAMESPACE
+#endif
+
+
+/*===========================================================================*/
+/* Global delete operator */
+/*===========================================================================*/
+
+/*
+ * The ICU4C library must not use the global new and delete operators.
+ * These operators here are defined to enable testing for this.
+ * See Jitterbug 2581 for details of why this is necessary.
+ *
+ * Verification that ICU4C's memory usage is correct, i.e.,
+ * that global new/delete are not used:
+ *
+ * a) Check for imports of global new/delete (see uobject.cpp for details)
+ * b) Verify that new is never imported.
+ * c) Verify that delete is only imported from object code for interface/mixin classes.
+ * d) Add global delete and delete[] only for the ICU4C library itself
+ * and define them in a way that crashes or otherwise easily shows a problem.
+ *
+ * The following implements d).
+ * The operator implementations crash; this is intentional and used for library debugging.
+ *
+ * Note: This is currently only done on Windows because
+ * some Linux/Unix compilers have problems with defining global new/delete.
+ * On Windows, WIN32 is defined, and it is _MSC_Ver>=1200 for MSVC 6.0 and higher.
+ */
+#if defined(XP_CPLUSPLUS) && defined(WIN32) && (_MSC_Ver>=1200) && (defined(U_COMMON_IMPLEMENTATION) || defined(U_I18N_IMPLEMENTATION) || defined(U_LAYOUT_IMPLEMENTATION) || defined(U_USTDIO_IMPLEMENTATION))
+
+/**
+ * Global operator new, defined only inside ICU4C, must not be used.
+ * Crashes intentionally.
+ * @internal
+ */
+inline void *
+operator new(size_t /*size*/) {
+ char *q=NULL;
+ *q=5; /* break it */
+ return q;
+}
+
+/**
+ * Global operator new[], defined only inside ICU4C, must not be used.
+ * Crashes intentionally.
+ * @internal
+ */
+inline void *
+operator new[](size_t /*size*/) {
+ char *q=NULL;
+ *q=5; /* break it */
+ return q;
+}
+
+/**
+ * Global operator delete, defined only inside ICU4C, must not be used.
+ * Crashes intentionally.
+ * @internal
+ */
+inline void
+operator delete(void * /*p*/) {
+ char *q=NULL;
+ *q=5; /* break it */
+}
+
+/**
+ * Global operator delete[], defined only inside ICU4C, must not be used.
+ * Crashes intentionally.
+ * @internal
+ */
+inline void
+operator delete[](void * /*p*/) {
+ char *q=NULL;
+ *q=5; /* break it */
+}
+
+#endif
+
+/*===========================================================================*/
+/* UErrorCode */
+/*===========================================================================*/
+
+/**
+ * Error code to replace exception handling, so that the code is compatible with all C++ compilers,
+ * and to use the same mechanism for C and C++.
+ *
+ * \par
+ * ICU functions that take a reference (C++) or a pointer (C) to a UErrorCode
+ * first test if(U_FAILURE(errorCode)) { return immediately; }
+ * so that in a chain of such functions the first one that sets an error code
+ * causes the following ones to not perform any operations.
+ *
+ * \par
+ * Error codes should be tested using U_FAILURE() and U_SUCCESS().
+ * @stable ICU 2.0
+ */
+typedef enum UErrorCode {
+ /* The ordering of U_ERROR_INFO_START Vs U_USING_FALLBACK_WARNING looks weird
+ * and is that way because VC++ debugger displays first encountered constant,
+ * which is not the what the code is used for
+ */
+
+ U_USING_FALLBACK_WARNING = -128, /**< A resource bundle lookup returned a fallback result (not an error) */
+
+ U_ERROR_WARNING_START = -128, /**< Start of information results (semantically successful) */
+
+ U_USING_DEFAULT_WARNING = -127, /**< A resource bundle lookup returned a result from the root locale (not an error) */
+
+ U_SAFECLONE_ALLOCATED_WARNING = -126, /**< A SafeClone operation required allocating memory (informational only) */
+
+ U_STATE_OLD_WARNING = -125, /**< ICU has to use compatibility layer to construct the service. Expect performance/memory usage degradation. Consider upgrading */
+
+ U_STRING_NOT_TERMINATED_WARNING = -124,/**< An output string could not be NUL-terminated because output length==destCapacity. */
+
+ U_SORT_KEY_TOO_SHORT_WARNING = -123, /**< Number of levels requested in getBound is higher than the number of levels in the sort key */
+
+ U_AMBIGUOUS_ALIAS_WARNING = -122, /**< This converter alias can go to different converter implementations */
+
+ U_DIFFERENT_UCA_VERSION = -121, /**< ucol_open encountered a mismatch between UCA version and collator image version, so the collator was constructed from rules. No impact to further function */
+
+ U_ERROR_WARNING_LIMIT, /**< This must always be the last warning value to indicate the limit for UErrorCode warnings (last warning code +1) */
+
+
+ U_ZERO_ERROR = 0, /**< No error, no warning. */
+
+ U_ILLEGAL_ARGUMENT_ERROR = 1, /**< Start of codes indicating failure */
+ U_MISSING_RESOURCE_ERROR = 2, /**< The requested resource cannot be found */
+ U_INVALID_FORMAT_ERROR = 3, /**< Data format is not what is expected */
+ U_FILE_ACCESS_ERROR = 4, /**< The requested file cannot be found */
+ U_INTERNAL_PROGRAM_ERROR = 5, /**< Indicates a bug in the library code */
+ U_MESSAGE_PARSE_ERROR = 6, /**< Unable to parse a message (message format) */
+ U_MEMORY_ALLOCATION_ERROR = 7, /**< Memory allocation error */
+ U_INDEX_OUTOFBOUNDS_ERROR = 8, /**< Trying to access the index that is out of bounds */
+ U_PARSE_ERROR = 9, /**< Equivalent to Java ParseException */
+ U_INVALID_CHAR_FOUND = 10, /**< Character conversion: Unmappable input sequence. In other APIs: Invalid character. */
+ U_TRUNCATED_CHAR_FOUND = 11, /**< Character conversion: Incomplete input sequence. */
+ U_ILLEGAL_CHAR_FOUND = 12, /**< Character conversion: Illegal input sequence/combination of input units.. */
+ U_INVALID_TABLE_FORMAT = 13, /**< Conversion table file found, but corrupted */
+ U_INVALID_TABLE_FILE = 14, /**< Conversion table file not found */
+ U_BUFFER_OVERFLOW_ERROR = 15, /**< A result would not fit in the supplied buffer */
+ U_UNSUPPORTED_ERROR = 16, /**< Requested operation not supported in current context */
+ U_RESOURCE_TYPE_MISMATCH = 17, /**< an operation is requested over a resource that does not support it */
+ U_ILLEGAL_ESCAPE_SEQUENCE = 18, /**< ISO-2022 illlegal escape sequence */
+ U_UNSUPPORTED_ESCAPE_SEQUENCE = 19, /**< ISO-2022 unsupported escape sequence */
+ U_NO_SPACE_AVAILABLE = 20, /**< No space available for in-buffer expansion for Arabic shaping */
+ U_CE_NOT_FOUND_ERROR = 21, /**< Currently used only while setting variable top, but can be used generally */
+ U_PRIMARY_TOO_LONG_ERROR = 22, /**< User tried to set variable top to a primary that is longer than two bytes */
+ U_STATE_TOO_OLD_ERROR = 23, /**< ICU cannot construct a service from this state, as it is no longer supported */
+ U_TOO_MANY_ALIASES_ERROR = 24, /**< There are too many aliases in the path to the requested resource.
+ It is very possible that a circular alias definition has occured */
+ U_ENUM_OUT_OF_SYNC_ERROR = 25, /**< UEnumeration out of sync with underlying collection */
+ U_INVARIANT_CONVERSION_ERROR = 26, /**< Unable to convert a UChar* string to char* with the invariant converter. */
+ U_INVALID_STATE_ERROR = 27, /**< Requested operation can not be completed with ICU in its current state */
+ U_COLLATOR_VERSION_MISMATCH = 28, /**< Collator version is not compatible with the base version */
+ U_USELESS_COLLATOR_ERROR = 29, /**< Collator is options only and no base is specified */
+
+ U_STANDARD_ERROR_LIMIT, /**< This must always be the last value to indicate the limit for standard errors */
+ /*
+ * the error code range 0x10000 0x10100 are reserved for Transliterator
+ */
+ U_BAD_VARIABLE_DEFINITION=0x10000,/**< Missing '$' or duplicate variable name */
+ U_PARSE_ERROR_START = 0x10000, /**< Start of Transliterator errors */
+ U_MALFORMED_RULE, /**< Elements of a rule are misplaced */
+ U_MALFORMED_SET, /**< A UnicodeSet pattern is invalid*/
+ U_MALFORMED_SYMBOL_REFERENCE, /**< UNUSED as of ICU 2.4 */
+ U_MALFORMED_UNICODE_ESCAPE, /**< A Unicode escape pattern is invalid*/
+ U_MALFORMED_VARIABLE_DEFINITION, /**< A variable definition is invalid */
+ U_MALFORMED_VARIABLE_REFERENCE, /**< A variable reference is invalid */
+ U_MISMATCHED_SEGMENT_DELIMITERS, /**< UNUSED as of ICU 2.4 */
+ U_MISPLACED_ANCHOR_START, /**< A start anchor appears at an illegal position */
+ U_MISPLACED_CURSOR_OFFSET, /**< A cursor offset occurs at an illegal position */
+ U_MISPLACED_QUANTIFIER, /**< A quantifier appears after a segment close delimiter */
+ U_MISSING_OPERATOR, /**< A rule contains no operator */
+ U_MISSING_SEGMENT_CLOSE, /**< UNUSED as of ICU 2.4 */
+ U_MULTIPLE_ANTE_CONTEXTS, /**< More than one ante context */
+ U_MULTIPLE_CURSORS, /**< More than one cursor */
+ U_MULTIPLE_POST_CONTEXTS, /**< More than one post context */
+ U_TRAILING_BACKSLASH, /**< A dangling backslash */
+ U_UNDEFINED_SEGMENT_REFERENCE, /**< A segment reference does not correspond to a defined segment */
+ U_UNDEFINED_VARIABLE, /**< A variable reference does not correspond to a defined variable */
+ U_UNQUOTED_SPECIAL, /**< A special character was not quoted or escaped */
+ U_UNTERMINATED_QUOTE, /**< A closing single quote is missing */
+ U_RULE_MASK_ERROR, /**< A rule is hidden by an earlier more general rule */
+ U_MISPLACED_COMPOUND_FILTER, /**< A compound filter is in an invalid location */
+ U_MULTIPLE_COMPOUND_FILTERS, /**< More than one compound filter */
+ U_INVALID_RBT_SYNTAX, /**< A "::id" rule was passed to the RuleBasedTransliterator parser */
+ U_INVALID_PROPERTY_PATTERN, /**< UNUSED as of ICU 2.4 */
+ U_MALFORMED_PRAGMA, /**< A 'use' pragma is invlalid */
+ U_UNCLOSED_SEGMENT, /**< A closing ')' is missing */
+ U_ILLEGAL_CHAR_IN_SEGMENT, /**< UNUSED as of ICU 2.4 */
+ U_VARIABLE_RANGE_EXHAUSTED, /**< Too many stand-ins generated for the given variable range */
+ U_VARIABLE_RANGE_OVERLAP, /**< The variable range overlaps characters used in rules */
+ U_ILLEGAL_CHARACTER, /**< A special character is outside its allowed context */
+ U_INTERNAL_TRANSLITERATOR_ERROR, /**< Internal transliterator system error */
+ U_INVALID_ID, /**< A "::id" rule specifies an unknown transliterator */
+ U_INVALID_FUNCTION, /**< A "&fn()" rule specifies an unknown transliterator */
+ U_PARSE_ERROR_LIMIT, /**< The limit for Transliterator errors */
+
+ /*
+ * the error code range 0x10100 0x10200 are reserved for formatting API parsing error
+ */
+ U_UNEXPECTED_TOKEN=0x10100, /**< Syntax error in format pattern */
+ U_FMT_PARSE_ERROR_START=0x10100, /**< Start of format library errors */
+ U_MULTIPLE_DECIMAL_SEPARATORS, /**< More than one decimal separator in number pattern */
+ U_MULTIPLE_DECIMAL_SEPERATORS = U_MULTIPLE_DECIMAL_SEPARATORS, /**< Typo: kept for backward compatibility. Use U_MULTIPLE_DECIMAL_SEPARATORS */
+ U_MULTIPLE_EXPONENTIAL_SYMBOLS, /**< More than one exponent symbol in number pattern */
+ U_MALFORMED_EXPONENTIAL_PATTERN, /**< Grouping symbol in exponent pattern */
+ U_MULTIPLE_PERCENT_SYMBOLS, /**< More than one percent symbol in number pattern */
+ U_MULTIPLE_PERMILL_SYMBOLS, /**< More than one permill symbol in number pattern */
+ U_MULTIPLE_PAD_SPECIFIERS, /**< More than one pad symbol in number pattern */
+ U_PATTERN_SYNTAX_ERROR, /**< Syntax error in format pattern */
+ U_ILLEGAL_PAD_POSITION, /**< Pad symbol misplaced in number pattern */
+ U_UNMATCHED_BRACES, /**< Braces do not match in message pattern */
+ U_UNSUPPORTED_PROPERTY, /**< UNUSED as of ICU 2.4 */
+ U_UNSUPPORTED_ATTRIBUTE, /**< UNUSED as of ICU 2.4 */
+ U_FMT_PARSE_ERROR_LIMIT, /**< The limit for format library errors */
+
+ /*
+ * the error code range 0x10200 0x102ff are reserved for Break Iterator related error
+ */
+ U_BRK_ERROR_START=0x10200, /**< Start of codes indicating Break Iterator failures */
+ U_BRK_INTERNAL_ERROR, /**< An internal error (bug) was detected. */
+ U_BRK_HEX_DIGITS_EXPECTED, /**< Hex digits expected as part of a escaped char in a rule. */
+ U_BRK_SEMICOLON_EXPECTED, /**< Missing ';' at the end of a RBBI rule. */
+ U_BRK_RULE_SYNTAX, /**< Syntax error in RBBI rule. */
+ U_BRK_UNCLOSED_SET, /**< UnicodeSet witing an RBBI rule missing a closing ']'. */
+ U_BRK_ASSIGN_ERROR, /**< Syntax error in RBBI rule assignment statement. */
+ U_BRK_VARIABLE_REDFINITION, /**< RBBI rule $Variable redefined. */
+ U_BRK_MISMATCHED_PAREN, /**< Mis-matched parentheses in an RBBI rule. */
+ U_BRK_NEW_LINE_IN_QUOTED_STRING, /**< Missing closing quote in an RBBI rule. */
+ U_BRK_UNDEFINED_VARIABLE, /**< Use of an undefined $Variable in an RBBI rule. */
+ U_BRK_INIT_ERROR, /**< Initialization failure. Probable missing ICU Data. */
+ U_BRK_RULE_EMPTY_SET, /**< Rule contains an empty Unicode Set. */
+ U_BRK_UNRECOGNIZED_OPTION, /**< !!option in RBBI rules not recognized. */
+ U_BRK_MALFORMED_RULE_TAG, /**< The {nnn} tag on a rule is mal formed */
+ U_BRK_ERROR_LIMIT, /**< This must always be the last value to indicate the limit for Break Iterator failures */
+
+ /*
+ * The error codes in the range 0x10300-0x103ff are reserved for regular expression related errrs
+ */
+ U_REGEX_ERROR_START=0x10300, /**< Start of codes indicating Regexp failures */
+ U_REGEX_INTERNAL_ERROR, /**< An internal error (bug) was detected. */
+ U_REGEX_RULE_SYNTAX, /**< Syntax error in regexp pattern. */
+ U_REGEX_INVALID_STATE, /**< RegexMatcher in invalid state for requested operation */
+ U_REGEX_BAD_ESCAPE_SEQUENCE, /**< Unrecognized backslash escape sequence in pattern */
+ U_REGEX_PROPERTY_SYNTAX, /**< Incorrect Unicode property */
+ U_REGEX_UNIMPLEMENTED, /**< Use of regexp feature that is not yet implemented. */
+ U_REGEX_MISMATCHED_PAREN, /**< Incorrectly nested parentheses in regexp pattern. */
+ U_REGEX_NUMBER_TOO_BIG, /**< Decimal number is too large. */
+ U_REGEX_BAD_INTERVAL, /**< Error in {min,max} interval */
+ U_REGEX_MAX_LT_MIN, /**< In {min,max}, max is less than min. */
+ U_REGEX_INVALID_BACK_REF, /**< Back-reference to a non-existent capture group. */
+ U_REGEX_INVALID_FLAG, /**< Invalid value for match mode flags. */
+ U_REGEX_LOOK_BEHIND_LIMIT, /**< Look-Behind pattern matches must have a bounded maximum length. */
+ U_REGEX_SET_CONTAINS_STRING, /**< Regexps cannot have UnicodeSets containing strings.*/
+ U_REGEX_ERROR_LIMIT, /**< This must always be the last value to indicate the limit for regexp errors */
+
+ /*
+ * The error code in the range 0x10400-0x104ff are reserved for IDNA related error codes
+ */
+ U_IDNA_ERROR_START=0x10400,
+ U_IDNA_PROHIBITED_ERROR,
+ U_IDNA_UNASSIGNED_ERROR,
+ U_IDNA_CHECK_BIDI_ERROR,
+ U_IDNA_STD3_ASCII_RULES_ERROR,
+ U_IDNA_ACE_PREFIX_ERROR,
+ U_IDNA_VERIFICATION_ERROR,
+ U_IDNA_LABEL_TOO_LONG_ERROR,
+ U_IDNA_ERROR_LIMIT,
+ /*
+ * Aliases for StringPrep
+ */
+ U_STRINGPREP_PROHIBITED_ERROR = U_IDNA_PROHIBITED_ERROR,
+ U_STRINGPREP_UNASSIGNED_ERROR = U_IDNA_UNASSIGNED_ERROR,
+ U_STRINGPREP_CHECK_BIDI_ERROR = U_IDNA_CHECK_BIDI_ERROR,
+
+
+ U_ERROR_LIMIT=U_IDNA_ERROR_LIMIT /**< This must always be the last value to indicate the limit for UErrorCode (last error code +1) */
+} UErrorCode;
+
+/* Use the following to determine if an UErrorCode represents */
+/* operational success or failure. */
+
+#ifdef XP_CPLUSPLUS
+ /**
+ * Does the error code indicate success?
+ * @stable ICU 2.0
+ */
+ static
+ inline UBool U_SUCCESS(UErrorCode code) { return (UBool)(code<=U_ZERO_ERROR); }
+ /**
+ * Does the error code indicate a failure?
+ * @stable ICU 2.0
+ */
+ static
+ inline UBool U_FAILURE(UErrorCode code) { return (UBool)(code>U_ZERO_ERROR); }
+#else
+ /**
+ * Does the error code indicate success?
+ * @stable ICU 2.0
+ */
+# define U_SUCCESS(x) ((x)<=U_ZERO_ERROR)
+ /**
+ * Does the error code indicate a failure?
+ * @stable ICU 2.0
+ */
+# define U_FAILURE(x) ((x)>U_ZERO_ERROR)
+#endif
+
+/**
+ * Return a string for a UErrorCode value.
+ * The string will be the same as the name of the error code constant
+ * in the UErrorCode enum above.
+ * @stable ICU 2.0
+ */
+U_STABLE const char * U_EXPORT2
+u_errorName(UErrorCode code);
+
+
+#endif /* _UTYPES */
diff --git a/WebKit/mac/icu/unicode/uversion.h b/WebKit/mac/icu/unicode/uversion.h
new file mode 100644
index 0000000..f9a7755
--- /dev/null
+++ b/WebKit/mac/icu/unicode/uversion.h
@@ -0,0 +1,216 @@
+/*
+*******************************************************************************
+* Copyright (C) 2000-2004, International Business Machines
+* Corporation and others. All Rights Reserved.
+*******************************************************************************
+*
+* file name: uversion.h
+* encoding: US-ASCII
+* tab size: 8 (not used)
+* indentation:4
+*
+* Created by: Vladimir Weinstein
+*
+* Contains all the important version numbers for ICU.
+* Gets included by utypes.h and Windows .rc files
+*/
+
+/*===========================================================================*/
+/* Main ICU version information */
+/*===========================================================================*/
+
+#ifndef UVERSION_H
+#define UVERSION_H
+
+/** IMPORTANT: When updating version, the following things need to be done: */
+/** source/common/unicode/uversion.h - this file: update major, minor, */
+/** patchlevel, suffix, version, short version constants, namespace, */
+/** and copyright */
+/** source/common/common.dsp - update 'Output file name' on the link tab so */
+/** that it contains the new major/minor combination */
+/** source/i18n/i18n.dsp - same as for the common.dsp */
+/** source/layout/layout.dsp - same as for the common.dsp */
+/** source/stubdata/stubdata.dsp - same as for the common.dsp */
+/** source/extra/ustdio/ustdio.dsp - same as for the common.dsp */
+/** source/data/makedata.mak - change U_ICUDATA_NAME so that it contains */
+/** the new major/minor combination */
+/** source/tools/genren/genren.pl - use this script according to the README */
+/** in that folder */
+
+#include "unicode/umachine.h"
+
+/** The standard copyright notice that gets compiled into each library.
+ * This value will change in the subsequent releases of ICU
+ * @stable ICU 2.4
+ */
+#define U_COPYRIGHT_STRING \
+ " Copyright (C) 2004, International Business Machines Corporation and others. All Rights Reserved. "
+
+/** Maximum length of the copyright string.
+ * @stable ICU 2.4
+ */
+#define U_COPYRIGHT_STRING_LENGTH 128
+
+/** The current ICU major version as an integer.
+ * This value will change in the subsequent releases of ICU
+ * @stable ICU 2.4
+ */
+#define U_ICU_VERSION_MAJOR_NUM 3
+
+/** The current ICU minor version as an integer.
+ * This value will change in the subsequent releases of ICU
+ * @stable ICU 2.6
+ */
+#define U_ICU_VERSION_MINOR_NUM 2
+
+/** The current ICU patchlevel version as an integer.
+ * This value will change in the subsequent releases of ICU
+ * @stable ICU 2.4
+ */
+#define U_ICU_VERSION_PATCHLEVEL_NUM 0
+
+/** Glued version suffix for renamers
+ * This value will change in the subsequent releases of ICU
+ * @stable ICU 2.6
+ */
+#define U_ICU_VERSION_SUFFIX _3_2
+
+/** The current ICU library version as a dotted-decimal string. The patchlevel
+ * only appears in this string if it non-zero.
+ * This value will change in the subsequent releases of ICU
+ * @stable ICU 2.4
+ */
+#define U_ICU_VERSION "3.2"
+
+/** The current ICU library major/minor version as a string without dots, for library name suffixes.
+ * This value will change in the subsequent releases of ICU
+ * @stable ICU 2.6
+ */
+#define U_ICU_VERSION_SHORT "32"
+
+/** An ICU version consists of up to 4 numbers from 0..255.
+ * @stable ICU 2.4
+ */
+#define U_MAX_VERSION_LENGTH 4
+
+/** In a string, ICU version fields are delimited by dots.
+ * @stable ICU 2.4
+ */
+#define U_VERSION_DELIMITER '.'
+
+/** The maximum length of an ICU version string.
+ * @stable ICU 2.4
+ */
+#define U_MAX_VERSION_STRING_LENGTH 20
+
+/** The binary form of a version on ICU APIs is an array of 4 uint8_t.
+ * @stable ICU 2.4
+ */
+typedef uint8_t UVersionInfo[U_MAX_VERSION_LENGTH];
+
+#if U_HAVE_NAMESPACE && defined(XP_CPLUSPLUS)
+#if U_DISABLE_RENAMING
+#define U_ICU_NAMESPACE icu
+namespace U_ICU_NAMESPACE { }
+#else
+#define U_ICU_NAMESPACE icu_3_2
+namespace U_ICU_NAMESPACE { }
+namespace icu = U_ICU_NAMESPACE;
+#endif
+U_NAMESPACE_USE
+#endif
+
+
+/*===========================================================================*/
+/* General version helper functions. Definitions in putil.c */
+/*===========================================================================*/
+
+/**
+ * Parse a string with dotted-decimal version information and
+ * fill in a UVersionInfo structure with the result.
+ * Definition of this function lives in putil.c
+ *
+ * @param versionArray The destination structure for the version information.
+ * @param versionString A string with dotted-decimal version information,
+ * with up to four non-negative number fields with
+ * values of up to 255 each.
+ * @stable ICU 2.4
+ */
+U_STABLE void U_EXPORT2
+u_versionFromString(UVersionInfo versionArray, const char *versionString);
+
+/**
+ * Write a string with dotted-decimal version information according
+ * to the input UVersionInfo.
+ * Definition of this function lives in putil.c
+ *
+ * @param versionArray The version information to be written as a string.
+ * @param versionString A string buffer that will be filled in with
+ * a string corresponding to the numeric version
+ * information in versionArray.
+ * The buffer size must be at least U_MAX_VERSION_STRING_LENGTH.
+ * @stable ICU 2.4
+ */
+U_STABLE void U_EXPORT2
+u_versionToString(UVersionInfo versionArray, char *versionString);
+
+/**
+ * Gets the ICU release version. The version array stores the version information
+ * for ICU. For example, release "1.3.31.2" is then represented as 0x01031F02.
+ * Definition of this function lives in putil.c
+ *
+ * @param versionArray the version # information, the result will be filled in
+ * @stable ICU 2.0
+ */
+U_STABLE void U_EXPORT2
+u_getVersion(UVersionInfo versionArray);
+
+
+/*===========================================================================
+ * ICU collation framework version information
+ * Version info that can be obtained from a collator is affected by these
+ * numbers in a secret and magic way. Please use collator version as whole
+ *===========================================================================
+ */
+
+/** Collation runtime version (sort key generator, strcoll).
+ * If the version is different, sortkeys for the same string could be different
+ * version 2 was in ICU 1.8.1. changed is: compression intervals, French secondary
+ * compression, generating quad level always when strength is quad or more
+ * version 4 - ICU 2.2 - tracking UCA changes, ignore completely ignorables
+ * in contractions, ignore primary ignorables after shifted
+ * version 5 - ICU 2.8 - changed implicit generation code
+ * This value may change in the subsequent releases of ICU
+ * @stable ICU 2.4
+ */
+#define UCOL_RUNTIME_VERSION 5
+
+/** Builder code version. When this is different, same tailoring might result
+ * in assigning different collation elements to code points
+ * version 2 was in ICU 1.8.1. added support for prefixes, tweaked canonical
+ * closure. However, the tailorings should probably get same CEs assigned
+ * version 5 - ICU 2.2 - fixed some bugs, renamed some indirect values.
+ * version 6 - ICU 2.8 - fixed bug in builder that allowed 0xFF in primary values
+ * Backward compatible with the old rules.
+ * This value may change in the subsequent releases of ICU
+ * @stable ICU 2.4
+ */
+#define UCOL_BUILDER_VERSION 6
+
+/** *** Removed *** Instead we use the data we read from FractionalUCA.txt
+ * This is the version of FractionalUCA.txt tailoring rules
+ * Version 1 was in ICU 1.8.1. Version two contains canonical closure for
+ * supplementary code points
+ * Version 4 in ICU 2.2, following UCA=3.1.1d6, UCD=3.2.0
+ * This value may change in the subsequent releases of ICU
+ * @stable ICU 2.4
+ */
+/*#define UCOL_FRACTIONAL_UCA_VERSION 4*/
+
+/** This is the version of the tailorings
+ * This value may change in the subsequent releases of ICU
+ * @stable ICU 2.4
+ */
+#define UCOL_TAILORINGS_VERSION 1
+
+#endif