public method

Creates an HTML form, and optionally binds it to a data object which contains information on how to render form fields, any data to pre-populate the form with, and any validation errors. Typically, a data object will be a Record object returned from a Model, but you can define your own custom objects as well. For more information on custom data objects, see lithium\template\helper\Form::$_binding.


  • mixed $bindings

    List of objects, or the object to bind the form to. This is usually an instance of Record or Document, or some other class that extends lithium\data\Entity.

  • array $options

    Other parameters for creating the form. Available options are:

    • 'url' mixed: A string URL or URL array parameters defining where in the application the form should be submitted to.
    • 'action' string: This is a shortcut to be used if you wish to only specify the name of the action to submit to, and use the default URL parameters (i.e. the current controller, etc.) for generating the remainder of the URL. Ignored if the 'url' key is set.
    • 'type' string: Currently the only valid option is 'file'. Set this if the form will be used for file uploads.
    • 'method' string: Represents the HTTP method with which the form will be submitted ('get', 'post', 'put' or 'delete'). If 'put' or 'delete', the request method is simulated using a hidden input field.



Returns a <form /> open tag with the action attribute defined by either the 'action' or 'url' options (defaulting to the current page if none is specified), the HTTP method is defined by the 'method' option, and any HTML attributes passed in $options.


This method can be filtered.


	public function create($bindings = null, array $options = []) {
		$request = $this->_context ? $this->_context->request() : null;
		$binding = is_array($bindings) ? reset($bindings) : $bindings;

		$defaults = [
			'url' => $request ? $request->params : [],
			'type' => null,
			'action' => null,
			'method' => $binding ? ($binding->exists() ? 'put' : 'post') : 'post'

		list(, $options, $tpl) = $this->_defaults(__FUNCTION__, null, $options);
		list($scope, $options) = $this->_options($defaults, $options);

		$params = compact('scope', 'options', 'bindings');
		$extra = ['method' => __METHOD__] + compact('tpl', 'defaults');

		return Filters::run($this, __FUNCTION__, $params, function($params) use ($extra) {
			$scope = $params['scope'];
			$options = $params['options'];
			$this->_binding = $params['bindings'];
			$append = null;
			$scope['method'] = strtolower($scope['method']);

			if ($scope['type'] === 'file') {
				if ($scope['method'] === 'get') {
					$scope['method'] = 'post';
				$options['enctype'] = 'multipart/form-data';

			if (!($scope['method'] === 'get' || $scope['method'] === 'post')) {
				$append = $this->hidden('_method', ['value' => strtoupper($scope['method'])]);
				$scope['method'] = 'post';

			$url = $scope['action'] ? ['action' => $scope['action']] : $scope['url'];
			$options['method'] = strtolower($scope['method']);
			$this->_bindingOptions = $scope + $options;

			return $this->_render($extra['method'], $extra['tpl'],
				compact('url', 'options', 'append')