This guide will allow you to have a single option group for all your options, separating them into tabbed sections rather than forcing users to change option groups.

Examples

3947c489537c2.png

39a3389635c93.png


Code Event Listener
Event: templater_macro_pre_render
Event Hint: admin:eek:ption_macros:eek:ption_form_block
Execute Callback: Your\Namespace\Listener :: templaterMacroPreRender

PHP Code:
PHP:
<?php
namespace Your\Namespace;
class Listener
{
    public static function templaterMacroPreRender(\XF\Template\Templater $templater, &$type, &$template, &$name, array &$arguments, array &$globalVars)
    {
        if (!empty($arguments['group']) && $arguments['group']->group_id == 'your_group')
        {
            // Override template name
            $template = 'your_namespace_option_macros';
         
            // Or use 'option_form_block_tabs' for tabs
            $name = 'option_form_block';
         
            // Your block header configurations
            $arguments['headers'] = [
                'generalOptions'      => [
                    'label'           => \XF::phrase('general_options'),
                    'minDisplayOrder' => 0,
                    'maxDisplayOrder' => 2000,
                    'active'          => true // Only used for tabs, indicates default active tab
                ],
                'otherOptions'        => [
                    'label'           => \XF::phrase('other_options'),
                    'minDisplayOrder' => 2000,
                    'maxDisplayOrder' => 3000
                ],
                'evenMoreOptions'     => [
                    'label'           => \XF::phrase('even_more_options'),
                    'minDisplayOrder' => 3000,
                    'maxDisplayOrder' => -1 // This allows for any higher display order value
                ],
            ];
        }
    }
}
Admin Template
Template Name: your_namespace_option_macros

Template Contents:
HTML:
<xf:macro name="option_form_block" arg-group="" arg-options="!" arg-containerBeforeHtml="" arg-headers="{{ [] }}">
    <xf:if is="$options is not empty">
        <xf:form action="{{ link('options/update') }}" ajax="true" class="block">
            {$containerBeforeHtml|raw}
            <div class="block-container">
             
                <xf:foreach loop="$headers" value="$header">
                    <xf:macro name="option_rows" arg-header="{$header.label}"
                              arg-group="{$group}" arg-options="{$options}"
                              arg-minDisplayOrder="{$header.minDisplayOrder}" arg-maxDisplayOrder="{$header.maxDisplayOrder}" />
                </xf:foreach>

                <xf:submitrow sticky="true" icon="save" />
            </div>
        </xf:form>
    </xf:if>
</xf:macro>

<xf:macro name="option_form_block_tabs" arg-group="" arg-options="!" arg-containerBeforeHtml="" arg-headers="{{ [] }}">
    <xf:if is="$options is not empty">
        <xf:form action="{{ link('options/update') }}" ajax="true" class="block">
            {$containerBeforeHtml|raw}
            <div class="block-container">
                <h2 class="block-tabHeader tabs" data-xf-init="tabs" role="tablist">
                    <xf:foreach loop="$headers" key="$key" value="$header">
                        <a class="tabs-tab{{ $header.active ? ' is-active' : '' }}" role="tab" tabindex="0" aria-controls="{$key}">{$header.label}</a>
                    </xf:foreach>
                </h2>
                <ul class="tabPanes">
                    <xf:foreach loop="$headers" key="$key" value="$header">
                        <li class="{{ $header.active ? 'is-active' : '' }}" role="tabpanel" id="{$key}">
                            <xf:macro name="option_rows"
                                      arg-group="{$group}" arg-options="{$options}"
                                      arg-minDisplayOrder="{$header.minDisplayOrder}" arg-maxDisplayOrder="{$header.maxDisplayOrder}" />
                        </li>
                    </xf:foreach>
                </ul>
                <xf:submitrow sticky="true" icon="save" />
            </div>
        </xf:form>
    </xf:if>
</xf:macro>

<xf:macro name="option_rows" arg-header="" arg-group="!" arg-options="!" arg-minDisplayOrder="{{ 0 }}" arg-maxDisplayOrder="!">
    <xf:set var="$hundred" value="0" />

    <xf:if is="$header">
        <h3 class="block-formSectionHeader">{$header}</h3>
    </xf:if>

    <div class="block-body">
        <xf:foreach loop="$options" value="$option">
            <xf:if is="{$option.Relations.{$group.group_id}.display_order} >= $minDisplayOrder AND ({$option.Relations.{$group.group_id}.display_order} < $maxDisplayOrder OR $maxDisplayOrder == -1)">
                <xf:if is="$group">
                    <xf:set var="$curHundred" value="{{ floor($option.Relations.{$group.group_id}.display_order / 100) }}" />
                    <xf:if is="{{ $curHundred > $hundred }}">
                        <xf:set var="$hundred" value="{$curHundred}" />
                        <hr class="formRowSep" />
                    </xf:if>
                </xf:if>

                <xf:macro template="option_macros" name="option_row"
                          arg-group="{$group}" arg-option="{$option}" />
            </xf:if>
        </xf:foreach>
    </div>
</xf:macro>
There are two macros in this template. Change the configuration in the event listener as required.

  • Replace all instances of your_group with the option group ID you used.
  • Replace all instances of Your\Namespace or your_namespace with the relevant namespace you use.
  • I chose to separate my options per 1000 display order, but you can edit the PHP code and do it however you like
Author
shimmer
Views
475
First release
Last update
Rating
0.00 star(s) 0 ratings

More resources from shimmer

Top