mirror of
https://github.com/silverstripe/silverstripe-userforms.git
synced 2024-10-22 15:05:42 +00:00
Replace the form editor with GridField
This commit is contained in:
parent
8f92d75975
commit
ae7dd98be3
@ -4,6 +4,5 @@ name: userforms
|
|||||||
LeftAndMain:
|
LeftAndMain:
|
||||||
extra_requirements_javascript:
|
extra_requirements_javascript:
|
||||||
- userforms/javascript/UserForm.js
|
- userforms/javascript/UserForm.js
|
||||||
|
|
||||||
extra_requirements_css:
|
extra_requirements_css:
|
||||||
- userforms/css/FieldEditor.css
|
- userforms/css/FieldEditor.css
|
||||||
|
180
code/extensions/UserFormFieldEditorExtension.php
Normal file
180
code/extensions/UserFormFieldEditorExtension.php
Normal file
@ -0,0 +1,180 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @package userforms
|
||||||
|
*/
|
||||||
|
class UserFormFieldEditorExtension extends DataExtension {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
|
private static $has_many = array(
|
||||||
|
'Fields' => 'EditableFormField'
|
||||||
|
);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Adds the field editor to the page.
|
||||||
|
*
|
||||||
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function updateCMSFields(FieldList $fields) {
|
||||||
|
$fieldEditor = $this->getFieldEditorGrid();
|
||||||
|
|
||||||
|
$fields->findOrMakeTab('Root.Form', _t('UserDefinedForm.FORM', 'Form'));
|
||||||
|
$fields->addFieldToTab('Root.Form', $fieldEditor);
|
||||||
|
|
||||||
|
return $fields;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the field editor, for adding and removing EditableFormFields.
|
||||||
|
*
|
||||||
|
* @return GridField
|
||||||
|
*/
|
||||||
|
public function getFieldEditorGrid() {
|
||||||
|
$fieldEditor = GridField::create('Fields', _t('UserDefinedForm.FIELDS', 'Fields'), $this->owner->Fields());
|
||||||
|
|
||||||
|
$config = GridFieldConfig::create()
|
||||||
|
->addComponents(
|
||||||
|
(new GridFieldEditableColumns())
|
||||||
|
->setDisplayFields(array(
|
||||||
|
'ClassName' => function($record, $column, $grid) {
|
||||||
|
return DropdownField::create($column, '', $this->getEditableFieldClasses());
|
||||||
|
},
|
||||||
|
'Title' => function($record, $column, $grid) {
|
||||||
|
return TextField::create($column, ' ')
|
||||||
|
->setAttribute('placeholder', _t('UserDefinedForm.TITLE', 'Title'));
|
||||||
|
}
|
||||||
|
)),
|
||||||
|
new GridFieldButtonRow(),
|
||||||
|
new GridFieldAddNewInlineButton(),
|
||||||
|
new GridFieldEditButton(),
|
||||||
|
new GridFieldDeleteAction(),
|
||||||
|
new GridFieldToolbarHeader(),
|
||||||
|
new GridFieldOrderableRows('Sort'),
|
||||||
|
new GridState_Component(),
|
||||||
|
new GridFieldDetailForm()
|
||||||
|
);
|
||||||
|
|
||||||
|
$fieldEditor->setConfig($config);
|
||||||
|
|
||||||
|
return $fieldEditor;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return array
|
||||||
|
*/
|
||||||
|
public function getEditableFieldClasses() {
|
||||||
|
$classes = ClassInfo::getValidSubClasses('EditableFormField');
|
||||||
|
|
||||||
|
// Remove classes we don't want to display in the dropdown.
|
||||||
|
$classes = array_diff($classes, array(
|
||||||
|
'EditableFormField',
|
||||||
|
'EditableMultipleOptionField'
|
||||||
|
));
|
||||||
|
|
||||||
|
$editableFieldClasses = array();
|
||||||
|
|
||||||
|
foreach ($classes as $key => $className) {
|
||||||
|
$singleton = singleton($className);
|
||||||
|
|
||||||
|
if(!$singleton->canCreate()) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
$editableFieldClasses[$className] = $singleton->i18n_singular_name();
|
||||||
|
}
|
||||||
|
|
||||||
|
return $editableFieldClasses;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @see SiteTree::doPublish
|
||||||
|
* @param Page $original
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function onAfterPublish($original) {
|
||||||
|
// Remove fields on the live table which could have been orphaned.
|
||||||
|
$live = Versioned::get_by_stage("EditableFormField", "Live", array(
|
||||||
|
'ParentID' => $original->ID
|
||||||
|
));
|
||||||
|
|
||||||
|
if($live) {
|
||||||
|
foreach($live as $field) {
|
||||||
|
$field->doDeleteFromStage('Live');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
foreach($this->owner->Fields() as $field) {
|
||||||
|
$field->doPublish('Stage', 'Live');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @see SiteTree::doUnpublish
|
||||||
|
* @param Page $page
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function onAfterUnpublish($page) {
|
||||||
|
foreach($page->Fields() as $field) {
|
||||||
|
$field->doDeleteFromStage('Live');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @see SiteTree::duplicate
|
||||||
|
* @param DataObject $newPage
|
||||||
|
*
|
||||||
|
* @return DataObject
|
||||||
|
*/
|
||||||
|
public function onAfterDuplicate($newPage) {
|
||||||
|
foreach($this->owner->Fields() as $field) {
|
||||||
|
$newField = $field->duplicate();
|
||||||
|
$newField->ParentID = $newPage->ID;
|
||||||
|
$newField->ParentClass = $newPage->ClassName;
|
||||||
|
$newField->write();
|
||||||
|
|
||||||
|
foreach ($field->CustomRules() as $customRule) {
|
||||||
|
$newRule = $customRule->duplicate();
|
||||||
|
$newRule->ParentID = $newField->ID;
|
||||||
|
$newRule->write();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return $newPage;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @see SiteTree::getIsModifiedOnStage
|
||||||
|
* @param boolean $isModified
|
||||||
|
*
|
||||||
|
* @return boolean
|
||||||
|
*/
|
||||||
|
public function getIsModifiedOnStage($isModified) {
|
||||||
|
if(!$isModified) {
|
||||||
|
foreach($this->owner->Fields() as $field) {
|
||||||
|
if($field->getIsModifiedOnStage()) {
|
||||||
|
$isModified = true;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return $isModified;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @see SiteTree::doRevertToLive
|
||||||
|
* @param Page $page
|
||||||
|
*
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function onAfterRevertToLive($page) {
|
||||||
|
foreach($page->Fields() as $field) {
|
||||||
|
$field->publish('Live', 'Stage', false);
|
||||||
|
$field->writeWithoutVersion();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -1,338 +0,0 @@
|
|||||||
<?php
|
|
||||||
/**
|
|
||||||
* A form field allowing a user to customize and create form fields.
|
|
||||||
* for saving into a {@link UserDefinedForm}
|
|
||||||
*
|
|
||||||
* @package userforms
|
|
||||||
*/
|
|
||||||
|
|
||||||
class FieldEditor extends FormField {
|
|
||||||
|
|
||||||
private static $url_handlers = array(
|
|
||||||
'$Action!/$ID' => '$Action'
|
|
||||||
);
|
|
||||||
|
|
||||||
private static $allowed_actions = array(
|
|
||||||
'addfield',
|
|
||||||
'addoptionfield',
|
|
||||||
'handleField'
|
|
||||||
);
|
|
||||||
|
|
||||||
/**
|
|
||||||
* @param array $properties
|
|
||||||
*
|
|
||||||
* @return HTML
|
|
||||||
*/
|
|
||||||
public function FieldHolder($properties = array()) {
|
|
||||||
$add = Controller::join_links($this->Link('addfield'));
|
|
||||||
|
|
||||||
$this->setAttribute('data-add-url', '\''. $add.'\'');
|
|
||||||
|
|
||||||
return $this->renderWith("FieldEditor");
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns whether a user can edit the form.
|
|
||||||
*
|
|
||||||
* @param Member $member
|
|
||||||
*
|
|
||||||
* @return boolean
|
|
||||||
*/
|
|
||||||
public function canEdit($member = null) {
|
|
||||||
if($this->readonly) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
return $this->form->getRecord()->canEdit();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Returns whether a user delete a field in the form. The
|
|
||||||
* {@link EditableFormField} instances check if they can delete themselves
|
|
||||||
* but this counts as an {@link self::canEdit()} function rather than a
|
|
||||||
* delete.
|
|
||||||
*
|
|
||||||
* @param Member $member
|
|
||||||
* @return boolean
|
|
||||||
*/
|
|
||||||
public function canDelete($member = null) {
|
|
||||||
if($this->readonly) return false;
|
|
||||||
|
|
||||||
return $this->form->getRecord()->canEdit();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Transform this form field to a readonly version.
|
|
||||||
*
|
|
||||||
* @return ViewableData_Customised
|
|
||||||
*/
|
|
||||||
public function performReadonlyTransformation() {
|
|
||||||
$clone = clone $this;
|
|
||||||
$clone->readonly = true;
|
|
||||||
$fields = $clone->Fields();
|
|
||||||
|
|
||||||
if($fields) {
|
|
||||||
foreach($fields as $field) {
|
|
||||||
$field->setReadonly();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return $clone->customise(array(
|
|
||||||
'Fields' => $fields
|
|
||||||
));
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Return the fields.
|
|
||||||
*
|
|
||||||
* @return RelationList
|
|
||||||
*/
|
|
||||||
public function Fields() {
|
|
||||||
if($this->form && $this->form->getRecord() && $this->name) {
|
|
||||||
$relationName = $this->name;
|
|
||||||
$fields = $this->form->getRecord()->getComponents($relationName);
|
|
||||||
|
|
||||||
if($fields) {
|
|
||||||
foreach($fields as $field) {
|
|
||||||
if(!$this->canEdit() && is_a($field, 'FormField')) {
|
|
||||||
$fields->remove($field);
|
|
||||||
$fields->push($field->performReadonlyTransformation());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return $fields;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Return a {@link ArrayList} of all the addable fields to populate the add
|
|
||||||
* field menu.
|
|
||||||
*
|
|
||||||
* @return ArrayList
|
|
||||||
*/
|
|
||||||
public function CreatableFields() {
|
|
||||||
$fields = ClassInfo::subclassesFor('EditableFormField');
|
|
||||||
|
|
||||||
if($fields) {
|
|
||||||
array_shift($fields); // get rid of subclass 0
|
|
||||||
asort($fields); // get in order
|
|
||||||
|
|
||||||
$output = new ArrayList();
|
|
||||||
|
|
||||||
foreach($fields as $field => $title) {
|
|
||||||
// get the nice title and strip out field
|
|
||||||
$niceTitle = _t(
|
|
||||||
$field.'.SINGULARNAME',
|
|
||||||
$title
|
|
||||||
);
|
|
||||||
|
|
||||||
if($niceTitle && $field != "EditableMultipleOptionField") {
|
|
||||||
$output->push(new ArrayData(array(
|
|
||||||
'ClassName' => $field,
|
|
||||||
'Title' => "$niceTitle"
|
|
||||||
)));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return $output;
|
|
||||||
}
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Handles saving the page. Needs to keep an eye on fields and options which
|
|
||||||
* have been removed / added
|
|
||||||
*
|
|
||||||
* @param DataObject $record
|
|
||||||
*/
|
|
||||||
public function saveInto(DataObjectInterface $record) {
|
|
||||||
$name = $this->name;
|
|
||||||
$fieldSet = $record->$name();
|
|
||||||
|
|
||||||
// store the field IDs and delete the missing fields
|
|
||||||
// alternatively, we could delete all the fields and re add them
|
|
||||||
$missingFields = array();
|
|
||||||
|
|
||||||
foreach($fieldSet as $existingField) {
|
|
||||||
$missingFields[$existingField->ID] = $existingField;
|
|
||||||
}
|
|
||||||
|
|
||||||
if(isset($_REQUEST[$name]) && is_array($_REQUEST[$name])) {
|
|
||||||
foreach($_REQUEST[$name] as $newEditableID => $newEditableData) {
|
|
||||||
if(!is_numeric($newEditableID)) continue;
|
|
||||||
|
|
||||||
// get it from the db
|
|
||||||
$editable = DataObject::get_by_id('EditableFormField', $newEditableID);
|
|
||||||
|
|
||||||
// if it exists in the db update it
|
|
||||||
if($editable) {
|
|
||||||
|
|
||||||
// remove it from the removed fields list
|
|
||||||
if(isset($missingFields[$editable->ID]) && isset($newEditableData) && is_array($newEditableData)) {
|
|
||||||
unset($missingFields[$editable->ID]);
|
|
||||||
}
|
|
||||||
|
|
||||||
// set form id
|
|
||||||
if($editable->ParentID == 0) {
|
|
||||||
$editable->ParentID = $record->ID;
|
|
||||||
}
|
|
||||||
|
|
||||||
// save data
|
|
||||||
$editable->populateFromPostData($newEditableData);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// remove the fields not saved
|
|
||||||
if($this->canEdit()) {
|
|
||||||
foreach($missingFields as $removedField) {
|
|
||||||
if(is_numeric($removedField->ID)) {
|
|
||||||
// check we can edit this
|
|
||||||
$removedField->delete();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Add a field to the field editor. Called via a ajax get.
|
|
||||||
*
|
|
||||||
* @return bool|html
|
|
||||||
*/
|
|
||||||
public function addfield() {
|
|
||||||
if(!SecurityToken::inst()->checkRequest($this->request)) {
|
|
||||||
return $this->httpError(400);
|
|
||||||
}
|
|
||||||
|
|
||||||
// get the last field in this form editor
|
|
||||||
$parentID = $this->form->getRecord()->ID;
|
|
||||||
|
|
||||||
if($parentID) {
|
|
||||||
$parentID = (int)$parentID;
|
|
||||||
|
|
||||||
$sqlQuery = new SQLQuery();
|
|
||||||
$sqlQuery = $sqlQuery
|
|
||||||
->setSelect("MAX(\"Sort\")")
|
|
||||||
->setFrom("\"EditableFormField\"")
|
|
||||||
->setWhere("\"ParentID\" = $parentID");
|
|
||||||
|
|
||||||
$sort = $sqlQuery->execute()->value() + 1;
|
|
||||||
|
|
||||||
$className = (isset($_REQUEST['Type'])) ? $_REQUEST['Type'] : '';
|
|
||||||
|
|
||||||
if(!$className) {
|
|
||||||
// A possible reason for the classname being blank is because we have execeded
|
|
||||||
// the number of input requests
|
|
||||||
// http://www.php.net/manual/en/info.configuration.php#ini.max-input-vars
|
|
||||||
$maxRequests = ini_get('max_input_vars');
|
|
||||||
$numRequests = count($_REQUEST, COUNT_RECURSIVE);
|
|
||||||
if ($numRequests > $maxRequests) {
|
|
||||||
$error = sprintf('You have exceded the maximum number %s of input requests',
|
|
||||||
"[$maxRequests]");
|
|
||||||
user_error($error, E_USER_WARNING);
|
|
||||||
}
|
|
||||||
user_error('Please select a field type to created', E_USER_WARNING);
|
|
||||||
}
|
|
||||||
|
|
||||||
if(is_subclass_of($className, "EditableFormField")) {
|
|
||||||
$field = new $className();
|
|
||||||
$field->ParentID = $this->form->getRecord()->ID;
|
|
||||||
$field->Name = $field->class . $field->ID;
|
|
||||||
$field->Sort = $sort;
|
|
||||||
$field->write();
|
|
||||||
|
|
||||||
return $field->EditSegment();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Return the html for a field option such as a
|
|
||||||
* dropdown field or a radio check box field
|
|
||||||
*
|
|
||||||
* @return bool|html
|
|
||||||
*/
|
|
||||||
public function addoptionfield() {
|
|
||||||
if(!SecurityToken::inst()->checkRequest($this->request)) {
|
|
||||||
return $this->httpError(400);
|
|
||||||
}
|
|
||||||
|
|
||||||
// passed via the ajax
|
|
||||||
$parent = (isset($_REQUEST['Parent'])) ? $_REQUEST['Parent'] : false;
|
|
||||||
|
|
||||||
// work out the sort by getting the sort of the last field in the form +1
|
|
||||||
if($parent) {
|
|
||||||
$sql_parent = (int)$parent;
|
|
||||||
|
|
||||||
$parentObj = EditableFormField::get()->byID($parent);
|
|
||||||
$optionClass = ($parentObj && $parentObj->exists()) ? $parentObj->getRelationClass('Options') : 'EditableOption';
|
|
||||||
|
|
||||||
$sqlQuery = new SQLQuery();
|
|
||||||
$sqlQuery = $sqlQuery
|
|
||||||
->setSelect("MAX(\"Sort\")")
|
|
||||||
->setFrom("\"EditableOption\"")
|
|
||||||
->setWhere("\"ParentID\" = $sql_parent");
|
|
||||||
|
|
||||||
$sort = $sqlQuery->execute()->value() + 1;
|
|
||||||
|
|
||||||
if($parent) {
|
|
||||||
$object = Injector::inst()->create($optionClass);
|
|
||||||
$object->write();
|
|
||||||
$object->ParentID = $parent;
|
|
||||||
$object->Sort = $sort;
|
|
||||||
$object->Name = 'option' . $object->ID;
|
|
||||||
$object->write();
|
|
||||||
|
|
||||||
return $object->EditSegment();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Pass sub {@link FormField} requests through the editor. For example,
|
|
||||||
* option fields need to be able to call themselves.
|
|
||||||
*
|
|
||||||
* @param SS_HTTPRequest
|
|
||||||
*/
|
|
||||||
public function handleField(SS_HTTPRequest $request) {
|
|
||||||
if(!SecurityToken::inst()->checkRequest($this->request)) {
|
|
||||||
return $this->httpError(400);
|
|
||||||
}
|
|
||||||
|
|
||||||
$fields = $this->Fields();
|
|
||||||
|
|
||||||
// extract the ID and option field name
|
|
||||||
preg_match(
|
|
||||||
'/Fields\[(?P<ID>\d+)\]\[CustomSettings\]\[(?P<Option>\w+)\]/',
|
|
||||||
$request->param('ID'), $matches
|
|
||||||
);
|
|
||||||
|
|
||||||
if(isset($matches['ID']) && isset($matches['Option'])) {
|
|
||||||
foreach($fields as $field) {
|
|
||||||
$formField = $field->getFormField();
|
|
||||||
|
|
||||||
if($matches['ID'] == $field->ID) {
|
|
||||||
if($field->canEdit()) {
|
|
||||||
// find the option to handle
|
|
||||||
$options = $field->getFieldConfiguration();
|
|
||||||
$optionField = $options->fieldByName($request->param('ID'));
|
|
||||||
|
|
||||||
if($optionField) {
|
|
||||||
return $optionField->handleRequest($request, $optionField);
|
|
||||||
} else {
|
|
||||||
return $this->httpError(404);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return $this->httpError(403);
|
|
||||||
}
|
|
||||||
}
|
|
158
code/forms/UserForm.php
Normal file
158
code/forms/UserForm.php
Normal file
@ -0,0 +1,158 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @package userforms
|
||||||
|
*/
|
||||||
|
class UserForm extends Form {
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param Controller $controller
|
||||||
|
* @param string $name
|
||||||
|
*/
|
||||||
|
public function __construct(Controller $controller, $name = 'Form') {
|
||||||
|
|
||||||
|
$this->controller = $controller;
|
||||||
|
$this->setRedirectToFormOnValidationError(true);
|
||||||
|
|
||||||
|
parent::__construct(
|
||||||
|
$controller,
|
||||||
|
$name,
|
||||||
|
$this->getFormFields(),
|
||||||
|
$this->getFormActions(),
|
||||||
|
$this->getRequiredFields()
|
||||||
|
);
|
||||||
|
|
||||||
|
if($controller->DisableCsrfSecurityToken) {
|
||||||
|
$this->disableSecurityToken();
|
||||||
|
}
|
||||||
|
|
||||||
|
$data = Session::get("FormInfo.{$this->FormName()}.data");
|
||||||
|
|
||||||
|
if(is_array($data)) {
|
||||||
|
$this->loadDataFrom($data);
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->extend('updateForm');
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the form fields for the form on this page. Can modify this FieldSet
|
||||||
|
* by using {@link updateFormFields()} on an {@link Extension} subclass which
|
||||||
|
* is applied to this controller.
|
||||||
|
*
|
||||||
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function getFormFields() {
|
||||||
|
$fields = new FieldList();
|
||||||
|
|
||||||
|
foreach($this->controller->Fields() as $editableField) {
|
||||||
|
// get the raw form field from the editable version
|
||||||
|
$field = $editableField->getFormField();
|
||||||
|
|
||||||
|
if(!$field) continue;
|
||||||
|
|
||||||
|
// set the error / formatting messages
|
||||||
|
$field->setCustomValidationMessage($editableField->getErrorMessage());
|
||||||
|
|
||||||
|
// set the right title on this field
|
||||||
|
if($right = $editableField->getSetting('RightTitle')) {
|
||||||
|
// Since this field expects raw html, safely escape the user data prior
|
||||||
|
$field->setRightTitle(Convert::raw2xml($right));
|
||||||
|
}
|
||||||
|
|
||||||
|
// if this field is required add some
|
||||||
|
if($editableField->Required) {
|
||||||
|
$field->addExtraClass('requiredField');
|
||||||
|
|
||||||
|
if($identifier = UserDefinedForm::config()->required_identifier) {
|
||||||
|
|
||||||
|
$title = $field->Title() ." <span class='required-identifier'>". $identifier . "</span>";
|
||||||
|
$field->setTitle($title);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// if this field has an extra class
|
||||||
|
if($extraClass = $editableField->getSetting('ExtraClass')) {
|
||||||
|
$field->addExtraClass(Convert::raw2att($extraClass));
|
||||||
|
}
|
||||||
|
|
||||||
|
// set the values passed by the url to the field
|
||||||
|
$request = $this->controller->getRequest();
|
||||||
|
if($value = $request->getVar($field->getName())) {
|
||||||
|
$field->setValue($value);
|
||||||
|
}
|
||||||
|
|
||||||
|
$fields->push($field);
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->extend('updateFormFields', $fields);
|
||||||
|
|
||||||
|
return $fields;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Generate the form actions for the UserDefinedForm. You
|
||||||
|
* can manipulate these by using {@link updateFormActions()} on
|
||||||
|
* a decorator.
|
||||||
|
*
|
||||||
|
* @todo Make form actions editable via their own field editor.
|
||||||
|
*
|
||||||
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function getFormActions() {
|
||||||
|
$submitText = ($this->controller->SubmitButtonText) ? $this->controller->SubmitButtonText : _t('UserDefinedForm.SUBMITBUTTON', 'Submit');
|
||||||
|
$clearText = ($this->controller->ClearButtonText) ? $this->controller->ClearButtonText : _t('UserDefinedForm.CLEARBUTTON', 'Clear');
|
||||||
|
|
||||||
|
$actions = new FieldList(
|
||||||
|
new FormAction("process", $submitText)
|
||||||
|
);
|
||||||
|
|
||||||
|
if($this->controller->ShowClearButton) {
|
||||||
|
$actions->push(new ResetFormAction("clearForm", $clearText));
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->extend('updateFormActions', $actions);
|
||||||
|
|
||||||
|
return $actions;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get the required form fields for this form.
|
||||||
|
*
|
||||||
|
* @return RequiredFields
|
||||||
|
*/
|
||||||
|
public function getRequiredFields() {
|
||||||
|
// Generate required field validator
|
||||||
|
$requiredNames = $this
|
||||||
|
->controller
|
||||||
|
->Fields()
|
||||||
|
->filter('Required', true)
|
||||||
|
->column('Name');
|
||||||
|
$required = new RequiredFields($requiredNames);
|
||||||
|
|
||||||
|
$this->extend('updateRequiredFields', $required);
|
||||||
|
|
||||||
|
return $required;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Override validation so conditional fields can be validated correctly.
|
||||||
|
*
|
||||||
|
* @return boolean
|
||||||
|
*/
|
||||||
|
public function validate() {
|
||||||
|
$data = $this->getData();
|
||||||
|
|
||||||
|
Session::set("FormInfo.{$this->FormName()}.data", $data);
|
||||||
|
Session::clear("FormInfo.{$this->FormName()}.errors");
|
||||||
|
|
||||||
|
foreach ($this->controller->Fields() as $key => $field) {
|
||||||
|
$field->validateField($data, $this);
|
||||||
|
}
|
||||||
|
|
||||||
|
if(Session::get("FormInfo.{$this->FormName()}.errors")) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
}
|
60
code/model/EditableCustomRule.php
Normal file
60
code/model/EditableCustomRule.php
Normal file
@ -0,0 +1,60 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
/**
|
||||||
|
* A custom rule for showing / hiding an EditableFormField
|
||||||
|
* based the value of another EditableFormField.
|
||||||
|
*
|
||||||
|
* @package userforms
|
||||||
|
*/
|
||||||
|
class EditableCustomRule extends DataObject {
|
||||||
|
|
||||||
|
private static $condition_options = array(
|
||||||
|
"IsBlank" => "Is blank",
|
||||||
|
"IsNotBlank" => "Is not blank",
|
||||||
|
"HasValue" => "Equals",
|
||||||
|
"ValueNot" => "Doesn't equal",
|
||||||
|
"ValueLessThan" => "Less than",
|
||||||
|
"ValueLessThanEqual" => "Less than or equal",
|
||||||
|
"ValueGreaterThan" => "Greater than",
|
||||||
|
"ValueGreaterThanEqual" => "Greater than or equal"
|
||||||
|
);
|
||||||
|
|
||||||
|
private static $db = array(
|
||||||
|
'Display' => 'Enum("Show,Hide")',
|
||||||
|
'ConditionOption' => 'Enum("IsBlank,IsNotBlank,HasValue,ValueNot,ValueLessThan,ValueLessThanEqual,ValueGreaterThan,ValueGreaterThanEqual")',
|
||||||
|
'FieldValue' => 'Varchar'
|
||||||
|
);
|
||||||
|
|
||||||
|
private static $has_one = array(
|
||||||
|
'Parent' => 'EditableFormField',
|
||||||
|
'ConditionField' => 'EditableFormField'
|
||||||
|
);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Built in extensions required
|
||||||
|
*
|
||||||
|
* @config
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
|
private static $extensions = array(
|
||||||
|
"Versioned('Stage', 'Live')"
|
||||||
|
);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Publish this custom rule to the live site
|
||||||
|
*
|
||||||
|
* Wrapper for the {@link Versioned} publish function
|
||||||
|
*/
|
||||||
|
public function doPublish($fromStage, $toStage, $createNewVersion = false) {
|
||||||
|
$this->publish($fromStage, $toStage, $createNewVersion);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Delete this custom rule from a given stage
|
||||||
|
*
|
||||||
|
* Wrapper for the {@link Versioned} deleteFromStage function
|
||||||
|
*/
|
||||||
|
public function doDeleteFromStage($stage) {
|
||||||
|
$this->deleteFromStage($stage);
|
||||||
|
}
|
||||||
|
}
|
@ -13,11 +13,21 @@ class EditableCheckbox extends EditableFormField {
|
|||||||
|
|
||||||
private static $plural_name = 'Checkboxes';
|
private static $plural_name = 'Checkboxes';
|
||||||
|
|
||||||
public function getFieldConfiguration() {
|
/**
|
||||||
$options = parent::getFieldConfiguration();
|
* @return FieldList
|
||||||
$options->push(new CheckboxField("Fields[$this->ID][CustomSettings][Default]", _t('EditableFormField.CHECKEDBYDEFAULT', 'Checked by Default?'), $this->getSetting('Default')));
|
*/
|
||||||
|
public function getCMSFields() {
|
||||||
|
$fields = parent::getCMSFields();
|
||||||
|
|
||||||
return $options;
|
$fields->removeByName('Default');
|
||||||
|
|
||||||
|
$fields->addFieldToTab('Root.Main', CheckboxField::create(
|
||||||
|
"Fields[$this->ID][CustomSettings][Default]",
|
||||||
|
_t('EditableFormField.CHECKEDBYDEFAULT', 'Checked by Default?'),
|
||||||
|
$this->getSetting('Default')
|
||||||
|
));
|
||||||
|
|
||||||
|
return $fields;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getFormField() {
|
public function getFormField() {
|
||||||
@ -32,6 +42,8 @@ class EditableCheckbox extends EditableFormField {
|
|||||||
$field->setAttribute('data-msg-required', $errorMessage);
|
$field->setAttribute('data-msg-required', $errorMessage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$field->setValue($this->getSetting('Default'));
|
||||||
|
|
||||||
return $field;
|
return $field;
|
||||||
}
|
}
|
||||||
|
|
@ -19,7 +19,16 @@ class EditableCheckboxGroupField extends EditableMultipleOptionField {
|
|||||||
|
|
||||||
$optionMap = ($optionSet) ? $optionSet->map('EscapedTitle', 'Title') : array();
|
$optionMap = ($optionSet) ? $optionSet->map('EscapedTitle', 'Title') : array();
|
||||||
|
|
||||||
return new UserFormsCheckboxSetField($this->Name, $this->Title, $optionMap);
|
$field = new UserFormsCheckboxSetField($this->Name, $this->Title, $optionMap);
|
||||||
|
|
||||||
|
// Set the default checked items
|
||||||
|
$defaultCheckedItems = $optionSet->filter('Default', 1);
|
||||||
|
|
||||||
|
if ($defaultCheckedItems->count()) {
|
||||||
|
$field->setDefaultItems($optionSet->filter('Default', 1)->map('EscapedTitle')->keys());
|
||||||
|
}
|
||||||
|
|
||||||
|
return $field;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getValueFromData($data) {
|
public function getValueFromData($data) {
|
@ -11,8 +11,19 @@ class EditableCountryDropdownField extends EditableFormField {
|
|||||||
|
|
||||||
private static $plural_name = 'Country Dropdowns';
|
private static $plural_name = 'Country Dropdowns';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function getCMSFields() {
|
||||||
|
$fields = parent::getCMSFields();
|
||||||
|
|
||||||
|
$fields->removeByName('Default');
|
||||||
|
|
||||||
|
return $fields;
|
||||||
|
}
|
||||||
|
|
||||||
public function getFormField() {
|
public function getFormField() {
|
||||||
return new CountryDropdownField($this->Name, $this->Title);
|
return CountryDropdownField::create($this->Name, $this->Title);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getValueFromData($data) {
|
public function getValueFromData($data) {
|
@ -13,23 +13,24 @@ class EditableDateField extends EditableFormField {
|
|||||||
|
|
||||||
private static $plural_name = 'Date Fields';
|
private static $plural_name = 'Date Fields';
|
||||||
|
|
||||||
public function getFieldConfiguration() {
|
/**
|
||||||
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function getCMSFields() {
|
||||||
|
$fields = parent::getCMSFields();
|
||||||
|
|
||||||
|
$fields->removeByName('Default');
|
||||||
|
|
||||||
$default = ($this->getSetting('DefaultToToday')) ? $this->getSetting('DefaultToToday') : false;
|
$default = ($this->getSetting('DefaultToToday')) ? $this->getSetting('DefaultToToday') : false;
|
||||||
$label = _t('EditableFormField.DEFAULTTOTODAY', 'Default to Today?');
|
$label = _t('EditableFormField.DEFAULTTOTODAY', 'Default to Today?');
|
||||||
|
|
||||||
return new FieldList(
|
$fields->addFieldToTab('Root.Main', CheckboxField::create(
|
||||||
new CheckboxField($this->getSettingName("DefaultToToday"), $label, $default)
|
$this->getSettingName('DefaultToToday'),
|
||||||
);
|
$label,
|
||||||
}
|
$default
|
||||||
|
));
|
||||||
|
|
||||||
public function populateFromPostData($data) {
|
return $fields;
|
||||||
$fieldPrefix = 'Default-';
|
|
||||||
|
|
||||||
if(empty($data['Default']) && !empty($data[$fieldPrefix.'Year']) && !empty($data[$fieldPrefix.'Month']) && !empty($data[$fieldPrefix.'Day'])) {
|
|
||||||
$data['Default'] = $data['Year'] . '-' . $data['Month'] . '-' . $data['Day'];
|
|
||||||
}
|
|
||||||
|
|
||||||
parent::populateFromPostData($data);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
@ -13,11 +13,23 @@ class EditableDropdown extends EditableMultipleOptionField {
|
|||||||
|
|
||||||
private static $plural_name = 'Dropdowns';
|
private static $plural_name = 'Dropdowns';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function getCMSFields() {
|
||||||
|
$fields = parent::getCMSFields();
|
||||||
|
|
||||||
|
$fields->removeByName('Default');
|
||||||
|
|
||||||
|
return $fields;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return DropdownField
|
* @return DropdownField
|
||||||
*/
|
*/
|
||||||
public function getFormField() {
|
public function getFormField() {
|
||||||
$optionSet = $this->Options();
|
$optionSet = $this->Options();
|
||||||
|
$defaultOptions = $optionSet->filter('Default', 1);
|
||||||
$options = array();
|
$options = array();
|
||||||
|
|
||||||
if($optionSet) {
|
if($optionSet) {
|
||||||
@ -36,6 +48,10 @@ class EditableDropdown extends EditableMultipleOptionField {
|
|||||||
$field->setAttribute('data-msg-required', $errorMessage);
|
$field->setAttribute('data-msg-required', $errorMessage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if($defaultOptions->count()) {
|
||||||
|
$field->setValue($defaultOptions->First()->EscapedTitle);
|
||||||
|
}
|
||||||
|
|
||||||
return $field;
|
return $field;
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -29,6 +29,8 @@ class EditableEmailField extends EditableFormField {
|
|||||||
$field->setAttribute('data-msg-required', $errorMessage);
|
$field->setAttribute('data-msg-required', $errorMessage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$field->setValue($this->Default);
|
||||||
|
|
||||||
return $field;
|
return $field;
|
||||||
}
|
}
|
||||||
|
|
@ -12,21 +12,21 @@ class EditableFileField extends EditableFormField {
|
|||||||
|
|
||||||
private static $plural_names = 'File Fields';
|
private static $plural_names = 'File Fields';
|
||||||
|
|
||||||
public function getFieldConfiguration() {
|
/**
|
||||||
$field = parent::getFieldConfiguration();
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function getCMSFields() {
|
||||||
|
$fields = parent::getCMSFields();
|
||||||
|
|
||||||
$folder = ($this->getSetting('Folder')) ? $this->getSetting('Folder') : null;
|
$folder = ($this->getSetting('Folder')) ? $this->getSetting('Folder') : null;
|
||||||
|
|
||||||
$tree = UserformsTreeDropdownField::create(
|
$fields->addFieldToTab('Root.Main', UserformsTreeDropdownField::create(
|
||||||
$this->getSettingName("Folder"),
|
$this->getSettingName('Folder'),
|
||||||
_t('EditableUploadField.SELECTUPLOADFOLDER', 'Select upload folder'),
|
_t('EditableUploadField.SELECTUPLOADFOLDER', 'Select upload folder'),
|
||||||
"Folder"
|
'Folder'
|
||||||
);
|
)->setValue($folder));
|
||||||
|
|
||||||
$tree->setValue($folder);
|
return $fields;
|
||||||
|
|
||||||
$field->push($tree);
|
|
||||||
|
|
||||||
return $field;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getFormField() {
|
public function getFormField() {
|
@ -8,7 +8,13 @@
|
|||||||
|
|
||||||
class EditableFormField extends DataObject {
|
class EditableFormField extends DataObject {
|
||||||
|
|
||||||
private static $default_sort = "Sort";
|
/**
|
||||||
|
* Default sort order
|
||||||
|
*
|
||||||
|
* @config
|
||||||
|
* @var string
|
||||||
|
*/
|
||||||
|
private static $default_sort = '"Sort"';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* A list of CSS classes that can be added
|
* A list of CSS classes that can be added
|
||||||
@ -17,6 +23,18 @@ class EditableFormField extends DataObject {
|
|||||||
*/
|
*/
|
||||||
public static $allowed_css = array();
|
public static $allowed_css = array();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @config
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
|
private static $summary_fields = array(
|
||||||
|
'Title'
|
||||||
|
);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @config
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
private static $db = array(
|
private static $db = array(
|
||||||
"Name" => "Varchar",
|
"Name" => "Varchar",
|
||||||
"Title" => "Varchar(255)",
|
"Title" => "Varchar(255)",
|
||||||
@ -24,19 +42,35 @@ class EditableFormField extends DataObject {
|
|||||||
"Sort" => "Int",
|
"Sort" => "Int",
|
||||||
"Required" => "Boolean",
|
"Required" => "Boolean",
|
||||||
"CustomErrorMessage" => "Varchar(255)",
|
"CustomErrorMessage" => "Varchar(255)",
|
||||||
"CustomRules" => "Text",
|
"CustomSettings" => "Text"
|
||||||
"CustomSettings" => "Text",
|
|
||||||
"CustomParameter" => "Varchar(200)"
|
|
||||||
);
|
);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @config
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
private static $has_one = array(
|
private static $has_one = array(
|
||||||
"Parent" => "UserDefinedForm",
|
"Parent" => "UserDefinedForm",
|
||||||
);
|
);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Built in extensions required
|
||||||
|
*
|
||||||
|
* @config
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
private static $extensions = array(
|
private static $extensions = array(
|
||||||
"Versioned('Stage', 'Live')"
|
"Versioned('Stage', 'Live')"
|
||||||
);
|
);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @config
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
|
private static $has_many = array(
|
||||||
|
"CustomRules" => "EditableCustomRule.Parent"
|
||||||
|
);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @var bool
|
* @var bool
|
||||||
*/
|
*/
|
||||||
@ -61,12 +95,179 @@ class EditableFormField extends DataObject {
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Template to render the form field into
|
* @return FieldList
|
||||||
*
|
|
||||||
* @return String
|
|
||||||
*/
|
*/
|
||||||
public function EditSegment() {
|
public function getCMSFields() {
|
||||||
return $this->renderWith('EditableFormField');
|
$fields = $this->scaffoldFormFields(array(
|
||||||
|
'tabbed' => true
|
||||||
|
));
|
||||||
|
|
||||||
|
$fields->removeByName('Sort');
|
||||||
|
$fields->removeByName('Version');
|
||||||
|
$fields->removeByName('ParentID');
|
||||||
|
$fields->removeByName('CustomSettings');
|
||||||
|
$fields->removeByName('Name');
|
||||||
|
|
||||||
|
$fields->insertBefore(ReadonlyField::create(
|
||||||
|
'Type',
|
||||||
|
_t('EditableFormField.TYPE', 'Type'),
|
||||||
|
$this->config()->get('singular_name')),
|
||||||
|
'Title'
|
||||||
|
);
|
||||||
|
|
||||||
|
$fields->insertBefore(LiteralField::create(
|
||||||
|
'MergeField',
|
||||||
|
_t('EditableFormField.MERGEFIELDNAME',
|
||||||
|
'<div class="field readonly">' .
|
||||||
|
'<label class="left">Merge field</label>' .
|
||||||
|
'<div class="middleColumn">' .
|
||||||
|
'<span class="readonly">$' . $this->Name . '</span>' .
|
||||||
|
'</div>' .
|
||||||
|
'</div>')),
|
||||||
|
'Title'
|
||||||
|
);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Validation
|
||||||
|
*/
|
||||||
|
$requiredCheckbox = $fields->fieldByName('Root')->fieldByName('Main')->fieldByName('Required');
|
||||||
|
$customErrorMessage = $fields->fieldByName('Root')->fieldByName('Main')->fieldByName('CustomErrorMessage');
|
||||||
|
|
||||||
|
$fields->removeFieldFromTab('Root.Main', 'Required');
|
||||||
|
$fields->removeFieldFromTab('Root.Main', 'CustomErrorMessage');
|
||||||
|
|
||||||
|
$fields->addFieldToTab('Root.Validation', $requiredCheckbox);
|
||||||
|
$fields->addFieldToTab('Root.Validation', $customErrorMessage);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Custom rules
|
||||||
|
*/
|
||||||
|
|
||||||
|
$customRulesConfig = GridFieldConfig::create()
|
||||||
|
->addComponents(
|
||||||
|
(new GridFieldEditableColumns())
|
||||||
|
->setDisplayFields(array(
|
||||||
|
'Display' => '',
|
||||||
|
'ConditionFieldID' => function($record, $column, $grid) {
|
||||||
|
return DropdownField::create(
|
||||||
|
$column,
|
||||||
|
'',
|
||||||
|
EditableFormField::get()
|
||||||
|
->filter(array(
|
||||||
|
'ParentID' => $this->ParentID
|
||||||
|
))
|
||||||
|
->exclude(array(
|
||||||
|
'ID' => $this->ID
|
||||||
|
))
|
||||||
|
->map('ID', 'Title')
|
||||||
|
);
|
||||||
|
},
|
||||||
|
'ConditionOption' => function($record, $column, $grid) {
|
||||||
|
$options = Config::inst()->get('EditableCustomRule', 'condition_options');
|
||||||
|
return DropdownField::create($column, '', $options);
|
||||||
|
},
|
||||||
|
'FieldValue' => function($record, $column, $grid) {
|
||||||
|
return TextField::create($column);
|
||||||
|
},
|
||||||
|
'ParentID' => function($record, $column, $grid) {
|
||||||
|
return HiddenField::create($column, '', $this->ID);
|
||||||
|
}
|
||||||
|
)),
|
||||||
|
new GridFieldButtonRow(),
|
||||||
|
new GridFieldToolbarHeader(),
|
||||||
|
new GridFieldAddNewInlineButton(),
|
||||||
|
new GridFieldDeleteAction(),
|
||||||
|
new GridState_Component()
|
||||||
|
);
|
||||||
|
|
||||||
|
|
||||||
|
$customRulesGrid = GridField::create(
|
||||||
|
'CustomRules',
|
||||||
|
_t('EditableFormField.CUSTOMRULES', 'Custom Rules'),
|
||||||
|
$this->CustomRules(),
|
||||||
|
$customRulesConfig
|
||||||
|
);
|
||||||
|
|
||||||
|
$fields->addFieldToTab('Root.CustomRules', $customRulesGrid);
|
||||||
|
|
||||||
|
/*
|
||||||
|
* Custom settings
|
||||||
|
*/
|
||||||
|
$extraClass = ($this->getSetting('ExtraClass')) ? $this->getSetting('ExtraClass') : '';
|
||||||
|
|
||||||
|
if (is_array(self::$allowed_css) && !empty(self::$allowed_css)) {
|
||||||
|
foreach(self::$allowed_css as $k => $v) {
|
||||||
|
if (!is_array($v)) $cssList[$k]=$v;
|
||||||
|
elseif ($k == $this->ClassName()) $cssList = array_merge($cssList, $v);
|
||||||
|
}
|
||||||
|
|
||||||
|
$fields->addFieldToTab('Root.Main',
|
||||||
|
new DropdownField(
|
||||||
|
$this->getSettingName('ExtraClass'),
|
||||||
|
_t('EditableFormField.EXTRACLASSA', 'Extra Styling/Layout'),
|
||||||
|
$cssList,
|
||||||
|
$extraClass
|
||||||
|
)
|
||||||
|
);
|
||||||
|
} else {
|
||||||
|
$fields->addFieldToTab('Root.Main',
|
||||||
|
new TextField(
|
||||||
|
$this->getSettingName('ExtraClass'),
|
||||||
|
_t('EditableFormField.EXTRACLASSB', 'Extra CSS class - separate multiples with a space'),
|
||||||
|
$extraClass
|
||||||
|
)
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
$fields->addFieldToTab('Root.Main',
|
||||||
|
new TextField(
|
||||||
|
$this->getSettingName('RightTitle'),
|
||||||
|
_t('EditableFormField.RIGHTTITLE', 'Right Title'),
|
||||||
|
$this->getSetting('RightTitle')
|
||||||
|
)
|
||||||
|
);
|
||||||
|
|
||||||
|
$this->extend('updateCMSFields', $fields);
|
||||||
|
|
||||||
|
return $fields;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function onBeforeWrite() {
|
||||||
|
parent::onBeforeWrite();
|
||||||
|
|
||||||
|
// Save custom settings.
|
||||||
|
$fields = $this->toMap();
|
||||||
|
$settings = $this->getSettings();
|
||||||
|
|
||||||
|
foreach($fields as $field => $value) {
|
||||||
|
if(preg_match("/\[CustomSettings\]\[((\w)+)\]$/", $field, $matches)) {
|
||||||
|
$settings[$matches[1]] = $value;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
$this->setSettings($settings);
|
||||||
|
|
||||||
|
if(!isset($this->Sort)) {
|
||||||
|
$parentID = ($this->ParentID) ? $this->ParentID : 0;
|
||||||
|
|
||||||
|
$this->Sort = EditableFormField::get()->filter('ParentID', $parentID)->max('Sort') + 1;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return void
|
||||||
|
*/
|
||||||
|
public function onAfterWrite() {
|
||||||
|
parent::onAfterWrite();
|
||||||
|
|
||||||
|
// Set a field name.
|
||||||
|
if(!$this->Name) {
|
||||||
|
$this->Name = $this->RecordClassName . $this->ID;
|
||||||
|
$this->write();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -85,7 +286,11 @@ class EditableFormField extends DataObject {
|
|||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function canDelete($member = null) {
|
public function canDelete($member = null) {
|
||||||
return ($this->Parent()->canEdit($member = null) && !$this->isReadonly());
|
if($this->Parent()) {
|
||||||
|
return $this->Parent()->canEdit($member) && !$this->isReadonly();
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -95,7 +300,11 @@ class EditableFormField extends DataObject {
|
|||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function canEdit($member = null) {
|
public function canEdit($member = null) {
|
||||||
return ($this->Parent()->canEdit($member = null) && !$this->isReadonly());
|
if($this->Parent()) {
|
||||||
|
return $this->Parent()->canEdit($member) && !$this->isReadonly();
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -105,6 +314,11 @@ class EditableFormField extends DataObject {
|
|||||||
*/
|
*/
|
||||||
public function doPublish($fromStage, $toStage, $createNewVersion = false) {
|
public function doPublish($fromStage, $toStage, $createNewVersion = false) {
|
||||||
$this->publish($fromStage, $toStage, $createNewVersion);
|
$this->publish($fromStage, $toStage, $createNewVersion);
|
||||||
|
|
||||||
|
// Don't forget to publish the related custom rules...
|
||||||
|
foreach ($this->CustomRules() as $rule) {
|
||||||
|
$rule->doPublish($fromStage, $toStage, $createNewVersion);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -114,6 +328,11 @@ class EditableFormField extends DataObject {
|
|||||||
*/
|
*/
|
||||||
public function doDeleteFromStage($stage) {
|
public function doDeleteFromStage($stage) {
|
||||||
$this->deleteFromStage($stage);
|
$this->deleteFromStage($stage);
|
||||||
|
|
||||||
|
// Don't forget to delete the related custom rules...
|
||||||
|
foreach ($this->CustomRules() as $rule) {
|
||||||
|
$rule->deleteFromStage($stage);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -244,51 +463,6 @@ class EditableFormField extends DataObject {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Return the custom validation fields for this field for the CMS
|
|
||||||
*
|
|
||||||
* @return array
|
|
||||||
*/
|
|
||||||
public function Dependencies() {
|
|
||||||
return ($this->CustomRules) ? unserialize($this->CustomRules) : array();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Return the custom validation fields for the field
|
|
||||||
*
|
|
||||||
* @return DataObjectSet
|
|
||||||
*/
|
|
||||||
public function CustomRules() {
|
|
||||||
$output = new ArrayList();
|
|
||||||
$fields = $this->Parent()->Fields();
|
|
||||||
|
|
||||||
// check for existing ones
|
|
||||||
if($rules = $this->Dependencies()) {
|
|
||||||
foreach($rules as $rule => $data) {
|
|
||||||
// recreate all the field object to prevent caching
|
|
||||||
$outputFields = new ArrayList();
|
|
||||||
|
|
||||||
foreach($fields as $field) {
|
|
||||||
$new = clone $field;
|
|
||||||
|
|
||||||
$new->isSelected = ($new->Name == $data['ConditionField']) ? true : false;
|
|
||||||
$outputFields->push($new);
|
|
||||||
}
|
|
||||||
|
|
||||||
$output->push(new ArrayData(array(
|
|
||||||
'FieldName' => $this->getFieldName(),
|
|
||||||
'Display' => $data['Display'],
|
|
||||||
'Fields' => $outputFields,
|
|
||||||
'ConditionField' => $data['ConditionField'],
|
|
||||||
'ConditionOption' => $data['ConditionOption'],
|
|
||||||
'Value' => $data['Value']
|
|
||||||
)));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return $output;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Title field of the field in the backend of the page
|
* Title field of the field in the backend of the page
|
||||||
*
|
*
|
||||||
@ -336,118 +510,6 @@ class EditableFormField extends DataObject {
|
|||||||
return $name . '[' . $field .']';
|
return $name . '[' . $field .']';
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* How to save the data submitted in this field into the database object
|
|
||||||
* which this field represents.
|
|
||||||
*
|
|
||||||
* Any class's which call this should also call
|
|
||||||
* {@link parent::populateFromPostData()} to ensure that this method is
|
|
||||||
* called
|
|
||||||
*
|
|
||||||
* @access public
|
|
||||||
*
|
|
||||||
* @param array $data
|
|
||||||
*/
|
|
||||||
public function populateFromPostData($data) {
|
|
||||||
$this->Title = (isset($data['Title'])) ? $data['Title']: "";
|
|
||||||
$this->Default = (isset($data['Default'])) ? $data['Default'] : "";
|
|
||||||
$this->Sort = (isset($data['Sort'])) ? $data['Sort'] : null;
|
|
||||||
$this->Required = !empty($data['Required']) ? 1 : 0;
|
|
||||||
$this->Name = $this->class.$this->ID;
|
|
||||||
$this->CustomRules = "";
|
|
||||||
$this->CustomErrorMessage = (isset($data['CustomErrorMessage'])) ? $data['CustomErrorMessage'] : "";
|
|
||||||
$this->CustomSettings = "";
|
|
||||||
|
|
||||||
// custom settings
|
|
||||||
if(isset($data['CustomSettings'])) {
|
|
||||||
$this->setSettings($data['CustomSettings']);
|
|
||||||
}
|
|
||||||
|
|
||||||
// custom validation
|
|
||||||
if(isset($data['CustomRules'])) {
|
|
||||||
$rules = array();
|
|
||||||
|
|
||||||
foreach($data['CustomRules'] as $key => $value) {
|
|
||||||
|
|
||||||
if(is_array($value)) {
|
|
||||||
$fieldValue = (isset($value['Value'])) ? $value['Value'] : '';
|
|
||||||
|
|
||||||
if(isset($value['ConditionOption']) && $value['ConditionOption'] == "Blank" || $value['ConditionOption'] == "NotBlank") {
|
|
||||||
$fieldValue = "";
|
|
||||||
}
|
|
||||||
|
|
||||||
$rules[] = array(
|
|
||||||
'Display' => (isset($value['Display'])) ? $value['Display'] : "",
|
|
||||||
'ConditionField' => (isset($value['ConditionField'])) ? $value['ConditionField'] : "",
|
|
||||||
'ConditionOption' => (isset($value['ConditionOption'])) ? $value['ConditionOption'] : "",
|
|
||||||
'Value' => $fieldValue
|
|
||||||
);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
$this->CustomRules = serialize($rules);
|
|
||||||
}
|
|
||||||
|
|
||||||
$this->extend('onPopulateFromPostData', $data);
|
|
||||||
$this->write();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Implement custom field Configuration on this field. Includes such things as
|
|
||||||
* settings and options of a given editable form field
|
|
||||||
*
|
|
||||||
* @return FieldSet
|
|
||||||
*/
|
|
||||||
public function getFieldConfiguration() {
|
|
||||||
$extraClass = ($this->getSetting('ExtraClass')) ? $this->getSetting('ExtraClass') : '';
|
|
||||||
|
|
||||||
$mergeFieldName = new LiteralField('MergeFieldName', _t('EditableFormField.MERGEFIELDNAME',
|
|
||||||
'<div class="field">' .
|
|
||||||
'<label class="left" for="Fields-6-CustomSettings-RightTitle">Merge field</label>' .
|
|
||||||
'<div class="middleColumn">' .
|
|
||||||
'<p>$' . $this->Name . '</p>' .
|
|
||||||
'<em>Use this to display the field\'s value in email content.</em>' .
|
|
||||||
'</div>' .
|
|
||||||
'</div>'
|
|
||||||
));
|
|
||||||
|
|
||||||
if (is_array(self::$allowed_css) && !empty(self::$allowed_css)) {
|
|
||||||
foreach(self::$allowed_css as $k => $v) {
|
|
||||||
if (!is_array($v)) $cssList[$k]=$v;
|
|
||||||
elseif ($k == $this->ClassName()) $cssList = array_merge($cssList, $v);
|
|
||||||
}
|
|
||||||
|
|
||||||
$ec = new DropdownField(
|
|
||||||
$this->getSettingName('ExtraClass'),
|
|
||||||
_t('EditableFormField.EXTRACLASSA', 'Extra Styling/Layout'),
|
|
||||||
$cssList, $extraClass
|
|
||||||
);
|
|
||||||
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
$ec = new TextField(
|
|
||||||
$this->getSettingName('ExtraClass'),
|
|
||||||
_t('EditableFormField.EXTRACLASSB', 'Extra css Class - separate multiples with a space'),
|
|
||||||
$extraClass
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
$right = new TextField(
|
|
||||||
$this->getSettingName('RightTitle'),
|
|
||||||
_t('EditableFormField.RIGHTTITLE', 'Right Title'),
|
|
||||||
$this->getSetting('RightTitle')
|
|
||||||
);
|
|
||||||
|
|
||||||
$fields = FieldList::create(
|
|
||||||
$mergeFieldName,
|
|
||||||
$ec,
|
|
||||||
$right
|
|
||||||
);
|
|
||||||
$this->extend('updateFieldConfiguration', $fields);
|
|
||||||
|
|
||||||
return $fields;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Append custom validation fields to the default 'Validation'
|
* Append custom validation fields to the default 'Validation'
|
||||||
* section in the editable options view
|
* section in the editable options view
|
||||||
@ -533,4 +595,32 @@ class EditableFormField extends DataObject {
|
|||||||
|
|
||||||
return DBField::create_field('Varchar', $errorMessage);
|
return DBField::create_field('Varchar', $errorMessage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Validate the field taking into account its custom rules.
|
||||||
|
*
|
||||||
|
* @param Array $data
|
||||||
|
* @param UserForm $form
|
||||||
|
*
|
||||||
|
* @return boolean
|
||||||
|
*/
|
||||||
|
public function validateField($data, $form) {
|
||||||
|
if($this->Required && $this->CustomRules()->Count() == 0) {
|
||||||
|
$formField = $this->getFormField();
|
||||||
|
|
||||||
|
if(isset($data[$this->Name])) {
|
||||||
|
$formField->setValue($data[$this->Name]);
|
||||||
|
}
|
||||||
|
|
||||||
|
if(
|
||||||
|
!isset($data[$this->Name]) ||
|
||||||
|
!$data[$this->Name] ||
|
||||||
|
!$formField->validate($form->getValidator())
|
||||||
|
) {
|
||||||
|
$form->addErrorMessage($this->Name, $this->getErrorMessage(), 'bad');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
}
|
}
|
@ -11,7 +11,15 @@ class EditableFormHeading extends EditableFormField {
|
|||||||
|
|
||||||
private static $plural_name = 'Headings';
|
private static $plural_name = 'Headings';
|
||||||
|
|
||||||
public function getFieldConfiguration() {
|
/**
|
||||||
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function getCMSFields() {
|
||||||
|
$fields = parent::getCMSFields();
|
||||||
|
|
||||||
|
$fields->removeByName('Default');
|
||||||
|
$fields->removeByName('Validation');
|
||||||
|
|
||||||
$levels = array(
|
$levels = array(
|
||||||
'1' => '1',
|
'1' => '1',
|
||||||
'2' => '2',
|
'2' => '2',
|
||||||
@ -24,25 +32,21 @@ class EditableFormHeading extends EditableFormField {
|
|||||||
$level = ($this->getSetting('Level')) ? $this->getSetting('Level') : 3;
|
$level = ($this->getSetting('Level')) ? $this->getSetting('Level') : 3;
|
||||||
$label = _t('EditableFormHeading.LEVEL', 'Select Heading Level');
|
$label = _t('EditableFormHeading.LEVEL', 'Select Heading Level');
|
||||||
|
|
||||||
$options = parent::getFieldConfiguration();
|
$fields->addFieldsToTab('Root.Main', array(
|
||||||
|
DropdownField::create(
|
||||||
$options->push(
|
$this->getSettingName('Level'),
|
||||||
new DropdownField($this->getSettingName("Level"), $label, $levels, $level)
|
$label,
|
||||||
);
|
$levels,
|
||||||
|
$level
|
||||||
if($this->readonly) {
|
),
|
||||||
$extraFields = $options->makeReadonly();
|
CheckboxField::create(
|
||||||
}
|
|
||||||
|
|
||||||
$options->push(
|
|
||||||
new CheckboxField(
|
|
||||||
$this->getSettingName('HideFromReports'),
|
$this->getSettingName('HideFromReports'),
|
||||||
_t('EditableLiteralField.HIDEFROMREPORT', 'Hide from reports?'),
|
_t('EditableLiteralField.HIDEFROMREPORT', 'Hide from reports?'),
|
||||||
$this->getSetting('HideFromReports')
|
$this->getSetting('HideFromReports')
|
||||||
)
|
)
|
||||||
);
|
));
|
||||||
|
|
||||||
return $options;
|
return $fields;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getFormField() {
|
public function getFormField() {
|
@ -71,23 +71,30 @@ class EditableLiteralField extends EditableFormField {
|
|||||||
$this->setSetting('Content', $content);
|
$this->setSetting('Content', $content);
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getFieldConfiguration() {
|
/**
|
||||||
$textAreaField = new HTMLEditorField(
|
* @return FieldList
|
||||||
$this->getSettingName('Content'),
|
*/
|
||||||
"HTML",
|
public function getCMSFields() {
|
||||||
$this->getContent()
|
$fields = parent::getCMSFields();
|
||||||
);
|
|
||||||
$textAreaField->setRows(4);
|
|
||||||
$textAreaField->setColumns(20);
|
|
||||||
|
|
||||||
return new FieldList(
|
$fields->removeByName('Default');
|
||||||
$textAreaField,
|
$fields->removeByName('Validation');
|
||||||
new CheckboxField(
|
|
||||||
|
$fields->addFieldsToTab('Root.Main', array(
|
||||||
|
HTMLEditorField::create(
|
||||||
|
$this->getSettingName('Content'),
|
||||||
|
'HTML',
|
||||||
|
$this->getContent())
|
||||||
|
->setRows(4)
|
||||||
|
->setColumns(20),
|
||||||
|
CheckboxField::create(
|
||||||
$this->getSettingName('HideFromReports'),
|
$this->getSettingName('HideFromReports'),
|
||||||
_t('EditableLiteralField.HIDEFROMREPORT', 'Hide from reports?'),
|
_t('EditableLiteralField.HIDEFROMREPORT', 'Hide from reports?'),
|
||||||
$this->getSetting('HideFromReports')
|
$this->getSetting('HideFromReports')
|
||||||
)
|
)
|
||||||
);
|
));
|
||||||
|
|
||||||
|
return $fields;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getFormField() {
|
public function getFormField() {
|
@ -11,15 +11,28 @@ class EditableMemberListField extends EditableFormField {
|
|||||||
|
|
||||||
private static $plural_name = 'Member List Fields';
|
private static $plural_name = 'Member List Fields';
|
||||||
|
|
||||||
public function getFieldConfiguration() {
|
/**
|
||||||
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function getCMSFields() {
|
||||||
|
$fields = parent::getCMSFields();
|
||||||
|
|
||||||
|
$fields->removeByName('Default');
|
||||||
|
$fields->removeByName('Validation');
|
||||||
|
|
||||||
$groupID = ($this->getSetting('GroupID')) ? $this->getSetting('GroupID') : 0;
|
$groupID = ($this->getSetting('GroupID')) ? $this->getSetting('GroupID') : 0;
|
||||||
$groups = DataObject::get("Group");
|
$groups = DataObject::get('Group');
|
||||||
|
|
||||||
if($groups) $groups = $groups->map('ID', 'Title');
|
if($groups) {
|
||||||
|
$groups = $groups->map('ID', 'Title');
|
||||||
|
}
|
||||||
|
|
||||||
$fields = new FieldList(
|
$fields->addFieldToTab('Root.Main', DropdownField::create(
|
||||||
new DropdownField("Fields[$this->ID][CustomSettings][GroupID]", _t('EditableFormField.GROUP', 'Group'), $groups, $groupID)
|
"Fields[$this->ID][CustomSettings][GroupID]",
|
||||||
);
|
_t('EditableFormField.GROUP', 'Group'),
|
||||||
|
$groups,
|
||||||
|
$groupID
|
||||||
|
));
|
||||||
|
|
||||||
return $fields;
|
return $fields;
|
||||||
}
|
}
|
@ -19,6 +19,46 @@ class EditableMultipleOptionField extends EditableFormField {
|
|||||||
"Options" => "EditableOption"
|
"Options" => "EditableOption"
|
||||||
);
|
);
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function getCMSFields() {
|
||||||
|
$fields = parent::getCMSFields();
|
||||||
|
|
||||||
|
$optionsGrid = GridField::create(
|
||||||
|
'Options',
|
||||||
|
_t('EditableFormField.CUSTOMOPTIONS', 'Options'),
|
||||||
|
$this->Options()
|
||||||
|
);
|
||||||
|
|
||||||
|
$optionsConfig = GridFieldConfig::create()
|
||||||
|
->addComponents(
|
||||||
|
(new GridFieldEditableColumns())
|
||||||
|
->setDisplayFields(array(
|
||||||
|
'Title' => function($record, $column, $grid) {
|
||||||
|
return TextField::create($column);
|
||||||
|
},
|
||||||
|
'Default' => function($record, $column, $grid) {
|
||||||
|
return CheckboxField::create($column);
|
||||||
|
},
|
||||||
|
'ParentID' => function($record, $column, $grid) {
|
||||||
|
return HiddenField::create($column, '', $this->ID);
|
||||||
|
}
|
||||||
|
)),
|
||||||
|
new GridFieldButtonRow(),
|
||||||
|
new GridFieldToolbarHeader(),
|
||||||
|
new GridFieldAddNewInlineButton(),
|
||||||
|
new GridFieldDeleteAction(),
|
||||||
|
new GridState_Component()
|
||||||
|
);
|
||||||
|
|
||||||
|
$optionsGrid->setConfig($optionsConfig);
|
||||||
|
|
||||||
|
$fields->addFieldToTab('Root.Options', $optionsGrid);
|
||||||
|
|
||||||
|
return $fields;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Publishing Versioning support.
|
* Publishing Versioning support.
|
||||||
*
|
*
|
||||||
@ -100,29 +140,6 @@ class EditableMultipleOptionField extends EditableFormField {
|
|||||||
return $clonedNode;
|
return $clonedNode;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* On before saving this object we need to go through and keep an eye on
|
|
||||||
* all our option fields that are related to this field in the form
|
|
||||||
*
|
|
||||||
* @param ArrayData
|
|
||||||
*/
|
|
||||||
public function populateFromPostData($data) {
|
|
||||||
parent::populateFromPostData($data);
|
|
||||||
|
|
||||||
// get the current options
|
|
||||||
$fieldSet = $this->Options();
|
|
||||||
|
|
||||||
// go over all the current options and check if ID and Title still exists
|
|
||||||
foreach($fieldSet as $option) {
|
|
||||||
if(isset($data[$option->ID]) && isset($data[$option->ID]['Title']) && $data[$option->ID]['Title'] != "field-node-deleted") {
|
|
||||||
$option->populateFromPostData($data[$option->ID]);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
$option->delete();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Return whether or not this field has addable options such as a
|
* Return whether or not this field has addable options such as a
|
||||||
* {@link EditableDropdownField} or {@link EditableRadioField}
|
* {@link EditableDropdownField} or {@link EditableRadioField}
|
@ -23,6 +23,7 @@ class EditableNumericField extends EditableFormField {
|
|||||||
public function getFormField() {
|
public function getFormField() {
|
||||||
$field = new NumericField($this->Name, $this->Title);
|
$field = new NumericField($this->Name, $this->Title);
|
||||||
$field->addExtraClass('number');
|
$field->addExtraClass('number');
|
||||||
|
$field->setValue($this->Default);
|
||||||
|
|
||||||
if ($this->Required) {
|
if ($this->Required) {
|
||||||
// Required and numeric validation can conflict so add the
|
// Required and numeric validation can conflict so add the
|
@ -69,20 +69,6 @@ class EditableOption extends DataObject {
|
|||||||
return "Fields[{$this->ParentID}][{$this->ID}]";
|
return "Fields[{$this->ParentID}][{$this->ID}]";
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Populate this option from the form field
|
|
||||||
*
|
|
||||||
* @param Array Data
|
|
||||||
*/
|
|
||||||
public function populateFromPostData($data) {
|
|
||||||
$this->Title = (isset($data['Title'])) ? $data['Title'] : "";
|
|
||||||
$this->Default = (isset($data['Default'])) ? $data['Default'] : "";
|
|
||||||
$this->Sort = (isset($data['Sort'])) ? $data['Sort'] : 0;
|
|
||||||
|
|
||||||
$this->extend('onPopulateFromPostData', $data);
|
|
||||||
$this->write();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Make this option readonly
|
* Make this option readonly
|
||||||
*/
|
*/
|
@ -13,16 +13,34 @@ class EditableRadioField extends EditableMultipleOptionField {
|
|||||||
|
|
||||||
private static $plural_name = 'Radio fields';
|
private static $plural_name = 'Radio fields';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function getCMSFields() {
|
||||||
|
$fields = parent::getCMSFields();
|
||||||
|
|
||||||
|
$fields->removeByName('Default');
|
||||||
|
|
||||||
|
return $fields;
|
||||||
|
}
|
||||||
|
|
||||||
public function getFormField() {
|
public function getFormField() {
|
||||||
$optionSet = $this->Options();
|
$optionSet = $this->Options();
|
||||||
|
$defaultOptions = $optionSet->filter('Default', 1);
|
||||||
$options = array();
|
$options = array();
|
||||||
|
|
||||||
if($optionSet) {
|
if($optionSet) {
|
||||||
foreach( $optionSet as $option ) {
|
foreach($optionSet as $option) {
|
||||||
$options[$option->EscapedTitle] = $option->Title;
|
$options[$option->EscapedTitle] = $option->Title;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return new OptionsetField($this->Name, $this->Title, $options);
|
$field = OptionsetField::create($this->Name, $this->Title, $options);
|
||||||
|
|
||||||
|
if($defaultOptions->count()) {
|
||||||
|
$field->setValue($defaultOptions->First()->EscapedTitle);
|
||||||
|
}
|
||||||
|
|
||||||
|
return $field;
|
||||||
}
|
}
|
||||||
}
|
}
|
@ -13,24 +13,29 @@ class EditableTextField extends EditableFormField {
|
|||||||
|
|
||||||
private static $plural_name = 'Text Fields';
|
private static $plural_name = 'Text Fields';
|
||||||
|
|
||||||
public function getFieldConfiguration() {
|
/**
|
||||||
$fields = parent::getFieldConfiguration();
|
* @return FieldList
|
||||||
|
*/
|
||||||
|
public function getCMSFields() {
|
||||||
|
$fields = parent::getCMSFields();
|
||||||
|
|
||||||
$min = ($this->getSetting('MinLength')) ? $this->getSetting('MinLength') : '';
|
$min = ($this->getSetting('MinLength')) ? $this->getSetting('MinLength') : '';
|
||||||
$max = ($this->getSetting('MaxLength')) ? $this->getSetting('MaxLength') : '';
|
$max = ($this->getSetting('MaxLength')) ? $this->getSetting('MaxLength') : '';
|
||||||
|
|
||||||
$rows = ($this->getSetting('Rows')) ? $this->getSetting('Rows') : '1';
|
$rows = ($this->getSetting('Rows')) ? $this->getSetting('Rows') : '1';
|
||||||
|
|
||||||
$extraFields = new FieldList(
|
$fields->addFieldsToTab('Root.Main', array(
|
||||||
new FieldGroup(_t('EditableTextField.TEXTLENGTH', 'Text length'),
|
FieldGroup::create(
|
||||||
new NumericField($this->getSettingName('MinLength'), "", $min),
|
_t('EditableTextField.TEXTLENGTH', 'Text length'),
|
||||||
new NumericField($this->getSettingName('MaxLength'), " - ", $max)
|
NumericField::create($this->getSettingName('MinLength'), '', $min),
|
||||||
|
NumericField::create($this->getSettingName('MaxLength'), ' - ', $max)
|
||||||
),
|
),
|
||||||
new NumericField($this->getSettingName('Rows'), _t('EditableTextField.NUMBERROWS',
|
NumericField::create(
|
||||||
'Number of rows'), $rows)
|
'Rows',
|
||||||
);
|
_t('EditableTextField.NUMBERROWS', 'Number of rows'),
|
||||||
|
$rows
|
||||||
$fields->merge($extraFields);
|
)
|
||||||
|
));
|
||||||
|
|
||||||
return $fields;
|
return $fields;
|
||||||
}
|
}
|
||||||
@ -58,6 +63,8 @@ class EditableTextField extends EditableFormField {
|
|||||||
$field->setAttribute('data-msg-required', $errorMessage);
|
$field->setAttribute('data-msg-required', $errorMessage);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$field->setValue($this->Default);
|
||||||
|
|
||||||
return $field;
|
return $field;
|
||||||
}
|
}
|
||||||
|
|
@ -16,21 +16,20 @@ class UserDefinedForm extends Page {
|
|||||||
*/
|
*/
|
||||||
private static $required_identifier = null;
|
private static $required_identifier = null;
|
||||||
|
|
||||||
/**
|
|
||||||
* Prevent translatable module from attepmting to translate FieldEditor
|
|
||||||
*
|
|
||||||
* @var array
|
|
||||||
* @config
|
|
||||||
*/
|
|
||||||
private static $translate_excluded_fields = array(
|
|
||||||
'Fields'
|
|
||||||
);
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @var string
|
* @var string
|
||||||
*/
|
*/
|
||||||
private static $email_template_directory = 'userforms/templates/email/';
|
private static $email_template_directory = 'userforms/templates/email/';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Built in extensions required by this page
|
||||||
|
* @config
|
||||||
|
* @var array
|
||||||
|
*/
|
||||||
|
private static $extensions = array(
|
||||||
|
'UserFormFieldEditorExtension'
|
||||||
|
);
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @var array Fields on the user defined form page.
|
* @var array Fields on the user defined form page.
|
||||||
*/
|
*/
|
||||||
@ -60,7 +59,6 @@ class UserDefinedForm extends Page {
|
|||||||
* @var array
|
* @var array
|
||||||
*/
|
*/
|
||||||
private static $has_many = array(
|
private static $has_many = array(
|
||||||
"Fields" => "EditableFormField",
|
|
||||||
"Submissions" => "SubmittedForm",
|
"Submissions" => "SubmittedForm",
|
||||||
"EmailRecipients" => "UserDefinedForm_EmailRecipient"
|
"EmailRecipients" => "UserDefinedForm_EmailRecipient"
|
||||||
);
|
);
|
||||||
@ -98,14 +96,10 @@ class UserDefinedForm extends Page {
|
|||||||
$this->beforeUpdateCMSFields(function($fields) use ($self) {
|
$this->beforeUpdateCMSFields(function($fields) use ($self) {
|
||||||
|
|
||||||
// define tabs
|
// define tabs
|
||||||
$fields->findOrMakeTab('Root.FormContent', _t('UserDefinedForm.FORM', 'Form'));
|
|
||||||
$fields->findOrMakeTab('Root.FormOptions', _t('UserDefinedForm.CONFIGURATION', 'Configuration'));
|
$fields->findOrMakeTab('Root.FormOptions', _t('UserDefinedForm.CONFIGURATION', 'Configuration'));
|
||||||
$fields->findOrMakeTab('Root.Recipients', _t('UserDefinedForm.RECIPIENTS', 'Recipients'));
|
$fields->findOrMakeTab('Root.Recipients', _t('UserDefinedForm.RECIPIENTS', 'Recipients'));
|
||||||
$fields->findOrMakeTab('Root.Submissions', _t('UserDefinedForm.SUBMISSIONS', 'Submissions'));
|
$fields->findOrMakeTab('Root.Submissions', _t('UserDefinedForm.SUBMISSIONS', 'Submissions'));
|
||||||
|
|
||||||
// field editor
|
|
||||||
$fields->addFieldToTab('Root.FormContent', new FieldEditor('Fields', 'Fields', '', $self ));
|
|
||||||
|
|
||||||
// text to show on complete
|
// text to show on complete
|
||||||
$onCompleteFieldSet = new CompositeField(
|
$onCompleteFieldSet = new CompositeField(
|
||||||
$label = new LabelField('OnCompleteMessageLabel',_t('UserDefinedForm.ONCOMPLETELABEL', 'Show on completion')),
|
$label = new LabelField('OnCompleteMessageLabel',_t('UserDefinedForm.ONCOMPLETELABEL', 'Show on completion')),
|
||||||
@ -210,125 +204,6 @@ SQL;
|
|||||||
return $fields;
|
return $fields;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* When publishing copy the editable form fields to the live database
|
|
||||||
* Not going to version emails and submissions as they are likely to
|
|
||||||
* persist over multiple versions.
|
|
||||||
*
|
|
||||||
* @return void
|
|
||||||
*/
|
|
||||||
public function doPublish() {
|
|
||||||
$parentID = (!empty($this->ID)) ? $this->ID : 0;
|
|
||||||
// remove fields on the live table which could have been orphaned.
|
|
||||||
$live = Versioned::get_by_stage("EditableFormField", "Live", "\"EditableFormField\".\"ParentID\" = $parentID");
|
|
||||||
|
|
||||||
if($live) {
|
|
||||||
foreach($live as $field) {
|
|
||||||
$field->doDeleteFromStage('Live');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// publish the draft pages
|
|
||||||
if($this->Fields()) {
|
|
||||||
foreach($this->Fields() as $field) {
|
|
||||||
$field->doPublish('Stage', 'Live');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
parent::doPublish();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* When un-publishing the page it has to remove all the fields from the
|
|
||||||
* live database table.
|
|
||||||
*
|
|
||||||
* @return void
|
|
||||||
*/
|
|
||||||
public function doUnpublish() {
|
|
||||||
if($this->Fields()) {
|
|
||||||
foreach($this->Fields() as $field) {
|
|
||||||
$field->doDeleteFromStage('Live');
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
parent::doUnpublish();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Roll back a form to a previous version.
|
|
||||||
*
|
|
||||||
* @param string|int Version to roll back to
|
|
||||||
*/
|
|
||||||
public function doRollbackTo($version) {
|
|
||||||
parent::doRollbackTo($version);
|
|
||||||
|
|
||||||
/*
|
|
||||||
Not implemented yet
|
|
||||||
|
|
||||||
// get the older version
|
|
||||||
$reverted = Versioned::get_version($this->ClassName, $this->ID, $version);
|
|
||||||
|
|
||||||
if($reverted) {
|
|
||||||
|
|
||||||
// using the lastedited date of the reverted object we can work out which
|
|
||||||
// form fields to revert back to
|
|
||||||
if($this->Fields()) {
|
|
||||||
foreach($this->Fields() as $field) {
|
|
||||||
// query to see when the version of the page was pumped
|
|
||||||
$editedDate = DB::query("
|
|
||||||
SELECT LastEdited
|
|
||||||
FROM \"SiteTree_versions\"
|
|
||||||
WHERE \"RecordID\" = '$this->ID' AND \"Version\" = $version
|
|
||||||
")->value();
|
|
||||||
|
|
||||||
|
|
||||||
// find a the latest version which has been edited
|
|
||||||
$versionToGet = DB::query("
|
|
||||||
SELECT *
|
|
||||||
FROM \"EditableFormField_versions\"
|
|
||||||
WHERE \"RecordID\" = '$field->ID' AND \"LastEdited\" <= '$editedDate'
|
|
||||||
ORDER BY Version DESC
|
|
||||||
LIMIT 1
|
|
||||||
")->record();
|
|
||||||
|
|
||||||
if($versionToGet) {
|
|
||||||
Debug::show('publishing field'. $field->Name);
|
|
||||||
Debug::show($versionToGet);
|
|
||||||
$field->publish($versionToGet, "Stage", true);
|
|
||||||
$field->writeWithoutVersion();
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
Debug::show('deleting field'. $field->Name);
|
|
||||||
$this->Fields()->remove($field);
|
|
||||||
|
|
||||||
$field->delete();
|
|
||||||
$field->destroy();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// @todo Emails
|
|
||||||
}
|
|
||||||
*/
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Revert the draft site to the current live site
|
|
||||||
*
|
|
||||||
* @return void
|
|
||||||
*/
|
|
||||||
public function doRevertToLive() {
|
|
||||||
if($this->Fields()) {
|
|
||||||
foreach($this->Fields() as $field) {
|
|
||||||
$field->publish("Live", "Stage", false);
|
|
||||||
$field->writeWithoutVersion();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
parent::doRevertToLive();
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Allow overriding the EmailRecipients on a {@link DataExtension}
|
* Allow overriding the EmailRecipients on a {@link DataExtension}
|
||||||
* so you can customise who receives an email.
|
* so you can customise who receives an email.
|
||||||
@ -350,67 +225,6 @@ SQL;
|
|||||||
return $recipients;
|
return $recipients;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Store new and old ids of duplicated fields.
|
|
||||||
* This method also serves as a hook for descendant classes.
|
|
||||||
*/
|
|
||||||
protected function afterDuplicateField($page, $fromField, $toField) {
|
|
||||||
$this->fieldsFromTo[$fromField->ClassName . $fromField->ID] = $toField->ClassName . $toField->ID;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Duplicate this UserDefinedForm page, and its form fields.
|
|
||||||
* Submissions, on the other hand, won't be duplicated.
|
|
||||||
*
|
|
||||||
* @return Page
|
|
||||||
*/
|
|
||||||
public function duplicate($doWrite = true) {
|
|
||||||
$page = parent::duplicate($doWrite);
|
|
||||||
|
|
||||||
// the form fields
|
|
||||||
if($this->Fields()) {
|
|
||||||
foreach($this->Fields() as $field) {
|
|
||||||
$newField = $field->duplicate();
|
|
||||||
$newField->ParentID = $page->ID;
|
|
||||||
$newField->write();
|
|
||||||
$this->afterDuplicateField($page, $field, $newField);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// the emails
|
|
||||||
if($this->EmailRecipients()) {
|
|
||||||
foreach($this->EmailRecipients() as $email) {
|
|
||||||
$newEmail = $email->duplicate();
|
|
||||||
$newEmail->FormID = $page->ID;
|
|
||||||
$newEmail->write();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// Rewrite CustomRules
|
|
||||||
if($page->Fields()) {
|
|
||||||
foreach($page->Fields() as $field) {
|
|
||||||
// Rewrite name to make the CustomRules-rewrite below work.
|
|
||||||
$field->Name = $field->ClassName . $field->ID;
|
|
||||||
$rules = unserialize($field->CustomRules);
|
|
||||||
|
|
||||||
if (count($rules) && isset($rules[0]['ConditionField'])) {
|
|
||||||
$from = $rules[0]['ConditionField'];
|
|
||||||
|
|
||||||
if (array_key_exists($from, $this->fieldsFromTo)) {
|
|
||||||
$rules[0]['ConditionField'] = $this->fieldsFromTo[$from];
|
|
||||||
$field->CustomRules = serialize($rules);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
$field->Write();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return $page;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Custom options for the form. You can extend the built in options by
|
* Custom options for the form. You can extend the built in options by
|
||||||
* using {@link updateFormOptions()}
|
* using {@link updateFormOptions()}
|
||||||
@ -437,36 +251,6 @@ SQL;
|
|||||||
return $options;
|
return $options;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Return if this form has been modified on the stage site and not published.
|
|
||||||
* this is used on the workflow module and for a couple highlighting things
|
|
||||||
*
|
|
||||||
* @return boolean
|
|
||||||
*/
|
|
||||||
public function getIsModifiedOnStage() {
|
|
||||||
// new unsaved pages could be never be published
|
|
||||||
if($this->isNew()) {
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
$stageVersion = Versioned::get_versionnumber_by_stage('UserDefinedForm', 'Stage', $this->ID);
|
|
||||||
$liveVersion = Versioned::get_versionnumber_by_stage('UserDefinedForm', 'Live', $this->ID);
|
|
||||||
|
|
||||||
$isModified = ($stageVersion && $stageVersion != $liveVersion);
|
|
||||||
|
|
||||||
if(!$isModified) {
|
|
||||||
if($this->Fields()) {
|
|
||||||
foreach($this->Fields() as $field) {
|
|
||||||
if($field->getIsModifiedOnStage()) {
|
|
||||||
$isModified = true;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return $isModified;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the HTML id of the error container displayed above the form.
|
* Get the HTML id of the error container displayed above the form.
|
||||||
*
|
*
|
||||||
@ -552,141 +336,23 @@ class UserDefinedForm_Controller extends Page_Controller {
|
|||||||
* Get the form for the page. Form can be modified by calling {@link updateForm()}
|
* Get the form for the page. Form can be modified by calling {@link updateForm()}
|
||||||
* on a UserDefinedForm extension.
|
* on a UserDefinedForm extension.
|
||||||
*
|
*
|
||||||
* @return Form|false
|
* @return Forms
|
||||||
*/
|
*/
|
||||||
public function Form() {
|
public function Form() {
|
||||||
$fields = $this->getFormFields();
|
$form = UserForm::create($this);
|
||||||
if(!$fields || !$fields->exists()) return false;
|
|
||||||
|
|
||||||
$actions = $this->getFormActions();
|
|
||||||
|
|
||||||
// get the required fields including the validation
|
|
||||||
$required = $this->getRequiredFields();
|
|
||||||
|
|
||||||
// generate the conditional logic
|
|
||||||
$this->generateConditionalJavascript();
|
$this->generateConditionalJavascript();
|
||||||
|
|
||||||
$form = new Form($this, "Form", $fields, $actions, $required);
|
|
||||||
$form->setRedirectToFormOnValidationError(true);
|
|
||||||
|
|
||||||
$data = Session::get("FormInfo.{$form->FormName()}.data");
|
|
||||||
|
|
||||||
if(is_array($data)) $form->loadDataFrom($data);
|
|
||||||
|
|
||||||
$this->extend('updateForm', $form);
|
|
||||||
|
|
||||||
if($this->DisableCsrfSecurityToken) {
|
|
||||||
$form->disableSecurityToken();
|
|
||||||
}
|
|
||||||
|
|
||||||
$this->generateValidationJavascript($form);
|
$this->generateValidationJavascript($form);
|
||||||
|
|
||||||
return $form;
|
return $form;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Get the form fields for the form on this page. Can modify this FieldSet
|
|
||||||
* by using {@link updateFormFields()} on an {@link Extension} subclass which
|
|
||||||
* is applied to this controller.
|
|
||||||
*
|
|
||||||
* @return FieldList
|
|
||||||
*/
|
|
||||||
public function getFormFields() {
|
|
||||||
$fields = new FieldList();
|
|
||||||
|
|
||||||
$editableFields = $this->Fields();
|
|
||||||
if($editableFields) foreach($editableFields as $editableField) {
|
|
||||||
// get the raw form field from the editable version
|
|
||||||
$field = $editableField->getFormField();
|
|
||||||
if(!$field) break;
|
|
||||||
|
|
||||||
// set the error / formatting messages
|
|
||||||
$field->setCustomValidationMessage($editableField->getErrorMessage());
|
|
||||||
|
|
||||||
// set the right title on this field
|
|
||||||
if($right = $editableField->getSetting('RightTitle')) {
|
|
||||||
// Since this field expects raw html, safely escape the user data prior
|
|
||||||
$field->setRightTitle(Convert::raw2xml($right));
|
|
||||||
}
|
|
||||||
|
|
||||||
// if this field is required add some
|
|
||||||
if($editableField->Required) {
|
|
||||||
$field->addExtraClass('requiredField');
|
|
||||||
|
|
||||||
if($identifier = UserDefinedForm::config()->required_identifier) {
|
|
||||||
|
|
||||||
$title = $field->Title() ." <span class='required-identifier'>". $identifier . "</span>";
|
|
||||||
$field->setTitle($title);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// if this field has an extra class
|
|
||||||
if($extraClass = $editableField->getSetting('ExtraClass')) {
|
|
||||||
$field->addExtraClass(Convert::raw2att($extraClass));
|
|
||||||
}
|
|
||||||
|
|
||||||
// set the values passed by the url to the field
|
|
||||||
$request = $this->getRequest();
|
|
||||||
if($value = $request->getVar($field->getName())) {
|
|
||||||
$field->setValue($value);
|
|
||||||
}
|
|
||||||
|
|
||||||
$fields->push($field);
|
|
||||||
}
|
|
||||||
$this->extend('updateFormFields', $fields);
|
|
||||||
|
|
||||||
return $fields;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Generate the form actions for the UserDefinedForm. You
|
|
||||||
* can manipulate these by using {@link updateFormActions()} on
|
|
||||||
* a decorator.
|
|
||||||
*
|
|
||||||
* @todo Make form actions editable via their own field editor.
|
|
||||||
*
|
|
||||||
* @return FieldList
|
|
||||||
*/
|
|
||||||
public function getFormActions() {
|
|
||||||
$submitText = ($this->SubmitButtonText) ? $this->SubmitButtonText : _t('UserDefinedForm.SUBMITBUTTON', 'Submit');
|
|
||||||
$clearText = ($this->ClearButtonText) ? $this->ClearButtonText : _t('UserDefinedForm.CLEARBUTTON', 'Clear');
|
|
||||||
|
|
||||||
$actions = new FieldList(
|
|
||||||
new FormAction("process", $submitText)
|
|
||||||
);
|
|
||||||
|
|
||||||
if($this->ShowClearButton) {
|
|
||||||
$actions->push(new ResetFormAction("clearForm", $clearText));
|
|
||||||
}
|
|
||||||
|
|
||||||
$this->extend('updateFormActions', $actions);
|
|
||||||
|
|
||||||
return $actions;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Get the required form fields for this form.
|
|
||||||
*
|
|
||||||
* @return RequiredFields
|
|
||||||
*/
|
|
||||||
public function getRequiredFields() {
|
|
||||||
// Generate required field validator
|
|
||||||
$requiredNames = $this
|
|
||||||
->Fields()
|
|
||||||
->filter('Required', true)
|
|
||||||
->column('Name');
|
|
||||||
$required = new RequiredFields($requiredNames);
|
|
||||||
|
|
||||||
$this->extend('updateRequiredFields', $required);
|
|
||||||
|
|
||||||
return $required;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Build jQuery validation script and require as a custom script
|
* Build jQuery validation script and require as a custom script
|
||||||
*
|
*
|
||||||
* @param Form $form
|
* @param UserForm $form
|
||||||
*/
|
*/
|
||||||
public function generateValidationJavascript($form) {
|
public function generateValidationJavascript(UserForm $form) {
|
||||||
// set the custom script for this form
|
// set the custom script for this form
|
||||||
Requirements::customScript(
|
Requirements::customScript(
|
||||||
$this
|
$this
|
||||||
@ -713,7 +379,7 @@ class UserDefinedForm_Controller extends Page_Controller {
|
|||||||
$fieldId = $field->Name;
|
$fieldId = $field->Name;
|
||||||
|
|
||||||
if($field->ClassName == 'EditableFormHeading') {
|
if($field->ClassName == 'EditableFormHeading') {
|
||||||
$fieldId = 'Form_Form_'.$field->Name;
|
$fieldId = 'UserForm_Form_' . $field->Name;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Is this Field Show by Default
|
// Is this Field Show by Default
|
||||||
@ -722,37 +388,30 @@ class UserDefinedForm_Controller extends Page_Controller {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Check for field dependencies / default
|
// Check for field dependencies / default
|
||||||
if($field->Dependencies()) {
|
foreach($field->CustomRules() as $rule) {
|
||||||
foreach($field->Dependencies() as $dependency) {
|
|
||||||
if(is_array($dependency) && isset($dependency['ConditionField']) && $dependency['ConditionField'] != "") {
|
|
||||||
// get the field which is effected
|
|
||||||
$formName = Convert::raw2sql($dependency['ConditionField']);
|
|
||||||
$formFieldWatch = DataObject::get_one("EditableFormField", "\"Name\" = '$formName'");
|
|
||||||
|
|
||||||
if(!$formFieldWatch) break;
|
// Get the field which is effected
|
||||||
|
$formFieldWatch = EditableFormField::get()->byId($rule->ConditionFieldID);
|
||||||
|
|
||||||
|
if($formFieldWatch->RecordClassName == 'EditableDropdown') {
|
||||||
// watch out for multiselect options - radios and check boxes
|
// watch out for multiselect options - radios and check boxes
|
||||||
if(is_a($formFieldWatch, 'EditableDropdown')) {
|
$fieldToWatch = "$(\"select[name='" . $formFieldWatch->Name . "']\")";
|
||||||
$fieldToWatch = "$(\"select[name='".$dependency['ConditionField']."']\")";
|
|
||||||
$fieldToWatchOnLoad = $fieldToWatch;
|
$fieldToWatchOnLoad = $fieldToWatch;
|
||||||
}
|
} else if($formFieldWatch->RecordClassName == 'EditableCheckboxGroupField') {
|
||||||
// watch out for checkboxs as the inputs don't have values but are 'checked
|
// watch out for checkboxs as the inputs don't have values but are 'checked
|
||||||
else if(is_a($formFieldWatch, 'EditableCheckboxGroupField')) {
|
$fieldToWatch = "$(\"input[name='" . $formFieldWatch->Name . "[" . $rule->FieldValue . "]']\")";
|
||||||
$fieldToWatch = "$(\"input[name='".$dependency['ConditionField']."[".$dependency['Value']."]']\")";
|
|
||||||
$fieldToWatchOnLoad = $fieldToWatch;
|
$fieldToWatchOnLoad = $fieldToWatch;
|
||||||
}
|
} else if($formFieldWatch->RecordClassName == 'EditableRadioField') {
|
||||||
else if(is_a($formFieldWatch, 'EditableRadioField')) {
|
$fieldToWatch = "$(\"input[name='" . $formFieldWatch->Name . "']\")";
|
||||||
$fieldToWatch = "$(\"input[name='".$dependency['ConditionField']."']\")";
|
|
||||||
// We only want to trigger on load once for the radio group - hence we focus on the first option only.
|
// We only want to trigger on load once for the radio group - hence we focus on the first option only.
|
||||||
$fieldToWatchOnLoad = "$(\"input[name='".$dependency['ConditionField']."']:first\")";
|
$fieldToWatchOnLoad = "$(\"input[name='" . $formFieldWatch->Name . "']:first\")";
|
||||||
}
|
} else {
|
||||||
else {
|
$fieldToWatch = "$(\"input[name='" . $formFieldWatch->Name . "']\")";
|
||||||
$fieldToWatch = "$(\"input[name='".$dependency['ConditionField']."']\")";
|
|
||||||
$fieldToWatchOnLoad = $fieldToWatch;
|
$fieldToWatchOnLoad = $fieldToWatch;
|
||||||
}
|
}
|
||||||
|
|
||||||
// show or hide?
|
// show or hide?
|
||||||
$view = (isset($dependency['Display']) && $dependency['Display'] == "Hide") ? "hide" : "show";
|
$view = ($rule->Display == 'Hide') ? 'hide' : 'show';
|
||||||
$opposite = ($view == "show") ? "hide" : "show";
|
$opposite = ($view == "show") ? "hide" : "show";
|
||||||
|
|
||||||
// what action do we need to keep track of. Something nicer here maybe?
|
// what action do we need to keep track of. Something nicer here maybe?
|
||||||
@ -770,16 +429,12 @@ class UserDefinedForm_Controller extends Page_Controller {
|
|||||||
if(in_array($formFieldWatch->ClassName, array('EditableCheckboxGroupField', 'EditableCheckbox'))) {
|
if(in_array($formFieldWatch->ClassName, array('EditableCheckboxGroupField', 'EditableCheckbox'))) {
|
||||||
$action = "click";
|
$action = "click";
|
||||||
$checkboxField = true;
|
$checkboxField = true;
|
||||||
}
|
} else if ($formFieldWatch->ClassName == "EditableRadioField") {
|
||||||
else if ($formFieldWatch->ClassName == "EditableRadioField") {
|
|
||||||
$radioField = true;
|
$radioField = true;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Escape the values.
|
|
||||||
$dependency['Value'] = str_replace('"', '\"', $dependency['Value']);
|
|
||||||
|
|
||||||
// and what should we evaluate
|
// and what should we evaluate
|
||||||
switch($dependency['ConditionOption']) {
|
switch($rule->ConditionOption) {
|
||||||
case 'IsNotBlank':
|
case 'IsNotBlank':
|
||||||
$expression = ($checkboxField || $radioField) ? '$(this).prop("checked")' :'$(this).val() != ""';
|
$expression = ($checkboxField || $radioField) ? '$(this).prop("checked")' :'$(this).val() != ""';
|
||||||
|
|
||||||
@ -793,26 +448,26 @@ class UserDefinedForm_Controller extends Page_Controller {
|
|||||||
$expression = '$(this).prop("checked")';
|
$expression = '$(this).prop("checked")';
|
||||||
} else if ($radioField) {
|
} else if ($radioField) {
|
||||||
// We cannot simply get the value of the radio group, we need to find the checked option first.
|
// We cannot simply get the value of the radio group, we need to find the checked option first.
|
||||||
$expression = '$(this).parents(".field, .control-group").find("input:checked").val()=="'. $dependency['Value'] .'"';
|
$expression = '$(this).parents(".field, .control-group").find("input:checked").val()=="'. $rule->FieldValue .'"';
|
||||||
} else {
|
} else {
|
||||||
$expression = '$(this).val() == "'. $dependency['Value'] .'"';
|
$expression = '$(this).val() == "'. $rule->FieldValue .'"';
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 'ValueLessThan':
|
case 'ValueLessThan':
|
||||||
$expression = '$(this).val() < parseFloat("'. $dependency['Value'] .'")';
|
$expression = '$(this).val() < parseFloat("'. $rule->FieldValue .'")';
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 'ValueLessThanEqual':
|
case 'ValueLessThanEqual':
|
||||||
$expression = '$(this).val() <= parseFloat("'. $dependency['Value'] .'")';
|
$expression = '$(this).val() <= parseFloat("'. $rule->FieldValue .'")';
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 'ValueGreaterThan':
|
case 'ValueGreaterThan':
|
||||||
$expression = '$(this).val() > parseFloat("'. $dependency['Value'] .'")';
|
$expression = '$(this).val() > parseFloat("'. $rule->FieldValue .'")';
|
||||||
|
|
||||||
break;
|
break;
|
||||||
case 'ValueGreaterThanEqual':
|
case 'ValueGreaterThanEqual':
|
||||||
$expression = '$(this).val() >= parseFloat("'. $dependency['Value'] .'")';
|
$expression = '$(this).val() >= parseFloat("'. $rule->FieldValue .'")';
|
||||||
|
|
||||||
break;
|
break;
|
||||||
default: // ==HasNotValue
|
default: // ==HasNotValue
|
||||||
@ -820,9 +475,9 @@ class UserDefinedForm_Controller extends Page_Controller {
|
|||||||
$expression = '!$(this).prop("checked")';
|
$expression = '!$(this).prop("checked")';
|
||||||
} else if ($radioField) {
|
} else if ($radioField) {
|
||||||
// We cannot simply get the value of the radio group, we need to find the checked option first.
|
// We cannot simply get the value of the radio group, we need to find the checked option first.
|
||||||
$expression = '$(this).parents(".field, .control-group").find("input:checked").val()!="'. $dependency['Value'] .'"';
|
$expression = '$(this).parents(".field, .control-group").find("input:checked").val()!="'. $rule->FieldValue .'"';
|
||||||
} else {
|
} else {
|
||||||
$expression = '$(this).val() != "'. $dependency['Value'] .'"';
|
$expression = '$(this).val() != "'. $rule->FieldValue .'"';
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
@ -841,9 +496,6 @@ class UserDefinedForm_Controller extends Page_Controller {
|
|||||||
);
|
);
|
||||||
|
|
||||||
$watchLoad[$fieldToWatchOnLoad] = true;
|
$watchLoad[$fieldToWatchOnLoad] = true;
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -903,26 +555,6 @@ JS
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* Convert a PHP array to a JSON string. We cannot use {@link Convert::array2json}
|
|
||||||
* as it escapes our values with "" which appears to break the validate plugin
|
|
||||||
*
|
|
||||||
* @param Array array to convert
|
|
||||||
* @return JSON
|
|
||||||
*/
|
|
||||||
public function array2json($array) {
|
|
||||||
foreach($array as $key => $value) {
|
|
||||||
if(is_array( $value )) {
|
|
||||||
$result[] = "$key:" . $this->array2json($value);
|
|
||||||
} else {
|
|
||||||
$value = ( is_bool($value) || is_numeric($value) ) ? $value : "\"$value\"";
|
|
||||||
$result[] = "$key:$value";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
return (isset($result)) ? "{\n".implode( ', ', $result ) ."\n}\n": '{}';
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Process the form that is submitted through the site
|
* Process the form that is submitted through the site
|
||||||
*
|
*
|
||||||
@ -1125,7 +757,6 @@ JS
|
|||||||
|
|
||||||
$referrer = (isset($data['Referrer'])) ? '?referrer=' . urlencode($data['Referrer']) : "";
|
$referrer = (isset($data['Referrer'])) ? '?referrer=' . urlencode($data['Referrer']) : "";
|
||||||
|
|
||||||
|
|
||||||
// set a session variable from the security ID to stop people accessing
|
// set a session variable from the security ID to stop people accessing
|
||||||
// the finished method directly.
|
// the finished method directly.
|
||||||
if(!$this->DisableAuthenicatedFinishAction) {
|
if(!$this->DisableAuthenicatedFinishAction) {
|
168
code/tasks/UserFormsUpgradeTask.php
Normal file
168
code/tasks/UserFormsUpgradeTask.php
Normal file
@ -0,0 +1,168 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Assists with upgrade of userforms to 3.0
|
||||||
|
*
|
||||||
|
* @author dmooyman
|
||||||
|
*/
|
||||||
|
class UserFormsUpgradeTask extends BuildTask {
|
||||||
|
|
||||||
|
protected $title = "UserForms 3.0 Migration Tool";
|
||||||
|
|
||||||
|
protected $description = "Upgrade tool for sites upgrading to userforms 3.0";
|
||||||
|
|
||||||
|
public function run($request) {
|
||||||
|
$this->log("Upgrading userforms module");
|
||||||
|
$this->upgradeRules();
|
||||||
|
$this->log("Done");
|
||||||
|
}
|
||||||
|
|
||||||
|
protected function log($message) {
|
||||||
|
if(Director::is_cli()) {
|
||||||
|
echo "{$message}\n";
|
||||||
|
} else {
|
||||||
|
echo "{$message}<br />";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
protected function upgradeRules() {
|
||||||
|
$this->log("Upgrading formfield rules");
|
||||||
|
|
||||||
|
// Upgrade rules from EditableFormField.CustomRules into dataobjects
|
||||||
|
$fields = DB::fieldList('EditableFormField');
|
||||||
|
if(!isset($fields['CustomRules'])) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// List of rules that have been created in all stages
|
||||||
|
$fields = Versioned::get_including_deleted('EditableFormField');
|
||||||
|
foreach($fields as $field) {
|
||||||
|
$this->upgradeFieldRules($field);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Migrate a versioned field in all stages
|
||||||
|
*
|
||||||
|
* @param EditableFormField $field
|
||||||
|
*/
|
||||||
|
protected function upgradeFieldRules(EditableFormField $field) {
|
||||||
|
$this->log("Upgrading formfield ID = ".$field->ID);
|
||||||
|
|
||||||
|
// Check versions this field exists on
|
||||||
|
$filter = sprintf('"EditableFormField"."ID" = \'%d\'', $field->ID);
|
||||||
|
$stageField = Versioned::get_one_by_stage('EditableFormField', 'Stage', $filter);
|
||||||
|
$liveField = Versioned::get_one_by_stage('EditableFormField', 'Live', $filter);
|
||||||
|
|
||||||
|
if($stageField) {
|
||||||
|
$this->upgradeFieldRulesInStage($stageField, 'Stage');
|
||||||
|
}
|
||||||
|
|
||||||
|
if($liveField) {
|
||||||
|
$this->upgradeFieldRulesInStage($liveField, 'Live');
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Migrate a versioned field in a single stage
|
||||||
|
*
|
||||||
|
* @param EditableFormField $field
|
||||||
|
* @param stage $stage
|
||||||
|
*/
|
||||||
|
protected function upgradeFieldRulesInStage(EditableFormField $field, $stage) {
|
||||||
|
Versioned::reading_stage($stage);
|
||||||
|
|
||||||
|
// Skip rules with empty data
|
||||||
|
$rulesData = $this->getRuleData($field->ID);
|
||||||
|
if(empty($rulesData)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Skip migrated records
|
||||||
|
if($field->CustomRules()->count()) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Check value of this condition
|
||||||
|
foreach($rulesData as $ruleDataItem) {
|
||||||
|
if(empty($ruleDataItem['ConditionOption']) || empty($ruleDataItem['Display'])) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
// Get data for this rule
|
||||||
|
$conditionOption = $ruleDataItem['ConditionOption'];
|
||||||
|
$display = $ruleDataItem['Display'];
|
||||||
|
$conditionFieldName = empty($ruleDataItem['ConditionField']) ? null : $ruleDataItem['ConditionField'];
|
||||||
|
$value = isset($ruleDataItem['Value'])
|
||||||
|
? $ruleDataItem['Value']
|
||||||
|
: null;
|
||||||
|
|
||||||
|
// Create rule
|
||||||
|
$rule = $this->findOrCreateRule($field, $stage, $conditionOption, $display, $conditionFieldName, $value);
|
||||||
|
$this->log("Upgrading rule ID = " . $rule->ID);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create or find an existing field with the matched specification
|
||||||
|
*
|
||||||
|
* @param EditableFormField $field
|
||||||
|
* @param string $stage
|
||||||
|
* @param string $conditionOption
|
||||||
|
* @param string $display
|
||||||
|
* @param string $conditionFieldName
|
||||||
|
* @param string $value
|
||||||
|
* @return EditableCustomRule
|
||||||
|
*/
|
||||||
|
protected function findOrCreateRule(EditableFormField $field, $stage, $conditionOption, $display, $conditionFieldName, $value) {
|
||||||
|
// Get id of field
|
||||||
|
$conditionField = $conditionFieldName
|
||||||
|
? EditableFormField::get()->filter('Name', $conditionFieldName)->first()
|
||||||
|
: null;
|
||||||
|
|
||||||
|
// If live, search stage record for matching one
|
||||||
|
if($stage === 'Live') {
|
||||||
|
$list = Versioned::get_by_stage('EditableCustomRule', 'Stage')
|
||||||
|
->filter(array(
|
||||||
|
'ParentID' => $field->ID,
|
||||||
|
'ConditionFieldID' => $conditionField ? $conditionField->ID : 0,
|
||||||
|
'Display' => $display,
|
||||||
|
'ConditionOption' => $conditionOption
|
||||||
|
));
|
||||||
|
if($value) {
|
||||||
|
$list = $list->filter('FieldValue', $value);
|
||||||
|
} else {
|
||||||
|
$list = $list->where('"FieldValue" IS NULL OR "FieldValue" = \'\'');
|
||||||
|
}
|
||||||
|
$rule = $list->first();
|
||||||
|
if($rule) {
|
||||||
|
$rule->write();
|
||||||
|
$rule->publish("Stage", "Live");
|
||||||
|
return $rule;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
// If none found, or in stage, create new record
|
||||||
|
$rule = new EditableCustomRule();
|
||||||
|
$rule->ParentID = $field->ID;
|
||||||
|
$rule->ConditionFieldID = $conditionField ? $conditionField->ID : 0;
|
||||||
|
$rule->Display = $display;
|
||||||
|
$rule->ConditionOption = $conditionOption;
|
||||||
|
$rule->FieldValue = $value;
|
||||||
|
$rule->write();
|
||||||
|
return $rule;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get deserialised rule data for a field
|
||||||
|
*
|
||||||
|
* @param type $id
|
||||||
|
*/
|
||||||
|
protected function getRuleData($id) {
|
||||||
|
$rules = DB::query(sprintf(
|
||||||
|
'SELECT "CustomRules" FROM "EditableFormField" WHERE "ID" = %d',
|
||||||
|
$id
|
||||||
|
))->value();
|
||||||
|
return $rules ? unserialize($rules) : array();
|
||||||
|
}
|
||||||
|
}
|
Binary file not shown.
Before Width: | Height: | Size: 50 KiB After Width: | Height: | Size: 76 KiB |
Binary file not shown.
Before Width: | Height: | Size: 42 KiB After Width: | Height: | Size: 45 KiB |
Binary file not shown.
Before Width: | Height: | Size: 88 KiB After Width: | Height: | Size: 82 KiB |
@ -53,8 +53,8 @@ puts the form at the end of all the content.
|
|||||||
## Adding fields
|
## Adding fields
|
||||||
|
|
||||||
To add a field to the form, click on the "Form" tab under the "Content" tab in the
|
To add a field to the form, click on the "Form" tab under the "Content" tab in the
|
||||||
Editing Pane. Select the type of field you want to add from the drop-down menu and
|
Editing Pane. Click the "Add" button then select the type of field you want from the dropdown.
|
||||||
press the "Add" button. You can label any field by typing in the appropriate label field in the backend.
|
Save or publish the form to start editing your new field's properties.
|
||||||
|
|
||||||
![Adding fields](_images/add-fields.png)
|
![Adding fields](_images/add-fields.png)
|
||||||
|
|
||||||
|
@ -1,134 +0,0 @@
|
|||||||
<!-- JS Relys on EditableFormField as a class - and the 3 ids in this order - do not change -->
|
|
||||||
<li class="$ClassName EditableFormField" id="$Name.ATT EditableItem_$Pos $Name">
|
|
||||||
<div class="fieldInfo">
|
|
||||||
<% if canEdit %>
|
|
||||||
<img class="fieldHandler" src="$ModulePath(framework)/images/drag.gif" alt="<% _t('EditableFormField.DRAG', 'Drag to rearrange order of fields') %>" />
|
|
||||||
<% else %>
|
|
||||||
<img class="fieldHandler" src="$ModulePath(framework)/images/drag_readonly.gif" alt="<% _t('EditableFormField.LOCKED', 'These fields cannot be modified') %>" />
|
|
||||||
<% end_if %>
|
|
||||||
|
|
||||||
<img class="icon" src="$Icon" alt="$ClassName" title="$singular_name" />
|
|
||||||
|
|
||||||
$TitleField
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="fieldActions">
|
|
||||||
<% if showExtraOptions %>
|
|
||||||
<a class="moreOptions" href="#" title="<% _t('EditableFormField.SHOWOPTIONS', 'Show Options') %>"><% _t('EditableFormField.SHOWOPTIONS','Show Options') %></a>
|
|
||||||
<% end_if %>
|
|
||||||
|
|
||||||
<% if canDelete %>
|
|
||||||
<a class="delete" href="#" title="<% _t('EditableFormField.DELETE', 'Delete') %>"><% _t('EditableFormField.DELETE', 'Delete') %></a>
|
|
||||||
<% end_if %>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<% if showExtraOptions %>
|
|
||||||
<div class="extraOptions hidden" id="$Name.ATT-extraOptions">
|
|
||||||
<% if HasAddableOptions %>
|
|
||||||
<fieldset class="fieldOptionsGroup">
|
|
||||||
<legend><% _t('EditableFormField.OPTIONS', 'Options') %></legend>
|
|
||||||
<ul class="editableOptions" id="$FieldName.ATT-list">
|
|
||||||
|
|
||||||
<% if canEdit %>
|
|
||||||
<% loop Options %>
|
|
||||||
$EditSegment
|
|
||||||
<% end_loop %>
|
|
||||||
<% if HasAddableOptions %>
|
|
||||||
<li class="{$ClassName}Option">
|
|
||||||
<a href="#" rel="$ID" class="addableOption" title="<% _t('EditableFormField.ADD', 'Add option to field') %>">
|
|
||||||
<% _t('EditableFormField.ADDLabel', 'Add option') %>
|
|
||||||
</a>
|
|
||||||
</li>
|
|
||||||
<% end_if %>
|
|
||||||
<% else %>
|
|
||||||
<% loop Options %>
|
|
||||||
$ReadonlyOption
|
|
||||||
<% end_loop %>
|
|
||||||
<% end_if %>
|
|
||||||
</ul>
|
|
||||||
</fieldset>
|
|
||||||
<% end_if %>
|
|
||||||
|
|
||||||
<% if FieldConfiguration %>
|
|
||||||
<fieldset class="fieldOptionsGroup">
|
|
||||||
<legend><% _t('EditableFormField.FIELDCONFIGURATION', 'Field Configuration') %></legend>
|
|
||||||
<% loop FieldConfiguration %>
|
|
||||||
$FieldHolder
|
|
||||||
<% end_loop %>
|
|
||||||
</fieldset>
|
|
||||||
<% end_if %>
|
|
||||||
|
|
||||||
<% if FieldValidationOptions %>
|
|
||||||
<fieldset class="fieldOptionsGroup">
|
|
||||||
<legend><% _t('EditableFormField.VALIDATION', 'Validation') %></legend>
|
|
||||||
<% loop FieldValidationOptions %>
|
|
||||||
$FieldHolder
|
|
||||||
<% end_loop %>
|
|
||||||
</fieldset>
|
|
||||||
<% end_if %>
|
|
||||||
|
|
||||||
<fieldset class="customRules fieldOptionsGroup">
|
|
||||||
<legend><% _t('EditableFormField.CUSTOMRULES', 'Custom Rules') %></legend>
|
|
||||||
<ul id="{$FieldName}-customRules">
|
|
||||||
<li>
|
|
||||||
<a href="#" class="addCondition" title="<% _t('EditableFormField.ADD', 'Add') %>"><% _t('EditableFormField.ADDRULE', 'Add Rule') %></a>
|
|
||||||
</li>
|
|
||||||
<li class="addCustomRule">
|
|
||||||
<select name="{$FieldName}[CustomSettings][ShowOnLoad]">
|
|
||||||
<option value="Show" <% if ShowOnLoad %>selected="selected"<% end_if %>><% _t('EditableFormField.SHOW', 'Show') %></option>
|
|
||||||
<option value="Hide" <% if ShowOnLoad %><% else %>selected="selected"<% end_if %>><% _t('EditableFormField.HIDE', 'Hide') %></option>
|
|
||||||
</select>
|
|
||||||
|
|
||||||
<label class="left"><% _t('EditableFormField.FIELDONDEFAULT', 'Field On Default') %></label>
|
|
||||||
</li>
|
|
||||||
<li class="hidden">
|
|
||||||
<select class="displayOption customRuleField" name="{$FieldName}[CustomRules][Display]">
|
|
||||||
<option value="Show"><% _t('EditableFormField.SHOWTHISFIELD', 'Show This Field') %></option>
|
|
||||||
<option value="Hide"><% _t('EditableFormField.HIDETHISFIELD', 'Hide This Field') %></option>
|
|
||||||
</select>
|
|
||||||
|
|
||||||
<label><% _t('EditableFormField.WHEN', 'When') %></label>
|
|
||||||
<select class="fieldOption customRuleField" name="{$FieldName}[CustomRules][ConditionField]">
|
|
||||||
<option></option>
|
|
||||||
<% loop Parent %>
|
|
||||||
<% if Fields %>
|
|
||||||
<% loop Fields %>
|
|
||||||
<option value="$Name"><% if Title %>$Title<% else %>$Name<% end_if %></option>
|
|
||||||
<% end_loop %>
|
|
||||||
<% end_if %>
|
|
||||||
<% end_loop %>
|
|
||||||
</select>
|
|
||||||
|
|
||||||
<label><% _t('EditableFormField.IS', 'Is') %></label>
|
|
||||||
<select class="conditionOption customRuleField" name="{$FieldName}[CustomRules][ConditionOption]">
|
|
||||||
<option value=""></option>
|
|
||||||
<option value="IsBlank"><% _t('EditableFormField.BLANK', 'Blank') %></option>
|
|
||||||
<option value="IsNotBlank"><% _t('EditableFormField.NOTBLANK', 'Not Blank') %></option>
|
|
||||||
<option value="HasValue"><% _t('EditableFormField.VALUE', 'Value') %></option>
|
|
||||||
<option value="ValueNot"><% _t('EditableFormField.NOTVALUE', 'Not Value') %></option>
|
|
||||||
<option value="ValueLessThan"><% _t('EditableFormField.LESSTHAN', 'Value Less Than') %></option>
|
|
||||||
<option value="ValueLessThanEqual"><% _t('EditableFormField.LESSTHANEQUAL', 'Value Less Than Or Equal') %></option>
|
|
||||||
<option value="ValueGreaterThan"><% _t('EditableFormField.GREATERTHAN', 'Value Greater Than') %></option>
|
|
||||||
<option value="ValueGreaterThanEqual"><% _t('EditableFormField.GREATERTHANEQUAL', 'Value Greater Than Or Equal') %></option>
|
|
||||||
</select>
|
|
||||||
|
|
||||||
<input type="text" class="ruleValue hidden customRuleField" name="{$FieldName}[CustomRules][Value]" />
|
|
||||||
|
|
||||||
<a href="#" class="deleteCondition" title="<% _t('EditableFormField.DELETE', 'Delete') %>"><img src="cms/images/delete.gif" alt="<% _t('EditableFormField.DELETE', 'Delete') %>" /></a>
|
|
||||||
</li>
|
|
||||||
<% if CustomRules %>
|
|
||||||
<% loop CustomRules %>
|
|
||||||
<li>
|
|
||||||
<% include CustomRule %>
|
|
||||||
</li>
|
|
||||||
<% end_loop %>
|
|
||||||
<% end_if %>
|
|
||||||
</ul>
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
|
||||||
<% end_if %>
|
|
||||||
|
|
||||||
<!-- Hidden option Fields -->
|
|
||||||
<input type="hidden" class="typeHidden" name="{$FieldName}[Type]" value="$ClassName" />
|
|
||||||
<input type="hidden" class="sortHidden" name="{$FieldName}[Sort]" value="$Sort" />
|
|
||||||
</li>
|
|
@ -1,28 +0,0 @@
|
|||||||
<select class="displayOption customRuleField" name="{$FieldName}[CustomRules][$Pos][Display]">
|
|
||||||
<option value="Show" <% if Display = Show %>selected="selected"<% end_if %>><% _t('CustomRule.SHOWTHISFIELD', 'Show This Field') %></option>
|
|
||||||
<option value="Hide" <% if Display = Hide %>selected="selected"<% end_if %>><% _t('CustomRule.HIDETHISFIELD', 'Hide This Field') %></option>
|
|
||||||
</select>
|
|
||||||
|
|
||||||
<label><% _t('CustomRule.WHEN', 'When') %></label>
|
|
||||||
<select class="fieldOption customRuleField" name="{$FieldName}[CustomRules][$Pos][ConditionField]">
|
|
||||||
<option value="" selected="selected"></option>
|
|
||||||
<% loop Fields %>
|
|
||||||
<option value="$Name" <% if isSelected %>selected="selected"<% end_if %>>$Title</option>
|
|
||||||
<% end_loop %>
|
|
||||||
</select>
|
|
||||||
|
|
||||||
<label><% _t('CustomRule.IS', 'Is') %></label>
|
|
||||||
<select class="conditionOption customRuleField" name="{$FieldName}[CustomRules][$Pos][ConditionOption]">
|
|
||||||
<option value="IsBlank" <% if ConditionOption = IsBlank %>selected="selected"<% end_if %>><% _t('CustomRule.BLANK', 'Blank') %></option>
|
|
||||||
<option value="IsNotBlank" <% if ConditionOption = IsNotBlank %>selected="selected"<% end_if %>><% _t('CustomRule.NOTBLANK', 'Not Blank') %></option>
|
|
||||||
<option value="HasValue" <% if ConditionOption = HasValue %>selected="selected"<% end_if %>><% _t('CustomRule.VALUE', 'Value') %></option>
|
|
||||||
<option value="ValueNot" <% if ConditionOption = ValueNot %>selected="selected"<% end_if %>><% _t('CustomRule.NOTVALUE', 'Not Value') %></option>
|
|
||||||
<option value="ValueLessThan" <% if ConditionOption = ValueLessThan %>selected="selected"<% end_if %>><% _t('CustomRule.LESSTHAN', 'Value Less Than') %></option>
|
|
||||||
<option value="ValueLessThanEqual" <% if ConditionOption = ValueLessThanEqual %>selected="selected"<% end_if %>><% _t('CustomRule.LESSTHANEQUAL', 'Value Less Than Or Equal') %></option>
|
|
||||||
<option value="ValueGreaterThan" <% if ConditionOption = ValueGreaterThan %>selected="selected"<% end_if %>><% _t('CustomRule.GREATERTHAN', 'Value Greater Than') %></option>
|
|
||||||
<option value="ValueGreaterThanEqual" <% if ConditionOption = ValueGreaterThanEqual %>selected="selected"<% end_if %>><% _t('CustomRule.GREATERTHANEQUAL', 'Value Greater Than Or Equal') %></option>
|
|
||||||
</select>
|
|
||||||
|
|
||||||
<input type="text" class="ruleValue <% if ConditionOption %><% if ConditionOption = IsBlank %>hidden<% else_if ConditionOption = IsNotBlank %>hidden<% end_if %><% else %>hidden<% end_if %> customRuleField" name="{$FieldName}[CustomRules][$Pos][Value]" value="$Value" />
|
|
||||||
|
|
||||||
<a href="#" class="deleteCondition" title="<% _t('CustomRule.DELETE', 'Delete') %>"><img src="cms/images/delete.gif" alt="<% _t('CustomRule.DELETE', 'Delete') %>" /></a>
|
|
@ -83,58 +83,6 @@ class EditableFormFieldTest extends FunctionalTest {
|
|||||||
$this->assertTrue($text->getShowOnLoad());
|
$this->assertTrue($text->getShowOnLoad());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
function testPopulateFromPostData() {
|
|
||||||
$this->logInWithPermission('ADMIN');
|
|
||||||
$set = new ArrayList();
|
|
||||||
|
|
||||||
$field = new EditableFormField();
|
|
||||||
|
|
||||||
$data = array(
|
|
||||||
'Title' => 'Field Title',
|
|
||||||
'Default' => 'Default Value',
|
|
||||||
'Sort' => '2',
|
|
||||||
'Required' => 0,
|
|
||||||
'CustomErrorMessage' => 'Custom'
|
|
||||||
);
|
|
||||||
|
|
||||||
$field->populateFromPostData($data);
|
|
||||||
$set->push($field);
|
|
||||||
$this->assertDOSEquals(array($data), $set);
|
|
||||||
|
|
||||||
// test the custom settings
|
|
||||||
$data['CustomSettings'] = array(
|
|
||||||
'Foo' => 'Bar'
|
|
||||||
);
|
|
||||||
|
|
||||||
$checkbox = new EditableCheckbox();
|
|
||||||
$checkbox->write();
|
|
||||||
|
|
||||||
$checkbox->populateFromPostData(array('Title' => 'Checkbox'));
|
|
||||||
|
|
||||||
$field->populateFromPostData($data);
|
|
||||||
|
|
||||||
$this->assertEquals($field->getSettings(), array('Foo' => 'Bar'));
|
|
||||||
|
|
||||||
$rule = array(
|
|
||||||
'Display' => 'Hide',
|
|
||||||
'ConditionField' => $checkbox->Name,
|
|
||||||
'ConditionOption' => 'HasValue',
|
|
||||||
'Value' => 6
|
|
||||||
);
|
|
||||||
|
|
||||||
// test the custom rules
|
|
||||||
$data['CustomRules'] = array(
|
|
||||||
'Rule1' => $rule
|
|
||||||
);
|
|
||||||
|
|
||||||
$field->populateFromPostData($data);
|
|
||||||
|
|
||||||
$rules = unserialize($field->CustomRules);
|
|
||||||
|
|
||||||
$this->assertEquals($rules[0], $rule);
|
|
||||||
}
|
|
||||||
|
|
||||||
function testCustomRules() {
|
function testCustomRules() {
|
||||||
$this->logInWithPermission('ADMIN');
|
$this->logInWithPermission('ADMIN');
|
||||||
$form = $this->objFromFixture('UserDefinedForm', 'custom-rules-form');
|
$form = $this->objFromFixture('UserDefinedForm', 'custom-rules-form');
|
||||||
@ -142,58 +90,18 @@ class EditableFormFieldTest extends FunctionalTest {
|
|||||||
$checkbox = $form->Fields()->find('ClassName', 'EditableCheckbox');
|
$checkbox = $form->Fields()->find('ClassName', 'EditableCheckbox');
|
||||||
$field = $form->Fields()->find('ClassName', 'EditableTextField');
|
$field = $form->Fields()->find('ClassName', 'EditableTextField');
|
||||||
|
|
||||||
$rule = array(
|
$rules = $checkbox->CustomRules();
|
||||||
'Display' => 'Hide',
|
|
||||||
'ConditionField' => $checkbox->Name,
|
|
||||||
'ConditionOption' => 'HasValue',
|
|
||||||
'Value' => 6
|
|
||||||
);
|
|
||||||
|
|
||||||
$data['CustomRules'] = array(
|
|
||||||
'Rule1' => $rule
|
|
||||||
);
|
|
||||||
|
|
||||||
$field->populateFromPostData($data);
|
|
||||||
|
|
||||||
$rules = $field->CustomRules();
|
|
||||||
|
|
||||||
// form has 2 fields - a checkbox and a text field
|
// form has 2 fields - a checkbox and a text field
|
||||||
// it has 1 rule - when ticked the checkbox hides the text field
|
// it has 1 rule - when ticked the checkbox hides the text field
|
||||||
$this->assertEquals($rules->Count(), 1);
|
$this->assertEquals($rules->Count(), 1);
|
||||||
|
|
||||||
// rules are ArrayDatas not dataobjects
|
|
||||||
// $this->assertDOSEquals(array($rule), $rules);
|
|
||||||
|
|
||||||
$checkboxRule = $rules->First();
|
$checkboxRule = $rules->First();
|
||||||
|
$checkboxRule->ConditionFieldID = $field->ID;
|
||||||
|
|
||||||
$this->assertEquals($checkboxRule->Display, 'Hide');
|
$this->assertEquals($checkboxRule->Display, 'Hide');
|
||||||
$this->assertEquals($checkboxRule->ConditionField, $checkbox->Name);
|
|
||||||
$this->assertEquals($checkboxRule->ConditionOption, 'HasValue');
|
$this->assertEquals($checkboxRule->ConditionOption, 'HasValue');
|
||||||
$this->assertEquals($checkboxRule->Value, '6');
|
$this->assertEquals($checkboxRule->FieldValue, '6');
|
||||||
|
|
||||||
foreach($checkboxRule->Fields as $condition) {
|
|
||||||
if($checkbox->Name == $condition->Name) {
|
|
||||||
$this->assertTrue($condition->isSelected);
|
|
||||||
}
|
|
||||||
else {
|
|
||||||
$this->assertFalse($condition->isSelected);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
$data['CustomRules'] = array(
|
|
||||||
'Rule2' => array(
|
|
||||||
'Display' => 'Hide',
|
|
||||||
'ConditionField' => $checkbox->Name,
|
|
||||||
'ConditionOption' => 'Blank'
|
|
||||||
)
|
|
||||||
);
|
|
||||||
|
|
||||||
$field->populateFromPostData($data);
|
|
||||||
|
|
||||||
$rules = $field->CustomRules();
|
|
||||||
|
|
||||||
// test that saving additional rules deletes the old one
|
|
||||||
$this->assertEquals($rules->Count(), 1);
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
function testEditableDropdownField() {
|
function testEditableDropdownField() {
|
||||||
@ -263,50 +171,6 @@ class EditableFormFieldTest extends FunctionalTest {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
function testMultipleOptionPopulateFromPostData() {
|
|
||||||
$dropdown = $this->objFromFixture('EditableDropdown','basic-dropdown');
|
|
||||||
|
|
||||||
$data = array();
|
|
||||||
|
|
||||||
foreach($dropdown->Options() as $option) {
|
|
||||||
$orginal[$option->ID] = array(
|
|
||||||
'Title' => $option->Title,
|
|
||||||
'Sort' => $option->Sort
|
|
||||||
);
|
|
||||||
|
|
||||||
$data[$option->ID] = array(
|
|
||||||
'Title' => 'New - '. $option->Title,
|
|
||||||
'Sort' => $option->Sort + 1
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
$dropdown->populateFromPostData($data);
|
|
||||||
|
|
||||||
$count = $dropdown->Options()->Count();
|
|
||||||
|
|
||||||
foreach($dropdown->Options() as $option) {
|
|
||||||
$this->assertEquals($option->Title, 'New - '. $orginal[$option->ID]['Title']);
|
|
||||||
$this->assertEquals($option->Sort, $orginal[$option->ID]['Sort'] + 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
// remove the first one. can't assume by ID
|
|
||||||
foreach($data as $key => $value) {
|
|
||||||
unset($data[$key]);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
$dropdown->populateFromPostData($data);
|
|
||||||
|
|
||||||
$this->assertEquals($dropdown->Options()->Count(), $count-1);
|
|
||||||
}
|
|
||||||
|
|
||||||
function testEditableTextFieldConfiguration() {
|
|
||||||
// $text = $this->objFromFixture('EditableTextField', 'basic-text');
|
|
||||||
|
|
||||||
// $configuration = $text->getFieldConfiguration();
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
function testExtendedEditableFormField() {
|
function testExtendedEditableFormField() {
|
||||||
/** @var ExtendedEditableFormField $field */
|
/** @var ExtendedEditableFormField $field */
|
||||||
$field = $this->objFromFixture('ExtendedEditableFormFieldTestOnly', 'extended-field');
|
$field = $this->objFromFixture('ExtendedEditableFormFieldTestOnly', 'extended-field');
|
||||||
@ -316,11 +180,6 @@ class EditableFormFieldTest extends FunctionalTest {
|
|||||||
$this->assertTrue(array_key_exists('TestExtraField', $dbFields));
|
$this->assertTrue(array_key_exists('TestExtraField', $dbFields));
|
||||||
$this->assertTrue(array_key_exists('TestValidationField', $dbFields));
|
$this->assertTrue(array_key_exists('TestValidationField', $dbFields));
|
||||||
|
|
||||||
// Check Field Configuration
|
|
||||||
$fieldConfiguration = $field->getFieldConfiguration();
|
|
||||||
$extraField = $fieldConfiguration->dataFieldByName($field->getSettingName('TestExtraField'));
|
|
||||||
$this->assertNotNull($extraField);
|
|
||||||
|
|
||||||
// Check Validation Fields
|
// Check Validation Fields
|
||||||
$fieldValidation = $field->getFieldValidationOptions();
|
$fieldValidation = $field->getFieldValidationOptions();
|
||||||
$validationField = $fieldValidation->dataFieldByName($field->getSettingName('TestValidationField'));
|
$validationField = $fieldValidation->dataFieldByName($field->getSettingName('TestValidationField'));
|
||||||
|
@ -1,3 +1,9 @@
|
|||||||
|
EditableCustomRule:
|
||||||
|
rule-1:
|
||||||
|
Display: Hide
|
||||||
|
ConditionOption: HasValue
|
||||||
|
FieldValue: 6
|
||||||
|
|
||||||
EditableOption:
|
EditableOption:
|
||||||
option-1:
|
option-1:
|
||||||
Name: Option1
|
Name: Option1
|
||||||
@ -84,6 +90,11 @@ EditableCheckbox:
|
|||||||
Name: checkbox-1
|
Name: checkbox-1
|
||||||
Title: Checkbox 1
|
Title: Checkbox 1
|
||||||
|
|
||||||
|
checkbox-with-rule:
|
||||||
|
Name: checkbox-with-rule
|
||||||
|
Title: Checkbox with rule
|
||||||
|
CustomRules: =>EditableCustomRule.rule-1
|
||||||
|
|
||||||
EditableCheckboxGroupField:
|
EditableCheckboxGroupField:
|
||||||
checkbox-group:
|
checkbox-group:
|
||||||
Name: check-box-group
|
Name: check-box-group
|
||||||
@ -95,14 +106,12 @@ EditableEmailField:
|
|||||||
Name: email-field
|
Name: email-field
|
||||||
Title: Email
|
Title: Email
|
||||||
|
|
||||||
|
|
||||||
EditableRadioField:
|
EditableRadioField:
|
||||||
radio-field:
|
radio-field:
|
||||||
Name: radio-option
|
Name: radio-option
|
||||||
Title: Radio Option
|
Title: Radio Option
|
||||||
Options: =>EditableOption.option-5, =>EditableOption.option-6
|
Options: =>EditableOption.option-5, =>EditableOption.option-6
|
||||||
|
|
||||||
|
|
||||||
EditableFileField:
|
EditableFileField:
|
||||||
file-field:
|
file-field:
|
||||||
Name: file-uploader
|
Name: file-uploader
|
||||||
@ -132,8 +141,6 @@ UserDefinedForm:
|
|||||||
|
|
||||||
custom-rules-form:
|
custom-rules-form:
|
||||||
Title: Custom Rules Form
|
Title: Custom Rules Form
|
||||||
Fields: =>EditableCheckbox.checkbox-2, =>EditableTextField.basic-text-2
|
Fields: =>EditableCheckbox.checkbox-with-rule, =>EditableTextField.basic-text-2
|
||||||
empty-form:
|
empty-form:
|
||||||
Title: Empty Form
|
Title: Empty Form
|
||||||
|
|
||||||
|
|
||||||
|
@ -1,46 +0,0 @@
|
|||||||
<?php
|
|
||||||
|
|
||||||
/**
|
|
||||||
* Tests covering the form editor / builder and
|
|
||||||
* some of the user interface
|
|
||||||
*
|
|
||||||
* @package userforms
|
|
||||||
*/
|
|
||||||
|
|
||||||
class FieldEditorTest extends FunctionalTest {
|
|
||||||
|
|
||||||
static $fixture_file = 'userforms/tests/UserDefinedFormTest.yml';
|
|
||||||
|
|
||||||
protected $editor;
|
|
||||||
|
|
||||||
function setUp() {
|
|
||||||
parent::setUp();
|
|
||||||
|
|
||||||
$form = $this->objFromFixture('UserDefinedForm', 'basic-form-page');
|
|
||||||
|
|
||||||
$controller = new FieldEditorTest_Controller($form);
|
|
||||||
|
|
||||||
$fields = $controller->Form()->Fields();
|
|
||||||
|
|
||||||
$this->editor = $fields->fieldByName('Fields');
|
|
||||||
}
|
|
||||||
|
|
||||||
function testSaveInto() {
|
|
||||||
$this->logInWithPermission('ADMIN');
|
|
||||||
|
|
||||||
// @todo
|
|
||||||
}
|
|
||||||
|
|
||||||
function testAddField() {
|
|
||||||
$this->logInWithPermission('ADMIN');
|
|
||||||
|
|
||||||
// Debug::show($this->editor->addfield());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class FieldEditorTest_Controller extends Controller {
|
|
||||||
|
|
||||||
public function Form() {
|
|
||||||
return new Form($this, 'Form', new FieldList(new FieldEditor('Fields')), new FieldList());
|
|
||||||
}
|
|
||||||
}
|
|
@ -18,7 +18,7 @@ class UserDefinedFormControllerTest extends FunctionalTest {
|
|||||||
|
|
||||||
// load the form
|
// load the form
|
||||||
$this->get($form->URLSegment);
|
$this->get($form->URLSegment);
|
||||||
$response = $this->submitForm('Form_Form', null, array('basic-text-name' => 'Basic Value'));
|
$response = $this->submitForm('UserForm_Form', null, array('basic-text-name' => 'Basic Value'));
|
||||||
|
|
||||||
// should have a submitted form field now
|
// should have a submitted form field now
|
||||||
$submitted = DataObject::get('SubmittedFormField', "\"Name\" = 'basic-text-name'");
|
$submitted = DataObject::get('SubmittedFormField', "\"Name\" = 'basic-text-name'");
|
||||||
@ -106,7 +106,7 @@ class UserDefinedFormControllerTest extends FunctionalTest {
|
|||||||
|
|
||||||
$controller = new UserDefinedFormControllerTest_Controller($form);
|
$controller = new UserDefinedFormControllerTest_Controller($form);
|
||||||
|
|
||||||
$fields = $controller->getFormFields();
|
$fields = $controller->Form()->getFormFields();
|
||||||
|
|
||||||
$this->assertEquals($fields->Count(), 1);
|
$this->assertEquals($fields->Count(), 1);
|
||||||
|
|
||||||
@ -116,7 +116,7 @@ class UserDefinedFormControllerTest extends FunctionalTest {
|
|||||||
|
|
||||||
UserDefinedForm::config()->required_identifier = "*";
|
UserDefinedForm::config()->required_identifier = "*";
|
||||||
|
|
||||||
$fields = $controller->getFormFields();
|
$fields = $controller->Form()->getFormFields();
|
||||||
|
|
||||||
$this->assertEquals($fields->First()->getCustomValidationMessage()->getValue(), 'Custom Error Message');
|
$this->assertEquals($fields->First()->getCustomValidationMessage()->getValue(), 'Custom Error Message');
|
||||||
$this->assertEquals($fields->First()->Title(), 'Required Text Field <span class=\'required-identifier\'>*</span>');
|
$this->assertEquals($fields->First()->Title(), 'Required Text Field <span class=\'required-identifier\'>*</span>');
|
||||||
@ -127,7 +127,7 @@ class UserDefinedFormControllerTest extends FunctionalTest {
|
|||||||
$field->write();
|
$field->write();
|
||||||
|
|
||||||
$controller = new UserDefinedFormControllerTest_Controller($form);
|
$controller = new UserDefinedFormControllerTest_Controller($form);
|
||||||
$fields = $controller->getFormFields();
|
$fields = $controller->Form()->getFormFields();
|
||||||
|
|
||||||
$this->assertEquals($fields->First()->RightTitle(), "Right Title");
|
$this->assertEquals($fields->First()->RightTitle(), "Right Title");
|
||||||
|
|
||||||
@ -135,7 +135,7 @@ class UserDefinedFormControllerTest extends FunctionalTest {
|
|||||||
$emptyForm = $this->objFromFixture('UserDefinedForm', 'empty-form');
|
$emptyForm = $this->objFromFixture('UserDefinedForm', 'empty-form');
|
||||||
$controller = new UserDefinedFormControllerTest_Controller($emptyForm);
|
$controller = new UserDefinedFormControllerTest_Controller($emptyForm);
|
||||||
|
|
||||||
$this->assertFalse($controller->Form());
|
$this->assertFalse($controller->Form()->getFormFields()->exists());
|
||||||
}
|
}
|
||||||
|
|
||||||
function testGetFormActions() {
|
function testGetFormActions() {
|
||||||
@ -143,7 +143,7 @@ class UserDefinedFormControllerTest extends FunctionalTest {
|
|||||||
$form = $this->objFromFixture('UserDefinedForm', 'basic-form-page');
|
$form = $this->objFromFixture('UserDefinedForm', 'basic-form-page');
|
||||||
|
|
||||||
$controller = new UserDefinedFormControllerTest_Controller($form);
|
$controller = new UserDefinedFormControllerTest_Controller($form);
|
||||||
$actions = $controller->getFormActions();
|
$actions = $controller->Form()->getFormActions();
|
||||||
|
|
||||||
// by default will have 1 submit button which links to process
|
// by default will have 1 submit button which links to process
|
||||||
$expected = new FieldList(new FormAction('process', 'Submit'));
|
$expected = new FieldList(new FormAction('process', 'Submit'));
|
||||||
@ -153,8 +153,7 @@ class UserDefinedFormControllerTest extends FunctionalTest {
|
|||||||
// the custom popup should have a reset button and a custom text
|
// the custom popup should have a reset button and a custom text
|
||||||
$custom = $this->objFromFixture('UserDefinedForm', 'form-with-reset-and-custom-action');
|
$custom = $this->objFromFixture('UserDefinedForm', 'form-with-reset-and-custom-action');
|
||||||
$controller = new UserDefinedFormControllerTest_Controller($custom);
|
$controller = new UserDefinedFormControllerTest_Controller($custom);
|
||||||
|
$actions = $controller->Form()->getFormActions();
|
||||||
$actions = $controller->getFormActions();
|
|
||||||
|
|
||||||
$expected = new FieldList(new FormAction('process', 'Custom Button'));
|
$expected = new FieldList(new FormAction('process', 'Custom Button'));
|
||||||
$expected->push(new ResetFormAction("clearForm", "Clear"));
|
$expected->push(new ResetFormAction("clearForm", "Clear"));
|
||||||
@ -162,14 +161,6 @@ class UserDefinedFormControllerTest extends FunctionalTest {
|
|||||||
$this->assertEquals($actions, $expected);
|
$this->assertEquals($actions, $expected);
|
||||||
}
|
}
|
||||||
|
|
||||||
function testArrayToJson() {
|
|
||||||
$array = array('1' => 'one', '2' => 'two');
|
|
||||||
$string = "{\n1:\"one\", 2:\"two\"\n}\n";
|
|
||||||
$form = new UserDefinedFormControllerTest_Controller();
|
|
||||||
$this->assertEquals($form->array2json($array), $string);
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
function testRenderingIntoFormTemplate() {
|
function testRenderingIntoFormTemplate() {
|
||||||
$form = $this->setupFormFrontend();
|
$form = $this->setupFormFrontend();
|
||||||
|
|
||||||
@ -210,7 +201,7 @@ class UserDefinedFormControllerTest extends FunctionalTest {
|
|||||||
}
|
}
|
||||||
|
|
||||||
function checkTemplateIsCorrect($parser) {
|
function checkTemplateIsCorrect($parser) {
|
||||||
$this->assertArrayHasKey(0, $parser->getBySelector('form#Form_Form'));
|
$this->assertArrayHasKey(0, $parser->getBySelector('form#UserForm_Form'));
|
||||||
|
|
||||||
// check for the input
|
// check for the input
|
||||||
$this->assertArrayHasKey(0, $parser->getBySelector('input.text'));
|
$this->assertArrayHasKey(0, $parser->getBySelector('input.text'));
|
||||||
|
Loading…
x
Reference in New Issue
Block a user