ソースを参照

Make it easy to put inputs *inside* label elements.

This is a frequently requested feature that is much easier to implement
now. Add it so it is easy to integrate bootstrap & older versions of
foundation.
mark_story 12 年 前
コミット
f179736aae
2 ファイル変更50 行追加3 行削除
  1. 20 3
      src/View/Input/Radio.php
  2. 30 0
      tests/TestCase/View/Input/RadioTest.php

+ 20 - 3
src/View/Input/Radio.php

@@ -36,6 +36,16 @@ class Radio {
 /**
  * Constructor
  *
+ * This class uses a few templates:
+ *
+ * - `radio` Used to generate the input for a radio button.
+ *   Can use the following variables `name`, `value`, `attrs`.
+ * - `label` Used to generate the label for a radio button.
+ *   Can use the following variables `attrs`, `text` and `input`.
+ * - `radioContainer` Used to generate the container element for
+ *   the radio + input element. Can use the `input` and `label`
+ *   variables.
+ *
  * @param Cake\View\StringTemplate $templates
  */
 	public function __construct($templates) {
@@ -135,14 +145,19 @@ class Radio {
 			$radio['disabled'] = true;
 		}
 
-		$label = $this->_renderLabel($radio, $data['label'], $escape);
-
 		$input = $this->_templates->format('radio', [
 			'name' => $radio['name'],
 			'value' => $escape ? h($radio['value']) : $radio['value'],
 			'attrs' => $this->_templates->formatAttributes($radio, ['name', 'value', 'text']),
 		]);
 
+		$label = $this->_renderLabel(
+			$radio,
+			$data['label'],
+			$input,
+			$escape
+		);
+
 		return $this->_templates->format('radioContainer', [
 			'input' => $input,
 			'label' => $label,
@@ -157,10 +172,11 @@ class Radio {
  *
  * @param array $radio The input properties.
  * @param false|string|array $label The properties for a label.
+ * @param string $input The input widget.
  * @param boolean $escape Whether or not to HTML escape the label.
  * @return string Generated label.
  */
-	protected function _renderLabel($radio, $label, $escape) {
+	protected function _renderLabel($radio, $label, $input, $escape) {
 		if (!$label) {
 			return false;
 		}
@@ -169,6 +185,7 @@ class Radio {
 
 		return $this->_templates->format('label', [
 			'text' => $escape ? h($radio['text']) : $radio['text'],
+			'input' => $input,
 			'attrs' => $this->_templates->formatAttributes($labelAttrs),
 		]);
 	}

+ 30 - 0
tests/TestCase/View/Input/RadioTest.php

@@ -177,6 +177,36 @@ class RadioTest extends TestCase {
 	}
 
 /**
+ * Test rendering the input inside the label.
+ *
+ * @return void
+ */
+	public function testRenderInputInsideLabel() {
+		$this->templates->add([
+			'label' => '<label{{attrs}}>{{input}}{{text}}</label>',
+			'radioContainer' => '{{label}}',
+		]);
+		$radio = new Radio($this->templates);
+		$data = [
+			'name' => 'Crayons[color]',
+			'options' => ['r' => 'Red'],
+		];
+		$result = $radio->render($data);
+		$expected = [
+			['label' => ['for' => 'Crayons_color_r']],
+			['input' => [
+				'type' => 'radio',
+				'name' => 'Crayons[color]',
+				'value' => 'r',
+				'id' => 'Crayons_color_r'
+			]],
+			'Red',
+			'/label',
+		];
+		$this->assertTags($result, $expected);
+	}
+
+/**
  * test render() and selected inputs.
  *
  * @return void