0

I've been trying to learn how to make a plugin in my spare time. I'd previously done all of the coding pertaining to the settings page and it all appeared to work well. Having completed some other parts of the test plugin I returned (a few weeks later) and now when I save adjustments to the settings I get shown a long list of database field names with associated input/textarea values returned but adjustments are not saved. I'm confident that nothing else is using add_action('admin_menu/admin_init')

The plugin is built as a class. Here's all the code relating to the settings page

class rifh_tester{

 public function __construct(){
  /* admin */
  if(is_admin()){
   add_action('admin_menu', array($this, 'settings_add_menu'));
   add_action('admin_init', array($this, 'settings_admin_init'));
  }
 }

 public function settings_add_menu(){
  add_options_page('RifH Tester Settings', 'RifH Tester', 'manage_options', 'rifh_tester', array($this, 'settings_opts_page'));
 }

 public function settings_opts_page(){
  echo '<div id="rifh-tester-setup"><form action="options.php" method="post">
       ' . settings_fields("rifh_tester_options") . do_settings_sections("rifh_tester") . '
       <input name="submit" type="submit" value="Save Changes">
       </form>
       </div>';
 }

 public function settings_admin_init(){
  register_setting('rifh_tester_options', 'rifh_tester_options', array($this, 'rifh_tester_options_validate'));
  add_settings_section('rifh_tester_options_main', __('Welcome to the RifH Tester Setup Page'), array($this, 'rifh_tester_options_text'), 'rifh_tester');
  add_settings_field('rifh_tester_option_image_generate', __('Test Creating An Image?'), array($this, 'rifh_tester_option_image_generate'), 'rifh_tester', 'rifh_tester_options_main');
  add_settings_field('rifh_tester_option_image_limit', __('Test Define An Image Size'), array($this, 'rifh_tester_option_image_limit'),  'rifh_tester', 'rifh_tester_options_main');
  add_settings_field('rifh_tester_option_appears_on', __('Where Should Test Images Show?'), array($this, 'rifh_tester_option_appears_on'),  'rifh_tester', 'rifh_tester_options_main');
  add_settings_field('rifh_tester_option_image_type', __('Preferred Format For Test Images?'), array($this, 'rifh_tester_option_image_type'), 'rifh_tester', 'rifh_tester_options_main');
 }

 public function rifh_tester_option_image_generate(){
  echo "<label><input id='rifh_tester_option_image_generate' name='rifh_tester_options[image_gen]' type='checkbox' ".($this->options['image_gen'] ? 'checked>Yes' : '>No')."</label>";
 }

 public function rifh_tester_option_image_limit(){
  echo "<label><input id='rifh_tester_option_image_limit' name='rifh_tester_options[image_lim]' type='text' value='{$this->options['image_lim']}'> Width of each Linky box in pixels.</label>";
 }

 public function rifh_tester_option_appears_on(){
  echo "<label><input id='rifh_tester_option_appears_on' name='rifh_tester_options[single]' type='checkbox' ".($this->options['single'] ? "checked>Yes" : ">No")."</label>";
 }

 public function rifh_tester_option_image_type(){
  $html = "<select id='rifh_tester_option_image_type' name='rifh_tester_options[image_type]'>";
  $values = array('png','jpg','gif');
  foreach($values as $format){
   $html .= "<option value='$format'";
   if($format == $this->options['image_type']){
    $html .= " selected";
   }
   $html .= ">$format</option>";
  }
  $html .= "</select>";
  echo $html;
 }

 public function rifh_tester_options_validate($input){
  $newinput = array();
  $newinput['image_gen'] = false;
  if(isset($input['image_gen'])){
   $newinput['image_gen'] = true;
  }

  if(isset($input['image_lim']) && preg_match('#^([1-9]([0-9]{1,2})?|1000)$#', $input['image_lim'])){
   // I've excluded private isFloat function as it's a basic function of the class
   if($this->isfloat($input['image_lim'])){
    $input['image_lim'] = round($input['image_lim'], 4);
   }
   $newinput['image_lim'] = $input['image_lim'];
  }

  if(isset($input['image_type']) && preg_match('#^(jpg|png|gif)$#', $input['image_type'], $match)){
   $newinput['image_type'] = $match[1];
  }

  $newinput['single'] = false;
  if(isset($input['single'])){
   $newinput['single'] = true;
  }
  return $newinput;
 }

 public function rifh_tester_options_text($args){
  echo "<div id='{$args['id']}'></div>";
 }
}

When I actually look at the HTML generated on the settings page it appears also that the <form> appears after all the fields and only has a Submit input. Making me think that the error is with the settings_opts_page function defined in the class but I can't see what it would be.

I've re-read all the guidance I can find on the Settings-API for WP, I can't understand what I'm doing wrong. Can anyone point me in the right direction?

1

So having another look at this again today it occurred to me that it definitely must be an issue with settings_opts_page. In the light of a new day the answer is obvious, clearly settings_fields and do_settings_sections are intended to echo their contents and this is breaking the page render and seeing the form and contents displaced.

public function settings_opts_page(){
 echo '<div id="rifh-tester-setup"><form action="options.php" method="post">
  ' . settings_fields("rifh_tester_options") . do_settings_sections("rifh_tester") . '
  <input name="submit" type="submit" value="Save Changes">
  </form>
  </div>';
}

Should be

public function settings_opts_page(){
 echo '<div id="rifh-tester-setup"><form action="options.php" method="post">';
 settings_fields("rifh_tester_options");
 do_settings_sections("rifh_tester");
 echo '<input name="submit" type="submit" value="Save Changes"></form></div>';
}

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.