X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/c9ccc09c64f4c29d4667796bef7b507d9e8d25ed..eea4d01c65f9b29baa1193db762b4c6b8144af24:/src/osx/webview_webkit.mm diff --git a/src/osx/webview_webkit.mm b/src/osx/webview_webkit.mm index 59ede2dbb4..f3efc4e2e5 100644 --- a/src/osx/webview_webkit.mm +++ b/src/osx/webview_webkit.mm @@ -14,6 +14,9 @@ #include "wx/osx/webview_webkit.h" +#if wxUSE_WEBVIEW_WEBKIT && (defined(__WXOSX_COCOA__) \ + || defined(__WXOSX_CARBON__)) + // For compilers that support precompilation, includes "wx.h". #include "wx/wxprec.h" @@ -21,31 +24,24 @@ #include "wx/wx.h" #endif -#if wxHAVE_WEB_BACKEND_OSX_WEBKIT - -#ifdef __WXCOCOA__ -#include "wx/cocoa/autorelease.h" -#else #include "wx/osx/private.h" +#include "wx/cocoa/string.h" +#include "wx/hashmap.h" +#include "wx/filesys.h" #include #include #include -#endif #include -// FIXME: find cleaner way to find the wxWidgets ID of a webview than this hack -#include -std::map wx_webviewctrls; - #define DEBUG_WEBKIT_SIZING 0 // ---------------------------------------------------------------------------- // macros // ---------------------------------------------------------------------------- -IMPLEMENT_DYNAMIC_CLASS(wxWebViewWebKit, wxControl) +wxIMPLEMENT_DYNAMIC_CLASS(wxWebViewWebKit, wxWebView); BEGIN_EVENT_TABLE(wxWebViewWebKit, wxControl) #if defined(__WXMAC__) && wxOSX_USE_CARBON @@ -301,48 +297,16 @@ DEFINE_ONE_SHOT_HANDLER_GETTER( wxWebViewWebKitEventHandler ) #endif -//--------------------------------------------------------- -// helper functions for NSString<->wxString conversion -//--------------------------------------------------------- - -inline wxString wxStringWithNSString(NSString *nsstring) +@interface WebViewLoadDelegate : NSObject { -#if wxUSE_UNICODE - return wxString([nsstring UTF8String], wxConvUTF8); -#else - return wxString([nsstring lossyCString]); -#endif // wxUSE_UNICODE -} - -inline NSString* wxNSStringWithWxString(const wxString &wxstring) -{ -#if wxUSE_UNICODE - return [NSString stringWithUTF8String: wxstring.mb_str(wxConvUTF8)]; -#else - return [NSString stringWithCString: wxstring.c_str() length:wxstring.Len()]; -#endif // wxUSE_UNICODE + wxWebViewWebKit* webKitWindow; } -inline int wxNavTypeFromWebNavType(int type){ - if (type == WebNavigationTypeLinkClicked) - return wxWEBKIT_NAV_LINK_CLICKED; - - if (type == WebNavigationTypeFormSubmitted) - return wxWEBKIT_NAV_FORM_SUBMITTED; - - if (type == WebNavigationTypeBackForward) - return wxWEBKIT_NAV_BACK_NEXT; - - if (type == WebNavigationTypeReload) - return wxWEBKIT_NAV_RELOAD; - - if (type == WebNavigationTypeFormResubmitted) - return wxWEBKIT_NAV_FORM_RESUBMITTED; +- initWithWxWindow: (wxWebViewWebKit*)inWindow; - return wxWEBKIT_NAV_OTHER; -} +@end -@interface MyFrameLoadMonitor : NSObject +@interface WebViewPolicyDelegate : NSObject { wxWebViewWebKit* webKitWindow; } @@ -351,13 +315,14 @@ inline int wxNavTypeFromWebNavType(int type){ @end -@interface MyPolicyDelegate : NSObject -{ - wxWebViewWebKit* webKitWindow; -} +//We use a hash to map scheme names to wxWebHandlers +WX_DECLARE_STRING_HASH_MAP(wxSharedPtr, wxStringToWebHandlerMap); -- initWithWxWindow: (wxWebViewWebKit*)inWindow; +static wxStringToWebHandlerMap g_stringHandlerMap; +@interface WebViewCustomProtocol : NSURLProtocol +{ +} @end // ---------------------------------------------------------------------------- @@ -372,125 +337,80 @@ bool wxWebViewWebKit::Create(wxWindow *parent, const wxString& name) { m_busy = false; - //m_pageTitle = _("Untitled Page"); - //still needed for wxCocoa?? -/* - int width, height; - wxSize sizeInstance; - if (size.x == wxDefaultCoord || size.y == wxDefaultCoord) - { - m_parent->GetClientSize(&width, &height); - sizeInstance.x = width; - sizeInstance.y = height; - } - else - { - sizeInstance.x = size.x; - sizeInstance.y = size.y; - } -*/ - // now create and attach WebKit view... -#ifdef __WXCOCOA__ - wxControl::Create(parent, m_windowID, pos, sizeInstance, style, name); - SetSize(pos.x, pos.y, sizeInstance.x, sizeInstance.y); - - wxTopLevelWindowCocoa *topWin = wxDynamicCast(this, wxTopLevelWindowCocoa); - NSWindow* nsWin = topWin->GetNSWindow(); - NSRect rect; - rect.origin.x = pos.x; - rect.origin.y = pos.y; - rect.size.width = sizeInstance.x; - rect.size.height = sizeInstance.y; - m_webView = (WebView*)[[WebView alloc] initWithFrame:rect - frameName:@"webkitFrame" - groupName:@"webkitGroup"]; - SetNSView(m_webView); - [m_cocoaNSView release]; - - if(m_parent) m_parent->CocoaAddChild(this); - SetInitialFrameRect(pos,sizeInstance); -#else - m_macIsUserPane = false; + DontCreatePeer(); wxControl::Create(parent, winID, pos, size, style, wxDefaultValidator, name); #if wxOSX_USE_CARBON - m_peer = new wxMacControl(this); + wxMacControl* peer = new wxMacControl(this); WebInitForCarbon(); - HIWebViewCreate( m_peer->GetControlRefAddr() ); + HIWebViewCreate( peer->GetControlRefAddr() ); - m_webView = (WebView*) HIWebViewGetWebView( m_peer->GetControlRef() ); + m_webView = (WebView*) HIWebViewGetWebView( peer->GetControlRef() ); #if MAC_OS_X_VERSION_MAX_ALLOWED >= MAC_OS_X_VERSION_10_3 if ( UMAGetSystemVersion() >= 0x1030 ) - HIViewChangeFeatures( m_peer->GetControlRef() , kHIViewIsOpaque , 0 ) ; + HIViewChangeFeatures( peer->GetControlRef() , kHIViewIsOpaque , 0 ) ; #endif - InstallControlEventHandler(m_peer->GetControlRef(), + InstallControlEventHandler(peer->GetControlRef(), GetwxWebViewWebKitEventHandlerUPP(), GetEventTypeCount(eventList), eventList, this, (EventHandlerRef *)&m_webKitCtrlEventHandler); + SetPeer(peer); #else NSRect r = wxOSXGetFrameForControl( this, pos , size ) ; m_webView = [[WebView alloc] initWithFrame:r frameName:@"webkitFrame" groupName:@"webkitGroup"]; - m_peer = new wxWidgetCocoaImpl( this, m_webView ); + SetPeer(new wxWidgetCocoaImpl( this, m_webView )); #endif - wx_webviewctrls[m_webView] = this; - MacPostControlCreate(pos, size); #if wxOSX_USE_CARBON - HIViewSetVisible( m_peer->GetControlRef(), true ); + HIViewSetVisible( GetPeer()->GetControlRef(), true ); #endif [m_webView setHidden:false]; -#endif + // Register event listener interfaces - MyFrameLoadMonitor* myFrameLoadMonitor = - [[MyFrameLoadMonitor alloc] initWithWxWindow: this]; + WebViewLoadDelegate* loadDelegate = + [[WebViewLoadDelegate alloc] initWithWxWindow: this]; - [m_webView setFrameLoadDelegate:myFrameLoadMonitor]; + [m_webView setFrameLoadDelegate:loadDelegate]; // this is used to veto page loads, etc. - MyPolicyDelegate* myPolicyDelegate = - [[MyPolicyDelegate alloc] initWithWxWindow: this]; + WebViewPolicyDelegate* policyDelegate = + [[WebViewPolicyDelegate alloc] initWithWxWindow: this]; + + [m_webView setPolicyDelegate:policyDelegate]; - [m_webView setPolicyDelegate:myPolicyDelegate]; + //Register our own class for custom scheme handling + [NSURLProtocol registerClass:[WebViewCustomProtocol class]]; - InternalLoadURL(strURL); + LoadUrl(strURL); return true; } wxWebViewWebKit::~wxWebViewWebKit() { - MyFrameLoadMonitor* myFrameLoadMonitor = [m_webView frameLoadDelegate]; - MyPolicyDelegate* myPolicyDelegate = [m_webView policyDelegate]; + WebViewLoadDelegate* loadDelegate = [m_webView frameLoadDelegate]; + WebViewPolicyDelegate* policyDelegate = [m_webView policyDelegate]; [m_webView setFrameLoadDelegate: nil]; [m_webView setPolicyDelegate: nil]; - if (myFrameLoadMonitor) - [myFrameLoadMonitor release]; + if (loadDelegate) + [loadDelegate release]; - if (myPolicyDelegate) - [myPolicyDelegate release]; + if (policyDelegate) + [policyDelegate release]; } // ---------------------------------------------------------------------------- // public methods // ---------------------------------------------------------------------------- -void wxWebViewWebKit::InternalLoadURL(const wxString &url) -{ - if( !m_webView ) - return; - - [[m_webView mainFrame] loadRequest:[NSURLRequest requestWithURL: - [NSURL URLWithString:wxNSStringWithWxString(url)]]]; -} - bool wxWebViewWebKit::CanGoBack() { if ( !m_webView ) @@ -512,10 +432,7 @@ void wxWebViewWebKit::GoBack() if ( !m_webView ) return; - bool result = [(WebView*)m_webView goBack]; - - // TODO: return result (if it also exists in other backends...) - //return result; + [(WebView*)m_webView goBack]; } void wxWebViewWebKit::GoForward() @@ -523,10 +440,7 @@ void wxWebViewWebKit::GoForward() if ( !m_webView ) return; - bool result = [(WebView*)m_webView goForward]; - - // TODO: return result (if it also exists in other backends...) - //return result; + [(WebView*)m_webView goForward]; } void wxWebViewWebKit::Reload(wxWebViewReloadFlags flags) @@ -587,15 +501,6 @@ wxString wxWebViewWebKit::GetPageSource() return wxEmptyString; } -wxString wxWebViewWebKit::GetSelection() -{ - if ( !m_webView ) - return wxEmptyString; - - NSString* selectedText = [[m_webView selectedDOMRange] toString]; - return wxStringWithNSString( selectedText ); -} - bool wxWebViewWebKit::CanIncreaseTextSize() { if ( !m_webView ) @@ -735,7 +640,7 @@ wxString wxWebViewWebKit::GetSelectedText() void wxWebViewWebKit::RunScript(const wxString& javascript) { if ( !m_webView ) - return wxEmptyString; + return; [[m_webView windowScriptObject] evaluateWebScript: (NSString*)wxNSStringWithWxString( javascript )]; @@ -822,7 +727,7 @@ void wxWebViewWebKit::OnSize(wxSizeEvent &event) void wxWebViewWebKit::MacVisibilityChanged(){ #if defined(__WXMAC__) && wxOSX_USE_CARBON - bool isHidden = !IsControlVisible( m_peer->GetControlRef()); + bool isHidden = !IsControlVisible( GetPeer()->GetControlRef()); if (!isHidden) [(WebView*)m_webView display]; @@ -832,7 +737,8 @@ void wxWebViewWebKit::MacVisibilityChanged(){ void wxWebViewWebKit::LoadUrl(const wxString& url) { - InternalLoadURL(url); + [[m_webView mainFrame] loadRequest:[NSURLRequest requestWithURL: + [NSURL URLWithString:wxNSStringWithWxString(url)]]]; } wxString wxWebViewWebKit::GetCurrentURL() @@ -842,7 +748,7 @@ wxString wxWebViewWebKit::GetCurrentURL() wxString wxWebViewWebKit::GetCurrentTitle() { - return GetPageTitle(); + return wxStringWithNSString([m_webView mainFrameTitle]); } float wxWebViewWebKit::GetWebkitZoom() @@ -932,7 +838,7 @@ void wxWebViewWebKit::Cut() if ( !m_webView ) return; - [(WebView*)m_webView cut]; + [(WebView*)m_webView cut:m_webView]; } void wxWebViewWebKit::Copy() @@ -940,7 +846,7 @@ void wxWebViewWebKit::Copy() if ( !m_webView ) return; - [(WebView*)m_webView copy]; + [(WebView*)m_webView copy:m_webView]; } void wxWebViewWebKit::Paste() @@ -948,7 +854,7 @@ void wxWebViewWebKit::Paste() if ( !m_webView ) return; - [(WebView*)m_webView paste]; + [(WebView*)m_webView paste:m_webView]; } void wxWebViewWebKit::DeleteSelection() @@ -959,6 +865,128 @@ void wxWebViewWebKit::DeleteSelection() [(WebView*)m_webView deleteSelection]; } +bool wxWebViewWebKit::HasSelection() +{ + DOMRange* range = [m_webView selectedDOMRange]; + if(!range) + { + return false; + } + else + { + return true; + } +} + +void wxWebViewWebKit::ClearSelection() +{ + //We use javascript as selection isn't exposed at the moment in webkit + RunScript("window.getSelection().removeAllRanges();"); +} + +void wxWebViewWebKit::SelectAll() +{ + RunScript("window.getSelection().selectAllChildren(document.body);"); +} + +wxString wxWebViewWebKit::GetSelectedSource() +{ + wxString script = ("var range = window.getSelection().getRangeAt(0);" + "var element = document.createElement('div');" + "element.appendChild(range.cloneContents());" + "return element.innerHTML;"); + id result = [[m_webView windowScriptObject] + evaluateWebScript:wxNSStringWithWxString(script)]; + return wxStringWithNSString([result stringValue]); +} + +wxString wxWebViewWebKit::GetPageText() +{ + id result = [[m_webView windowScriptObject] + evaluateWebScript:@"document.body.textContent"]; + return wxStringWithNSString([result stringValue]); +} + +void wxWebViewWebKit::EnableHistory(bool enable) +{ + if ( !m_webView ) + return; + + [m_webView setMaintainsBackForwardList:enable]; +} + +void wxWebViewWebKit::ClearHistory() +{ + [m_webView setMaintainsBackForwardList:NO]; + [m_webView setMaintainsBackForwardList:YES]; +} + +wxVector > wxWebViewWebKit::GetBackwardHistory() +{ + wxVector > backhist; + WebBackForwardList* history = [m_webView backForwardList]; + int count = [history backListCount]; + for(int i = -count; i < 0; i++) + { + WebHistoryItem* item = [history itemAtIndex:i]; + wxString url = wxStringWithNSString([item URLString]); + wxString title = wxStringWithNSString([item title]); + wxWebHistoryItem* wxitem = new wxWebHistoryItem(url, title); + wxitem->m_histItem = item; + wxSharedPtr itemptr(wxitem); + backhist.push_back(itemptr); + } + return backhist; +} + +wxVector > wxWebViewWebKit::GetForwardHistory() +{ + wxVector > forwardhist; + WebBackForwardList* history = [m_webView backForwardList]; + int count = [history forwardListCount]; + for(int i = 1; i <= count; i++) + { + WebHistoryItem* item = [history itemAtIndex:i]; + wxString url = wxStringWithNSString([item URLString]); + wxString title = wxStringWithNSString([item title]); + wxWebHistoryItem* wxitem = new wxWebHistoryItem(url, title); + wxitem->m_histItem = item; + wxSharedPtr itemptr(wxitem); + forwardhist.push_back(itemptr); + } + return forwardhist; +} + +void wxWebViewWebKit::LoadHistoryItem(wxSharedPtr item) +{ + [m_webView goToBackForwardItem:item->m_histItem]; +} + +bool wxWebViewWebKit::CanUndo() +{ + return [[m_webView undoManager] canUndo]; +} + +bool wxWebViewWebKit::CanRedo() +{ + return [[m_webView undoManager] canRedo]; +} + +void wxWebViewWebKit::Undo() +{ + [[m_webView undoManager] undo]; +} + +void wxWebViewWebKit::Redo() +{ + [[m_webView undoManager] redo]; +} + +void wxWebViewWebKit::RegisterHandler(wxSharedPtr handler) +{ + g_stringHandlerMap[handler->GetName()] = handler; +} + //------------------------------------------------------------ // Listener interfaces //------------------------------------------------------------ @@ -968,7 +996,7 @@ void wxWebViewWebKit::DeleteSelection() // destroyed. Therefore, we must be careful to check both the existence // of the Carbon control and the event handler before firing events. -@implementation MyFrameLoadMonitor +@implementation WebViewLoadDelegate - initWithWxWindow: (wxWebViewWebKit*)inWindow { @@ -980,20 +1008,18 @@ void wxWebViewWebKit::DeleteSelection() - (void)webView:(WebView *)sender didStartProvisionalLoadForFrame:(WebFrame *)frame { - wxASSERT(wx_webviewctrls.find(sender) != wx_webviewctrls.end()); - wx_webviewctrls[sender]->m_busy = true; + webKitWindow->m_busy = true; } - (void)webView:(WebView *)sender didCommitLoadForFrame:(WebFrame *)frame { - wxASSERT(wx_webviewctrls.find(sender) != wx_webviewctrls.end()); - wx_webviewctrls[sender]->m_busy = true; + webKitWindow->m_busy = true; if (webKitWindow && frame == [sender mainFrame]){ NSString *url = [[[[frame dataSource] request] URL] absoluteString]; wxString target = wxStringWithNSString([frame name]); wxWebNavigationEvent thisEvent(wxEVT_COMMAND_WEB_VIEW_NAVIGATED, - wx_webviewctrls[sender]->GetId(), + webKitWindow->GetId(), wxStringWithNSString( url ), target, false); @@ -1004,15 +1030,14 @@ void wxWebViewWebKit::DeleteSelection() - (void)webView:(WebView *)sender didFinishLoadForFrame:(WebFrame *)frame { - wxASSERT(wx_webviewctrls.find(sender) != wx_webviewctrls.end()); - wx_webviewctrls[sender]->m_busy = false; + webKitWindow->m_busy = false; if (webKitWindow && frame == [sender mainFrame]){ NSString *url = [[[[frame dataSource] request] URL] absoluteString]; wxString target = wxStringWithNSString([frame name]); wxWebNavigationEvent thisEvent(wxEVT_COMMAND_WEB_VIEW_LOADED, - wx_webviewctrls[sender]->GetId(), + webKitWindow->GetId(), wxStringWithNSString( url ), target, false); @@ -1098,8 +1123,7 @@ wxString nsErrorToWxHtmlError(NSError* error, wxWebNavigationError* out) - (void)webView:(WebView *)sender didFailLoadWithError:(NSError*) error forFrame:(WebFrame *)frame { - wxASSERT(wx_webviewctrls.find(sender) != wx_webviewctrls.end()); - wx_webviewctrls[sender]->m_busy = false; + webKitWindow->m_busy = false; if (webKitWindow && frame == [sender mainFrame]){ NSString *url = [[[[frame dataSource] request] URL] absoluteString]; @@ -1107,7 +1131,7 @@ wxString nsErrorToWxHtmlError(NSError* error, wxWebNavigationError* out) wxWebNavigationError type; wxString description = nsErrorToWxHtmlError(error, &type); wxWebNavigationEvent thisEvent(wxEVT_COMMAND_WEB_VIEW_ERROR, - wx_webviewctrls[sender]->GetId(), + webKitWindow->GetId(), wxStringWithNSString( url ), wxEmptyString, false); thisEvent.SetString(description); @@ -1124,8 +1148,7 @@ wxString nsErrorToWxHtmlError(NSError* error, wxWebNavigationError* out) didFailProvisionalLoadWithError:(NSError*)error forFrame:(WebFrame *)frame { - wxASSERT(wx_webviewctrls.find(sender) != wx_webviewctrls.end()); - wx_webviewctrls[sender]->m_busy = false; + webKitWindow->m_busy = false; if (webKitWindow && frame == [sender mainFrame]){ NSString *url = [[[[frame provisionalDataSource] request] URL] @@ -1134,7 +1157,7 @@ wxString nsErrorToWxHtmlError(NSError* error, wxWebNavigationError* out) wxWebNavigationError type; wxString description = nsErrorToWxHtmlError(error, &type); wxWebNavigationEvent thisEvent(wxEVT_COMMAND_WEB_VIEW_ERROR, - wx_webviewctrls[sender]->GetId(), + webKitWindow->GetId(), wxStringWithNSString( url ), wxEmptyString, false); thisEvent.SetString(description); @@ -1148,14 +1171,20 @@ wxString nsErrorToWxHtmlError(NSError* error, wxWebNavigationError* out) - (void)webView:(WebView *)sender didReceiveTitle:(NSString *)title forFrame:(WebFrame *)frame { - if (webKitWindow && frame == [sender mainFrame]) - { - webKitWindow->SetPageTitle(wxStringWithNSString( title )); - } + wxString target = wxStringWithNSString([frame name]); + wxWebNavigationEvent thisEvent(wxEVT_COMMAND_WEB_VIEW_TITLE_CHANGED, + webKitWindow->GetId(), + webKitWindow->GetCurrentURL(), + target, true); + + thisEvent.SetString(wxStringWithNSString(title)); + + if (webKitWindow && webKitWindow->GetEventHandler()) + webKitWindow->GetEventHandler()->ProcessEvent(thisEvent); } @end -@implementation MyPolicyDelegate +@implementation WebViewPolicyDelegate - initWithWxWindow: (wxWebViewWebKit*)inWindow { @@ -1170,15 +1199,13 @@ wxString nsErrorToWxHtmlError(NSError* error, wxWebNavigationError* out) frame:(WebFrame *)frame decisionListener:(id)listener { - //wxUnusedVar(sender); wxUnusedVar(frame); - wxASSERT(wx_webviewctrls.find(sender) != wx_webviewctrls.end()); - wx_webviewctrls[sender]->m_busy = true; + webKitWindow->m_busy = true; NSString *url = [[request URL] absoluteString]; wxString target = wxStringWithNSString([frame name]); wxWebNavigationEvent thisEvent(wxEVT_COMMAND_WEB_VIEW_NAVIGATING, - wx_webviewctrls[sender]->GetId(), + webKitWindow->GetId(), wxStringWithNSString( url ), target, true); if (webKitWindow && webKitWindow->GetEventHandler()) @@ -1186,7 +1213,7 @@ wxString nsErrorToWxHtmlError(NSError* error, wxWebNavigationError* out) if (thisEvent.IsVetoed()) { - wx_webviewctrls[sender]->m_busy = false; + webKitWindow->m_busy = false; [listener ignore]; } else @@ -1201,11 +1228,85 @@ wxString nsErrorToWxHtmlError(NSError* error, wxWebNavigationError* out) newFrameName:(NSString *)frameName decisionListener:(id < WebPolicyDecisionListener >)listener { - wxUnusedVar(sender); wxUnusedVar(actionInformation); + NSString *url = [[request URL] absoluteString]; + wxWebNavigationEvent thisEvent(wxEVT_COMMAND_WEB_VIEW_NEWWINDOW, + webKitWindow->GetId(), + wxStringWithNSString( url ), "", true); + + if (webKitWindow && webKitWindow->GetEventHandler()) + webKitWindow->GetEventHandler()->ProcessEvent(thisEvent); + [listener ignore]; } @end -#endif //wxHAVE_WEB_BACKEND_OSX_WEBKIT +@implementation WebViewCustomProtocol + ++ (BOOL)canInitWithRequest:(NSURLRequest *)request +{ + NSString *scheme = [[request URL] scheme]; + + wxStringToWebHandlerMap::const_iterator it; + for( it = g_stringHandlerMap.begin(); it != g_stringHandlerMap.end(); ++it ) + { + if(it->first.IsSameAs(wxStringWithNSString(scheme))) + { + return YES; + } + } + + return NO; +} + ++ (NSURLRequest *)canonicalRequestForRequest:(NSURLRequest *)request +{ + //We don't do any processing here as the wxWebHandler classes do it + return request; +} + +- (void)startLoading +{ + NSURLRequest *request = [self request]; + NSString* path = [[request URL] absoluteString]; + + wxString wxpath = wxStringWithNSString(path); + wxString scheme = wxStringWithNSString([[request URL] scheme]); + wxFSFile* file = g_stringHandlerMap[scheme]->GetFile(wxpath); + size_t length = file->GetStream()->GetLength(); + + + NSURLResponse *response = [[NSURLResponse alloc] initWithURL:[request URL] + MIMEType:wxNSStringWithWxString(file->GetMimeType()) + expectedContentLength:length + textEncodingName:nil]; + + //Load the data, we malloc it so it is tidied up properly + void* buffer = malloc(length); + file->GetStream()->Read(buffer, length); + NSData *data = [[NSData alloc] initWithBytesNoCopy:buffer length:length]; + + id client = [self client]; + + //We do not support caching anything yet + [client URLProtocol:self didReceiveResponse:response + cacheStoragePolicy:NSURLCacheStorageNotAllowed]; + + //Set the data + [client URLProtocol:self didLoadData:data]; + + //Notify that we have finished + [client URLProtocolDidFinishLoading:self]; + + [response release]; +} + +- (void)stopLoading +{ + +} + +@end + +#endif //wxUSE_WEBVIEW_WEBKIT