How to create a custom form for sending email in Magento 2

Fields are like

  • First name
  • Last name
  • Address
  • City
  • State
  • Zip code
  • Email
  • Phone
  • Product type: checkbox Option like (1) One (2) Two
  • File upload
  • comment
up vote 12 down vote accepted

Try below code in your controller

vendorname/modulename/controller/Index/index.php

<?php
/**
 *
 * Copyright © 2016 Magento. All rights reserved.
 * See COPYING.txt for license details.
 */
namespace Vendor\Module\Controller\Index;


use Magento\Framework\App\Action\Action;
use Magento\Framework\App\Action\Context;
use Magento\Framework\App\Filesystem\DirectoryList;
use Magento\Framework\Filesystem;
use Magento\Framework\App\Request\DataPersistorInterface;


class Index extends Action
{
    private $dataPersistor;
    /**
     * @return \Magento\Framework\Controller\Result\Redirect|\Magento\Framework\View\Result\Page
     */

    protected $context;
    private $fileUploaderFactory;
    private $fileSystem;


    /**
     * @var \Magento\Framework\Mail\Template\TransportBuilder
     */
    protected $_transportBuilder;

    /**
     * @var \Magento\Framework\Translate\Inline\StateInterface
     */
    protected $inlineTranslation;

    /**
     * @var \Magento\Framework\App\Config\ScopeConfigInterface
     */
    protected $scopeConfig;

    /**
     * @var \Magento\Store\Model\StoreManagerInterface
     */


    /**
     * @param \Magento\Framework\App\Action\Context $context
     * @param \Magento\Framework\Mail\Template\TransportBuilder $transportBuilder
     * @param \Magento\Framework\Translate\Inline\StateInterface $inlineTranslation
     * @param \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig
     */

     public function __construct(
        \Magento\Framework\App\Action\Context $context,
        Filesystem $fileSystem,
        \Magento\MediaStorage\Model\File\UploaderFactory $fileUploaderFactory,
        \Magento\Framework\Mail\Template\TransportBuilder $transportBuilder,
        \Magento\Framework\Translate\Inline\StateInterface $inlineTranslation,
        \Modia\Cform\Helper\Data $helper,
        \Magento\Framework\App\Config\ScopeConfigInterface $scopeConfig
    ) {
        parent::__construct($context,$transportBuilder,$inlineTranslation, $scopeConfig );
        $this->fileUploaderFactory = $fileUploaderFactory;
        $this->fileSystem          = $fileSystem;
        $this->_transportBuilder = $transportBuilder;
        $this->inlineTranslation = $inlineTranslation;
        $this->helper = $helper;
        $this->scopeConfig = $scopeConfig;
    }

    public function execute()
    {

        $post = $this->getRequest()->getPostValue();
        $filesData = $this->getRequest()->getFiles('upload_document');

        if ($filesData['name']) {
         $uploader = $this->fileUploaderFactory->create(['fileId' => 'upload_document']);
         $uploader->setAllowRenameFiles(true);
         $uploader->setFilesDispersion(true);
         $uploader->setAllowCreateFolders(true);
         $path = $this->fileSystem->getDirectoryRead(DirectoryList::MEDIA)->getAbsolutePath('test-doc');
         $result = $uploader->save($path);
         $upload_document = 'test-doc'.$uploader->getUploadedFilename();
         $filePath = $result['path'].$result['file'];
         $fileName = $result['name'];
    } else {
         $upload_document = '';
         $filePath = '';
         $fileName = '';
    }

        $txt='<table>';

        if($post['fname']){         
            $txt.='<tr><td><strong>Client Name</strong>:'.$post['fname'].'</td></tr>';          
        }
        if($post['address']){           
            $txt.='<tr><td><strong>Address</strong>:'.$post['address'].'</td></tr>';            
        }
        if($post['city']){
            $txt.='<tr><td><strong>City</strong>:'.$post['city'].'</td></tr>';
        }
        if($post['state']){
            $txt.='<tr><td><strong>State/Province</strong>:'.$post['state'].'</td></tr>';
        }
        if($post['zipcode']){
            $txt.='<tr><td><strong>Zip Code</strong>:'.$post['zipcode'].'</td></tr>';
        }
        if($post['phone']){
            $txt.='<tr><td><strong>Phone</strong>:'.$post['phone'].'</td></tr>';
        }
        if($post['email']){
            $txt.='<tr><td><strong>Email</strong>:'.$post['email'].'</td></tr>';
        }
        if(!empty($post['project_type'])){      
            $projecttypearray = implode(",",$post['project_type']);     
            $txt.='<tr><td><strong>Project Type</strong>:'.$projecttypearray.'</td></tr>';          
        }

        if($post['comment']){
            $txt.='<tr><td><strong>Comment</strong>:'.$post['comment'].'</td></tr>';
        }
        $txt.='</table>';
        //echo $txt;



        $customerName='Demo Form';
        $message=$txt;

        $userSubject= 'Demo From ';     
        $fromEmail= 'admin@gmail.com.com';
        $fromName = 'Test Demo Form';

         $templateVars = [
                    'store' => 1,
                    'customer_name' => $customerName,
                    'subject' => $userSubject,
                    'message'   => $message
                ];
        $from = ['email' => $fromEmail, 'name' => $fromName];
        $this->inlineTranslation->suspend();


        $to = 'test@gmail.com';     

        $storeScope = \Magento\Store\Model\ScopeInterface::SCOPE_STORE;

         $templateOptions = [
          'area' => \Magento\Framework\App\Area::AREA_FRONTEND,
          'store' => 1
        ];

        $transport = $this->_transportBuilder->setTemplateIdentifier(5, $storeScope)
                ->setTemplateOptions($templateOptions)
                ->setTemplateVars($templateVars)
                ->setFrom($from)
                ->addTo($to)
                ->addAttachment($filePath, $fileName)               
                ->getTransport();
        $transport->sendMessage();
        $this->inlineTranslation->resume();

        $this->messageManager->addSuccess(__('Form successfully submitted'));

        $this->_redirect('form');
    }

}

