Code: Select all
EnableExplicit
; *** import the required C functions ***
ImportC ""
HIWebViewGetWebView(inView)
oClassAddMethod(class, selector, imp, types.p-ascii) As "_class_addMethod"
oClass(name.p-ascii) As "_objc_lookUpClass"
oCreateClass(superclass, name.p-ascii, extraBytes = 0) As "_objc_allocateClassPair"
oInstance(class, extraBytes = 0) As "_class_createInstance"
CocoaMessageSend(receiver, selector, arg1 = #Null, arg2 = #Null, arg3 = #Null) As "_objc_msgSend"
oRegisterClass(class) As "_objc_registerClassPair"
oSel(name.p-ascii) As "_sel_registerName"
EndImport
; *** selectors that are used a lot ***
Global SEL_provisionalDataSource = oSel("provisionalDataSource")
Global SEL_dataSource = oSel("dataSource")
Global SEL_request = oSel("request")
Global SEL_URL = oSel("URL")
Global SEL_absoluteString = oSel("absoluteString")
Global SEL_length = oSel("length")
Global SEL_getCharacters_range_ = oSel("getCharacters:range:")
Global SEL_stopLoading = oSel("stopLoading")
; *** functions to get frame url ***
Procedure.s StringFromNSString(nsstring)
Protected len = CocoaMessageSend(nsstring, SEL_length)
Protected *mem = malloc_(len << 1); allocate 16 byte aligned uninitialized memory
CocoaMessageSend(nsstring, SEL_getCharacters_range_, *mem, 0, len)
Protected result.s = PeekS(*mem, len, #PB_Unicode)
free_(*mem)
ProcedureReturn result
EndProcedure
Procedure.s GetFrameURL(frame, provisional = #False)
Protected source
If provisional
source = CocoaMessageSend(frame, SEL_provisionalDataSource)
Else
source = CocoaMessageSend(frame, SEL_dataSource)
EndIf
Protected urlString = CocoaMessageSend(CocoaMessageSend(CocoaMessageSend(source, SEL_request), SEL_URL), SEL_absoluteString)
ProcedureReturn StringFromNSString(urlString)
EndProcedure
; *** the functions for our delegate class ***
ProcedureC DidStartProvisionalLoad(obj, sel, webview, frame); load starts
Protected frameUrl.s = GetFrameURL(frame, #True)
Debug "Load : " + frameUrl
If frameUrl = "http://www.purebasic.com/news.php"
CocoaMessageSend(frame, SEL_stopLoading)
MessageRequester("", "No news today!")
EndIf
EndProcedure
ProcedureC ServerRedirect(obj, sel, webview, frame); server redirect
Debug "Redirect : " + GetFrameURL(frame, #True)
EndProcedure
ProcedureC LoadComplete(obj, sel, webview, frame); load complete
Debug "Finished loading : " + GetFrameURL(frame)
EndProcedure
ProcedureC Anchor(obj, sel, webview, frame); anchor within page
Debug "Anchor : " + GetFrameURL(frame)
EndProcedure
; *** create the delegate class and instance ***
Define FrameLoadDelegateClass = oCreateClass(oClass("NSObject"), "PB_FrameLoadDelegate"); PB_FrameLoadDelegate class extends NSObject
oClassAddMethod(FrameLoadDelegateClass, oSel("webView:didStartProvisionalLoadForFrame:"), @DidStartProvisionalLoad(), "v@:@@")
oClassAddMethod(FrameLoadDelegateClass, oSel("webView:didReceiveServerRedirectForProvisionalLoadForFrame:"), @ServerRedirect(), "v@:@@")
oClassAddMethod(FrameLoadDelegateClass, oSel("webView:didFinishLoadForFrame:"), @LoadComplete(), "v@:@@")
oClassAddMethod(FrameLoadDelegateClass, oSel("webView:didChangeLocationWithinPageForFrame:"), @Anchor(), "v@:@@")
oRegisterClass(FrameLoadDelegateClass)
Define FrameLoadDelegate = oInstance(FrameLoadDelegateClass)
; *** class and instance are created now ***
; test the frame load delegate
If OpenWindow(0, 0, 0, 600, 340, "WebPrint", #PB_Window_SystemMenu | #PB_Window_ScreenCentered)
ButtonGadget(0, 10, 10, 100, 20, "Load page")
Define PBWebView = WebGadget(#PB_Any, 10, 50, 580, 280, "")
Define WebView = HIWebViewGetWebView(GadgetID(PBWebView))
CocoaMessageSend(WebView, oSel("setFrameLoadDelegate:"), FrameLoadDelegate)
Repeat
Define EventID = WaitWindowEvent()
If EventID = #PB_Event_Gadget
Select EventGadget()
Case 0
SetGadgetText(PBWebView, "http://www.purebasic.com")
EndSelect
EndIf
Until EventID = #PB_Event_CloseWindow
EndIf