1. This site uses cookies. By continuing to use this site, you are agreeing to our use of cookies. Learn More.

As Designed Inability To Clear Option With PHP Callback

Discussion in 'Resolved Bug Reports' started by digitalpoint, Apr 4, 2011.

  1. digitalpoint

    digitalpoint Well-Known Member

    If I have an option that is an array (checkboxes) with a PHP Callback, the $preparedOption variable passed to the method will include the last value if you uncheck it. Every other combination works (you can select any checkboxes you want), except if you uncheck them all. If you uncheck them all, $preparedOption['option_value'] still has a value (whatever the last item checked was). So it makes it so you can't uncheck all checkboxes for the array option.
     
  2. Kier

    Kier XenForo Developer Staff Member

    Could you post a simple test case?
     
  3. digitalpoint

    digitalpoint Well-Known Member

    The callback I'm using is to this file (obviously just one method, so the PHP Callback on the option is DigitalPointAdPositioning_Option_UsergroupSelector::renderOption:

    PHP:
    <?php

    abstract class DigitalPointAdPositioning_Option_UsergroupSelector
    {
    /**
    * Renders the usergroup chooser option.
    *
    * @param XenForo_View $view View object
    * @param string $fieldPrefix Prefix for the HTML form field name
    * @param array $preparedOption Prepared option info
    * @param boolean $canEdit True if an "edit" link should appear
    *
    * @return XenForo_Template_Abstract Template object
    */
    public static function renderOption(XenForo_View $view$fieldPrefix, array $preparedOption$canEdit)
    {
    $preparedOption['formatParams'] = array();
    $usergroups XenForo_Model::create('XenForo_Model_UserGroup')->getAllUserGroups();

    foreach (
    $usergroups as $key => $usergroup) {
    $preparedOption['options'][$usergroup['user_group_id']] = array('name' => $usergroup['title'], 'checked' => in_array($usergroup['user_group_id'], $preparedOption['option_value']));
    }

    return 
    XenForo_ViewAdmin_Helper_Option::renderOptionTemplateInternal(
    'option_template_AdPositioning_MultiSelect',
    $view$fieldPrefix$preparedOption$canEdit
    );
    }
    }
    The option_template_AdPositioning_MultiSelect admin template is as follows:

    Code:
    <xen:controlunit label="{$preparedOption.title}" hint="{$preparedOption.hint}">
    <xen:explain>{xen:raw $preparedOption.explain}</xen:explain>
    <xen:html>
    <ul>
    <xen:foreach loop="$preparedOption.options" key="$key" value="$item">
    <li><label for="ctrl_options{$preparedOption.option_id}_{$key}"><input type="checkbox" name="options[{$preparedOption.option_id}][]" value="{$key}" id="ctrl_options{$preparedOption.option_id}_{$key}"<xen:if is="{$item.checked}">checked="checked"</xen:if> /> {$item.name}</label></li>
    </xen:foreach>
    </ul>
    {xen:raw $editLink}
    </xen:html>
    </xen:controlunit>
    As mentioned in the first post, it works fine unless you try to unselect all checkboxes, at which point, the last value will "stick". I tried to find some sort of "clear if null parameter" I missed, but no such luck...

    Edit: No idea why tabs are getting stripped out... yuck! lol
     
  4. Kier

    Kier XenForo Developer Staff Member

    Something to do with the new TinyMCE I think... very very annoying.
     
  5. Kier

    Kier XenForo Developer Staff Member

    The reason for this is that we only update options that are detected as having submitted data via POST. In this way we can be very flexible in our option grouping.

    In the case of checkboxes, some genius at the W3C decided that they should submit no data whatsoever if they are unchecked, so we are unable to detect that they have been submitted and as a result we don't save the option if nothing is checked.

    To work around this, we have a special hidden field that instructs the system that an option is present, even if the controls for the option submit no data. You can see it in use in the XenForo option_list_option_checkbox admin template.

    Here is your template, updated to make use of it (immediately before the $editLink):
    HTML:
    <xen:controlunit label="{$preparedOption.title}" hint="{$preparedOption.hint}">
    	<xen:explain>{xen:raw $preparedOption.explain}</xen:explain>
    	<xen:html>
    		<ul>
    			<xen:foreach loop="$preparedOption.options" key="$key" value="$item">
    				<li><label for="ctrl_options{$preparedOption.option_id}_{$key}"><input type="checkbox" name="options[{$preparedOption.option_id}][]" value="{$key}" id="ctrl_options{$preparedOption.option_id}_{$key}"<xen:if is="{$item.checked}">checked="checked"</xen:if> /> {$item.name}</label></li>
    			</xen:foreach>
    		</ul>
    		<input type="hidden" name="{$listedFieldName}" value="{$preparedOption.option_id}" />
    		{xen:raw $editLink}
    	</xen:html>
    </xen:controlunit>
     
    digitalpoint and a legacy reborn like this.
  6. digitalpoint

    digitalpoint Well-Known Member

    Ah... makes perfect sense (it's why I was trying to find some sort of "clear if null parameter"). Sorry for bothering you.
     
  7. Kier

    Kier XenForo Developer Staff Member

    No problem :)
     
    arabic likes this.

Share This Page