vendorname/modulename/etc/di.xml

 <config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
    <preference for="\Magento\Framework\Mail\Template\TransportBuilder" type="\Vendorname\Modulename\Magento\Mail\Template\TransportBuilder" />
</config>

Vendorname/Modulename/Magento/Mail/Template/TransportBuilder.php

<?php
namespace Vendorname\Modulename\Magento\Mail\Template;

class TransportBuilder extends \Magento\Framework\Mail\Template\TransportBuilder
{
    public function addAttachment($file, $name)
    {
        if (!empty($file) && file_exists($file)) {
            $this->message
            ->createAttachment(
                file_get_contents($file),
                \Zend_Mime::TYPE_OCTETSTREAM,
                \Zend_Mime::DISPOSITION_ATTACHMENT,
                \Zend_Mime::ENCODING_BASE64,
                basename($name)
            );
        }
        return $this;
    }
}

Vendorname/Modulename/view/frontend/templates/test.phtml

 <div class="container">
    <form class="form-horizontal" method="post" enctype="multipart/form-data" action="url/cform/index/index">
        <div class="form-group">    
            <div class="row">
                <div class="col-sm-12">
                    <label for="">Name</label>
                </div>
            </div>
            <div class="row">
                <div class="col-sm-6">
                    <input class="form-control" type="text" id="" name="fname" placeholder="first name">
                </div>
                <div class="col-sm-6">
                    <input class="form-control" type="text" id="" name="lname" placeholder="last name">
                </div>          
            </div>
        </div>

        <div class="form-group">
            <label for="">Address</label>
            <textarea class="col-sm-12 form-control" rows="3" placeholder="" name="address"></textarea>
        </div>

        <div class="form-group">
            <div class="row">
                <div class="col-sm-5">
                    <label for="">City</label>
                    <input class="form-control" type="text" name="city" id="" placeholder="">
                </div>
                <div class="col-sm-4">
                    <label for="">State/Province</label>
                    <input class="form-control" type="text" name="state" id="" placeholder="">
                </div>
                <div class="col-sm-3">
                    <label for="">Zip Code</label>
                    <input class="form-control" type="text" name="zipcode" id="" placeholder="">
                </div>
            </div>
        </div>

        <div class="form-group">
            <div class="row">
                <div class="col-sm-8">
                    <label for="">Phone</label>
                        <div class="row">
                            <div class="col-sm-5">
                                <input class="form-control" type="text" id="" name="phone" placeholder="">
                            </div>  
                            <div class="col-sm-2 phone-or">
                                <span>OR</span>
                            </div>  
                            <div class="col-sm-5">
                                <input class="form-control" type="text" id="" placeholder="">
                            </div>  
                        </div>
                </div>
                <div class="col-sm-4">
                    <label for="">Email</label>
                    <input class="form-control" type="email" id="email" name="email" placeholder="">
                </div>
            </div>
        </div>

        <div class="form-group">
            <div class="row">
                <div class="col-sm-2">
                    <label for="">Project Type :</label>
                </div>
                <div class="col-sm-10">
                    <label class="checkbox-inline"> 
                        <input type="checkbox" id="" value="One1" name="project_type[]"> <span>Residential</span> 
                    </label> 
                    <label class="checkbox-inline"> 
                        <input type="checkbox" id="" value="One2" name="project_type[]"> <span>Commercial</span>
                    </label>        
                </div>      
            </div>
        </div>

        <div class="col-md-4 col-xs-12">
            <input accept="image/*" name="upload_document" type="file" value="" />
        </div>

        <div class="form-group">
            <div class="row">
                <div class="col-sm-2">
                    <label for="">Comment :</label>
                </div>
                <div class="col-sm-10">
                    <textarea class="form-control comment" rows="3" name="comment" placeholder="additional information about your project"></textarea>  
                </div>
            </div>
        </div>

        <div class="row">
                <button type="submit" class="btn btn-primary">SUBMIT</button>
        </div>

    </form>
