Reputation: 4022
Currently in my /etc/system.xml file I can use this to pull through a complete list of regions that are stored in Magento and display them as a multiselect. This works fine, however I would prefer to only pull through the regions for one country, e.g. the UK counties or US states:
<counties translate="label">
<label>Counties</label>
<frontend_type>multiselect</frontend_type>
<sort_order>10</sort_order>
<source_model>adminhtml/system_config_source_allregion</source_model>
<show_in_default>1</show_in_default>
<show_in_website>1</show_in_website>
<show_in_store>1</show_in_store>
</counties>
The reason for this is that I have added a lot of regions/states/counties on the system and it is now not a very user friendly multi-select box.
After not immediately acting on the solutions provided below I revisited this problem some time later to put together my own solution inspired by the answers provided.
I copied app/code/core/Mage/Adminhtml/Model/System/Config/Source/Allregion.php to app/code/core/Mage/Adminhtml/Model/System/Config/Source/Ukregion.php
Then I changed the class definition to Mage_Adminhtml_Model_System_Config_Source_Ukregion.
Then I changed:
$regionsCollection = Mage::getResourceModel('directory/region_collection')->load();
to include a country filter:
$regionsCollection = Mage::getResourceModel('directory/region_collection')->addCountryFilter('GB')->load();
I now get the counties for the UK (which I had to edit myself but that is a different story-style-magento-problem).
Finally I changed my system.xml:
<counties translate="label">
<label>Counties</label>
<frontend_type>multiselect</frontend_type>
<sort_order>10</sort_order>
<source_model>adminhtml/system_config_source_ukregion</source_model>
<show_in_default>1</show_in_default>
<show_in_website>1</show_in_website>
<show_in_store>1</show_in_store>
</counties>
The use of 'UK' instead of 'GB' is entirely deliberate - GB does not include the NI counties it is just used for 'legacy reasons'. 'UK' does include Northern Ireland, as does my county list.
Upvotes: 3
Views: 11689
Reputation: 37700
Take a look at the page System > Configuration > Shipping Settings, you can recreate how it's regions are adjusted to match the selected country.
Now look at the file app/code/core/Mage/Shipping/etc/system.xml
. The country and region fields look like this:
<country_id translate="label">
<label>Country</label>
<frontend_type>select</frontend_type>
<frontend_class>countries</frontend_class>
<source_model>adminhtml/system_config_source_country</source_model>
<sort_order>10</sort_order>
<show_in_default>1</show_in_default>
<show_in_website>1</show_in_website>
<show_in_store>0</show_in_store>
</country_id>
<region_id translate="label">
<label>Region/State</label>
<frontend_type>text</frontend_type>
<sort_order>20</sort_order>
<show_in_default>1</show_in_default>
<show_in_website>1</show_in_website>
<show_in_store>0</show_in_store>
</region_id>
The important parts are:
countries
and an ID of country_id
.region_id
.The javascript is already in place for config pages. It finds elements with a class of countries
and uses it's ID to find a similarly named element (the region). When the first element changes the second is updated by AJAX.
When using this in the past I sometimes had trouble when there is more than one country/region pair on a page so it's best to avoid that situation.
Upvotes: 4
Reputation: 472
The source_model attribute defines the class "where" are the options of this multiselect field. You can create a new class with only the options you want to show in this field and point the source_model to this new class.
You should use the toOptionArray() method to define the options. A quick way of doing this is like the below example:
public function toOptionArray()
{
return array(
array( 'value' => VALUE,
'label' => LABEL ) ),
array( 'value' => VALUE2,
'label' => LABEL2 )
);
}
Of course, get the options from a database table would be a better practice.
Upvotes: 1