Executing an objective-c function from JavaScript

How can I call an Objective-C method from JavaScript in a UIWebView, passing and alerting a parameter? I have tried various methods but none seem to work.

- (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType
{
    NSURL *URL = [request URL];
    if ([[URL scheme] isEqualToString:@"donordialog"])
    {
        // Extract the function name from the URL
        NSString *functionString = [URL resourceSpecifier];

        if ([functionString hasPrefix:@"bloodTypeChanged"])
        {
            // Extract and log the parameter passed in the function call
            NSString *parameter = [functionString stringByReplacingOccurrencesOfString:@"bloodTypeChanged" withString:@""];
            parameter = [parameter stringByReplacingOccurrencesOfString:@"(" withString:@""];
            parameter = [parameter stringByReplacingOccurrencesOfString:@")" withString:@""];

            UIAlertView *alert=[[UIAlertView alloc] initWithTitle:@"iosdan javascripti"
                                                           message:@"ddddddddd"
                                                          delegate:nil
                                                     cancelButtonTitle:@"OK"
                                                     otherButtonTitles:nil];

            [alert show];
        }

        return NO;
    }

    return YES;
}

JavaScript function:

function myFunction() {
    url = "http://example.com";
    window.location = "donordialog:blooTypeChanged(" + url + ")";
}

HTML button:

<button onclick="myFunction()">click me</button>

I am trying to achieve functionality similar to calling a Java method from JavaScript on an Android WebView. Any help would be appreciated. Thank you.

Answer №1

Looking for a simple solution that doesn't rely on JavascriptCore for compatibility with older systems? Consider this implementation without JavaScriptCore, perfect for UIWebView (not UIScrollView).

//viewcontroller.h

@interface ViewController : UIViewController<UIWebViewDelegate>

@property (strong, nonatomic) IBOutlet UIWebView *viewWeb;
@end

//viewcontroller.m

- (void)viewDidLoad
{
    [super viewDidLoad];


    NSString *fullURL = @"http:player.fusion.fm";
    NSURL *url = [NSURL URLWithString:fullURL];
    NSURLRequest *requestObj = [NSURLRequest requestWithURL:url];
    [_viewWeb loadRequest:requestObj];
   _viewWeb.delegate = self;
 }

 -(BOOL)webView:(UIWebView *)_viewWeb shouldStartLoadWithRequest:(NSURLRequest *)request   navigationType:(UIWebViewNavigationType)navigationType {
    NSURL *url = request.URL;
    if ([[url scheme] isEqualToString:@"ios"])
    {
        [self mute]; // <-- INSERT YOUR OBJ-C FUNCTION HERE
        NSLog(@"test");
        return YES;
    }else
     {
        return YES;
    }

 }

// The Javascript (within webview)

try
{
  window.location="ios://null"
}
catch(err)
{
}

Source:

Answer №2

I have found that a common method for interacting between JavaScript and Objective-C is by changing the hash. When a specific event is triggered in your JavaScript code, you can use the following line to change the hash:

window.location.hash = '#cmd_alertMessage';
This will then prompt the execution of your
- (BOOL)webView: shouldStartLoadWithRequest: navigationType:
function.

   - (BOOL)webView:(UIWebView *)webView shouldStartLoadWithRequest:(NSURLRequest *)request navigationType:(UIWebViewNavigationType)navigationType
{
    NSArray * compenents = [request.URL.absoluteString componentsSeparatedByString:@"#"];
    if (compenents.count > 1) {
        NSString * cmd = compenents[1];
        if ([cmd rangeOfString:@"cmd_alertMessage"].location != NSNotFound) {
            // Call your obj-c method and get appropriated param
            NSString * jsFunction = [NSString stringWithFormat:@"setParameterFromAAAMethod('%@')", [self aaa]];
            // Return this param back to js
            NSString * alertMessage = [webView stringByEvaluatingJavaScriptFromString:jsFunction];
        }
    }


    return YES;
}

- (NSString *)aaa
{
    return @"This is special parameter that you need";
}

This process involves 3 steps:

  1. Initiate a hash change to request a parameter from Objective-C code in JavaScript;
  2. Handle the changed hash (requested parameter) and send it back to JavaScript in Objective-C;
  3. Manage the received parameter back in JavaScript

Answer №3

By setting the location of a hidden iframe to a specific value within your app, you can then capture and process that request using Obj-C.

If you're interested, here's an overview along with some practical examples:

Answer №4

Although I'm not entirely certain if I understood your inquiry correctly, if you're looking to invoke a JavaScript function, you can achieve this by utilizing the following approach:-

[yourWebView stringByEvaluatingJavaScriptFromString:@"yourMethodName()"];


It's also possible to include parameters in the mentioned method.

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Move the camera left and right, up and down using the arrow keys in WebGL

I am currently working on implementing a basic camera movement system in WebGL using JavaScript and the keyboard to control the camera's movement along the X and Y axes. However, I am facing an issue where the camera moves in world coordinates rather ...

Facing a challenge in configuring MongoDB automatic data expiration based on specific time zones

I am currently facing an issue with clearing data in MongoDB at the start of each day. For example, on July 15, 2020 at 00:00:00, data is deleted from the database based on a specific time. I am having trouble properly assigning the expiresAt attribute in ...

Obtaining asynchronous data with nodejs is possible through several methods

I am currently trying to retrieve data from a MySQL table using Node.js. I have a SQL routine in another Node.js file that I am calling, but I am struggling to get the callback function to return the data. I suspect that the issue may be related to calling ...

Currently, I am attempting to retrieve text input through the use of AngularJS

Having trouble retrieving text input values using Angular JS? The console keeps showing undefined. <div ng-controller="favouritesController" class="col-xs-12 favList"> <input type="text" ng-model="newFav" ng-keyup= "add($event)" class="col-xs-1 ...

tips for resizing bootstrap dropdown menu to fill entire page

The image clearly shows that the zabubi solution network platform has a dropdown menu with the label "no request for collaboration to be accepted" on top. The menu occupies half of the page and does not seem to be responsive. Even when the page is resized, ...

Converting table rows into an array that consists of arrays of table data using jQuery

I want to form a list of table rows with each cell being represented as an element in an array of strings. ...

Activating/Deactivating the Submit Button with jQuery and Bootstrap

Some of my form fields are outside of the <form> tag. I want the form to be disabled on load, and only enable once users input data into multiple fields. I'm facing two issues. Firstly, the jQuery code I have only works for one field at a time. ...

What is the reason behind Jquery targeting only the initial div element?

I am attempting to use the "replace" method in jQuery to eliminate all non-numeric characters within a div. However, I have found that the replace function in jQuery is only impacting the first element it encounters. Below is the snippet of my jQuery cod ...

Issue with error handling not being triggered when calling SAPUI5 function()

IBAN validation within a SAPUI5 Wizard is causing some issues for me. I am utilizing a functionImport on a V2 ODataModel (sap.ui.model.odata.v2.ODataModel) to perform this validation. Despite receiving a 202 status code, the request actually failed. Here ...

Failure to display updated property value

After rendering an array of objects, I am attempting to add a new property using a function. However, the new property value is not displaying on the page even though it is present when I log the object in the console. The new property that I want to add ...

Decomposing a Vue.js API response into multiple variables

Utilizing vue to send http requests and store data in variables can be done like so: the api response will have the following structure: data: data: [id:1... etc] function: fetchOffers() { this.$http.get('http://127.0.0.1:8000/api/of ...

Implementing an active class in Vue.js for the router-link component

I am facing an issue with my sidebar item becoming inactive when I click on a sublink inside a component. How can I prevent the active class from switching off? Here is my sidebar: <router-link to='/sub/success_tools_subscriptions' ...

Obtaining a result from a Promise in AngularJS

Here is a snippet of an Angular JS Service that I have: 'use strict'; app.factory('loggedService', ['$http', 'authService', 'customerService', function ($http, authService, customerService) { var out = ...

Is it true that iframe doesn't function as createpopup does?

I decided to use an iframe over window.createPopup, but I'm encountering an error in the console saying "oDocument is not defined". Check out my code below: function ShowDropdown(oMenu, oMenuDropDown){ //Setting up iframe html var iframe='<i ...

React hooks: Unable to modify state within functional component

Exploring the realm of React, I've embarked on a journey to create a digital phonebook. Progress has been made, but alas, an elusive challenge remains unresolved in my use of React Hooks. All seems well until the moment I invoke the setNewNumber(&apo ...

Guide on using a pipe feature with varying arguments when the main function is called

I am delving into functional programming for the first time and have a query regarding using pipes. Imagine I have this particular function: const updateArray = R.curry((index, value, array) => Object.assign([], array, {[index]: v ...

Using Three.js to render JSON models multiple times

Is there a way to load a JSON model just once and then add it to the scene multiple times? I am currently calling the model loading function twice, but I believe there might be a more efficient solution out there. If anyone has a working example or sugges ...

Calculate the total number of pages within an epub document

As a beginner in the world of epub, I have acquired numerous files in different epub formats and now wish to make them easily readable online. I'm not quite sure what an epub file contains. Is there a method to determine the number of pages in my epub ...

Transferring a row name from PHP to AJAX using jQuery - the complete guide

In my current project, I have a table that displays details fetched from the database. if(mysql_num_rows($sql) > 0) { $row_count_n = 1; while($rows = mysql_fetch_assoc($sql)) { extract($rows); $options1 = select_data_as_options( ...

Creating objects that are a fraction of another's width

My goal is to create 3 responsive divs that fill the width of the window and adjust their width based on the window dimensions. However, I'm facing an issue with JavaScript where it seems to be miscalculating the window width, causing the objects to o ...