Skip to content

Commit

Permalink
FIX: WidgetControllerTest failing due to 3.1 API. Update package info…
Browse files Browse the repository at this point in the history
…rmation
  • Loading branch information
wilr committed May 7, 2013
1 parent 6167c70 commit dd6ffbf
Show file tree
Hide file tree
Showing 8 changed files with 235 additions and 210 deletions.
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -241,7 +241,7 @@ sure that your controller follows the usual naming conventions, and it will be a
);
}

class MyWidget_Controller extends Widget_Controller {
class MyWidget_Controller extends WidgetController {
public function MyFormName() {
return new Form(
$this,
Expand Down
43 changes: 24 additions & 19 deletions code/controller/WidgetContentControllerExtension.php
Original file line number Diff line number Diff line change
@@ -1,6 +1,9 @@

<?php
/**
* Add this to ContentController to enable widgets
*
* @package widgets
*/
class WidgetContentControllerExtension extends Extension {

Expand All @@ -13,9 +16,12 @@ class WidgetContentControllerExtension extends Extension {
);

/**
* Handles widgets attached to a page through one or more {@link WidgetArea} elements.
* Iterated through each $has_one relation with a {@link WidgetArea}
* and looks for connected widgets by their database identifier.
* Handles widgets attached to a page through one or more {@link WidgetArea}
* elements.
*
* Iterated through each $has_one relation with a {@link WidgetArea} and
* looks for connected widgets by their database identifier.
*
* Assumes URLs in the following format: <URLSegment>/widget/<Widget-ID>.
*
* @return RequestHandler
Expand All @@ -27,7 +33,11 @@ public function handleWidget() {
// find WidgetArea relations
$widgetAreaRelations = array();
$hasOnes = $this->owner->data()->has_one();
if(!$hasOnes) return false;

if(!$hasOnes) {
return false;
}

foreach($hasOnes as $hasOneName => $hasOneClass) {
if($hasOneClass == 'WidgetArea' || is_subclass_of($hasOneClass, 'WidgetArea')) {
$widgetAreaRelations[] = $hasOneName;
Expand All @@ -36,26 +46,21 @@ public function handleWidget() {

// find widget
$widget = null;

foreach($widgetAreaRelations as $widgetAreaRelation) {
if($widget) break;
if($widget) {
break;
}

$widget = $this->owner->data()->$widgetAreaRelation()->Widgets(
sprintf('"Widget"."ID" = %d', $SQL_id)
)->First();
}
if(!$widget) user_error('No widget found', E_USER_ERROR);

// find controller
$controllerClass = '';
foreach(array_reverse(ClassInfo::ancestry($widget->class)) as $widgetClass) {
$controllerClass = "{$widgetClass}_Controller";
if(class_exists($controllerClass)) break;
}
if(!$controllerClass) user_error(
sprintf('No controller available for %s', $widget->class),
E_USER_ERROR
);

return new $controllerClass($widget);
if(!$widget) {
user_error('No widget found', E_USER_ERROR);
}

return $widget->getController();
}

}
121 changes: 121 additions & 0 deletions code/controller/WidgetController.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,121 @@
<?php

/**
* Optional controller for every widget which has its own logic, e.g. in forms.
*
* It always handles a single widget, usually passed in as a database
* identifier through the controller URL. Needs to be constructed as a nested
* controller within a {@link ContentController}.
*
* ## Forms
* You can add forms like in any other SilverStripe controller. If you need
* access to the widget from within a form, you can use
* `$this->controller->getWidget()` inside the form logic.
*
* Note: Widget controllers currently only work on {@link Page} objects,
* because the logic is implemented in {@link ContentController->handleWidget()}.
* Copy this logic and the URL rules to enable it for other controllers.
*
* @package widgets
*/
class WidgetController extends Controller {

/**
* @var Widget
*/
protected $widget;

/**
* @var array
*/
private static $allowed_actions = array(
'editablesegment'
);

/**
* @param Widget $widget
*/
public function __construct($widget = null) {
if($widget) {
$this->widget = $widget;
$this->failover = $widget;
}

parent::__construct();
}

/**
* @param string $action
* @return string
*/
public function Link($action = null) {
$id = ($this->widget) ? $this->widget->ID : null;
$segment = Controller::join_links('widget', $id, $action);

if($page = Director::get_current_page()) {
return $page->Link($segment);
}

return Controller::curr()->Link($segment);
}

/**
* @return Widget
*/
public function getWidget() {
return $this->widget;
}

/**
* Overloaded from {@link Widget->Content()} to allow for controller / form
* linking.
*
* @return string HTML
*/
public function Content() {
return $this->renderWith(array_reverse(ClassInfo::ancestry($this->widget->class)));
}

/**
* Overloaded from {@link Widget->WidgetHolder()} to allow for controller/
* form linking.
*
* @return string HTML
*/
public function WidgetHolder() {
return $this->renderWith("WidgetHolder");
}

/**
* Uses the `WidgetEditor.ss` template and {@link Widget->editablesegment()}
* to render a administrator-view of the widget. It is assumed that this
* view contains form elements which are submitted and saved through
* {@link WidgetAreaEditor} within the CMS interface.
*
* @return string HTML
*/
public function editablesegment() {
$className = $this->urlParams['ID'];
if (class_exists('Translatable') && Member::currentUserID()) {
// set current locale based on logged in user's locale
$locale = Member::currentUser()->Locale;
Translatable::set_current_locale($locale);
i18n::set_locale($locale);
}
if(class_exists($className) && is_subclass_of($className, 'Widget')) {
$obj = new $className();
return $obj->EditableSegment();
} else {
user_error("Bad widget class: $className", E_USER_WARNING);
return "Bad widget class name given";
}
}
}

/**
* @deprecated Use WidgetController
* @package widgets
*/
class Widget_Controller extends WidgetController {

}
24 changes: 14 additions & 10 deletions code/form/WidgetAreaEditor.php
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
<?php

/**
* Special field type for selecting and configuring widgets on a page.
* @package cms
* @subpackage content
*
* @package widgets
*/
class WidgetAreaEditor extends FormField {

/**
*
* @param string $name
* @param array $widgetClasses
* @param int $maxWidgets
Expand All @@ -20,13 +20,14 @@ public function __construct($name, $widgetClasses = array('Widget'), $maxWidgets
}

/**
*
* @param array $properties
* @return string - HTML for this formfield
*
* @return string - HTML
*/
public function FieldHolder($properties = array()) {
Requirements::css('widgets/css/WidgetAreaEditor.css');
Requirements::javascript('widgets/javascript/WidgetAreaEditor.js');

return $this->renderWith("WidgetAreaEditor");
}

Expand All @@ -40,7 +41,11 @@ public function AvailableWidgets() {

foreach($this->widgetClasses as $widgetClass) {
$classes = ClassInfo::subclassesFor($widgetClass);
if(count($classes) > 1) array_shift($classes);

if(count($classes) > 1) {
array_shift($classes);
}

foreach($classes as $class) {
$widgets->push(singleton($class));
}
Expand All @@ -50,7 +55,6 @@ public function AvailableWidgets() {
}

/**
*
* @return HasManyList
*/
public function UsedWidgets() {
Expand All @@ -59,11 +63,11 @@ class_exists('Widget');

$relationName = $this->name;
$widgets = $this->form->getRecord()->getComponent($relationName)->Items();

return $widgets;
}

/**
*
* @return string
*/
public function IdxField() {
Expand All @@ -76,11 +80,11 @@ public function IdxField() {
*/
public function Value() {
$relationName = $this->name;

return $this->form->getRecord()->getComponent($relationName)->ID;
}

/**
*
* @param DataObjectInterface $record
*/
public function saveInto(DataObjectInterface $record) {
Expand Down Expand Up @@ -145,7 +149,7 @@ public function saveInto(DataObjectInterface $record) {
if($widget->ParentID == 0) {
$widget->ParentID = $record->$name()->ID;
}
// echo "Saving $widget->ID into $name/$widget->ParentID\n<br/>";

$widget->populateFromPostData($newWidgetData);
}
}
Expand Down
Loading

0 comments on commit dd6ffbf

Please sign in to comment.