00001 <?php
00002
00003
00004
00005 class WidgetTree implements IWidget {
00006 const OPEN_UNTIL_LEVEL = 512;
00007 const OPEN_LEAF = 1024;
00008
00009
00010
00011
00012 const P_LEVEL = 'level';
00013
00014
00015
00016 const P_LEAF = 'leaf';
00017
00018
00019
00020 const P_ROOTS = 'roots';
00021
00022
00023
00024 const P_ACTION = 'action';
00025
00026 public $params = array();
00027
00028 public static function output($params, $policy = self::OPEN_LEAF) {
00029 $w = new WidgetTree($params);
00030 return $w->render($policy);
00031 }
00032
00033 public function __construct($params) {
00034 $this->params = $params;
00035 }
00036
00037 public function render($policy = self::NONE) {
00038
00039 $branch = $this->build_branch_array($this->params, $policy);
00040 $tree = $this->build_tree_array($this->params, $policy, $branch);
00041
00042 $view = ViewFactory::create_view(IViewFactory::MESSAGE, 'widgets/tree');
00043 $view->assign('tree', $tree);
00044 $view->assign('action', Arr::get_item($this->params, self::P_ACTION, 'view'));
00045 $view->assign('params', $this->params);
00046 return $view->render();
00047 }
00048
00049
00050
00051
00052 protected function build_branch_array($params, $policy) {
00053 $ret = array();
00054 $leaf = Arr::get_item($params, self::P_LEAF, false);
00055 if ($leaf) {
00056 $item = $leaf;
00057 while($item) {
00058 array_unshift($ret, $item);
00059 $item = $item->get_parent();
00060 }
00061 }
00062 return $ret;
00063 }
00064
00065
00066
00067
00068 protected function build_tree_array($params, $policy, $branch) {
00069 $max_level = Common::flag_is_set($policy, self::OPEN_UNTIL_LEVEL) ? Arr::get_item($params, self::P_LEVEL, 0) : 0;
00070 $roots = Arr::force(Arr::get_item($params, self::P_ROOTS, array()), false);
00071 return $this->create_level(0, $max_level, $roots, $policy, $branch);
00072 }
00073
00074
00075
00076
00077
00078
00079
00080
00081
00082
00083 protected function create_level($level, $max_level, $items, $policy, $branch) {
00084 $ret = array();
00085
00086 $has_next_level = ($level < $max_level);
00087
00088 $branch_item = array_shift($branch);
00089 foreach($items as $item) {
00090
00091 $is_branch = ($branch_item) ? $item->is_same_as($branch_item) : false;
00092
00093 $is_leaf = $is_branch && (count($branch) == 0);
00094 if ($is_branch) {
00095
00096
00097 $expand_branch = (!$is_leaf || Common::flag_is_set($policy, self::OPEN_LEAF));
00098 if ($expand_branch) {
00099 $childs = $this->create_level($level + 1, $max_level, $item->get_childs(), $policy, $branch);
00100 }
00101 }
00102 else if ($has_next_level) {
00103
00104 $childs = $this->create_level($level + 1, $max_level, $item->get_childs(), $policy, array());
00105 }
00106 else {
00107 $childs = array();
00108 }
00109 $ret[] = $this->create_node($item, $childs, $is_branch, $is_leaf);
00110 }
00111 return $ret;
00112 }
00113
00114 protected function create_node($item, $childs, $is_branch, $is_leaf) {
00115 return array('item' => $item, 'childs' => $childs, 'is_branch' => $is_branch, 'is_leaf' => $is_leaf);
00116 }
00117 }