简体   繁体   中英

Best practice for using jquery to interact with php classes?

I have a dropdown selector on a page that allows a user to select a template type (for example, "human" or "dog").

  1. Based on what template is selected, different fields will need to populate below the dropdown (for example, text fields for "parents names" or a dropdown list for "breed") that are unique to each template.

  2. I will have a button that the user will click once the data fields are put in that will output data to an "output div" section of the same page when clicked (no POSTing data as it's not being saved). The output will have different output logic based on the selected template (for example, "I'm a human named X" or "I'm a dog, my breed is Y").

My real program will be more complex and each template will have a php class that stores all of the logic. Since I will be dealing with both php objects and variables gathered by jquery, what's the best way to let them interact?

For 1., I know I can do something easy like -

var selected_template = $('#my-template-dropdown :selected').text();
if (selected_template == 'Human'){
                $('#my-fields').html('<?php echo HumanTemplate::render_fields(); ?>');
            }

which is easy enough, but for 2. I need to pass variables from jquery to php, then return output back to jquery.

I would like some advice on the easiest way to do this before I start down the wrong path.

The best way to pass data from jQuery to PHP, is by using AJAX. Mozilla has an excellent guide on getting started , that i recommend you follow. An example of how you can achieve what you are requesting, is by trying the following:

var selected_template = $('#my-template-dropdown :selected').text();
var ajaxurl = 'ajax.php',
data =  {'select_template': selected_template };
$.post(ajaxurl, data, function (response) {
    console.log(response);
});

On the PHP end (Ajax.php in my example) It could look something like this

if(isset($_POST['select_template'])) {
    // do something with the input from jQuery
    $selected_template = $_POST['select_template'];
    // return the result back to the client
    echo $seleted_template;
}

?>

$selected_template will be sent back to the client, and response in the AJAX function will be whatever the server returned. So the console.log(response) should display whatever was being sent to the server

HTML

Allow the user to select the template type:

<form>
    <select id="my-template-dropdown" name='template'>
        <option value="dogs">Dogs</option>
        <option value="humans">Humans</option>
    </select>
</form>

<div id="my-fields"><div>
<div id="output"><div>

jQuery

Any time the user changes the template selection, request new content to display via AJAX, and insert it on the current page so the page does not have to refresh:

$('#my-template-dropdown').on('change', function() {
    var template = $(this).val();
    $.ajax({
        url: 'http://your-site/path/to/' + template,
        success: function(resp) {
            $('#my-fields').html(resp);
        }
    });
});

PHP

http://your-site/path/to/template simply generates the HTML you want to display for that template, eg (just an example, don't know if this is suitable for your app):

if ($template == 'humans') {
    echo HumanTemplate::render_fields();
} else if ($template == 'dogs') {
    echo DogTemplate::render_fields();
}

For part 2, assuming all the logic you refer to is in the template rendered by PHP, you could then handle it with jQuery. This is pretty crude, you probably need something more sophisticated (eg a full template which you swap variables into?), but you get the idea:

$('#output').on('click', 'button', function(e) {
    e.preventDefault();
    // fields in your template which the user will fill
    var species = $('#species').val(),
        title = $('#title').val();
    // Probably better to have this text as a template in your source
    $('#output').html("I'm a " + species + ' named ' + title);
});

NOTE the gotcha in the event handler. Event handlers will only attach to elements that exist at the time the handler is defined. Since the content is injected after page load, an event handler like $('#button).on('click', function() {... would have no effect when clicking a button inserted via AJAX. The syntax here attaches to the parent #output div, which does exist at page load, and filters for clicks on a button. See the jQuery event delegation docs for more info.

Another option would be to POST the submitted data to some PHP controller, which generates and returns the output. This way all your logic is in the one place. For example, here the user's click will query the same PHP file which generated the initial template, this time including the values the user has entered. It could then generate the required output and return it, to be inserted on the page. You'd need to update the PHP so it can determine which of these cases it is handling (eg hidden field?); alternatively if you wanted to keep those separate you could hit another PHP file all together.

$('#output').on('click', 'button', function(e) {
    var template = $('#my-template-dropdown').val(),
        $form = $('form'),
        data = $form.serialize(); // Values from all fields user has entered
    $.ajax({
        url: 'http://your-site/path/to/' + template,
        data: data,
        success: function(resp) {
            $('#output').html(resp);
        }
    });
});

You can have a look to the function wp_localize_script .

This function make available PHP datas to JS files on the page load through the wp_enqueue_scripts action.

This will not work like an Ajax request and only populate data for a specific handle on page load. But you can mix this method with ajax in the same script.

Hope it helps even it doesn't seems to fit to your case.

As your class not fires on page load, you can use the action wp_ajax_{custom _action} and wp_ajax_nopriv_{custom_action} . For example, that's usually used to populate multiple dropdown, each time an event is trigger by the user, a php function returns result the js script.

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