Many of the HTML 5 new widgets are automatically supported by CakePHP. Unfortunatelly datalist is not supported by default.
With the datalist HTML 5 element you can create a widget similar to select elements, but with datalist you are not forced to select one of the options, but you can add any new value also.
If you are looking for plain datalist support by a CakePHP plugin you should check dereuromark/cakephp-tools
This plugin adds an extra feature on a plain datalist. If you create a new option, than CakePHP will save the value in the associted model as a new record.
From version 1.0.0 we have renamed the widget, so in the AppView.php
and in your template files you should use datalistJs
instead of datalist
as described below.
Sorry for breaking backward compatibility, but there were only a few installs of the previous versions and as dereuromark/cakephp-tools implemented plain datalist, this was the easiest way to do...
You can install this plugin into your CakePHP application using composer.
The recommended way to install the plugin is via composer:
composer require rrd108/cakephp-datalist
Than you should load the plugin by issuing the following command in your terminal.
bin/cake plugin load Datalist
As the plugin extends the core HTML widgets you should load the form helper in your /src/View/AppView.php
file like this:
public function initialize()
{
parent::initialize();
$this->loadHelper('Form', [
'templates' => 'Datalist.form-templates',
'widgets' => [
'datalistJs' => ['Datalist\View\Widget\DatalistJsWidget']
]
]);
}
In any model where you want to use datalist you should add datalist behavior.
For example in your /src/Model/Table/SkillsTable.php
you should have the following code, where Languages
should be associated to SkillsTable
and name
is the field on what we want to use datalist.
public function initialize(array $config)
{
parent::initialize($config);
$this->addBehavior(
'Datalist.Datalist',
['Languages' => 'name']
);
$this->belongsTo('Languages', [
'foreignKey' => 'language_id',
'joinType' => 'INNER'
]);
}
If you want more datalists you can add more models to the behavior.
$this->addBehavior(
'Datalist.Datalist',
['Languages' => 'name', 'Countries' => 'country']
);
}
Than in your controller you do a simple find operation and set the result to the view.
//src/Controller/SkillsController.php
public function add()
{
// your controller code
$languages = $this->Skills->Languages->find('list', ['limit' => 200]);
$this->set(compact('languages'));
}
By this the $languages
variable is available at /src/Template/Skills/add.ctp
file.
<?= $this->Form->create($skill) ?>
<?php
echo $this->Form->control(
'language_id',
['type' => 'datalistJs', 'options' => $languages]
);
?>
The end result should work like a charm and if you do not select one of the options but type in a new one, CakePHP will save it as a new entry in the associated model.