</div>

Now call in cms page

{{block class="Magento\Framework\View\Element\Template" template="Vendorname_Modulename::test.phtml" }}
  • I tried this code but it's not working – kiran Oct 4 at 16:43

app/code/Vendor/Cform/etc/module.xml

<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:Module/etc/module.xsd">
    <module name="Vendor_Cform" setup_version="2.2.0">

    </module>
</config>

app/code/Vendor/Cform/registration.php

\Magento\Framework\Component\ComponentRegistrar::register(
    \Magento\Framework\Component\ComponentRegistrar::MODULE,
    'Vendor_Cform',
    __DIR__
);

app/code/Vendor/Cform/etc/frontend/routes.xml

<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="../../../../../../lib/internal/Magento/Framework/App/etc/routes.xsd">
    <router id="standard">
        <route id="cform" frontName="cform">
            <module name="Vendor_Cform" />
        </route>
    </router>
</config>

app/code/Vendor/Cform/Setup/InstallSchema.php

<?php
namespace Vendor\Cform\Setup;

use Magento\Framework\Setup\InstallSchemaInterface;
use Magento\Framework\Setup\ModuleContextInterface;
use Magento\Framework\Setup\SchemaSetupInterface;

/**
 * @codeCoverageIgnore
 */
class InstallSchema implements InstallSchemaInterface
{

    public function install(SchemaSetupInterface $setup, ModuleContextInterface $context)
    {
        $installer = $setup;
        $installer->startSetup();
        /**
         * Create table 'vendor_contect'
         */
        $table = $installer->getConnection()->newTable(
            $installer->getTable('vendor_contect')
        )->addColumn(
            'contect_id',
            \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
            null,
            ['identity' => true, 'unsigned' => true, 'nullable' => false, 'primary' => true],
            'Contect Id'
        )->addColumn(
            'name',
            \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
            255,
            ['nullable' => false],
            'Name'
        )->addColumn(
            'email',
            \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
            255,
            ['nullable' => false],
            'Email Id'
        )->addColumn(
            'telephone',
            \Magento\Framework\DB\Ddl\Table::TYPE_INTEGER,
            null,
            ['nullable'=> false],
            'Phone Number'
        )->addColumn(
            'comment',
            \Magento\Framework\DB\Ddl\Table::TYPE_TEXT,
            255,
            ['nullable' => false],
            'What’s on your mind?'
        );
        $installer->getConnection()->createTable($table);
    }
}

app/code/Vendor/Cform/view/frontend/templates/form.phtml

<form id="contact-form" class="form-horizontal" method="post" enctype="multipart/form-data" action="<?php echo $this->getUrl("cform/index/index")?>">
    <h1><?= $block->escapeHtml(__('Contact Form')) ?></h1>
    <fieldset class="fieldset">
        <div class="field name">
            <label class="label" for="name"><span><?= $block->escapeHtml(__('Name')) ?></span></label>
            <div class="control">
                <input name="name" id="name" class="input-text" type="text" />
            </div>
        </div>
        <div class="field email">
            <label class="label" for="email"><span><?= $block->escapeHtml(__('Email')) ?></span></label>
            <div class="control">
                <input name="email" id="email" class="input-text" type="email" />
            </div>
        </div>
        <div class="field telephone">
            <label class="label" for="telephone"><span><?= $block->escapeHtml(__('Phone Number')) ?></span></label>
            <div class="control">
                <input name="telephone" id="telephone" class="input-text" type="text" />
            </div>
        </div>
        <div class="field comment">
            <label class="label" for="comment"><span><?= $block->escapeHtml(__('What’s on your mind?')) ?></span></label>
            <div class="control">
                <textarea name="comment" id="comment" class="input-text" cols="5" rows="3" ></textarea>
            </div>
        </div>
        <?= $block->getChildHtml('form.additional.info') ?>
    </fieldset>
    <div class="actions-toolbar">
        <div class="primary">
            <input type="hidden" name="hideit" id="hideit" value="" />
            <button type="submit" id="add" title="" class="action submit primary">
                <span><?= $block->escapeHtml(__('Submit')) ?></span>
            </button>
        </div>
    </div>
