Merge pull request #4079 from assertchris/add-row-and-cell-generator-methods

Add row and cell generator methods
This commit is contained in:
Damian Mooyman 2015-04-20 10:01:05 +12:00
commit f76ba9afc9

View File

@ -1,25 +1,26 @@
<?php <?php
/** /**
* Displays a {@link SS_List} in a grid format. * Displays a {@link SS_List} in a grid format.
* *
* GridField is a field that takes an SS_List and displays it in an table with rows * GridField is a field that takes an SS_List and displays it in an table with rows
* and columns. It reminds of the old TableFields but works with SS_List types * and columns. It reminds of the old TableFields but works with SS_List types
* and only loads the necessary rows from the list. * and only loads the necessary rows from the list.
* *
* The minimum configuration is to pass in name and title of the field and a * The minimum configuration is to pass in name and title of the field and a
* SS_List. * SS_List.
* *
* <code> * <code>
* $gridField = new GridField('ExampleGrid', 'Example grid', new DataList('Page')); * $gridField = new GridField('ExampleGrid', 'Example grid', new DataList('Page'));
* </code> * </code>
* *
* @see SS_List * @see SS_List
* *
* @package forms * @package forms
* @subpackage fields-gridfield * @subpackage fields-gridfield
*/ */
class GridField extends FormField { class GridField extends FormField {
/** /**
* *
* @var array * @var array
@ -28,46 +29,49 @@ class GridField extends FormField {
'index', 'index',
'gridFieldAlterAction' 'gridFieldAlterAction'
); );
/** /**
* The datasource * The datasource
*
* @var SS_List * @var SS_List
*/ */
protected $list = null; protected $list = null;
/** /**
* The classname of the DataObject that the GridField will display. Defaults to the value of $this->list->dataClass * The classname of the DataObject that the GridField will display. Defaults to the value of $this->list->dataClass
*
* @var string * @var string
*/ */
protected $modelClassName = ''; protected $modelClassName = '';
/** /**
* the current state of the GridField * the current state of the GridField
*
* @var GridState * @var GridState
*/ */
protected $state = null; protected $state = null;
/** /**
* *
* @var GridFieldConfig * @var GridFieldConfig
*/ */
protected $config = null; protected $config = null;
/** /**
* The components list * The components list
* *
* @var array * @var array
*/ */
protected $components = array(); protected $components = array();
/** /**
* Internal dispatcher for column handlers. * Internal dispatcher for column handlers.
* Keys are column names and values are GridField_ColumnProvider objects * Keys are column names and values are GridField_ColumnProvider objects
* *
* @var array * @var array
*/ */
protected $columnDispatch = null; protected $columnDispatch = null;
/** /**
* Map of callbacks for custom data fields * Map of callbacks for custom data fields
* *
@ -99,37 +103,38 @@ class GridField extends FormField {
$this->setConfig($config ?: GridFieldConfig_Base::create()); $this->setConfig($config ?: GridFieldConfig_Base::create());
$this->config->addComponent(new GridState_Component()); $this->config->addComponent(new GridState_Component());
$this->state = new GridState($this); $this->state = new GridState($this);
$this->addExtraClass('ss-gridfield'); $this->addExtraClass('ss-gridfield');
} }
public function index($request) { public function index($request) {
return $this->gridFieldAlterAction(array(), $this->getForm(), $request); return $this->gridFieldAlterAction(array(), $this->getForm(), $request);
} }
/** /**
* Set the modelClass (dataobject) that this field will get it column headers from. * Set the modelClass (dataobject) that this field will get it column headers from.
* If no $displayFields has been set, the displayfields will be fetched from * If no $displayFields has been set, the displayfields will be fetched from
* this modelclass $summary_fields * this modelclass $summary_fields
* *
* @param string $modelClassName * @param string $modelClassName
*
* @see GridFieldDataColumns::getDisplayFields() * @see GridFieldDataColumns::getDisplayFields()
*/ */
public function setModelClass($modelClassName) { public function setModelClass($modelClassName) {
$this->modelClassName = $modelClassName; $this->modelClassName = $modelClassName;
return $this; return $this;
} }
/** /**
* Returns a dataclass that is a DataObject type that this GridField should look like. * Returns a dataclass that is a DataObject type that this GridField should look like.
* *
* @throws Exception * @throws Exception
* @return string * @return string
*/ */
public function getModelClass() { public function getModelClass() {
if ($this->modelClassName) return $this->modelClassName; if($this->modelClassName) return $this->modelClassName;
if ($this->list && method_exists($this->list, 'dataClass')) { if($this->list && method_exists($this->list, 'dataClass')) {
$class = $this->list->dataClass(); $class = $this->list->dataClass();
if($class) return $class; if($class) return $class;
} }
@ -149,6 +154,7 @@ class GridField extends FormField {
/** /**
* @param GridFieldConfig $config * @param GridFieldConfig $config
*
* @return GridField * @return GridField
*/ */
public function setConfig(GridFieldConfig $config) { public function setConfig(GridFieldConfig $config) {
@ -159,12 +165,13 @@ class GridField extends FormField {
public function getComponents() { public function getComponents() {
return $this->config->getComponents(); return $this->config->getComponents();
} }
/** /**
* Cast a arbitrary value with the help of a castingDefintion * Cast a arbitrary value with the help of a castingDefintion
* *
* @param $value * @param $value
* @param $castingDefinition * @param $castingDefinition
*
* @todo refactor this into GridFieldComponent * @todo refactor this into GridFieldComponent
*/ */
public function getCastedValue($value, $castingDefinition) { public function getCastedValue($value, $castingDefinition) {
@ -175,21 +182,21 @@ class GridField extends FormField {
} else { } else {
$castingParams = array(); $castingParams = array();
} }
if(strpos($castingDefinition,'->') === false) { if(strpos($castingDefinition, '->') === false) {
$castingFieldType = $castingDefinition; $castingFieldType = $castingDefinition;
$castingField = DBField::create_field($castingFieldType, $value); $castingField = DBField::create_field($castingFieldType, $value);
$value = call_user_func_array(array($castingField,'XML'),$castingParams); $value = call_user_func_array(array($castingField, 'XML'), $castingParams);
} else { } else {
$fieldTypeParts = explode('->', $castingDefinition); $fieldTypeParts = explode('->', $castingDefinition);
$castingFieldType = $fieldTypeParts[0]; $castingFieldType = $fieldTypeParts[0];
$castingMethod = $fieldTypeParts[1]; $castingMethod = $fieldTypeParts[1];
$castingField = DBField::create_field($castingFieldType, $value); $castingField = DBField::create_field($castingFieldType, $value);
$value = call_user_func_array(array($castingField,$castingMethod),$castingParams); $value = call_user_func_array(array($castingField, $castingMethod), $castingParams);
} }
return $value; return $value;
} }
/** /**
* Set the datasource * Set the datasource
@ -224,7 +231,7 @@ class GridField extends FormField {
} }
return $list; return $list;
} }
/** /**
* Get the current GridState_Data or the GridState * Get the current GridState_Data or the GridState
* *
@ -262,7 +269,7 @@ class GridField extends FormField {
// Get data // Get data
$list = $this->getManipulatedList(); $list = $this->getManipulatedList();
// Render headers, footers, etc // Render headers, footers, etc
$content = array( $content = array(
"before" => "", "before" => "",
@ -271,7 +278,7 @@ class GridField extends FormField {
"footer" => "", "footer" => "",
); );
foreach($this->getComponents() as $item) { foreach($this->getComponents() as $item) {
if($item instanceof GridField_HTMLProvider) { if($item instanceof GridField_HTMLProvider) {
$fragments = $item->getHTMLFragments($this); $fragments = $item->getHTMLFragments($this);
if($fragments) foreach($fragments as $k => $v) { if($fragments) foreach($fragments as $k => $v) {
@ -290,10 +297,10 @@ class GridField extends FormField {
// Nested dependencies are handled by deferring the rendering of any content item that // Nested dependencies are handled by deferring the rendering of any content item that
// Circular dependencies are detected by disallowing any item to be deferred more than 5 times // Circular dependencies are detected by disallowing any item to be deferred more than 5 times
// It's a fairly crude algorithm but it works // It's a fairly crude algorithm but it works
$fragmentDefined = array('header' => true, 'footer' => true, 'before' => true, 'after' => true); $fragmentDefined = array('header' => true, 'footer' => true, 'before' => true, 'after' => true);
reset($content); reset($content);
while(list($k,$v) = each($content)) { while(list($k, $v) = each($content)) {
if(preg_match_all('/\$DefineFragment\(([a-z0-9\-_]+)\)/i', $v, $matches)) { if(preg_match_all('/\$DefineFragment\(([a-z0-9\-_]+)\)/i', $v, $matches)) {
foreach($matches[1] as $match) { foreach($matches[1] as $match) {
$fragmentName = strtolower($match); $fragmentName = strtolower($match);
@ -305,10 +312,10 @@ class GridField extends FormField {
if(preg_match('/\$DefineFragment\(([a-z0-9\-_]+)\)/i', $fragment, $matches)) { if(preg_match('/\$DefineFragment\(([a-z0-9\-_]+)\)/i', $fragment, $matches)) {
// If we've already deferred this fragment, then we have a circular dependency // If we've already deferred this fragment, then we have a circular dependency
if(isset($fragmentDeferred[$k]) && $fragmentDeferred[$k] > 5) { if(isset($fragmentDeferred[$k]) && $fragmentDeferred[$k] > 5) {
throw new LogicException("GridField HTML fragment '$fragmentName' and '$matches[1]' " . throw new LogicException("GridField HTML fragment '$fragmentName' and '$matches[1]' " .
"appear to have a circular dependency."); "appear to have a circular dependency.");
} }
// Otherwise we can push to the end of the content array // Otherwise we can push to the end of the content array
unset($content[$k]); unset($content[$k]);
$content[$k] = $v; $content[$k] = $v;
@ -331,7 +338,7 @@ class GridField extends FormField {
foreach($content as $k => $v) { foreach($content as $k => $v) {
if(empty($fragmentDefined[$k])) { if(empty($fragmentDefined[$k])) {
throw new LogicException("GridField HTML fragment '$k' was given content," throw new LogicException("GridField HTML fragment '$k' was given content,"
. " but not defined. Perhaps there is a supporting GridField component you need to add?"); . " but not defined. Perhaps there is a supporting GridField component you need to add?");
} }
} }
@ -345,30 +352,22 @@ class GridField extends FormField {
$rowContent = ''; $rowContent = '';
foreach($this->getColumns() as $column) { foreach($this->getColumns() as $column) {
$colContent = $this->getColumnContent($record, $column); $colContent = $this->getColumnContent($record, $column);
// A return value of null means this columns should be skipped altogether. // A return value of null means this columns should be skipped altogether.
if($colContent === null) continue; if($colContent === null) {
continue;
}
$colAttributes = $this->getColumnAttributes($record, $column); $colAttributes = $this->getColumnAttributes($record, $column);
$rowContent .= FormField::create_tag('td', $colAttributes, $colContent);
$rowContent .= $this->newCell($this, $total, $idx, $record, $colAttributes, $colContent);
} }
$classes = array('ss-gridfield-item');
if ($idx == 0) $classes[] = 'first'; $rows[] = $this->newRow($this, $total, $idx, $record, array(), $rowContent);
if ($idx == $total-1) $classes[] = 'last';
$classes[] = ($idx % 2) ? 'even' : 'odd';
$row = FormField::create_tag(
'tr',
array(
"class" => implode(' ', $classes),
'data-id' => $record->ID,
// TODO Allow per-row customization similar to GridFieldDataColumns
'data-class' => $record->ClassName,
),
$rowContent
);
$rows[] = $row;
} }
$content['body'] = implode("\n", $rows); $content['body'] = implode("\n", $rows);
} }
// Display a message when the grid field is empty // Display a message when the grid field is empty
if(!(isset($content['body']) && $content['body'])) { if(!(isset($content['body']) && $content['body'])) {
$content['body'] = FormField::create_tag( $content['body'] = FormField::create_tag(
@ -395,7 +394,7 @@ class GridField extends FormField {
$this->addExtraClass('ss-gridfield field'); $this->addExtraClass('ss-gridfield field');
$attrs = array_diff_key( $attrs = array_diff_key(
$this->getAttributes(), $this->getAttributes(),
array('value' => false, 'type' => false, 'name' => false) array('value' => false, 'type' => false, 'name' => false)
); );
$attrs['data-name'] = $this->getName(); $attrs['data-name'] = $this->getName();
@ -403,25 +402,77 @@ class GridField extends FormField {
'id' => isset($this->id) ? $this->id : null, 'id' => isset($this->id) ? $this->id : null,
'class' => 'ss-gridfield-table', 'class' => 'ss-gridfield-table',
'cellpadding' => '0', 'cellpadding' => '0',
'cellspacing' => '0' 'cellspacing' => '0'
); );
if($this->getDescription()) { if($this->getDescription()) {
$content['after'] .= FormField::create_tag( $content['after'] .= FormField::create_tag(
'span', 'span',
array('class' => 'description'), array('class' => 'description'),
$this->getDescription() $this->getDescription()
); );
} }
return return
FormField::create_tag('fieldset', $attrs, FormField::create_tag('fieldset', $attrs,
$content['before'] . $content['before'] .
FormField::create_tag('table', $tableAttrs, $head."\n".$foot."\n".$body) . FormField::create_tag('table', $tableAttrs, $head . "\n" . $foot . "\n" . $body) .
$content['after'] $content['after']
); );
} }
/**
* @param GridField $gridfield
* @param int $total
* @param int $index
* @param DataObject $record
* @param array $attributes
* @param string $content
*
* @return string
*/
protected function newCell($gridfield, $total, $index, $record, $attributes, $content) {
return FormField::create_tag(
'td',
$attributes,
$content
);
}
/**
* @param GridField $gridfield
* @param int $total
* @param int $index
* @param DataObject $record
* @param array $attributes
* @param string $content
*
* @return string
*/
protected function newRow($gridfield, $total, $index, $record, $attributes, $content) {
$classes = array('ss-gridfield-item');
if($index == 0) {
$classes[] = 'first';
}
if($index == $total - 1) {
$classes[] = 'last';
}
$classes[] = ($index % 2) ? 'even' : 'odd';
return FormField::create_tag(
'tr',
array(
'class' => implode(' ', $classes),
'data-id' => $record->ID,
'data-class' => $record->ClassName,
),
$content
);
}
public function Field($properties = array()) { public function Field($properties = array()) {
return $this->FieldHolder($properties); return $this->FieldHolder($properties);
} }
@ -452,6 +503,7 @@ class GridField extends FormField {
* *
* @param DataObject $record * @param DataObject $record
* @param string $column * @param string $column
*
* @return string * @return string
* @throws InvalidArgumentException * @throws InvalidArgumentException
*/ */
@ -460,7 +512,7 @@ class GridField extends FormField {
if(!$this->columnDispatch) { if(!$this->columnDispatch) {
$this->buildColumnDispatch(); $this->buildColumnDispatch();
} }
if(!empty($this->columnDispatch[$column])) { if(!empty($this->columnDispatch[$column])) {
$content = ""; $content = "";
foreach($this->columnDispatch[$column] as $handler) { foreach($this->columnDispatch[$column] as $handler) {
@ -471,12 +523,12 @@ class GridField extends FormField {
throw new InvalidArgumentException("Bad column '$column'"); throw new InvalidArgumentException("Bad column '$column'");
} }
} }
/** /**
* Add additional calculated data fields to be used on this GridField * Add additional calculated data fields to be used on this GridField
* *
* @param array $fields a map of fieldname to callback. The callback will * @param array $fields a map of fieldname to callback. The callback will
* be passed the record as an argument. * be passed the record as an argument.
*/ */
public function addDataFields($fields) { public function addDataFields($fields) {
if($this->customDataFields) { if($this->customDataFields) {
@ -485,7 +537,7 @@ class GridField extends FormField {
$this->customDataFields = $fields; $this->customDataFields = $fields;
} }
} }
/** /**
* Get the value of a named field on the given record. * Get the value of a named field on the given record.
* Use of this method ensures that any special rules around the data for this gridfield are followed. * Use of this method ensures that any special rules around the data for this gridfield are followed.
@ -496,7 +548,7 @@ class GridField extends FormField {
$callback = $this->customDataFields[$fieldName]; $callback = $this->customDataFields[$fieldName];
return $callback($record); return $callback($record);
} }
// Default implementation // Default implementation
if($record->hasMethod('relField')) { if($record->hasMethod('relField')) {
return $record->relField($fieldName); return $record->relField($fieldName);
@ -512,6 +564,7 @@ class GridField extends FormField {
* *
* @param DataObject $record * @param DataObject $record
* @param string $column * @param string $column
*
* @return array * @return array
* @throws LogicException * @throws LogicException
* @throws InvalidArgumentException * @throws InvalidArgumentException
@ -521,7 +574,7 @@ class GridField extends FormField {
if(!$this->columnDispatch) { if(!$this->columnDispatch) {
$this->buildColumnDispatch(); $this->buildColumnDispatch();
} }
if(!empty($this->columnDispatch[$column])) { if(!empty($this->columnDispatch[$column])) {
$attrs = array(); $attrs = array();
@ -546,6 +599,7 @@ class GridField extends FormField {
* Get metadata for a column, example array('Title'=>'Email address') * Get metadata for a column, example array('Title'=>'Email address')
* *
* @param string $column * @param string $column
*
* @return array * @return array
* @throws LogicException * @throws LogicException
* @throws InvalidArgumentException * @throws InvalidArgumentException
@ -555,22 +609,22 @@ class GridField extends FormField {
if(!$this->columnDispatch) { if(!$this->columnDispatch) {
$this->buildColumnDispatch(); $this->buildColumnDispatch();
} }
if(!empty($this->columnDispatch[$column])) { if(!empty($this->columnDispatch[$column])) {
$metadata = array(); $metadata = array();
foreach($this->columnDispatch[$column] as $handler) { foreach($this->columnDispatch[$column] as $handler) {
$column_metadata = $handler->getColumnMetadata($this, $column); $column_metadata = $handler->getColumnMetadata($this, $column);
if(is_array($column_metadata)) { if(is_array($column_metadata)) {
$metadata = array_merge($metadata, $column_metadata); $metadata = array_merge($metadata, $column_metadata);
} else { } else {
$methodSignature = get_class($handler) . "::getColumnMetadata()"; $methodSignature = get_class($handler) . "::getColumnMetadata()";
throw new LogicException("Non-array response from $methodSignature."); throw new LogicException("Non-array response from $methodSignature.");
} }
} }
return $metadata; return $metadata;
} }
throw new InvalidArgumentException("Bad column '$column'"); throw new InvalidArgumentException("Bad column '$column'");
@ -584,13 +638,13 @@ class GridField extends FormField {
public function getColumnCount() { public function getColumnCount() {
// Build the column dispatch // Build the column dispatch
if(!$this->columnDispatch) $this->buildColumnDispatch(); if(!$this->columnDispatch) $this->buildColumnDispatch();
return count($this->columnDispatch); return count($this->columnDispatch);
} }
/** /**
* Build an columnDispatch that maps a GridField_ColumnProvider to a column * Build an columnDispatch that maps a GridField_ColumnProvider to a column
* for reference later * for reference later
* *
*/ */
protected function buildColumnDispatch() { protected function buildColumnDispatch() {
$this->columnDispatch = array(); $this->columnDispatch = array();
@ -610,7 +664,8 @@ class GridField extends FormField {
* This is the action that gets executed when a GridField_AlterAction gets clicked. * This is the action that gets executed when a GridField_AlterAction gets clicked.
* *
* @param array $data * @param array $data
* @return string *
* @return string
*/ */
public function gridFieldAlterAction($data, $form, SS_HTTPRequest $request) { public function gridFieldAlterAction($data, $form, SS_HTTPRequest $request) {
$html = ''; $html = '';
@ -639,7 +694,7 @@ class GridField extends FormField {
if($html) return $html; if($html) return $html;
} }
} }
switch($request->getHeader('X-Pjax')) { switch($request->getHeader('X-Pjax')) {
case 'CurrentField': case 'CurrentField':
return $this->FieldHolder(); return $this->FieldHolder();
@ -661,6 +716,7 @@ class GridField extends FormField {
* @param string $actionName * @param string $actionName
* @param mixed $args * @param mixed $args
* @param arrray $data - send data from a form * @param arrray $data - send data from a form
*
* @return type * @return type
* @throws InvalidArgumentException * @throws InvalidArgumentException
*/ */
@ -670,17 +726,17 @@ class GridField extends FormField {
if(!($component instanceof GridField_ActionProvider)) { if(!($component instanceof GridField_ActionProvider)) {
continue; continue;
} }
if(in_array($actionName, array_map('strtolower', (array)$component->getActions($this)))) { if(in_array($actionName, array_map('strtolower', (array) $component->getActions($this)))) {
return $component->handleAction($this, $actionName, $args, $data); return $component->handleAction($this, $actionName, $args, $data);
} }
} }
throw new InvalidArgumentException("Can't handle action '$actionName'"); throw new InvalidArgumentException("Can't handle action '$actionName'");
} }
/** /**
* Custom request handler that will check component handlers before proceeding to the default implementation. * Custom request handler that will check component handlers before proceeding to the default implementation.
* *
* @todo There is too much code copied from RequestHandler here. * @todo There is too much code copied from RequestHandler here.
*/ */
public function handleRequest(SS_HTTPRequest $request, DataModel $model) { public function handleRequest(SS_HTTPRequest $request, DataModel $model) {
@ -693,18 +749,18 @@ class GridField extends FormField {
$fieldData = $this->request->requestVar($this->getName()); $fieldData = $this->request->requestVar($this->getName());
if($fieldData && isset($fieldData['GridState'])) $this->getState(false)->setValue($fieldData['GridState']); if($fieldData && isset($fieldData['GridState'])) $this->getState(false)->setValue($fieldData['GridState']);
foreach($this->getComponents() as $component) { foreach($this->getComponents() as $component) {
if(!($component instanceof GridField_URLHandler)) { if(!($component instanceof GridField_URLHandler)) {
continue; continue;
} }
$urlHandlers = $component->getURLHandlers($this); $urlHandlers = $component->getURLHandlers($this);
if($urlHandlers) foreach($urlHandlers as $rule => $action) { if($urlHandlers) foreach($urlHandlers as $rule => $action) {
if($params = $request->match($rule, true)) { if($params = $request->match($rule, true)) {
// Actions can reference URL parameters, eg, '$Action/$ID/$OtherID' => '$Action', // Actions can reference URL parameters, eg, '$Action/$ID/$OtherID' => '$Action',
if($action[0] == '$') $action = $params[substr($action,1)]; if($action[0] == '$') $action = $params[substr($action, 1)];
if(!method_exists($component, 'checkAccessAction') || $component->checkAccessAction($action)) { if(!method_exists($component, 'checkAccessAction') || $component->checkAccessAction($action)) {
if(!$action) { if(!$action) {
$action = "index"; $action = "index";
@ -723,7 +779,8 @@ class GridField extends FormField {
} }
if($this !== $result && !$request->isEmptyPattern($rule) && is_object($result) if($this !== $result && !$request->isEmptyPattern($rule) && is_object($result)
&& $result instanceof RequestHandler) { && $result instanceof RequestHandler
) {
$returnValue = $result->handleRequest($request, $model); $returnValue = $result->handleRequest($request, $model);
@ -733,11 +790,11 @@ class GridField extends FormField {
return $returnValue; return $returnValue;
// If we return some other data, and all the URL is parsed, then return that // If we return some other data, and all the URL is parsed, then return that
} else if($request->allParsed()) { } else if($request->allParsed()) {
return $result; return $result;
// But if we have more content on the URL and we don't know what to do with it, return an error // But if we have more content on the URL and we don't know what to do with it, return an error
} else { } else {
return $this->httpError(404, return $this->httpError(404,
"I can't handle sub-URLs of a " . get_class($result) . " object."); "I can't handle sub-URLs of a " . get_class($result) . " object.");
@ -746,7 +803,7 @@ class GridField extends FormField {
} }
} }
} }
return parent::handleRequest($request, $model); return parent::handleRequest($request, $model);
} }
@ -762,10 +819,10 @@ class GridField extends FormField {
/** /**
* This class is the base class when you want to have an action that alters * This class is the base class when you want to have an action that alters
* the state of the {@link GridField}, rendered as a button element. * the state of the {@link GridField}, rendered as a button element.
* *
* @package forms * @package forms
* @subpackage fields-gridfield * @subpackage fields-gridfield
*/ */
class GridField_FormAction extends FormAction { class GridField_FormAction extends FormAction {
@ -774,12 +831,12 @@ class GridField_FormAction extends FormAction {
* @var GridField * @var GridField
*/ */
protected $gridField; protected $gridField;
/** /**
* @var array * @var array
*/ */
protected $stateValues; protected $stateValues;
/** /**
* @var array * @var array
*/ */
@ -800,7 +857,7 @@ class GridField_FormAction extends FormAction {
* @param type $name * @param type $name
* @param type $label * @param type $label
* @param type $actionName * @param type $actionName
* @param type $args * @param type $args
*/ */
public function __construct(GridField $gridField, $name, $title, $actionName, $args) { public function __construct(GridField $gridField, $name, $title, $actionName, $args) {
$this->gridField = $gridField; $this->gridField = $gridField;
@ -811,9 +868,9 @@ class GridField_FormAction extends FormAction {
} }
/** /**
* urlencode encodes less characters in percent form than we need - we * urlencode encodes less characters in percent form than we need - we
* need everything that isn't a \w. * need everything that isn't a \w.
* *
* @param string $val * @param string $val
*/ */
public function nameEncode($val) { public function nameEncode($val) {
@ -822,11 +879,11 @@ class GridField_FormAction extends FormAction {
/** /**
* The callback for nameEncode * The callback for nameEncode
* *
* @param string $val * @param string $val
*/ */
public function _nameEncode($match) { public function _nameEncode($match) {
return '%'.dechex(ord($match[0])); return '%' . dechex(ord($match[0]));
} }
/** /**
@ -841,16 +898,16 @@ class GridField_FormAction extends FormAction {
); );
// Ensure $id doesn't contain only numeric characters // Ensure $id doesn't contain only numeric characters
$id = 'gf_'.substr(md5(serialize($state)), 0, 8); $id = 'gf_' . substr(md5(serialize($state)), 0, 8);
Session::set($id, $state); Session::set($id, $state);
$actionData['StateID'] = $id; $actionData['StateID'] = $id;
return array_merge( return array_merge(
parent::getAttributes(), parent::getAttributes(),
array( array(
// Note: This field needs to be less than 65 chars, otherwise Suhosin security patch // Note: This field needs to be less than 65 chars, otherwise Suhosin security patch
// will strip it from the requests // will strip it from the requests
'name' => 'action_gridFieldAlterAction'. '?' . http_build_query($actionData), 'name' => 'action_gridFieldAlterAction' . '?' . http_build_query($actionData),
'data-url' => $this->gridField->Link(), 'data-url' => $this->gridField->Link(),
) )
); );
@ -860,16 +917,17 @@ class GridField_FormAction extends FormAction {
* Calculate the name of the gridfield relative to the Form * Calculate the name of the gridfield relative to the Form
* *
* @param GridField $base * @param GridField $base
*
* @return string * @return string
*/ */
protected function getNameFromParent() { protected function getNameFromParent() {
$base = $this->gridField; $base = $this->gridField;
$name = array(); $name = array();
do { do {
array_unshift($name, $base->getName()); array_unshift($name, $base->getName());
$base = $base->getForm(); $base = $base->getForm();
} while ($base && !($base instanceof Form)); } while($base && !($base instanceof Form));
return implode('.', $name); return implode('.', $name);
} }