简体   繁体   中英

how to pass data from javascript to IOS Objective-c in webview?

I have a web app which i am using as Web-view app for android and IOS app.I need to pass user data to the web-view app which i achieved for android but i have no knowledge on how to do it for IOS web-view. I have my IOS code in x-code which is in objective-c and i need to send data from frontend javascript to Objective-c, which can access it. below is my javascript code


var myAppName = 'myfakeappname';
var myActionType = 'myJavascriptActionType';
var myActionParameters = {}; // put extra info into a dict if you need it

// (separating the actionType from parameters makes it easier to parse in ObjC.)
var jsonString = (JSON.stringify(myActionParameters));
var escapedJsonParameters = escape(jsonString);
var url = myAppName + '://' + myActionType + "#" + escapedJsonParameters;
document.location.href = url;

below is my code from Viewcontroller.m

#import "ViewController.h"
#import <WebKit/WebKit.h>


@interface ViewController ()<WKNavigationDelegate>
@property (weak, nonatomic) IBOutlet WKWebView *vwWeb;
@property (weak, nonatomic) IBOutlet UIView *vwLoading;

@end

@implementation ViewController

- (void)viewDidLoad {
    [super viewDidLoad];


    self.vwWeb.navigationDelegate = self;
    NSURL *nsurl=[NSURL URLWithString:@"http://localhost:3000"];
    NSURLRequest *nsrequest=[NSURLRequest requestWithURL:nsurl];
    [self.vwWeb loadRequest:nsrequest];
    // Do any additional setup after loading the view, typically from a nib.
}

-(void)webView:(WKWebView *)webView didFinishNavigation:(WKNavigation *)navigation{

    self.vwLoading.hidden = YES;
}




//below is the code i copy pasted from various resourses i found from forums

- (BOOL)webView:( WKWebView *)webView
        shouldStartLoadWithRequest:(NSURLRequest *)request
                    navigationType:(UIWebViewNavigationType)navigationType {

    // these need to match the values defined in your JavaScript
    NSString *myAppScheme = @"myfakeappname";
    NSString *myActionType = @"myJavascriptActionType";

    // ignore legit webview requests so they load normally
    if (![request.URL.scheme isEqualToString:myAppScheme]) {
        return YES;
    }

    // get the action from the path
    NSString *actionType = request.URL.host;
    // deserialize the request JSON
    NSString *jsonDictString = [request.URL.fragment stringByAddingPercentEncodingWithAllowedCharacters:[NSCharacterSet URLHostAllowedCharacterSet]];
    NSLog(@"Hello, World!");
    // look at the actionType and do whatever you want here
    if ([actionType isEqualToString:myActionType]) {
        NSLog(@"Missing function name");
        // do something in response to your javascript action
        // if you used an action parameters dict, deserialize and inspect it here
    }


    // make sure to return NO so that your webview doesn't try to load your made-up URL
    return NO;
}


@end

Any help or suggestion will be greatly appreciated.

If your parameters is in the url, extract it by this property navigationAction.request.url in this function to get the params:

func webView(_ webView: WKWebView, decidePolicyFor navigationAction: WKNavigationAction, decisionHandler: @escaping (WKNavigationActionPolicy) -> Void)

Exactly like you started:

  1. In JavaScript the buttons/links that need to trigger something on iOS app should do: window.location="myappname://func1";

  2. Javascript should also have a accessible method (ie should be accessible from browser console for example) myobject.jsfunc()

  3. On iOS WebView you intercept requests with myappname:// URL, something like:

- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType {

    NSURL *URL = [request URL];
    NSString *requestStr = [[request URL] absoluteString]; //Get the URL
    //NSLog(@"Native method call '%@'", requestStr);

    if ([requestStr hasPrefix:@"openpanzer"]) {
        //The [URL host] is the next part of the link so we can use that like a selector
        NSString *selectorName = [URL host];
        id data = nil;        
        NSMutableArray *parameters = [NSMutableArray array];
        if ( ![[URL path] isEqualToString:@""] )
        {
            selectorName =  [NSString stringWithFormat:@"%@:", selectorName];
            parameters = [NSMutableArray arrayWithArray: [[URL path] componentsSeparatedByString:@"/"] ];
            [parameters removeObjectAtIndex:0]; //first object is just a slash "/"
            if ( [parameters count] == 0 ) {
                data = nil;
                NSLog(@"NIL parameter call");
            }
            else if ( [parameters count] == 1 ) {
                data = [parameters objectAtIndex:0];
                NSLog(@"Single parameter call %@", data);
            }
            else {
                data = parameters;
            }
        }

        SEL method = NSSelectorFromString( selectorName );
        if ([nativeGlue respondsToSelector:method]) {
            if (data == nil)
                [nativeGlue performSelector:method];
            else
                [nativeGlue performSelector:method withObject:data];
        }
        else {
            NSLog(@"Can't find native method '%@' with param '%@'", selectorName, data);
        }


        return NO;
    }
    return YES;
}
  1. On iOS (WebViewDelegate or AppDelegate) define your func1 ie: - (void) func1

  2. If you need to send back results to your javascript app use:

[webView callJSFunction: jsFunc];

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM