Update 07/05/2016: This post was created in 2013 and the theme templates have changed a bit since I wrote this. Instead of copying a file from default/template, use Rwd’s version.
Update 07/05/2016: As per request I have updated this tutorial to always display the custom choose text as originally it was only working on when you interacted with the select menu.
If you have any ideas for a tutorial frontend wise please contact me. I am currently writing a Magento 2 tutorial regarding customising/replacing the product view fotorama component.
In this post we will be dealing with changing the default text “Choose an Option…” in the the product view page for configurable products.
To accomplish this we will need to modify one file, configurable.phtml in app/design/frontend/base/default/template/catalog/product/view/type/options/.
If you deal with Magento theming you will know that you should never edit the base theme files (I remember I made this awesome mistake when I first started learning Magento *sad face), so copy configurable.phtml into your own theme folder. The theme I will be using is default in a package called philip. Example app/design/frontend/philip/default/template/catalog/product/view/type/options/.
If you open up the file you should see code resembling the one below.
<?php $_product = $this->getProduct(); $_attributes = Mage::helper('core')->decorateArray($this->getAllowAttributes()); $_jsonConfig = $this->getJsonConfig(); $_renderers = $this->getChild('attr_renderers')->getSortedChildren(); ?> <?php if ($_product->isSaleable() && count($_attributes)):?> <dl> <?php foreach($_attributes as $_attribute): ?> <?php $_rendered = false; foreach ($_renderers as $_rendererName): $_renderer = $this->getChild('attr_renderers')->getChild($_rendererName); if (method_exists($_renderer, 'shouldRender') && $_renderer->shouldRender($_attribute, $_jsonConfig)): $_renderer->setProduct($_product); $_renderer->setAttributeObj($_attribute); echo $_renderer->toHtml(); $_rendered = true; break; endif; endforeach; if (!$_rendered): ?> <dt><label class="required"><em>*</em><?php echo $_attribute->getLabel() ?></label></dt> <dd<?php if ($_attribute->decoratedIsLast){?> class="last"<?php }?>> <div class="input-box"> <select name="super_attribute[<?php echo $_attribute->getAttributeId() ?>]" id="attribute<?php echo $_attribute->getAttributeId() ?>" class="required-entry super-attribute-select"> <option><?php echo $this->__('Choose an Option test...') ?></option> </select> </div> </dd> <?php endif; ?> <?php endforeach; ?> </dl> <script type="text/javascript"> var spConfig = new Product.Config(<?php echo $_jsonConfig ?>); </script> <?php echo $this->getChildHtml('after') ?> <?php endif;?>
Before we start editing, look at line 19 and you will see a javascript class Product.Config. What we will need to do is extend this class to show our new new custom text. The Product.Config class code is located in js/varien/configurable.js. Note: I am using Magento version 1.8 which uses prototype(1.7) so I will be using the latest way to extend a class. More on overriding classes is found here.
In configurable.js you will see that the class Product.Config is being created and objects are being attached to the prototype(Prototype Inheritance). What we need to look at is the “fillSelect” property (Line 167 – 172). Here is where the “Choose an Option…” is being defined. We need to override this so go back to your configurable.phtml file.
var spConfig = new Product.Config(<?php echo $_jsonConfig ?>);
In your configurable.phtml file replace line 64(above) with the code below withing your script tags.
Product.Configtxt = new Class.create(Product.Config, { initialize: function($super, config){ $super(config); var _this = this; // fill state _this.settings.each(function(element) { _this.chooseTxt(element); }); }, fillSelect: function($super, element) { $super(element); this.chooseTxt(element); }, // create a simple function to change the txt for each select chooseTxt: function(element) { var chooseTxt = element.getAttribute('data-choosetxt'); element.options[0] = new Option(chooseTxt, ''); element.options[0].selected = true } }); var spConfig = new Product.Configtxt(<?php echo $this->getJsonConfig() ?>);
What this bit of javascript does is extends the Product.Config class and allows us to override it. The overridden fillSelect passes in a custom chooseTxt function we have created and this in turns looks for a data-attribute data-choosetxt (More on this below) on the select menu which updates the ‘Choose an Option..’ with our custom text.
Now the next step is to create this data-choosetxt attribute on the select menu. Replace the select menu between line 38-40 with the code below.
<select name="super_attribute[<?php echo $_attribute->getAttributeId() ?>]" data-choosetxt="<?php echo $this->__('Choose an %s', $_attribute->getLabel());?>" data-attribute="<?php echo $_attribute->getLabel() ;?>" id="attribute<?php echo $_attribute->getAttributeId() ?>" class="required-entry super-attribute-select"> <option><?php echo $this->__('Choose %s',$_attribute->getLabel()); ?></option> </select>
What we have done here is assigned data-choosetxt to each select menu e.g.colour, size which will in turn be update each select menu with our new customised option text. This concludes the short tutorial. I hope this has been useful to someone out there working with Magento.
Any suggestions for future tutorial ideas are more than welcome. Please contact me if you have any suggestions
The completed configurable.phtml code is found below
<?php /** * Magento * * NOTICE OF LICENSE * * This source file is subject to the Academic Free License (AFL 3.0) * that is bundled with this package in the file LICENSE_AFL.txt. * It is also available through the world-wide-web at this URL: * http://opensource.org/licenses/afl-3.0.php * If you did not receive a copy of the license and are unable to * obtain it through the world-wide-web, please send an email * to license@magento.com so we can send you a copy immediately. * * DISCLAIMER * * Do not edit or add to this file if you wish to upgrade Magento to newer * versions in the future. If you wish to customize Magento for your * needs please refer to http://www.magento.com for more information. * * @category design * @package rwd_default * @copyright Copyright (c) 2006-2016 X.commerce, Inc. and affiliates (http://www.magento.com) * @license http://opensource.org/licenses/afl-3.0.php Academic Free License (AFL 3.0) */ ?> <?php $_product = $this->getProduct(); $_attributes = Mage::helper('core')->decorateArray($this->getAllowAttributes()); $_jsonConfig = $this->getJsonConfig(); $_renderers = $this->getChild('attr_renderers')->getSortedChildren(); ?> <?php if ($_product->isSaleable() && count($_attributes)):?> <dl> <?php foreach($_attributes as $_attribute): ?> <?php $_rendered = false; foreach ($_renderers as $_rendererName): $_renderer = $this->getChild('attr_renderers')->getChild($_rendererName); if (method_exists($_renderer, 'shouldRender') && $_renderer->shouldRender($_attribute, $_jsonConfig)): $_renderer->setProduct($_product); $_renderer->setAttributeObj($_attribute); echo $_renderer->toHtml(); $_rendered = true; break; endif; endforeach; if (!$_rendered): ?> <dt><label class="required"><em>*</em><?php echo $_attribute->getLabel() ?></label></dt> <dd<?php if ($_attribute->decoratedIsLast){?> class="last"<?php }?>> <div class="input-box"> <select name="super_attribute[<?php echo $_attribute->getAttributeId() ?>]" data-choosetxt="<?php echo $this->__('Choose an %s', $_attribute->getLabel());?>" data-attribute="<?php echo $_attribute->getLabel() ;?>" id="attribute<?php echo $_attribute->getAttributeId() ?>" class="required-entry super-attribute-select"> <option><?php echo $this->__('Choose %s',$_attribute->getLabel()); ?></option> </select> </div> </dd> <?php endif; ?> <?php endforeach; ?> </dl> <script type="text/javascript"> Product.Configtxt = new Class.create(Product.Config, { initialize: function($super, config){ $super(config); var _this = this; // fill state _this.settings.each(function(element) { _this.chooseTxt(element); }); }, fillSelect: function($super, element) { $super(element); this.chooseTxt(element); }, // create a simple function to change the txt for each select chooseTxt: function(element) { var chooseTxt = element.getAttribute('data-choosetxt'); element.options[0] = new Option(chooseTxt, ''); element.options[0].selected = true } }); var spConfig = new Product.Configtxt(<?php echo $this->getJsonConfig() ?>); </script> <?php echo $this->getChildHtml('after') ?> <?php endif;?>
Thanks for this tutorial. I tried doing this about a year ago myself and couldn’t get it to work.
There’s a small error in the code. In the select…
data-attribute=””
Should be called
data-choosetxt=””
Otherwise it returns a null value.
Great tutorial dude I’d never have been able to get this done for a customer without you!
I’ve update the reference error, thanks for spotting that and I’m glad you found this useful.
Thanks a million for this tutorial, I have been trying to do this by myself for a while and was struggling. Life saver!
Thanks, very helpful.
Thanks for taking the time to document this. Any ideas on how to update code to populate the value of $choose_txt for ALL select menus on a product that has more than one option? Right now only the first select menu is populated until it is selected, and then the next select menu is filled.
Hey Jason, sorry for the late reply.
So you would like to pre-populate the select menu with the first option that it shows by default when a user lands on the product page?
Example Configurable product – Options
Colour- Black, Orange, Green
Sizes – S, M,L S M L XL
So by default it will auto select Black and Size Small
Colour: Black
Size: S
Is this what you are after?
Cheers
Very efficiently written information. It will be beneficial to everyone who employess it, including myself. Keep up the good work for sure i will check out more posts.
this code helped me lot , thanks 🙂
Hi Philip,
Great tutorial, although I did get a little confused when you state update configurable.js above, which you don’t mean to say, as everything gets done within configurable.phtml template file.
I too have the same request as Jason above. When we have colour, letter and size as three selects, the second element doesn’t update till the first select has taken place
So it will look like:
1. Select Colour
2. Choose An Option
3. Choose An Option
When they select a colour it then goes
1. Black
2. Select Letter
3. Choose An Option
I simply would like it to say:
1. Select Colour
2. Select Letter
3. Select Size
Hi Sorry for the very late reply, I have been quite busy with Magento 2 studying. 🙂
I have now done a mini update to this tutorial with the latest Magento 1.9 files. This should now keep all select custom chooseTxt intact on load and when users interact with the select menus.
Sorry for the wait 🙂
Thanks, this post helped me