Is there a way to programmatically add a region to an Upfront page from a plugin?

I'm writing a plugin and trying to keep most of my changes out of the themes as much as possible, so that I can avoid editing themes and minimize difficulties of upgrades later. I'd like to programmatically add regions to Upfront pages from my plugin. Is this possible? I noticed you can't just call "get_header()" and have it work like other themes do. Please advise.

Best,
Dave

  • Sajid

    Hi @dave184,

    Hope you are doing good today :slight_smile:

    First of all I want to make it clear that, when you create regions in upfront editor then you should not worried about those changes being overridden when you will update the theme. Its because all regions, elements, styles and content is stored into database.

    Yes, its different then regular WordPress theme so you can not access those functions directly. Because most of the content is coming from framework engine.

    If you still want to add regions dynamically then let me know and I will try to dig into the code or call one of our developer to get assistance regarding this matter.

    Take care and have a nice weekend :slight_smile:
    Cheers, Sajid

  • Sajid

    Hi @dave184,

    Hope you are doing good today :slight_smile:

    I have discussed it with the developer and he said right now its not possible. However it would be great addition in the framework to allow developers interact with the framework programmatically to extends the core functionality of the framework.

    I am moving it to Features and Feedback section from where it will be considered for development if it gets enough +1's from other members of community.

    It gets my +1, any more +1's folks ?

    Thanks for taking time and bringing in our attention, sending some points your way for appreciation :slight_smile:
    Cheers, Sajid

  • David Thibault

    Thanks for the points and the plus one! :slight_smile:

    I did find this work-around which may be helpful for some people. You can either add programmatic content to a page this way or replace content this way. I used this to add a registration form to my page. I did all this in a plugin, but you can do it in a theme as well if you'd like. The general idea is to stuff your custom HTML in a hidden input in the footer and then dig it out and replace some page content with it via javascript.

    1) Go in Upfront, edit the page where you want your programmatic content to show up, and use the code widget to add an empty div with a certain ID, like:
    <div id="myForm"></div>
    2) In my plugin (either in functions.php or some other plugin file), add something like this:

    if ($_SERVER['REQUEST_URI'] == '/page-where-i-added-the-empty-div-above/') {
                add_action('wp_footer',  'addMyForm', 99);
    }
    
    function addMyForm() {
          if ($_POST) {
                   $form_data = array();
                   $errors = array();
                   $fname = (isset($_POST['fname'])) ? $_POST['fname'] : '';
                   $lname = (isset($_POST['lname'])) ? $_POST['lname'] : '';
    
                   //validate however you want...for example, assume both fields are required.
                  if (empty($fname))
                        array_push($errors, 'Please enter first name.');
                  if (empty($lname))
                       array_push($errors, 'Please enter last name.');
                 if (empty($errors)) {
                         //handle submitted form data...stuff it in the db or whatever you want.
                         //if everything is successful in here, then send success message back to page:
                         $message = 'Form submitted successfully.';
                         $args = array(
                                   'success' => $message,
                         );
                        $formdata = formData($args);
                        echo ($formdata);
                        exit;
                }
                else { //send form data back with error messages
                       $args = array(
                                    'errors' => $errors,
                                    'fname' => $fname,
                                    'lname' => $lname,
                         );
                        $formdata = formData($args);
                        echo $formdata;
                        exit;
                }
           }
           else {
                   $args = array();
                   $formdata = formData($args);
                   echo $formdata;
           }
    }
    
    function formData($args) {
            ob_start();
            /*under the plugin folder make a templates folder.  In there we'll make the
           form template...more details below*/
            include dirname(__FILE__) . '/templates/form-template.php';
            $retval = ob_get_clean();
            return  '<input type="hidden" id="form_html_hidden" value="' . htmlspecialchars($retval) . '"/>';
    }
    add_action('wp_enqueue_scripts', 'generate_scripts');
    
    function generate_scripts() {
        wp_register_script( 'myForm_js', plugins_url( 'js/myForm.js', __FILE__ ), array('jquery'), '1.0', true );
        wp_enqueue_script('myForm_js');
    }

    3) Make the folder 'templates' under your theme or plugin (in the same directory as the functions.php if that's where you put the code in step 2). Under that folder, make the file form-template.php. In that file, create your form:

    <?php
    if (! defined('ABSPATH' )) {
        exit;
    }
    if (isset($args['success'])) { ?>
            <div id='info_message'>  <!--style this however you want your success message to look -->
                    <?php echo $args['success']; ?>
            </div>
    <?php
    }
    else {
            if( isset($args['errors']) && count($args['errors']) > 0) {
                   foreach ( $args['errors'] as $error ) {
                         echo '<p class="frm_error">' . $error . '</p>'; //style this frm_error class however you want your error messages to look.
                   }
            }
            ?>
    
            <form id='myForm' method='post' action='<?php echo get_site_url() . '/page-where-i-added-the-empty-div-above/'; ?>'>
    
                    <label for="fname">First Name:</label>
                    <input placeholder="Enter first name here." type="text" id='fname' name="fname" value='<?php echo isset( $args['fname'] ) ? $args['fname'] : ''; ?>'  />
    
                    <label for="lname">Last Name:</label>
                    <input placeholder="Enter last name here." type="text" id='lname' name='lname' value='<?php echo isset( $args['lname'] ) ? $args['lname'] : ''; ?>'  />
    
                    <button style="width: 100%;" type='submit'>Submit</button>
            </form>
    <?php
    }?>

    4) in the same folder as you put the functions.php file and the templates folder, also add a js folder and create myForm.js:

    jQuery(document).ready(function() {
    	if (jQuery('div#myForm').length && jQuery('input#form_html_hidden').length) {
    		jQuery('div#myForm').html(htmlspecialchars_decode(jQuery('input#form_html_hidden').val()));
    	}
    });
    function htmlspecialchars_decode(string, quote_style) { //found this function at http://phpjs.org/functions/htmlspecialchars_decode/
    	  //       discuss at: http://phpjs.org/functions/htmlspecialchars_decode/
    	  //      original by: Mirek Slugen
    	  //      improved by: Kevin van Zonneveld (http://kevin.vanzonneveld.net)
    	  //      bugfixed by: Mateusz "loonquawl" Zalega
    	  //      bugfixed by: Onno Marsman
    	  //      bugfixed by: Brett Zamir (http://brett-zamir.me)
    	  //      bugfixed by: Brett Zamir (http://brett-zamir.me)
    	  //         input by: ReverseSyntax
    	  //         input by: Slawomir Kaniecki
    	  //         input by: Scott Cariss
    	  //         input by: Francois
    	  //         input by: Ratheous
    	  //         input by: Mailfaker (http://www.weedem.fr/)
    	  //       revised by: Kevin van Zonneveld (http://kevin.vanzonneveld.net)
    	  // reimplemented by: Brett Zamir (http://brett-zamir.me)
    	  //        example 1: htmlspecialchars_decode("<p>this -> "</p>", 'ENT_NOQUOTES');
    	  //        returns 1: '<p>this -> "</p>'
    	  //        example 2: htmlspecialchars_decode(""");
    	  //        returns 2: '"'
    
    	  var optTemp = 0,
    	    i = 0,
    	    noquotes = false;
    	  if (typeof quote_style === 'undefined') {
    	    quote_style = 2;
    	  }
    	  string = string.toString()
    	    .replace(/</g, '<')
    	    .replace(/>/g, '>');
    	  var OPTS = {
    	    'ENT_NOQUOTES'          : 0,
    	    'ENT_HTML_QUOTE_SINGLE' : 1,
    	    'ENT_HTML_QUOTE_DOUBLE' : 2,
    	    'ENT_COMPAT'            : 2,
    	    'ENT_QUOTES'            : 3,
    	    'ENT_IGNORE'            : 4
    	  };
    	  if (quote_style === 0) {
    	    noquotes = true;
    	  }
    	  if (typeof quote_style !== 'number') {
    	    // Allow for a single string or an array of string flags
    	    quote_style = [].concat(quote_style);
    	    for (i = 0; i < quote_style.length; i++) {
    	      // Resolve string input to bitwise e.g. 'PATHINFO_EXTENSION' becomes 4
    	      if (OPTS[quote_style[i]] === 0) {
    	        noquotes = true;
    	      } else if (OPTS[quote_style[i]]) {
    	        optTemp = optTemp | OPTS[quote_style[i]];
    	      }
    	    }
    	    quote_style = optTemp;
    	  }
    	  if (quote_style & OPTS.ENT_HTML_QUOTE_SINGLE) {
    	    string = string.replace(/&#0*39;/g, "'"); // PHP doesn't currently escape if more than one 0, but it should
    	    // string = string.replace(/'|&#x0*27;/g, "'"); // This would also be useful here, but not a part of PHP
    	  }
    	  if (!noquotes) {
    	    string = string.replace(/"/g, '"');
    	  }
    	  // Put this in last place to avoid escape being double-decoded
    	  string = string.replace(/&/g, '&');
    
    	  return string;
    }

    That should do it! Let me know if anyone finds this helpful. The same system could be used to replace existing divs instead of adding a new one in step one (for example, to programmatically theme the single-post content by using the div ID default-post-object.

    Best,
    Dave
    PS--I just tested this and I think it all works to copy and paste, but I apologize in advance if it doesn't :slight_smile:

Thank NAME, for their help.

Let NAME know exactly why they deserved these points.

Gift a custom amount of points.