CWIS Developer Documentation
ItemListUI.php
Go to the documentation of this file.
1 <?PHP
2 #
3 # FILE: ItemListUI.php
4 #
5 # Part of the Collection Workflow Integration System (CWIS)
6 # Copyright 2016 Edward Almasy and Internet Scout Research Group
7 # http://scout.wisc.edu/cwis/
8 #
9 
14 {
15 
16  # ---- PUBLIC INTERFACE --------------------------------------------------
17 
44  public function __construct($Heading, $Fields, $ItemsPerPage, $BaseLink,
46  {
47  # normalize and save field info
48  if ($SchemaId == TransportControlsUI::NO_ITEM_TYPE)
49  {
50  $this->Fields = $Fields;
51  }
52  else
53  {
54  $this->Fields = array();
55  foreach ($Fields as $FieldId => $FieldInfo)
56  {
57  $CanonicalId = MetadataSchema::GetCanonicalFieldIdentifier($FieldId);
58  $this->Fields[$CanonicalId] = $FieldInfo;
59  }
60  }
61 
62  # save other supplied settings for later use
63  $this->BaseLink = $BaseLink;
64  $this->Heading = $Heading;
65  $this->ItemsPerPage = $ItemsPerPage;
66  $this->SchemaId = $SchemaId;
67  }
68 
76  public function AddTopButton($Label, $Link, $Icon = NULL)
77  {
78  $this->Buttons[] = array(
79  "Label" => $Label,
80  "Link" => $Link,
81  "Icon" => $Icon);
82  }
83 
101  public function AddActionButton(
102  $Label, $Link, $Icon = NULL, $DisplayTestFunc = NULL,
103  $AdditionalAttributes = array())
104  {
105  $this->Actions[] = array(
106  "Label" => $Label,
107  "Link" => $Link,
108  "Icon" => $Icon,
109  "TestFunc" => $DisplayTestFunc,
110  "AddAttribs" => $AdditionalAttributes);
111  }
112 
118  public function NoItemsMessage($NewValue = NULL)
119  {
120  if ($NewValue !== NULL)
121  {
122  $this->NoItemsMsg = $NewValue;
123  }
124  return $this->NoItemsMsg;
125  }
126 
141  public function Display($Items, $TotalItemCount = NULL,
142  $StartingIndex = NULL, $TransportMsg = NULL)
143  {
144  # set up transport controls (doing it early to retrieve sort info)
145  foreach ($this->Fields as $FieldId => $FieldInfo)
146  {
147  if (isset($FieldInfo["DefaultSortField"]))
148  {
150  }
151  }
152  $TransportUI = new TransportControlsUI($this->SchemaId, $this->ItemsPerPage);
153  $StartingIndex = $TransportUI->StartingIndex($StartingIndex);
154  $SortFieldId = $TransportUI->SortField();
155  $ReverseSort = $TransportUI->ReverseSortFlag();
156 
157  # display buttons above list
158  if (count($this->Buttons))
159  {
160  print '<span style="float: right; padding-top: 1.5em;">';
161  foreach ($this->Buttons as $Info)
162  {
163  if ($Info["Icon"])
164  {
165  $IconFile = $GLOBALS["AF"]->GUIFile($Info["Icon"]);
166  $IconTag = $IconFile
167  ? '<img class="cw-button-icon" src="'
168  .$IconFile.'" alt=""> '
169  : "";
170  $IconButtonClass = " cw-button-iconed";
171  }
172  else
173  {
174  $IconTag = "";
175  $IconButtonClass = "";
176  }
177  ?><a class="cw-button cw-button-elegant cw-button-constrained<?=
178  $IconButtonClass ?>"
179  href="<?= $Info["Link"] ?>"><?= $IconTag ?><?=
180  htmlspecialchars($Info["Label"]) ?></a><?PHP
181  }
182  print "</span>";
183  }
184 
185  # display heading
186  if ($this->Heading !== NULL)
187  {
188  if ($this->Heading == strip_tags($this->Heading))
189  {
190  print "<h1>".$this->Heading."</h1>\n";
191  }
192  else
193  {
194  print $this->Heading."\n";
195  }
196  }
197 
198  # display "no items" message and exit if no items
199  if (count($Items) == 0)
200  {
201  print "<span class=\"cw-itemlist-empty\">";
202  if (strlen($this->NoItemsMsg))
203  {
204  print $this->NoItemsMsg;
205  }
206  elseif ($this->SchemaId !== TransportControlsUI::NO_ITEM_TYPE)
207  {
208  $Schema = new MetadataSchema($this->SchemaId);
209  print "(no ".strtolower(StdLib::Pluralize(
210  $Schema->ResourceName()))." to display)";
211  }
212  else
213  {
214  print "(no items to display)";
215  }
216  print "</span>";
217  return;
218  }
219 
220  # begin item table
221  print '<table class="cw-table cw-table-sideheaders cw-table-fullsize
222  cw-table-padded cw-table-striped">';
223 
224  # begin header row
225  print "<thead><tr>";
226 
227  # for each field
228  foreach ($this->Fields as $FieldId => $FieldInfo)
229  {
230  # if header value supplied
231  if (isset($FieldInfo["Heading"]))
232  {
233  # use supplied value
234  $Heading = $FieldInfo["Heading"];
235  }
236  # else if we can get header from schema
237  elseif ($this->SchemaId !== TransportControlsUI::NO_ITEM_TYPE)
238  {
239  # use name of field (with any leading schema name stripped)
240  $Heading = MetadataSchema::GetPrintableFieldName($FieldId);
241  $Heading = preg_replace("/.+\: /", "", $Heading);
242  }
243  # else if field ID appears like it may be a name
244  elseif (is_string($FieldId) && !is_numeric($FieldId))
245  {
246  $Heading = $FieldId;
247  }
248  else
249  {
250  $Heading = "(NO HEADER SET)";
251  }
252 
253  # if sorting is disabled for field
254  if (isset($FieldInfo["NoSorting"]))
255  {
256  # print header
257  print "<th>".$Heading."</th>\n";
258  }
259  else
260  {
261  # build sort link
262  $SortLink = $this->BaseLink."&amp;SF=".$FieldId
263  .$TransportUI->UrlParameterString(TRUE, array("SF", "RS"));
264 
265  # determine current sort direction
266  if (isset($FieldInfo["DefaultToDescendingSort"]))
267  {
268  $SortAscending = $ReverseSort ? TRUE : FALSE;
269  }
270  else
271  {
272  $SortAscending = $ReverseSort ? FALSE : TRUE;
273  }
274 
275  # set sort direction indicator (if any)
276  if ($FieldId == $SortFieldId)
277  {
278  $DirIndicator = ($SortAscending) ? "&uarr;" : "&darr;";
279  if (!$ReverseSort)
280  {
281  $SortLink .= "&amp;RS=1";
282  }
283  }
284  else
285  {
286  $DirIndicator = "";
287  }
288 
289  # print header
290  print "<th><a href=\"".$SortLink."\">".$Heading."</a>"
291  .$DirIndicator."</th>\n";
292  }
293  }
294 
295  # add action header if needed
296  if (count($this->Actions))
297  {
298  print "<th>Actions</th>\n";
299  }
300 
301  # end header row
302  print "</tr></thead>\n";
303 
304  # for each item
305  print "<tbody>\n";
306  foreach ($Items as $ItemId => $Item)
307  {
308  # start row
309  print "<tr>\n";
310 
311  # for each field
312  foreach ($this->Fields as $FieldId => $FieldInfo)
313  {
314  # if there is value function defined for field
315  if (isset($FieldInfo["ValueFunction"]))
316  {
317  # call function for value
318  $Value = $FieldInfo["ValueFunction"]($Item, $FieldId);
319  }
320  else
321  {
322  # if item is associative array
323  if (is_array($Item))
324  {
325  # retrieve value for field (if any) from item
326  $Value = isset($Item[$FieldId])
327  ? $Item[$FieldId] : "";
328  }
329  # else if field ID is item method
330  elseif (method_exists($Item, $FieldId))
331  {
332  # get field value via item method
333  $Value = $Item->$FieldId();
334  }
335  else
336  {
337  # get field value from item via Get()
338  $Values = $Item->Get($FieldId);
339  $Value = is_array($Values) ? array_shift($Values) : $Values;
340  }
341 
342  # if max length specified for field
343  if (isset($FieldInfo["MaxLength"]))
344  {
345  $Value = NeatlyTruncateString(
346  $Value, $FieldInfo["MaxLength"]);
347  }
348 
349  # encode any HTML-significant chars in value
350  if (!isset($FieldInfo["AllowHTML"]))
351  {
352  $Value = htmlspecialchars($Value);
353  }
354  }
355 
356  # get link value (if any)
357  if (isset($FieldInfo["Link"]))
358  {
359  if (method_exists($Item, "Id"))
360  {
361  $Link = preg_replace('/\$ID/', $Item->Id(),
362  $FieldInfo["Link"]);
363  }
364  else
365  {
366  $Link = preg_replace('/\$ID/', $ItemId,
367  $FieldInfo["Link"]);
368  }
369  $LinkStart = '<a href="'.$Link.'">';
370  $LinkEnd = "</a>";
371  }
372  else
373  {
374  $LinkStart = "";
375  $LinkEnd = "";
376  }
377 
378  # display cell with value
379  print "<td>".$LinkStart.$Value.$LinkEnd."</td>\n";
380  }
381 
382  # add action buttons
383  if (count($this->Actions))
384  {
385  print "<td>";
386  foreach ($this->Actions as $ActionInfo)
387  {
388  if ($ActionInfo["TestFunc"] !== NULL)
389  {
390  $DisplayButton = $ActionInfo["TestFunc"]($Item);
391  }
392  elseif (method_exists($Item, "UserCanEdit"))
393  {
394  $DisplayButton = $Item->UserCanEdit($GLOBALS["G_User"]);
395  }
396  else
397  {
398  $DisplayButton = TRUE;
399  }
400  if ($DisplayButton)
401  {
402  $ButtonClasses = "cw-button cw-button-elegant"
403  ." cw-button-constrained";
404  $ExtraAttribs = "";
405  foreach ($ActionInfo["AddAttribs"]
406  as $AttribName => $AttribValue)
407  {
408  $AttribValue = htmlspecialchars($AttribValue);
409  if (strtolower($AttribName) == "class")
410  {
411  $ButtonClasses .= " ".$AttribValue;
412  }
413  else
414  {
415  $ExtraAttribs .= " ".$AttribName
416  .'="'.$AttribValue.'"';
417  }
418  }
419  if ($ActionInfo["Icon"])
420  {
421  $IconFile = $GLOBALS["AF"]->GUIFile($ActionInfo["Icon"]);
422  $IconTag = $IconFile
423  ? '<img class="cw-button-icon" src="'
424  .$IconFile.'" alt=""> '
425  : "";
426  $ButtonClasses .= " cw-button-iconed";
427  }
428  else
429  {
430  $IconTag = "";
431  }
432  if (is_callable($ActionInfo["Link"]))
433  {
434  $Link = $ActionInfo["Link"]($Item);
435  }
436  elseif (method_exists($Item, "Id"))
437  {
438  $Link = preg_replace('/\$ID/', $Item->Id(),
439  $ActionInfo["Link"]);
440  }
441  else
442  {
443  $Link = preg_replace('/\$ID/', $ItemId,
444  $ActionInfo["Link"]);
445  }
446  print '<a class="'.$ButtonClasses.'"'.$ExtraAttribs
447  .' href="'.$Link.'">'.$IconTag
448  .htmlspecialchars($ActionInfo["Label"]).'</a>';
449  }
450  }
451  if ($this->SchemaId !== TransportControlsUI::NO_ITEM_TYPE)
452  {
453  $GLOBALS["AF"]->SignalEvent("EVENT_HTML_INSERTION_POINT",
454  array($GLOBALS["AF"]->GetPageName(),
455  "Resource Summary Buttons", array(
456  "Resource" => $Item)));
457  }
458  print "</td>\n";
459  }
460 
461  # end row
462  print "</tr>\n";
463  }
464  print "</tbody>\n";
465 
466  # end item table
467  print "</table>\n";
468 
469  # if there are more items than are displayed
470  if ($TotalItemCount > count($Items))
471  {
472  # craft transport control message (if not supplied)
473  if ($TransportMsg === NULL)
474  {
475  $ItemsLabel = ($this->SchemaId !== TransportControlsUI::NO_ITEM_TYPE)
477  $Item->Schema()->ResourceName())
478  : "Items";
479  $TransportMsg = $ItemsLabel
480  ." <b>".($TransportUI->StartingIndex() + 1)
481  ."</b> - <b>"
482  .min(($TransportUI->StartingIndex() + $this->ItemsPerPage),
483  $TotalItemCount)
484  ."</b> of <b>".$TotalItemCount."</b>";
485  }
486 
487  # display transport controls
488  $TransportUI->StartingIndex($StartingIndex);
489  $TransportUI->ItemCount($TotalItemCount);
490  $TransportUI->PrintControls(
491  $this->SchemaId, $this->BaseLink, $TransportMsg);
492  }
493  }
494 
495 
496  # ---- PRIVATE INTERFACE -------------------------------------------------
497 
498  private $Actions;
499  private $BaseLink;
500  private $Buttons;
501  private $Fields;
502  private $Heading;
503  private $ItemsPerPage;
504  private $NoItemsMsg;
505  private $SchemaId;
506 }
Metadata schema (in effect a Factory class for MetadataField).
Class to provide a user interface for displaying a list of items.
Definition: ItemListUI.php:13
static GetPrintableFieldName($Field)
Retrieve label for field.
static DefaultSortField($NewValue=NULL)
Get/set default sort field value.
__construct($Heading, $Fields, $ItemsPerPage, $BaseLink, $SchemaId=TransportControlsUI::NO_ITEM_TYPE)
Constructor for item list UI class.
Definition: ItemListUI.php:44
static Pluralize($Word)
Pluralize an English word.
Definition: StdLib.php:105
Display($Items, $TotalItemCount=NULL, $StartingIndex=NULL, $TransportMsg=NULL)
Print list HTML with specified items.
Definition: ItemListUI.php:141
static GetCanonicalFieldIdentifier($Field)
Retrieve canonical identifier for field.
Class to provide support for transport controls (used for paging back and forth through a list) in th...
AddTopButton($Label, $Link, $Icon=NULL)
Add "button" above list.
Definition: ItemListUI.php:76
AddActionButton($Label, $Link, $Icon=NULL, $DisplayTestFunc=NULL, $AdditionalAttributes=array())
Add action "button" to each item in list.
Definition: ItemListUI.php:101
const NO_ITEM_TYPE
Constant to use when no item types available.
NoItemsMessage($NewValue=NULL)
Get/set message to display when there are no items to list.
Definition: ItemListUI.php:118