Samstag, 22. August 2009

symfony (1.2) Bug (sfWidgetFormInputCheckbox)

Das symfony-Framework ist phantastisch!
Die version 1.2 enthällt jedoch einen kleinen Bugg, der leicht zu beheben ist.
Und zwar werden Checkboxen initial mit haken (checked) dargestellt. Ein "jungfräulicher" checkbox soll ja normaler weise "nicht gesetzt" erscheinen.

Zu diesem Bug gibt es übrigens schon ein Ticket:
http://trac.symfony-project.org/ticket/3917

Das Problem liegt in der render-Methode der Klasse sfWidgetFormInputCheckbox, die Sie hier finden:
"dein Projekt"\lib\vendor\symfony\lib\widget\sfWidgetFormInputCheckbox.class.php

So sieht die Methode im Original aus:

public function render($name, $value = null, $attributes = array(), $errors = array())
{
if (!is_null($value) && $value !== false) {
$attributes['checked'] = 'checked';
}
if (!isset($attributes['value']) && !is_null($this->getOption('value_attribute_value'))) {
$attributes['value'] = $this->getOption('value_attribute_value');
}
return parent::render($name, null, $attributes, $errors);
}


Der Fehler ist leicht zu beheben in dem man eine zusätzliche Bedingung in der ersten if-abfrage hinzufügt. Um Probleme bei späteren symfony updates aus dem weg zu gehen, leitet man die vorhandene Klasse selbst ab. Wenn man dabei auch noch die Namenskonvention von symfony für Dateien und Klassen einhällt, wir die Klasse auch noch von dem class loader gefunden ;-)

Neue Datei: MyWidgetFormInputCheckbox.class.php
Klasse mit der überschriebene render-Methode:

class MyWidgetFormInputCheckbox extends sfWidgetFormInputCheckbox
{
public function render($name, $value = null, $attributes = array(), $errors = array())
{
if (!is_null($value) && $value !== false && $value != 0) {
$attributes['checked'] = 'checked';
}
if (!isset($attributes['value']) && !is_null($this->getOption('value_attribute_value'))) {
$attributes['value'] = $this->getOption('value_attribute_value');
}
return parent::render($name, null, $attributes, $errors);
}
}


Die zusätzliche Bedingung ist oben in rot gekennzeichnet (es ist eine null nach dem !=).
Der Wert von $value ist im ungesetzten (unchecked) Zustand 0 (null).

Bei der Erstellung des Widgets in der Form-Klasse, macht es Sinn einen Wert für den gesetzen Zustand zu definieren:

class MySampleForm extends BaseSampleForm
{
public function configure()
{
...
$this->widgetSchema['MyCheckbox'] = new MyWidgetFormInputCheckbox(array(), array('value' => 1));
...
}
}

Keine Kommentare:

Kommentar veröffentlichen