Can anyone provide a dummy guide \\ code snippets on how to create a front end form in Magento that posts data to a controller action.
Im trying to write a variant of th
To make $this->getFormAction()
return the URL to your custom controller, you have two options:
setFormAction()
somewhere else on the block. getFormAction()
.(1) is what happens in Mage_Contacts_IndexController::indexAction()
, but (2) is the cleaner approach and I'm going to explain it in detail:
app/etc/modules/Stack_Form.xml
:
true
local
app/code/local/Stack/Form/etc/config.xml
:
0.1.0
Stack_Form
feedback
Stack_Form_Block
This configuration registers the stack_form
block alias for own blocks and the feedback
front name for own controllers.
app/code/local/Stack/Form/Block/Form.php
class Stack_Form_Block_Form extends Mage_Core_Block_Template
{
public function getFormAction()
{
return $this->getUrl('stack_form/index/post`);
}
}
Here we implemented getFormAction()
to generate the URL for our custom controller (the result will be BASE_URL/feedback/index/post).
app/code/local/Stack/Form/controllers/IndexController.php
class Stack_Form_IndexController extends Mage_Contacts_IndexController
{
public function postAction()
{
// your custom post action
}
}
If the form should behave exactly like the contact form, just with a different email template and additional form fields, there are two solutions that I have outlined at https://magento.stackexchange.com/q/79602/243 where only one of them actually requires a custom controller action to send the form:
If you look at the contacts controller used in the form action, you will find that
- the transactional template is taken directly from the configuration
- all POST data is passed to the template (as template variable
data
), so that you can add any additional fields to the form template and use them in the email template. But validation is hard coded for "name", "comment", "email" and "hideit".So, if you need a completely different email template or additional/changed input validation, your best bet is to create a custom controller with a modified copy of the
postAction
ofMage_Contacts_IndexController
.But there is another solution that is a bit limited but without any custom code involved:
- create a hidden input that determines the type of the form. It could be just
.
in the contact transactional email template, use the
if
directive to show different content based on the form type:{{if data.custom}} ... custom contact form email ... {{else}} ... standard contact form email ... {{/if}}
You can add the form anywhere in the CMS using this code (CMS directive):
{{block type="stack_form/form" template="path/to/your/form.phtml"}}
If you do this, you need to add "stack_form/form" to the block whitelist under System > Permissions > Blocks!
Or in the layout using this code (layout XML):
If you use the solution without custom controller and a single email template mentioned above, you can set the form action using layout XML as well.
To achieve this, we use the feature to call helpers as parameters for block actions. Unfortunately, the core helper does not have a public method to get a URL but the helper from Mage_XmlConnect
has, so you can use that one:
contacts/index/post
In the CMS directive you cannot use helpers, so there you would need to put the actual URL:
{{block type="stack_form/form" template="path/to/your/form.phtml" form_action="/feedback/index/post"}}
Since you probably have different CMS pages/blocks in different store views, this should not be a big problem.