This is my current code in Twig for datepicker (it's only static, not dynamic, not yet linked with Form Type)
<div class="form-group">
<label>Date of Birth</label>
<select id="year"></select>
<select id="month"></select>
<select id="day"></select>
</div>
Below is JavaScript code
<script src="{{ asset('bundles/hearwegohearwego/js/homepage/select-birthday.js') }}"></script>
<script type="text/javascript">
var today= new Date();
var yy= today.getFullYear();
var dd=today.getDate();
var mm=today.getMonth()+1;
selectBirthday("#year", "#month", "#day", {
year : 1938,
month : mm,
day : dd,
yearRange : 75,
endYear : yy
});
</script>
In select-birthday.js
function selectBirthday(yearSelector, monthSelector, daySelector, config) {
if (config == undefined) {
config = {};
}
if (config.year == undefined) {
config.year = new Date().getFullYear();
}
if (config.month == undefined) {
config.day = new Date().getMonth() + 1;
}
if (config.month == undefined) {
config.day = new Date().getDate();
}
if (config.yearRange == undefined) {
config.yearRange = 100;
}
if (config.endYear == undefined) {
config.endYear = new Date().getFullYear();
}
var birthdayYear = $(yearSelector);
if (birthdayYear.length == 0) {
throw "can not find 'year' select control";
}
for (var y = config.endYear; y > config.endYear - config.yearRange; y--) {
if (y == config.year) {
$('<option value="' + y + '" selected="selected">' + y + '</option>').appendTo(birthdayYear);
} else {
$('<option value="' + y + '" >' + y + '</option>').appendTo(birthdayYear);
}
}
var birthdayMonth = $(monthSelector);
if (birthdayMonth.length == 0) {
throw "can not find 'month' select control";
}
for (var m = 1; m <= 12; m++) {
if (m == config.month) {
$('<option value="' + m + '" selected="selected">' + m + '</option>').appendTo(birthdayMonth);
} else {
$('<option value="' + m + '">' + m + '</option>').appendTo(birthdayMonth);
}
}
var birthdayDay = $(daySelector);
if (birthdayDay.length == 0) {
throw "can not find 'day' select control";
}
for (var d = 1; d <= 31; d++) {
if (d == config.day) {
$('<option value="' + d + '" selected="selected">' + d + '</option>').appendTo(birthdayDay);
} else {
$('<option value="' + d + '">' + d + '</option>').appendTo(birthdayDay);
}
}
birthdayYear.change(onBirthdayChanged);
birthdayMonth.change(onBirthdayChanged);
birthdayDay.change(onBirthdayChanged);
var day29 = birthdayDay.find('option[value="29"]');
var day30 = birthdayDay.find('option[value="30"]');
var day31 = birthdayDay.find('option[value="31"]');
function onBirthdayChanged() {
var year = parseInt(birthdayYear.val());
var month = parseInt(birthdayMonth.val());
var day = parseInt(birthdayDay.val());
switch (month) {
case 4:
case 6:
case 9:
case 11:
if (day > 30) {
birthdayDay.val(30);
}
day29.show();
day30.show();
day31.hide();
break;
case 2:
if (!isLeapYear(year)) {
if (day > 28) {
birthdayDay.val(28);
}
day29.hide();
} else {
if (day > 29) {
birthdayDay.val(29);
}
day29.show();
}
day30.hide();
day31.hide();
break;
default:
day29.show();
day30.show();
day31.show();
break;
}
}
function isLeapYear(year) {
return 0 == year % 4 && (year % 100 != 0 || year % 400 == 0);
}
}
The JavaScript code is to create 3 select tags to choose day, month, year so that they follows natural rules (28 days of February, leap year...)
If I create Form Type like this ( UserRegisterType.php
)
<?php
namespace HearWeGo\HearWeGoBundle\Form;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
class UserRegisterType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder->add('email', 'text')
->add('firstName', 'text')
->add('lastName', 'text')
->add('dateOfBirth', 'date', array(
'years' => range(date('Y') -100, date('Y')-5)
))
->add('phone', 'text')
->add('password', 'password')
;
}
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults(array(
'data_class' => 'HearWeGo\\HearWeGoBundle\\Entity\\User'
));
}
public function getName()
{
return 'user_register_type';
}
}
Only one field - dateOfBirth
of date
type - is created, and it doesn't follow natural rules I want. How can I inject a datepicker to my aforementioned frontend and JavaScript code?
A very simple solution is to create your own formtype element, you can call it datepicker for instance.
// YourBundle/Resources/views/Form/fields.html.twig
{% block datepicker_widget %}
<input type="date" {% if value is not empty %}value="{{ value }}" {% endif %} {{ block('widget_attributes') }}/>
{% endblock %}
Then at top of your twig call this file
// Top of yourTwigFile.html.twig
{% form_theme form 'YourAppYourBundle:Form:fields.html.twig' %}
Last step is to change the type of element used
// HearWeGo/HearWeGoBundle/Form/UserRegisterType.php
[...]
->add('dateOfBirth', 'datepicker', array(
'years' => range(date('Y') -100, date('Y')-5)
))
[...]
This way you will absolutly not need any complicated Javascript, just use the default render behaviour of the web browser (with <input type="date" />
)
If you are using Twitter Bootstrap, you can use this twig template instead of the first I gave in order to have a prettier rendering
{# DATEPICKER #}
{% block datepicker_widget %}
<input placeholder="Date" class="form-control datepicker" type="text" {% if value is not empty %}value="{{ value }}" {% endif %} {{ block('widget_attributes') }}/>
{% endblock %}
{# DATETIMEPICKER #}
{% block datetimepicker_widget %}
{{ form_errors(form.date) }}
{{ form_errors(form.time) }}
<div class="input-group datetimepicker">
<span class="input-group-addon">Le</span>
{{ form_widget(form.date) }}
<span class="input-group-addon inner-addon">à</span>
{{ form_widget(form.time) }}
</div>
{% endblock %}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.