1: <?php
2: /**
3: * PHP version 5
4: * @package generalDriver
5: * @author Christian Schiffler <c.schiffler@cyberspectrum.de>
6: * @author Stefan Heimes <stefan_heimes@hotmail.com>
7: * @author Tristan Lins <tristan.lins@bit3.de>
8: * @copyright The MetaModels team.
9: * @license LGPL.
10: * @filesource
11: */
12:
13: namespace DcGeneral\Panel;
14:
15: use DcGeneral\Contao\DataDefinition\Definition\Contao2BackendViewDefinitionInterface;
16: use DcGeneral\Data\ConfigInterface;
17: use DcGeneral\View\ViewTemplateInterface;
18:
19: /**
20: * Default implementation of a sort element.
21: *
22: * @package DcGeneral\Panel
23: */
24: class DefaultSortElement
25: extends AbstractElement
26: implements SortElementInterface
27: {
28: /**
29: * The default flag to use.
30: *
31: * @var int
32: */
33: public $intDefaultFlag;
34:
35: /**
36: * The sorting properties including the direction.
37: *
38: * @var array
39: */
40: protected $arrSorting = array();
41:
42: /**
43: * The selected sorting value.
44: *
45: * @var mixed
46: */
47: protected $strSelected;
48:
49: /**
50: * Retrieve the persistent value from the input provider.
51: *
52: * @return array
53: */
54: protected function getPersistent()
55: {
56: $arrValue = array();
57: if ($this->getInputProvider()->hasPersistentValue('sorting'))
58: {
59: $arrValue = $this->getInputProvider()->getPersistentValue('sorting');
60: }
61:
62: if (array_key_exists($this->getEnvironment()->getDataDefinition()->getName(), $arrValue))
63: {
64: return $arrValue[$this->getEnvironment()->getDataDefinition()->getName()];
65: }
66:
67: return array();
68: }
69:
70: /**
71: * Store the persistent value in the input provider.
72: *
73: * @param string $strProperty The name of the property to sort by.
74: *
75: * @return void
76: */
77: protected function setPersistent($strProperty)
78: {
79: $arrValue = array();
80: $definitionName = $this->getEnvironment()->getDataDefinition()->getName();
81:
82: if ($this->getInputProvider()->hasPersistentValue('sorting'))
83: {
84: $arrValue = $this->getInputProvider()->getPersistentValue('sorting');
85: }
86:
87: if ($strProperty)
88: {
89: if (!is_array($arrValue[$definitionName]))
90: {
91: $arrValue[$definitionName] = array();
92: }
93: $arrValue[$definitionName] = $strProperty;
94: }
95: else
96: {
97: unset($arrValue[$definitionName]);
98: }
99:
100: $this->getInputProvider()->setPersistentValue('sorting', $arrValue);
101: }
102:
103: /**
104: * Retrieve the sorting flag to use for a property.
105: *
106: * @param string $strProperty The property.
107: *
108: * @return int
109: */
110: protected function lookupFlag($strProperty)
111: {
112: return isset($this->arrSorting[$strProperty])
113: ? $this->arrSorting[$strProperty]
114: : $this->getDefaultFlag();
115: }
116:
117: /**
118: * Calculate the direction from a flag.
119: *
120: * @param int $intFlag The flag.
121: *
122: * @return string
123: */
124: protected function flagToDirection($intFlag)
125: {
126: return ($intFlag % 2) ? 'DESC' : 'ASC';
127: }
128:
129: /**
130: * Retrieve the additional sorting properties from the data definition.
131: *
132: * @return array
133: */
134: protected function getAdditionalSorting()
135: {
136: /** @var Contao2BackendViewDefinitionInterface $view */
137: $view = $this->getEnvironment()
138: ->getDataDefinition()
139: ->getDefinition(Contao2BackendViewDefinitionInterface::NAME);
140: $tmp = $view->getListingConfig()->getDefaultSortingFields();
141: if (!$tmp)
142: {
143: return array();
144: }
145:
146: $arrReturn = array();
147: foreach ($tmp as $strProperty => $strDirection)
148: {
149: if ($this->getSelected() == $strProperty)
150: {
151: continue;
152: }
153:
154: $arrReturn[$strProperty] = $strDirection;
155: }
156: return $arrReturn;
157: }
158:
159: /**
160: * {@inheritDoc}
161: */
162: public function initialize(ConfigInterface $objConfig, PanelElementInterface $objElement = null)
163: {
164: if (is_null($objElement))
165: {
166: $input = $this->getInputProvider();
167: $value = null;
168:
169: if ($this->getPanel()->getContainer()->updateValues() && $input->hasValue('tl_sort'))
170: {
171: $value = $input->getValue('tl_sort');
172:
173: $this->setPersistent($value);
174:
175: $this->setSelected($this->getPersistent());
176: }
177: else
178: {
179: $this->setSelected($this->getPersistent());
180: }
181: }
182:
183: $current = $objConfig->getSorting();
184:
185: if (!is_array($current))
186: {
187: $current = array();
188: }
189:
190: $arrSecondOrder = $this->getAdditionalSorting();
191:
192: if (!$this->getSelected())
193: {
194: if ($arrSecondOrder)
195: {
196: $filtered = array_intersect(array_keys($arrSecondOrder), $this->getPropertyNames());
197:
198: $this->setSelected($filtered[0]);
199: }
200:
201: // Still nothing selected? - use the first.
202: if (!$this->getSelected())
203: {
204: $all = $this->getPropertyNames();
205: $this->setSelected($all[0]);
206: }
207: }
208:
209: if ($this->getSelected())
210: {
211: $current[$this->getSelected()] = $this->flagToDirection($this->getFlag());
212: }
213:
214: $objConfig->setSorting($current);
215: }
216:
217: /**
218: * {@inheritDoc}
219: */
220: public function render(ViewTemplateInterface $objTemplate)
221: {
222: $arrOptions = array();
223: foreach ($this->getPropertyNames() as $field)
224: {
225: $arrLabel = $this->getEnvironment()->getDataDefinition()->getPropertiesDefinition()->getProperty($field)->getLabel();
226:
227: $arrOptions[] = array(
228: 'value' => specialchars($field),
229: 'attributes' => ($this->getSelected() == $field) ? ' selected="selected"' : '',
230: 'content' => is_array($arrLabel) ? $arrLabel[0] : $arrLabel
231: );
232: }
233:
234: // Sort by option values.
235: uksort($arrOptions, 'strcasecmp');
236:
237: $objTemplate->options = $arrOptions;
238:
239: return $this;
240: }
241:
242: /**
243: * {@inheritDoc}
244: */
245: public function setDefaultFlag($intFlag)
246: {
247: $this->intDefaultFlag = $intFlag;
248:
249: return $this;
250: }
251:
252: /**
253: * {@inheritDoc}
254: */
255: public function getDefaultFlag()
256: {
257: return $this->intDefaultFlag;
258: }
259:
260: /**
261: * {@inheritDoc}
262: */
263: public function addProperty($strPropertyName, $intFlag)
264: {
265: $this->arrSorting[$strPropertyName] = $intFlag;
266: }
267:
268: /**
269: * {@inheritDoc}
270: */
271: public function getPropertyNames()
272: {
273: return array_keys($this->arrSorting);
274: }
275:
276: /**
277: * {@inheritDoc}
278: */
279: public function setSelected($strPropertyName)
280: {
281: $this->strSelected = $strPropertyName;
282: }
283:
284: /**
285: * {@inheritDoc}
286: */
287: public function getSelected()
288: {
289: return $this->strSelected;
290: }
291:
292: /**
293: * {@inheritDoc}
294: */
295: public function getFlag()
296: {
297: return $this->lookupFlag($this->getSelected());
298: }
299: }
300: