Geoff
Geoff

Reputation: 3574

Magento - Add button [+ Add Field] that adds/shows a new text field in system.xml

I have a custom module with optional text fields (shown via the standard text field option in system.xml). What I'd like to do is to show 1 mandatory text field and have a button that says something like [+ Add Field]. When that button is pressed, another text field is added. I'd like to do this for up to 10 total text fields (max). Can someone help me to accomplish this or point me to a nice tutorial on how to do this?

EDIT 7/10/12 @ 11:30AM

I've been working on this and so far I can get the text fields to show up. However I have a few issues...

  1. When pressing the "Save Config" button, none of the values entered in these dynamically created textfields actually save.
  2. Is there a way to limit how many text fields actually save?
  3. I'm unsure of the correct way to retrieve the text field(s) data. This is mostly due to the fact that I cannot save the values...(I will add another update after #1 is fixed if I need help with this...)

My System.xml file has this in it (directly related to this)..

<labels translate="label">
    <label>This is some label</label>
    <comment>This is some comment.</comment>
    <tooltip><![CDATA[This is some tooltip]]></tooltip>
    <frontend_type>text</frontend_type>
    <frontend_model>Company_Namespace/adminhtml_textfields</frontend_model>
    <backend_model>adminhtml/system_config_backend_serialized</backend_model>
    <sort_order>50</sort_order>
    <show_in_default>1</show_in_default>
    <show_in_website>1</show_in_website>
    <show_in_store>0</show_in_store>
</labels>

My custom Textfields.php (frontend_model) file contents:

<?php

class Company_Namespace_Block_Adminhtml_Textfields extends Mage_Adminhtml_Block_System_Config_Form_Field
{
protected $_addRowButtonHtml = array();
protected $_removeRowButtonHtml = array();

protected function _getElementHtml(Varien_Data_Form_Element_Abstract $element)
{
    $this->setElement($element);

    $html = '<div id="code_label_textfields_template" style="display:none">';
    $html .= $this->_getRowTemplateHtml();
    $html .= '</div>';

    $html .= '<ul id="code_label_textfields_container">';

    if ($this->_getValue('method')) {
        foreach ($this->_getValue('method') as $i=>$f) {
            if ($i) {
                $html .= $this->_getRowTemplateHtml($i);
            }
        }
    }

    $html .= '</ul>';


    $html .= $this->_getAddRowButtonHtml('code_label_textfields_container', 'code_label_textfields_template', $this->__('Button Label Here'));

    return $html;
}

protected function _getRowTemplateHtml()
{
    $html = '<li>';

    $html .= '<div style="margin:5px 0 10px;">';
    $html .= '<input class="input-text" name="'.$this->getElement()->getName().'" value="'.$this->_getValue('price/'.$i).'" '.$this->_getDisabled().'/> ';

    $html .= $this->_getRemoveRowButtonHtml();
    $html .= '</div>';

    $html .= '</li>';

    return $html;
}



protected function _getDisabled()
{
    return $this->getElement()->getDisabled() ? ' disabled' : '';
}

protected function _getValue($key)
{
    return $this->getElement()->getData('value/'.$key);
}

protected function _getSelected($key, $value)
{
    return $this->getElement()->getData('value/'.$key)==$value ? 'selected="selected"' : '';
}

protected function _getAddRowButtonHtml($container, $template, $title='Add')
{
    if (!isset($this->_addRowButtonHtml[$container])) {
        $this->_addRowButtonHtml[$container] = $this->getLayout()->createBlock('adminhtml/widget_button')
                ->setType('button')
                ->setClass('add '.$this->_getDisabled())
                ->setLabel($this->__($title))
                //$this->__('Add')
                ->setOnClick("Element.insert($('".$container."'), {bottom: $('".$template."').innerHTML})")
                ->setDisabled($this->_getDisabled())
                ->toHtml();
    }
    return $this->_addRowButtonHtml[$container];
}

protected function _getRemoveRowButtonHtml($selector='li', $title='Remove')
{
    if (!$this->_removeRowButtonHtml) {
        $this->_removeRowButtonHtml = $this->getLayout()->createBlock('adminhtml/widget_button')
                ->setType('button')
                ->setClass('delete v-middle '.$this->_getDisabled())
                ->setLabel($this->__($title))
                //$this->__('Remove')
                ->setOnClick("Element.remove($(this).up('".$selector."'))")
                ->setDisabled($this->_getDisabled())
                ->toHtml();
    }
    return $this->_removeRowButtonHtml;
}
}

What am I missing, especially for saving values???

Upvotes: 1

Views: 3214

Answers (1)

benmarks
benmarks

Reputation: 23205

Refer to the system.xml and the Mage_GoogleCheckout_Block_Adminhtml_Shipping_Merchant block for an example. It's a little convoluted, but it works. You can see this in the Merchant Calculated settings in Google Checkout.

Upvotes: 1

Related Questions