</form>


<script>
require(['jquery'],function($){
    $(document).ready(function(){
        $("#add").click(function(){
        var customurl = "<?php echo $this->getUrl("cform/index/index") ?>";
        $.ajax({
            url: customurl,
            type: "POST",
            data: $(this).closest('form').serialize(),
            dataType: "json",
            success: function(result){
                console.log(result);
            }
        });
        $('#contact-form')[0].reset(); 
        return false;
        });
    });
}); 
</script>

app/code/Vendor/Cform/Controller/Index/index.php

<?php

namespace Vendor\Cform\Controller\Index;

use Magento\Framework\App\Action\Action;


class Index extends Action
{
    public function __construct(
        \Magento\Framework\App\Action\Context $context
    ) {
        parent::__construct($context);
    }   
    public function execute()
    {
        $post = $this->getRequest()->getPostValue();

        $objectManager = \Magento\Framework\App\ObjectManager::getInstance();       
        $data = $objectManager->create('Mconnect\Cform\Model\Cform');
        $data->setData($post);
        $data->save();
        /* echo "hello";
        exit; */

        $this->messageManager->addSuccess(__('Form successfully submitted'));

    }
}

app/code/Vendor/Cform/Model/Cform.php

<?php

namespace Vendor\Cform\Model;

class Cform extends \Magento\Framework\Model\AbstractModel
{
    /**
     * Initialize resource model
     *
     * @return void
     */

    protected function _construct()
    {
        $this->_init('Vendor\Cform\Model\ResourceModel\Cform');
    }

}

app/code/Vendor/Cform/Model/ResourceModel/Cform.php

<?php

namespace Vendor\Cform\Model\ResourceModel;

class Cform extends \Magento\Framework\Model\ResourceModel\Db\AbstractDb
{
    protected $storeManager;

    public function __construct(
        \Magento\Framework\Model\ResourceModel\Db\Context $context,
        \Magento\Store\Model\StoreManagerInterface $storeManager,
        $connectionName = null
    ) {
        parent::__construct($context, $connectionName);
        $this->storeManager = $storeManager;
    }

    protected function _construct()
    {
        $this->_init('vendor_contect', 'contect_id');
    }
}

app/code/Vendor/Cform/Model/ResourceModel/Cform/Collection.php

<?php
namespace Vendor\Cform\Model\ResourceModel\Cform;

use \Magento\Framework\Model\ResourceModel\Db\Collection\AbstractCollection;

class Collection extends AbstractCollection
{

    protected $_idFieldName = \Vendor\Cform\Model\Cform::CONTECT_ID;

    /**
     * Define resource model
     *
     * @return void
     */
    protected function _construct()
    {
        $this->_init('Vendor\Cform\Model\Cform', 'Vendor\Cform\Model\ResourceModel\Cform');
    }

}

CMS page Call

{{block class="Magento\Framework\View\Element\Template" template="Vendor_Cform::form.phtml" }}

app/code/Vendor/Cform/view/frontend/layout/contactform_index_index.xml

<?xml version="1.0"?>
<!--
/**
 * Copyright © Magento, Inc. All rights reserved.
 * See COPYING.txt for license details.
 */
-->
<page xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" layout="1column" xsi:noNamespaceSchemaLocation="urn:magento:framework:View/Layout/etc/page_configuration.xsd">
    <body>
        <referenceContainer name="content">
            <block class="Vendor\ContactForm\Block\Form" name="contactForm" template="Vendor_ContactForm::form.phtml">
                <container name="form.additional.info" label="Form Additional Info"/>
            </block>
        </referenceContainer>
    </body>
</page>
  1. Create a simple html form and submit data to your controller.
  2. Get all your post values in your controller and send mail using below function.

You can send mail using Zend_Mail() function.

// Get your post values
$firstname = "Dinesh";
$lastname = "Yadav";

// Send Mail functionality starts from here 
$from = "from_email_address@example.com";
$nameFrom = "From Name";
$to = "to_email_address@example.com";
$nameTo = "To Name";
$body = "
<div>
    <b>".$firstname."</b>
    <i>".$lastname."</i>
</div>";

$email = new \Zend_Mail();
$email->setSubject("Email Subject"); 
$email->setBodyHtml($body);     // use it to send html data
//$email->setBodyText($body);   // use it to send simple text data
$email->setFrom($from, $nameFrom);
$email->addTo($to, $nameTo);
$email->send();

Your Answer

 
discard

By clicking "Post Your Answer", you acknowledge that you have read our updated terms of service, privacy policy and cookie policy, and that your continued use of the website is subject to these policies.

Not the answer you're looking for? Browse other questions tagged or ask your own question.