Ty Bailey
Ty Bailey

Reputation: 2432

Get Form Input from Zend Framework

I am venturing into the Zend Framework and decided to build a simple application to practice with. The app I am building is a simple calculator that allows a user to add, subtract, multiply and divide two numbers.

I am having trouble retrieving the user input to calculate the answer. When I use Zend_Debug::dump($this->getRequest()->getParams()); in the IndexAction() method it displays the form data correctly on the page, but how do I send the data to the proper Model for processing?

Here is the IndexController.php file:

<?php

class IndexController extends Zend_Controller_Action
{

    //initialize calculator form on controller call
    public function init()
    {

        //istantiate Zend_Form object
        $form = new Zend_Form();
        $form->setAction('')
             ->setMethod('post');


        //first number input
        $num1 = $form->createElement('text', 'num1');
        $num1->addValidator('Digits')
             ->setRequired(true)
             ->setAttrib('placeholder', 'Enter First Number');

        //second number input    
        $num2 = $form->createElement('text', 'num2');
        $num2->addValidator('Digits')
             ->setRequired(true)
             ->setAttrib('placeholder', 'Enter Second Number');

        //math operator select box
        $op = $form->createElement('select', 'operator');
        $op->setRequired(true)
              ->setMultiOptions(array('1'=>'+', '2'=>'-', '3'=>'X', '4'=>'/'))
              ->setRequired(true);

        //add elements to form
        $form->addElement($num1)
             ->addElement($op)           
             ->addElement($num2)
             ->addElement('submit', 'equal', array('label' => '='));

        return $form;
    }

    public function indexAction()
    {
        //render the form view
        $this->view->form = $this->init();
        $this->render('index');

    }


    public function calcAction()
    {

        $form = $this->form;
        $data = $this->getRequest()->getParams();

        if ($data->isPost()) {

            if($data->isValid()) {

                $calculator = new Calculator_Model;

                switch($data['operator']) {
                    case $data['operator'] === '1':
                       $ans = $calculator->addNums($data['num1'], $data['num2']);
                       return $ans;
                       break;
                    case $data['operator'] === '2':
                        $ans = $calculator->subtractNums($data['num1'], $data['num2']);
                        return $ans;
                        break;
                    case $data['operator'] === '3':
                        $ans = $calculator->multiplyNums($data['num1'], $data['num2']);
                        return $ans;
                        break;
                    case $data['operator'] === '4':
                        $ans = $calculator->divideNums($data['num1'], $data['num2']);
                        return $ans;
                        break;
                }

            } else {
                return $form->getMessages();
            }
        } 
    }

}

I tried placing the calcAction() script into the indexAction() method but then the page doesn't render at all. How can I get the user input to the Calculator_Model for processing?

Upvotes: 0

Views: 2588

Answers (2)

Ty Bailey
Ty Bailey

Reputation: 2432

I found a solution to this problem.

I changed $data = $this->getRequest()->getParams(); to $data = $this->getRequest()->getPost(); and I began getting the data properly. I don't know what was stopping the data from coming through with getParams(); but I discovered that getParams(); doesn't validate the data using the Zend_Filter(); function, getPost(); however does.

The calculator app is now finished with completely different code than what is pasted here. You may view the final product at: https://github.com/TylerB24890/Zend-Calculator

In my final app I had to create a separate validator class for the number inputs to allow both integers and floats. I didn't assign these to the Zend_Filter() function because I wasn't able to properly get those working. If anyone has any tips on how to make those work please contribute to the GitHub project at the link above.

Upvotes: 0

Amit Kriplani
Amit Kriplani

Reputation: 682

I guess you are doing most of the things right but i personally think you should not do so much programing in controller. Your controller is not only passing data to model, it is actually trying to figure out which function to call.

That should have been done by the model. The problem is simple and so can be the solution, but this will not be scalable. Consider that you wish to add an operation, you will have to create it's function in the model and add a case in your controller as well.

What i usually do is

Check if form is valid : $form->isValid()

Instantiate the model : $cal = new Model()

Pass data to model : $calc->process($form->getValues())

The process() would be the only public method in my model. The switch case statement would go into that method and call appropriate protected method. also i would let the model decide the options for operator element in the form $op->setMultiOptions(Model::$availableOperations) This way i can just update my model whenever i need to add an operation.

I hope all this makes sense to someone. :)

Upvotes: 1

Related Questions