From b0edc4c6f928b2223b4a54c427b432b978b98b2c Mon Sep 17 00:00:00 2001 From: Roland Gruber Date: Tue, 23 Oct 2018 06:51:23 +0200 Subject: [PATCH 1/9] responsive account list --- lam/lib/lists.inc | 25 ++----------------------- 1 file changed, 2 insertions(+), 23 deletions(-) diff --git a/lam/lib/lists.inc b/lam/lib/lists.inc index 14bd4288..48a87db4 100644 --- a/lam/lib/lists.inc +++ b/lam/lib/lists.inc @@ -1,6 +1,5 @@ listGetParams(); // print HTML head - $this->listPrintHeader(); + $this->printHeader(); // print messages when redirected from other pages $this->listPrintRedirectMessages(); // refresh data if needed @@ -220,7 +219,7 @@ class lamList { $this->listPrintTableHeader(); echo "
\n"; } - $this->listPrintFooter(); + $this->printFooter(); } /** @@ -873,16 +872,6 @@ class lamList { // only used by subclasses } - /** - * Prints the HTML header. - * - * @deprecated - */ - protected function listPrintHeader() { - include '../main_header.php'; - $this->printHeaderContent(); - } - /** * Prints the header part of the page. */ @@ -898,16 +887,6 @@ class lamList { // implemented by child classes if needed } - /** - * Prints the HTML footer. - * - * @deprecated - */ - protected function listPrintFooter() { - $this->printFooterContent(); - include '../main_footer.php'; - } - /** * Prints the footer area of the page. */ From a6f11073ca2e8a10f064f9adc1c4c551cd37b4c9 Mon Sep 17 00:00:00 2001 From: Roland Gruber Date: Tue, 23 Oct 2018 20:25:45 +0200 Subject: [PATCH 2/9] responsive account lists --- lam/lib/lists.inc | 27 ++++++++++++++------------- lam/lib/types/dhcp.inc | 2 +- lam/style/responsive/120_lam.css | 4 ++++ 3 files changed, 19 insertions(+), 14 deletions(-) diff --git a/lam/lib/lists.inc b/lam/lib/lists.inc index 48a87db4..2bb8d29b 100644 --- a/lam/lib/lists.inc +++ b/lam/lib/lists.inc @@ -815,51 +815,52 @@ class lamList { * @param int $tabindex HTML tabindex counter */ protected function listPrintButtons($createOnly) { - $table = new htmlTable('100%'); + $row = new htmlResponsiveRow(); + $row->setCSSClasses(array('maxrow')); $left = new htmlGroup(); // button part - $left->alignment = htmlElement::ALIGN_LEFT; if (checkIfWriteAccessIsAllowed($this->type->getId())) { // add button if (checkIfNewEntriesAreAllowed($this->type->getId())) { $newButton = new htmlButton('new', $this->labels['newEntry']); $newButton->setIconClass('createButton'); + $newButton->setCSSClasses(array('fullwidth-mobile-only')); $left->addElement($newButton); } // delete button if (!$createOnly && checkIfDeleteEntriesIsAllowed($this->type->getId())) { - $left->addElement(new htmlSpacer('1px', null)); $delButton = new htmlButton('del', $this->labels['deleteEntry']); $delButton->setIconClass('deleteButton'); + $delButton->setCSSClasses(array('fullwidth-mobile-only')); $left->addElement($delButton); } $toolSettings = $_SESSION['config']->getToolSettings(); if ($this->type->getBaseType()->supportsFileUpload() && checkIfNewEntriesAreAllowed($this->type->getId()) && !(isset($toolSettings['tool_hide_toolFileUpload']) && ($toolSettings['tool_hide_toolFileUpload'] == 'true'))) { - $left->addElement(new htmlSpacer('20px', null)); $uploadButton = new htmlButton('fileUpload', _('File upload')); $uploadButton->setIconClass('upButton'); + $uploadButton->setCSSClasses(array('fullwidth-mobile-only')); $left->addElement($uploadButton); } } // OU selection and settings - $right = new htmlGroup(); - $right->alignment = htmlElement::ALIGN_RIGHT; - $right->addElement($this->listShowOUSelection()); + $right = new htmlResponsiveRow(); + $right->add($this->listShowOUSelection(), 12, 12, 10); + $rightButtonGroup = new htmlGroup(); $refreshButton = new htmlButton('refresh', 'refresh.png', true); $refreshButton->setTitle(_("Refresh")); - $right->addElement($refreshButton); - $right->addElement(new htmlSpacer('1px', null)); + $rightButtonGroup->addElement($refreshButton); $settingsLink = new htmlLink('', '#', '../../graphics/tools.png'); $settingsLink->setOnClick('listShowSettingsDialog(\'' . _('Change list settings') . '\', \'' . _('Ok') . '\', \'' . _('Cancel') . '\');'); $settingsLink->setTitle(_('Change settings')); - $right->addElement($settingsLink); + $rightButtonGroup->addElement($settingsLink); + $right->add($rightButtonGroup, 12, 12, 2); $this->addExtraInputElementsToTopArea($left, $right); - $table->addElement($left); - $table->addElement($right); - parseHtml(null, $table, array(), false, $this->tabindex, $this->type->getScope()); + $row->add($left, 12, 6, 6, 'text-left'); + $row->add($right, 12, 6, 6, 'text-right'); + parseHtml(null, $row, array(), false, $this->tabindex, $this->type->getScope()); } /** diff --git a/lam/lib/types/dhcp.inc b/lam/lib/types/dhcp.inc index 7d760171..71da7382 100644 --- a/lam/lib/types/dhcp.inc +++ b/lam/lib/types/dhcp.inc @@ -272,9 +272,9 @@ class lamDHCPList extends lamList { */ protected function addExtraInputElementsToTopArea(&$left, &$right) { if (checkIfWriteAccessIsAllowed($this->type->getId())) { - $left->addElement(new htmlSpacer('20px', null)); $dhcpButton = new htmlButton('dhcpDefaults', $this->labels['dhcpDefaults']); $dhcpButton->setIconClass('settingsButton'); + $dhcpButton->setCSSClasses(array('fullwidth-mobile-only')); $left->addElement($dhcpButton); } } diff --git a/lam/style/responsive/120_lam.css b/lam/style/responsive/120_lam.css index 6a3320eb..64f8a49c 100644 --- a/lam/style/responsive/120_lam.css +++ b/lam/style/responsive/120_lam.css @@ -145,6 +145,10 @@ table.responsive-table td { font-weight: bold; } + .fullwidth-mobile-only { + width: 100%; + } + } /* tablet */ From ec5fcebd7fcd99a05cbeaf37cdcfce53bfd5ea02 Mon Sep 17 00:00:00 2001 From: Roland Gruber Date: Fri, 26 Oct 2018 20:13:13 +0200 Subject: [PATCH 3/9] responsive navigation --- lam/lib/lists.inc | 71 ++++++++++++++++++++++++++++------------------- 1 file changed, 43 insertions(+), 28 deletions(-) diff --git a/lam/lib/lists.inc b/lam/lib/lists.inc index 2bb8d29b..01088254 100644 --- a/lam/lib/lists.inc +++ b/lam/lib/lists.inc @@ -312,23 +312,27 @@ class lamList { */ protected function listDrawNavigationBar($count) { $filter = $this->getFilterAsTextForURL(); - echo("\n"); - echo("\n"); - echo(""); - + $row = new htmlResponsiveRow(); + $row->setCSSClasses(array('maxrow')); + $countLabel = new htmlOutputText(sprintf($this->labels['nav'], $count)); + $row->add($countLabel, 12, 6, 6); + $navGroup = new htmlGroup(); if ($count > $this->maxPageEntries) { - echo(""; } - echo "
"); - printf($this->labels['nav'], $count); - echo(""); if ($this->page != 1) { - echo("type->getId() . "&norefresh=true&page=1" . - "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter . "\">" . - "\"\"\n"); + $linkHref = "list.php?type=" . $this->type->getId() . "&norefresh=true&page=1" . + "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter; + $link = new htmlLink(null, $linkHref, '../../graphics/go-first.png'); + $link->setTitle(_('Jump to first page')); + $link->setCSSClasses(array('margin5')); + $navGroup->addElement($link); } if ($this->page > 11) { - echo("type->getId() . "&norefresh=true&page=" . ($this->page - 10) . - "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter . "\">" . - "\"\"\n"); + $linkHref = "list.php?type=" . $this->type->getId() . "&norefresh=true&page=" . ($this->page - 10) . + "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter; + $link = new htmlLink(null, $linkHref, '../../graphics/go-previous.png'); + $link->setTitle(_('Jump 10 pages backward')); + $link->setCSSClasses(array('margin5')); + $navGroup->addElement($link); } $pageCount = ceil($count / $this->maxPageEntries); for ($i = $this->page - 6; $i < ($this->page + 5); $i++) { @@ -339,30 +343,41 @@ class lamList { continue; } if ($i == $this->page - 1) { - $url = "list.php?type=" . $this->type->getId() . "&norefresh=true" . - "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter; - echo ''; + $url = "list.php?type=" . $this->type->getId() . "&norefresh=true" . + "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter; + $navInput = new htmlInputField('listNavPage', ($i + 1)); + $navInput->setMinimumAndMaximumNumber(1, $pageCount); + $navInput->setCSSClasses(array('listPageInput')); + $navInput->setOnKeyPress('listPageNumberKeyPress(\'' . $url . '\', event);'); + $navGroup->addElement($navInput); } else { - echo " type->getId() . "&norefresh=true&page=" . ($i + 1) . - "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter . "\">" . ($i + 1) . "\n"; + $linkHref = "list.php?type=" . $this->type->getId() . "&norefresh=true&page=" . ($i + 1) . + "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter; + $link = new htmlLink(($i + 1), $linkHref); + $link->setCSSClasses(array('margin5')); + $navGroup->addElement($link); } } if ($this->page < ($pageCount - 10)) { - echo("type->getId() . "&norefresh=true&page=" . ($this->page + 10) . - "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter . "\">" . - "\"\"\n"); + $linkHref = "list.php?type=" . $this->type->getId() . "&norefresh=true&page=" . ($this->page + 10) . + "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter; + $link = new htmlLink(null, $linkHref, '../../graphics/go-next.png'); + $link->setTitle(_('Jump 10 pages forward')); + $link->setCSSClasses(array('margin5')); + $navGroup->addElement($link); } if ($this->page < $pageCount) { - echo("type->getId() . "&norefresh=true&page=" . $pageCount . - "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter . "\">" . - "\"\"\n"); + $linkHref = "list.php?type=" . $this->type->getId() . "&norefresh=true&page=" . $pageCount . + "&sort=" . $this->sortColumn . "&sortdirection=" . $this->sortDirection . $filter; + $link = new htmlLink(null, $linkHref, '../../graphics/go-last.png'); + $link->setTitle(_('Jump to last page')); + $link->setCSSClasses(array('margin5')); + $navGroup->addElement($link); } - echo "
\n"; + $row->add($navGroup, 12, 6, 6, 'responsiveLabel'); + parseHtml(null, $row, array(), false, $this->tabindex, $this->type->getScope()); } /** From aa921cadf867a94fff18c6a8234124e381e79913 Mon Sep 17 00:00:00 2001 From: Roland Gruber Date: Sat, 27 Oct 2018 11:42:45 +0200 Subject: [PATCH 4/9] responsive settings dialog --- lam/lib/lists.inc | 30 +++++++++++++----------------- lam/style/responsive/120_lam.css | 5 +++++ 2 files changed, 18 insertions(+), 17 deletions(-) diff --git a/lam/lib/lists.inc b/lam/lib/lists.inc index 01088254..141260f5 100644 --- a/lam/lib/lists.inc +++ b/lam/lib/lists.inc @@ -1171,20 +1171,18 @@ class lamList { * Prints the list configuration page. */ protected function listPrintConfigurationPage() { - echo "
\n"; + echo "
\n"; echo "
type->getId() . "&norefresh=true\" method=\"post\">\n"; - echo '
'; - $configContainer = new htmlTable(); + $configContainer = new htmlResponsiveRow(); for ($i = 0; $i < sizeof($this->configOptions); $i++) { - $configContainer->mergeTableElements($this->configOptions[$i]->getMetaHTML()); + $configContainer->add($this->configOptions[$i]->getMetaHTML(), 12); } - $configContainer->addElement(new htmlHiddenInput('saveConfigOptions', 'ok')); + $configContainer->add(new htmlHiddenInput('saveConfigOptions', 'ok'), 12); addSecurityTokenToMetaHTML($configContainer); parseHtml('', $configContainer, array(), false, $this->tabindex, $this->type->getScope()); - echo "
\n"; echo '
'; echo "
\n"; } @@ -1364,7 +1362,7 @@ abstract class lamListOption { /** * Returns the meta HTML data to display this option. * - * @return htmlTable meta HTML + * @return htmlResponsiveRow meta HTML */ public abstract function getMetaHTML(); @@ -1417,13 +1415,12 @@ class lamBooleanListOption extends lamListOption { } /** - * Returns the meta HTML data to display this option. - * - * @return htmlTable meta HTML + * {@inheritDoc} + * @see lamListOption::getMetaHTML() */ public function getMetaHTML() { - $return = new htmlTable(); - $return->addElement(new htmlTableExtendedInputCheckbox($this->getID(), $this->isSelected(), $this->name)); + $return = new htmlResponsiveRow(); + $return->add(new htmlResponsiveInputCheckbox($this->getID(), $this->isSelected(), $this->name), 12); return $return; } @@ -1482,13 +1479,12 @@ class lamSelectListOption extends lamListOption { } /** - * Returns the meta HTML data to display this option. - * - * @return htmlTable meta HTML + * {@inheritDoc} + * @see lamListOption::getMetaHTML() */ public function getMetaHTML() { - $return = new htmlTable(); - $return->addElement(new htmlTableExtendedSelect($this->getID(), $this->options, array($this->getValue()), $this->name, $this->helpID)); + $return = new htmlResponsiveRow(); + $return->add(new htmlResponsiveSelect($this->getID(), $this->options, array($this->getValue()), $this->name, $this->helpID), 12); return $return; } diff --git a/lam/style/responsive/120_lam.css b/lam/style/responsive/120_lam.css index 64f8a49c..cac4b3f8 100644 --- a/lam/style/responsive/120_lam.css +++ b/lam/style/responsive/120_lam.css @@ -61,6 +61,11 @@ div.lam-dialog-msg { margin: 10px; } +div.dialog-content { + overflow: visible !important; + margin: 2rem; +} + table.padding5 td { padding: 0.5rem; } From 62ae3267d20cad9390f4acd5f137bda3ef0bed50 Mon Sep 17 00:00:00 2001 From: Roland Gruber Date: Sat, 27 Oct 2018 14:39:37 +0200 Subject: [PATCH 5/9] responsive table head --- lam/graphics/downarrows-black.png | Bin 0 -> 719 bytes lam/graphics/downarrows.png | Bin 0 -> 801 bytes lam/graphics/uparrows-black.png | Bin 0 -> 686 bytes lam/graphics/uparrows.png | Bin 0 -> 764 bytes lam/lib/html.inc | 48 +++++++++++++- lam/lib/lists.inc | 101 +++++++++++++++++++++++++++++- lam/style/responsive/120_lam.css | 10 ++- 7 files changed, 151 insertions(+), 8 deletions(-) create mode 100644 lam/graphics/downarrows-black.png create mode 100644 lam/graphics/downarrows.png create mode 100644 lam/graphics/uparrows-black.png create mode 100644 lam/graphics/uparrows.png diff --git a/lam/graphics/downarrows-black.png b/lam/graphics/downarrows-black.png new file mode 100644 index 0000000000000000000000000000000000000000..644428ad96467689ca5d348b67328cc42418f6df GIT binary patch literal 719 zcmV;=0xClWT3W=RiIYq~N=sYbeLr};_jBK*^B|%juY-ut@Aokn4Bj^yja>ks)zww;FR~lQ@sCoeG^e#rlOzE%!*yLqDd9K{ zgb=xli;K!&FnGYsmYLba5{*LB?k-}g&t zntpMjDEc`)JuQpH;;hyh?RFc+7?H&%B1kF0%uq_9SS-#MV`i9{Pfkv@oo2K7aejXO z9y4!blaeGEnQW~czQX0@CDJrSr_*^|uh+{001giiH_y(_c7za6N`Z)O{DCYHGo#n* z?bYk`cK{$Vf$#gz&d<+(<@0&uayg8Hh#-VOzu*7E%C^75RN z^1I_WDh$Ji)oOL`R$=zmw{dA{>DA)m;@1B(e*xd?bG#kbBdq`c002ovPDHLkV1iV~ BN6r8M literal 0 HcmV?d00001 diff --git a/lam/graphics/downarrows.png b/lam/graphics/downarrows.png new file mode 100644 index 0000000000000000000000000000000000000000..8507145c166a980a91ca9e7892ce9d330f8418b0 GIT binary patch literal 801 zcmV++1K#|JP)2wJr$XzXCxw5hfsDU(i`Ka+GO&b)au@4kCo7>hRQfwMV$=i~4@BKN|# zlR-ZBQm|h)T9Fn)8>~*SiGjp`5MT_}0>)wzgKLaE+VABWx3@nK_nxVZ^;d3|pDYgd zEN^#+BaP`M*f<6Y?m#aplST#}()Z9paKumeVe(x4Le+g(SZgVKxbbX%eWkQ-U_VzY zZQ^zp8^u^_NsSaxxd12YBYJ#N9)wfpSzpn|b*VTd0X8T4Kd-DeO0KII&buf_A(TWa zi4Y+8vm6)n_hoiA?7O;DoB|MoXSbv^32~@Bs!Kl~J32aky&A@~S_fkc-hq2i*#Om- zAsctx^_lteVWgkZU1Ow4tke8%_U%-rFyZI*wiy~pE!T}1=yQqM2~j7((Fro@l5R8! zudf>Edxvsqr~E+PEu^FBmyT{$E{=~KQ^iLaTf80d&9x?pi%eta>I9)Aj_-m=kPjZB zc+ekiCk&4+EZV8r-boc-nZ9!J(;26oA1a33nDu(h@1Z8{XyQ15o&Y=t9r%d847Y@! zF~7>!=ayfuO+N971ZbW)e(F;Ba>?}^Mhh-d3St9xH$E!_(p8`!xYc0or={uWv*J4d zayMZ7(IYR;U0j+U?DfcJ9juff#hnjWA<1-Nwtrl_(M3%BwRcCbabhU8g@eysT3Bfv z9`Fc!i50sS0BHs7@{(=TqgPvJA79%e0N8qM`08eL^>nQ*I6RobaU}*&j>4&IP`g=w zqxJD)Gk@RthX5e_=$W@J&;9y^=P5=CE=WNTw%J_V{0di{x|`o40PqIyd;Y@Q^0fo| zQrw>t>{PbaG`zg?{v-BoR#>}d20-@B-^NGc+H6)y|Cg5kbokyw)Bg%uYyY!zCl^li fyfT0K|Cm1juflU7%yYIX00000NkvXXu0mjf_tto# literal 0 HcmV?d00001 diff --git a/lam/graphics/uparrows-black.png b/lam/graphics/uparrows-black.png new file mode 100644 index 0000000000000000000000000000000000000000..8573bdc2889b084bd2dc92866f77bceb08ea34fb GIT binary patch literal 686 zcmV;f0#W^mP)Pl97#|~Dm%|4xA8U*$Q5E2u`!l57B+T5gjiTw_yz1L1g%z! zi0GB)d2?x+B281&>-DQACns;tMPQ8C@qPbh=`l@HXsuDN*Y7kMjc0%3$1(`R@Rktb zqvv^)=Q)&8$nzYQWuaQF;`sRZC+B>1Z*TA083kb&&e^v8QV2m>>#{nwOUPN zS@w2gW8=aZ0wUV2R4R*FYfNgUC<+XRL(I&~TuYMV^%%j*%F2@<2sVkR%wgOo(O4d{ zv$I=EOG`TdKv5L6=jZ1?6A@XKg*c8;T98trC<<`S!5D*-617?lLI}ih93LGWJ>-t# z+#d`E-6TnR00PeWCD(P8lyaoR7z4*~U|E(G$MN@Wx0@MbE_$AKo%j3w2lRUw=lqip z;)>QV*mgE07*qoM6N<$f_^_NN&o-= literal 0 HcmV?d00001 diff --git a/lam/graphics/uparrows.png b/lam/graphics/uparrows.png new file mode 100644 index 0000000000000000000000000000000000000000..76478479cee7e599ccfc32eba987e11fc9f4c9f4 GIT binary patch literal 764 zcmV1v7?m3ycGs#Rc`7!BCr^z%mHPkjTRST`9l-6BJH;sanq74d$qDY}aH!317 z)QxV;Mi4<16?AKjl(vh~P__S+R#Fq1H0iXNNtm15d(Sy8EEO@9e(-HxULIb)_rp2I z|83Lo`46(MT{`q2k8sYh(xl$_b?}LF@I%em;D&B{s`hr@g_V4AB{BQ@*+Rxwqh@W9 zQh(mp)tleu-o2K5C_v`WxKQv}rr6qfz3P~{z0Br;o=3y!KfZjp1d%z~-rK&bp7Oyu zZp=l5p<%DRq&$bns--(MInAjkJII>)wUZ%}=wC7hHZvANTu@wR7 z7f*I(o0FgV<&s!3AnxhHIqHGs>P*PS{?%zQ_vcp~AK%pf0W{!7b6a}57ZV!cEC3F` zI)t@UYBAIEAp@IAj|UT1zW5g)`TW?Mollnr>s?teU?YRLSFgaKC0Og2n2U(Qn2qHP zLyfO~e-uDG_QR=t zqt{e_ZvMc9sr2ln-^S;RklA!5nV0KUnYbR}jKwOCB_!Rg8ZY#`6EkM&)WzSImntf! z8jG9MPuKlnE2}~^NSR8iA5+itt*+^WF?JCX#)P3EjvX_1Bi7}$JbiAWM!xi'; + $onClick = ''; + if (!empty($this->onClick)) { + $onClick = ' onclick="' . $this->onClick . '"'; + } + echo ''; echo $script; if ($this->transient) { return array(); @@ -2250,6 +2256,15 @@ class htmlInputCheckbox extends htmlElement { return 'tr'; } + /** + * Sets the onclick code. + * + * @param string $code JS code + */ + public function setOnClick($code) { + $this->onClick = $code; + } + } /** @@ -4663,6 +4678,10 @@ class htmlResponsiveTable extends htmlElement { /** highlighted rows */ private $highlighted = array(); + /** CSS class for odd row numbers */ + private $cssOddRow; + /** CSS class for even row numbers */ + private $cssEvenRow; /** * Creates the table. @@ -4689,7 +4708,8 @@ class htmlResponsiveTable extends htmlElement { $classes[] = 'responsive-table'; echo ''; echo ''; - echo ''; + $headClass = empty($this->cssOddRow) ? '' : ' class="' . $this->cssOddRow . '"'; + echo ''; $counter = 0; foreach ($this->titles as $title) { $width = ''; @@ -4706,8 +4726,18 @@ class htmlResponsiveTable extends htmlElement { $counter = 0; foreach ($this->data as $row) { $cssClass = ''; + $cssClasses = array(); if (in_array($counter, $this->highlighted)) { - $cssClass = ' class="bold"'; + $cssClasses[] = 'bold'; + } + if (!empty($this->cssEvenRow) && ($counter % 2 === 0)) { + $cssClasses[] = $this->cssEvenRow; + } + if (!empty($this->cssOddRow) && ($counter % 2 === 1)) { + $cssClasses[] = $this->cssOddRow; + } + if (!empty($cssClasses)) { + $cssClass = ' class="' . implode(' ', $cssClasses) . '"'; } echo ''; for ($i = 0; $i < $titleCount; $i++) { @@ -4728,6 +4758,18 @@ class htmlResponsiveTable extends htmlElement { $this->widths = $widths; } + /** + * Sets the CSS classes for odd and even rows. + * The title row counts as row number -1. + * + * @param string $oddClass class for odd rows + * @param string $evenClass class for even rows + */ + public function setRowClasses($oddClass, $evenClass) { + $this->cssOddRow = $oddClass; + $this->cssEvenRow = $evenClass; + } + } diff --git a/lam/lib/lists.inc b/lam/lib/lists.inc index 141260f5..0003e85c 100644 --- a/lam/lib/lists.inc +++ b/lam/lib/lists.inc @@ -202,6 +202,7 @@ class lamList { $this->listDrawNavigationBar(sizeof($this->entries)); echo ("
\n"); echo "
"; + $this->printAccountTable($this->entries); // account table head $this->listPrintTableHeader(); // account table body @@ -215,6 +216,8 @@ class lamList { // navigation bar $this->listDrawNavigationBar(sizeof($this->entries)); echo ("
\n"); + $accounts = array(); + $this->printAccountTable($accounts); // account table head $this->listPrintTableHeader(); echo "

\n"; @@ -388,11 +391,105 @@ class lamList { protected function getFilterAsTextForURL() { $text = ''; foreach ($this->filters as $attr => $filter) { - $text .= "&filter" . strtolower($attr) . '=' . $filter; + $text .= "&filter" . strtolower($attr) . '=' . $filter; } return $text; } + /** + * Prints the entry list + * + * @param array $info entries + */ + private function printAccountTable(&$info) { + $scope = $this->type->getScope(); + $titles = $this->descArray; + array_unshift($titles, _('Actions')); + $data = array(); + $data[] = $this->getSortingElements(); + $data[] = $this->getFilterElements(); + + $table = new htmlResponsiveTable($titles, $data); + $table->setRowClasses($scope . '-dark', $scope . '-bright'); + $table->setCSSClasses(array($scope . '-border accountlist')); + + parseHtml(null, $table, array(), false, $this->tabindex, $scope); + } + + /** + * Returns the elements to show in sorting row. + * + * @return htmlElement[] elements + */ + private function getSortingElements() { + $filter = $this->getFilterAsTextForURL(); + $sortElements = array(new htmlOutputText(_('Sort sequence'))); + foreach ($this->attrArray as $attributeName) { + $link = "list.php?type=" . $this->type->getId() . "&". + "sort=" . strtolower($attributeName) . $filter . "&norefresh=y"; + $buttons = new htmlGroup(); + if (strtolower($attributeName) == $this->sortColumn) { + if ($this->sortDirection < 0) { + $buttons->addElement(new htmlLink(null, $link . '&sortdirection=1', '../../graphics/downarrows.png')); + $buttons->addElement(new htmlLink(null, $link . '&sortdirection=-1', '../../graphics/uparrows-black.png')); + } + else { + $buttons->addElement(new htmlLink(null, $link . '&sortdirection=1', '../../graphics/downarrows-black.png')); + $buttons->addElement(new htmlLink(null, $link . '&sortdirection=-1', '../../graphics/uparrows.png')); + } + } + else { + $buttons->addElement(new htmlLink(null, $link . '&sortdirection=1', '../../graphics/downarrows.png')); + $buttons->addElement(new htmlLink(null, $link . '&sortdirection=-1', '../../graphics/uparrows.png')); + } + $sortElements[] = $buttons; + } + return $sortElements; + } + + /** + * Returns the elements to show in filter row. + * + * @return htmlElement[] elements + */ + private function getFilterElements() { + $actionElement = new htmlGroup(); + $selectAll = new htmlInputCheckbox('tableSelectAll', false); + $selectAll->setCSSClasses(array('align-middle')); + $selectAll->setOnClick('list_switchAccountSelection();'); + $actionElement->addElement($selectAll); + $actionElement->addElement(new htmlSpacer('1rem', null)); + $actionElement->addElement(new htmlOutputText(_('Filter'))); + $filterButton = new htmlButton('apply_filter', 'filter.png', true); + $filterButton->setTitle(_("Here you can input simple filter expressions (e.g. 'value' or 'v*'). The filter is case-insensitive.")); + $actionElement->addElement($filterButton); + if (sizeof($this->filters) > 0) { + $clearFilterButton = new htmlButton('clear_filter', 'clearFilter.png', true); + $clearFilterButton->setTitle(_('Clear filter')); + $actionElement->addElement($clearFilterButton); + } + + $filterElements = array($actionElement); + $clearFilter = isset($_POST['clear_filter']); + foreach ($this->attrArray as $attributeName) { + $attributeName = strtolower($attributeName); + if ($this->canBeFiltered($attributeName)) { + $value = ""; + if (!$clearFilter && isset($this->filters[$attributeName])) { + $value = $this->filters[$attributeName]; + } + $filterInput = new htmlInputField('filter' . $attributeName, $value); + $filterInput->setCSSClasses(array($this->type->getScope() . '-bright')); + $filterInput->setOnKeyPress("SubmitForm('apply_filter', event);"); + $filterElements[] = $filterInput; + } + else { + $filterElements[] = new htmlOutputText(''); + } + } + return $filterElements; + } + /** * Prints the attribute and filter row at the account table head */ @@ -981,7 +1078,7 @@ class lamList { } // get sort order if (isset($_GET['sortdirection'])) { - $this->sortDirection = $_GET['sortdirection']; + $this->sortDirection = htmlspecialchars($_GET['sortdirection']); } // check search suffix if (isset($_POST['suffix'])) { diff --git a/lam/style/responsive/120_lam.css b/lam/style/responsive/120_lam.css index cac4b3f8..5c207838 100644 --- a/lam/style/responsive/120_lam.css +++ b/lam/style/responsive/120_lam.css @@ -78,11 +78,15 @@ table.responsive-table { margin-top: 1rem; table-layout: fixed; width: 100%; + border-collapse: collapse; } table.responsive-table th { text-align: left; - padding: 0; + padding-bottom: 0.5rem; + padding-top: 0.5rem; + padding-right: 0.3rem; + padding-left: 0.3rem; } table.responsive-table td { @@ -90,8 +94,8 @@ table.responsive-table td { vertical-align: top; padding-bottom: 0.5rem; padding-top: 0.5rem; - padding-right: 0.1rem; - padding-left: 0.1rem; + padding-right: 0.3rem; + padding-left: 0.3rem; word-break: break-all; } From fe5260b5e6fc010be91507d62b45337c291167cd Mon Sep 17 00:00:00 2001 From: Roland Gruber Date: Sat, 27 Oct 2018 16:42:31 +0200 Subject: [PATCH 6/9] click and double click events for rows --- lam/lib/html.inc | 32 +++++++++++++++++++++++++++++++- 1 file changed, 31 insertions(+), 1 deletion(-) diff --git a/lam/lib/html.inc b/lam/lib/html.inc index e6d38819..d62cbeb9 100644 --- a/lam/lib/html.inc +++ b/lam/lib/html.inc @@ -4682,6 +4682,10 @@ class htmlResponsiveTable extends htmlElement { private $cssOddRow; /** CSS class for even row numbers */ private $cssEvenRow; + /** onclick code (row number => code) */ + private $onClick = array(); + /** ondoubleclick code (row number => code) */ + private $onDoubleClick = array(); /** * Creates the table. @@ -4739,7 +4743,15 @@ class htmlResponsiveTable extends htmlElement { if (!empty($cssClasses)) { $cssClass = ' class="' . implode(' ', $cssClasses) . '"'; } - echo ''; + $onClick = ''; + if (!empty($this->onClick[$counter])) { + $onClick = ' onclick="' . $this->onClick[$counter] . '"'; + } + $onDoubleClick = ''; + if (!empty($this->onDoubleClick[$counter])) { + $onDoubleClick = ' ondblclick="' . $this->onDoubleClick[$counter] . '"'; + } + echo ''; for ($i = 0; $i < $titleCount; $i++) { echo ''; $ids = parseHtml($module, $row[$i], $values, $restricted, $tabindex, $scope); @@ -4770,6 +4782,24 @@ class htmlResponsiveTable extends htmlElement { $this->cssEvenRow = $evenClass; } + /** + * Sets the onclick code for the rows. + * + * @param array $calls row number => code + */ + public function setOnClickEvents($calls) { + $this->onClick = $calls; + } + + /** + * Sets the ondoubleclick code for the rows. + * + * @param array $calls row number => code + */ + public function setOnDoubleClickEvents($calls) { + $this->onDoubleClick = $calls; + } + } From dec9585733eb954060466b06ed572b217f7663cd Mon Sep 17 00:00:00 2001 From: Roland Gruber Date: Sat, 27 Oct 2018 16:43:04 +0200 Subject: [PATCH 7/9] added row events and tools --- lam/lib/lists.inc | 91 +++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 91 insertions(+) diff --git a/lam/lib/lists.inc b/lam/lib/lists.inc index 0003e85c..82aaf494 100644 --- a/lam/lib/lists.inc +++ b/lam/lib/lists.inc @@ -408,10 +408,15 @@ class lamList { $data = array(); $data[] = $this->getSortingElements(); $data[] = $this->getFilterElements(); + $onClickEvents = array(); + $onDoubleClickEvents = array(); + $this->addDataElements($data, $info, $onClickEvents, $onDoubleClickEvents); $table = new htmlResponsiveTable($titles, $data); $table->setRowClasses($scope . '-dark', $scope . '-bright'); $table->setCSSClasses(array($scope . '-border accountlist')); + $table->setOnClickEvents($onClickEvents); + $table->setOnDoubleClickEvents($onDoubleClickEvents); parseHtml(null, $table, array(), false, $this->tabindex, $scope); } @@ -490,8 +495,91 @@ class lamList { return $filterElements; } + /** + * Adds the LDAP data elements to the given array. + * + * @param array $data data for responsible table + * @param array $info entries + * @param array $onClickEvents row number => code + * @param array $onDoubleClickEvents row number => code + */ + private function addDataElements(&$data, &$info, &$onClickEvents, &$onDoubleClickEvents) { + // calculate which rows to show + $table_begin = ($this->page - 1) * $this->maxPageEntries; + if (($this->page * $this->maxPageEntries) > sizeof($info)) $table_end = sizeof($info); + else $table_end = ($this->page * $this->maxPageEntries); + // get sort mapping + $sortMapping = &$this->sortMapping; + if (empty($sortMapping)) { + $sortMapping = array(); + $infoSize = sizeof($info); + for ($i = 0; $i < $infoSize; $i++) { + $sortMapping[$i] = $i; + } + } + // print account list + for ($i = $table_begin; $i < $table_end; $i++) { + $row = array(); + $index = $sortMapping[$i]; + $rowID = base64_encode($info[$index]['dn']); + $actionElement = new htmlGroup(); + $checkbox = new htmlInputCheckbox($rowID, false); + $checkbox->setOnClick("list_click('" . $rowID . "');"); + $checkbox->setCSSClasses(array('accountBoxUnchecked align-middle')); + $actionElement->addElement($checkbox); + $actionElement->addElement(new htmlSpacer('0.5rem', null)); + $onClickEvents[$i + 2] = "list_click('" . $rowID . "');"; + $onDoubleClickEvents[$i + 2] = "top.location.href='../account/edit.php?type=" . $this->type->getId() . "&DN=" . rawurlencode($info[$index]['dn']) . "';"; + $this->addToolLinks($info[$index], $rowID, $actionElement); + $row[] = $actionElement; + foreach ($this->attrArray as $attributeName) { + $attributeName = strtolower($attributeName); + $row[] = new htmlOutputText($attributeName); // TODO + //$this->listPrintTableCellContent($info[$index], $attributeName); + } + $data[] = $row; + } + } + + /** + * Adds the tool image links (e.g. edit and delete) for each account. + * + * @param array $account LDAP attributes + * @param String $id account ID + * @param htmlGroup $element location where to add tools + */ + private function addToolLinks($account, $id, &$element) { + $toolCount = 0; + // edit link + $editLink = new htmlLink('', "../account/edit.php?type=" . $this->type->getId() . "&DN='" . rawurlencode($account['dn']) . "'", '../../graphics/edit.png'); + $editLink->setTitle(_("Edit")); + $element->addElement($editLink); + $toolCount++; + // delete link + if (checkIfWriteAccessIsAllowed($this->type->getId()) && checkIfDeleteEntriesIsAllowed($this->type->getId())) { + $deleteLink = new htmlLink('', "deletelink.php?type=" . $this->type->getId() . "&DN='" . rawurlencode($account['dn']) . "'", '../../graphics/delete.png'); + $deleteLink->setTitle(_("Delete")); + $element->addElement($deleteLink); + $toolCount++; + } + // PDF button + $pdfButton = new htmlButton("createPDF_" . $id, 'pdf.png', true); + $pdfButton->setTitle(_('Create PDF file')); + $element->addElement($pdfButton); + $toolCount++; + // additional tools + $tools = $this->getAdditionalTools(); + for ($i = 0; $i < sizeof($tools); $i++) { + $toolLink = new htmlLink('', $tools[$i]->getLinkTarget() . "?type=" . $this->type->getId() . "&DN='" . rawurlencode($account['dn']) . "'", '../../graphics/' . $tools[$i]->getImage()); + $toolLink->setTitle($tools[$i]->getName()); + $element->addElement($toolLink); + $toolCount++; + } + } + /** * Prints the attribute and filter row at the account table head + * @deprecated */ protected function listPrintTableHeader() { $filter = $this->getFilterAsTextForURL(); @@ -551,6 +639,7 @@ class lamList { * * @param String $attrName attribute name * @param boolean $clearFilter true if filter value should be cleared + * @deprecated */ protected function printFilterArea($attrName, $clearFilter) { $value = ""; @@ -582,6 +671,7 @@ class lamList { * Prints the entry list * * @param array $info entries + * @deprecated */ protected function listPrintTableBody(&$info) { echo "\n"; @@ -638,6 +728,7 @@ class lamList { * * @param array $account LDAP attributes * @param String $id account ID + * @deprecated */ private function listPrintToolLinks($account, $id) { $toolCount = 0; From 985828da3a29eb90943cfe3dc05faeda1b588e3b Mon Sep 17 00:00:00 2001 From: Roland Gruber Date: Sun, 28 Oct 2018 10:11:45 +0100 Subject: [PATCH 8/9] responsive account table --- lam/lib/lists.inc | 206 ++--------------------------------- lam/lib/types/group.inc | 16 +-- lam/lib/types/user.inc | 46 ++++---- lam/templates/lib/500_lam.js | 17 --- 4 files changed, 37 insertions(+), 248 deletions(-) diff --git a/lam/lib/lists.inc b/lam/lib/lists.inc index 82aaf494..aa1fc07d 100644 --- a/lam/lib/lists.inc +++ b/lam/lib/lists.inc @@ -201,13 +201,7 @@ class lamList { // navigation bar $this->listDrawNavigationBar(sizeof($this->entries)); echo ("
\n"); - echo "
"; $this->printAccountTable($this->entries); - // account table head - $this->listPrintTableHeader(); - // account table body - $this->listPrintTableBody($this->entries); - echo "
"; } else { // buttons @@ -218,8 +212,6 @@ class lamList { echo ("
\n"); $accounts = array(); $this->printAccountTable($accounts); - // account table head - $this->listPrintTableHeader(); echo "
\n"; } $this->printFooter(); @@ -474,7 +466,7 @@ class lamList { $actionElement->addElement($clearFilterButton); } - $filterElements = array($actionElement); + $filterElements = array(new htmlDiv(null, $actionElement, array('nowrap'))); $clearFilter = isset($_POST['clear_filter']); foreach ($this->attrArray as $attributeName) { $attributeName = strtolower($attributeName); @@ -483,7 +475,7 @@ class lamList { if (!$clearFilter && isset($this->filters[$attributeName])) { $value = $this->filters[$attributeName]; } - $filterInput = new htmlInputField('filter' . $attributeName, $value); + $filterInput = new htmlInputField('filter' . $attributeName, $value, null); $filterInput->setCSSClasses(array($this->type->getScope() . '-bright')); $filterInput->setOnKeyPress("SubmitForm('apply_filter', event);"); $filterElements[] = $filterInput; @@ -531,11 +523,10 @@ class lamList { $onClickEvents[$i + 2] = "list_click('" . $rowID . "');"; $onDoubleClickEvents[$i + 2] = "top.location.href='../account/edit.php?type=" . $this->type->getId() . "&DN=" . rawurlencode($info[$index]['dn']) . "';"; $this->addToolLinks($info[$index], $rowID, $actionElement); - $row[] = $actionElement; + $row[] = new htmlDiv(null, $actionElement, array('nowrap')); foreach ($this->attrArray as $attributeName) { $attributeName = strtolower($attributeName); - $row[] = new htmlOutputText($attributeName); // TODO - //$this->listPrintTableCellContent($info[$index], $attributeName); + $row[] = $this->getTableCellContent($info[$index], $attributeName); } $data[] = $row; } @@ -577,84 +568,6 @@ class lamList { } } - /** - * Prints the attribute and filter row at the account table head - * @deprecated - */ - protected function listPrintTableHeader() { - $filter = $this->getFilterAsTextForURL(); - // print table header - echo "type->getScope() . "-border collapse accountlist ui-corner-all\" width=\"100%\">\n"; - echo "type->getScope() . "-dark\">\n"; - echo "\n"; - echo "\n"; - // table header - for ($k = 0; $k < sizeof($this->descArray); $k++) { - if (strtolower($this->attrArray[$k]) == $this->sortColumn) { - $sortImage = "sort_asc.png"; - if ($this->sortDirection < 0) { - $sortImage = "sort_desc.png"; - } - echo "\n"; - } - else echo "\n"; - } - echo "\n"; - - // print filter row - echo "type->getScope() . "-bright\">\n"; - echo "\n"; - echo "\n"; - // print input boxes for filters - for ($k = 0; $k < sizeof($this->descArray); $k++) { - echo "\n"; - } - echo "\n"; - } - - /** - * Prints the content of a single attribute filter area. - * - * @param String $attrName attribute name - * @param boolean $clearFilter true if filter value should be cleared - * @deprecated - */ - protected function printFilterArea($attrName, $clearFilter) { - $value = ""; - if (!$clearFilter) { - if (isset($this->filters[strtolower($attrName)])) { - $value = $this->filters[strtolower($attrName)]; - } - } - $filterInput = new htmlInputField('filter' . strtolower($attrName), $value); - $filterInput->setCSSClasses(array($this->type->getScope() . '-dark')); - $filterInput->setFieldSize('15'); - $filterInput->setOnKeyPress("SubmitForm('apply_filter', event);"); - parseHtml(null, $filterInput, array(), false, $this->tabindex, $this->type->getScope()); - } - /** * Returns if the given attribute can be filtered. * If filtering is not possible then no filter box will be displayed. @@ -668,123 +581,27 @@ class lamList { } /** - * Prints the entry list - * - * @param array $info entries - * @deprecated - */ - protected function listPrintTableBody(&$info) { - echo "\n"; - // calculate which rows to show - $table_begin = ($this->page - 1) * $this->maxPageEntries; - if (($this->page * $this->maxPageEntries) > sizeof($info)) $table_end = sizeof($info); - else $table_end = ($this->page * $this->maxPageEntries); - // get sort mapping - $sortMapping = &$this->sortMapping; - if (empty($sortMapping)) { - $sortMapping = array(); - $infoSize = sizeof($info); - for ($i = 0; $i < $infoSize; $i++) { - $sortMapping[$i] = $i; - } - } - // print account list - for ($i = $table_begin; $i < $table_end; $i++) { - $index = $sortMapping[$i]; - $rowID = base64_encode($info[$index]['dn']); - if ((($i - $table_begin) % 2) == 1) { - $classes = ' ' . $this->type->getScope() . '-bright'; - } - else { - $classes = ' ' . $this->type->getScope() . '-dark'; - } - echo("type->getId() . "&DN=" . rawurlencode($info[$index]['dn']) . "'\">\n"); - echo " \n"; - $this->listPrintToolLinks($info[$index], $rowID); - for ($k = 0; $k < sizeof($this->attrArray); $k++) { - echo ("\n"); - } - echo("\n"); - } - // display select all link - $colspan = sizeof($this->attrArray) + 1; - echo "type->getScope() . "-bright\">\n"; - echo "\n"; - echo "\n"; - echo "\n"; - echo "\n"; - echo "
\"select " . - "" . _("Select all") . "type->getId() . "&". - "sort=" . strtolower($this->attrArray[$k]) . $filter . "&norefresh=y" . "\">" . $this->descArray[$k] . - " \"sorttype->getId() . "&". - "sort=" . strtolower($this->attrArray[$k]) . $filter . "&norefresh=y" . "\">" . $this->descArray[$k] . "
"; - printHelpLink(getHelp('', '250'), '250'); - echo ""; - $filterGroup = new htmlGroup(); - $filterButton = new htmlButton('apply_filter', 'filter.png', true); - $filterButton->setTitle(_("Filter")); - $filterGroup->addElement($filterButton); - if (sizeof($this->filters) > 0) { - $filterGroup->addElement(new htmlSpacer('1px', null)); - $clearFilterButton = new htmlButton('clear_filter', 'clearFilter.png', true); - $clearFilterButton->setTitle(_('Clear filter')); - $filterGroup->addElement($clearFilterButton); - } - parseHtml(null, $filterGroup, array(), false, $this->tabindex, $this->type->getScope()); - echo ""; - if ($this->canBeFiltered($this->attrArray[$k])) { - $this->printFilterArea($this->attrArray[$k], isset($_POST['clear_filter'])); - } - echo "
"); - $attrName = strtolower($this->attrArray[$k]); - $this->listPrintTableCellContent($info[$index], $attrName); - echo ("
\"select " . - "" . _("Select all") . "
\n"; - } - - /** - * Prints the tool image links (e.g. edit and delete) for each account. - * - * @param array $account LDAP attributes - * @param String $id account ID - * @deprecated - */ - private function listPrintToolLinks($account, $id) { - $toolCount = 0; - $group = new htmlGroup(); - // edit link - $editLink = new htmlLink('', "../account/edit.php?type=" . $this->type->getId() . "&DN='" . rawurlencode($account['dn']) . "'", '../../graphics/edit.png'); - $editLink->setTitle(_("Edit")); - $group->addElement($editLink); - $toolCount++; - // delete link - if (checkIfWriteAccessIsAllowed($this->type->getId()) && checkIfDeleteEntriesIsAllowed($this->type->getId())) { - $deleteLink = new htmlLink('', "deletelink.php?type=" . $this->type->getId() . "&DN='" . rawurlencode($account['dn']) . "'", '../../graphics/delete.png'); - $deleteLink->setTitle(_("Delete")); - $group->addElement($deleteLink); - $toolCount++; - } - // PDF button - $pdfButton = new htmlButton("createPDF_" . $id, 'pdf.png', true); - $pdfButton->setTitle(_('Create PDF file')); - $group->addElement($pdfButton); - $toolCount++; - // additional tools - $tools = $this->getAdditionalTools(); - for ($i = 0; $i < sizeof($tools); $i++) { - $toolLink = new htmlLink('', $tools[$i]->getLinkTarget() . "?type=" . $this->type->getId() . "&DN='" . rawurlencode($account['dn']) . "'", '../../graphics/' . $tools[$i]->getImage()); - $toolLink->setTitle($tools[$i]->getName()); - $group->addElement($toolLink); - $toolCount++; - } - $width = ($toolCount * 20) + 20; - echo ""; - parseHtml(null, $group, array(), false, $this->tabindex, $this->type->getScope()); - echo "\n"; - } - - /** - * Prints the content of a cell in the account list for a given LDAP entry and attribute. + * Returns the content of a cell in the account list for a given LDAP entry and attribute. * * @param array $entry LDAP attributes * @param string $attribute attribute name + * @return htmlElement content */ - protected function listPrintTableCellContent(&$entry, &$attribute) { + protected function getTableCellContent(&$entry, &$attribute) { // print all attribute entries seperated by "; " if (isset($entry[$attribute]) && sizeof($entry[$attribute]) > 0) { if (is_array($entry[$attribute])) { if (($attribute == 'entryexpiretimestamp') && !empty($entry[$attribute][0])) { - echo formatLDAPTimestamp($entry[$attribute][0]); + return new htmlOutputText(formatLDAPTimestamp($entry[$attribute][0])); } else { // sort array sort($entry[$attribute]); - echo htmlspecialchars(implode("; ", $entry[$attribute]), ENT_QUOTES, "UTF-8"); + return new htmlOutputText(implode("; ", $entry[$attribute])); } } else { - echo htmlspecialchars($entry[$attribute], ENT_QUOTES, "UTF-8"); + return new htmlOutputText($entry[$attribute]); } } } @@ -1110,9 +927,6 @@ class lamList { jQuery(document).ready(function() { jQuery('#tab_type->getId(); ?>').addClass('ui-tabs-active'); jQuery('#tab_type->getId(); ?>').addClass('ui-state-active'); - window.onload = listResizeITabContentDiv; - window.onresize = listResizeITabContentDiv; - jQuery('#filterButton').button(); }); '; $values = $entry[$attribute]; if (!empty($values)) { usort($values, 'compareDN'); @@ -375,12 +372,11 @@ class lamGroupList extends lamList { $values[$i] = getAbstractDN($values[$i]); } } - echo implode('
', $values); - echo '
'; + return new htmlDiv(null, new htmlOutputText(implode('
', $values), false), array('rightToLeftText')); } // print all other attributes else { - parent::listPrintTableCellContent($entry, $attribute); + return parent::getTableCellContent($entry, $attribute); } } diff --git a/lam/lib/types/user.inc b/lam/lib/types/user.inc index 3079c86e..28aad542 100644 --- a/lam/lib/types/user.inc +++ b/lam/lib/types/user.inc @@ -717,24 +717,21 @@ class lamUserList extends lamList { } /** - * Prints the content of a cell in the account list for a given LDAP entry and attribute. - * - * @param array $entry LDAP attributes - * @param string $attribute attribute name + * {@inheritDoc} + * @see lamList::getTableCellContent() */ - protected function listPrintTableCellContent(&$entry, &$attribute) { + protected function getTableCellContent(&$entry, &$attribute) { // check if there is something to display at all if (($attribute != self::ATTR_ACCOUNT_STATUS) && (!isset($entry[$attribute]) || !is_array($entry[$attribute]) || (sizeof($entry[$attribute]) < 1))) { - parent::listPrintTableCellContent($entry, $attribute); - return; + return parent::getTableCellContent($entry, $attribute); } // translate GID to group name if (($attribute == "gidnumber") && ($this->trans_primary == "on")) { if (isset($this->trans_primary_hash[$entry[$attribute][0]])) { - echo $this->trans_primary_hash[$entry[$attribute][0]]; + return new htmlOutputText($this->trans_primary_hash[$entry[$attribute][0]]); } else { - parent::listPrintTableCellContent($entry, $attribute); + return parent::getTableCellContent($entry, $attribute); } } // show user photos @@ -764,47 +761,45 @@ class lamUserList extends lamList { if ($imgHeight < 64) { $minSize = $imgHeight; } - $imgTitle = _('Click to switch between thumbnail and original size.'); - echo "\"""; - echo ''; + return new htmlImage($photoFile, null, $minSize, _('Photo')); } elseif (($attribute == 'mail') || ($attribute == 'rfc822Mailbox')) { + $group = new htmlGroup(); if (isset($entry[$attribute][0]) && ($entry[$attribute][0] != '')) { for ($i = 0; $i < sizeof($entry[$attribute]); $i++) { if ($i > 0) { - echo ", "; + $group->addElement(new htmlOutputText(", ")); } - echo "" . $entry[$attribute][$i] . "\n"; + $group->addElement(new htmlLink($entry[$attribute][$i], "mailto:" . $entry[$attribute][$i])); } } + return $group; } // expire dates elseif ($attribute == 'shadowexpire') { if (!empty($entry[$attribute][0])) { $time = new DateTime('@' . $entry[$attribute][0] * 24 * 3600, getTimeZone()); - echo $time->format('d.m.Y'); + return new htmlOutputText($time->format('d.m.Y')); } } elseif ($attribute == 'sambakickofftime') { if (!empty($entry[$attribute][0])) { if ($entry[$attribute][0] > 2147483648) { - echo "∞"; + return new htmlOutputText("∞"); } else { $date = new DateTime('@' . $entry[$attribute][0], new DateTimeZone('UTC')); - echo $date->format('d.m.Y'); + return new htmlOutputText($date->format('d.m.Y')); } } } // account status elseif ($attribute == self::ATTR_ACCOUNT_STATUS) { - $this->printAccountStatus($entry); + return $this->getAccountStatus($entry); } // print all other attributes else { - parent::listPrintTableCellContent($entry, $attribute); + return parent::getTableCellContent($entry, $attribute); } } @@ -1040,11 +1035,12 @@ class lamUserList extends lamList { } /** - * Prints the account status. + * Returns the account status. * * @param array $attrs LDAP attributes + * @return htmlElement content */ - private function printAccountStatus(&$attrs) { + private function getAccountStatus(&$attrs) { // check status $unixAvailable = self::isUnixAvailable($attrs); $sambaAvailable = self::isSambaAvailable($attrs); @@ -1144,10 +1140,10 @@ class lamUserList extends lamList { $tipContent .= '' . _('Password expired') . '  '; } $tipContent .= ''; - echo 'status'; + return new htmlOutputText('status', false); } else { - echo 'status'; + return new htmlImage('../../graphics/' . $icon, 16, 16, 'status'); } } diff --git a/lam/templates/lib/500_lam.js b/lam/templates/lib/500_lam.js index d6ac8351..3996aef1 100644 --- a/lam/templates/lib/500_lam.js +++ b/lam/templates/lib/500_lam.js @@ -62,23 +62,6 @@ function listPageNumberKeyPress(url, e) { return true; } -/** - * Resizes the content area of the account lists to fit the window size. - * This prevents that the whole page is scrolled in the browser. Only the account table has scroll bars. - */ -function listResizeITabContentDiv() { - var myDiv = document.getElementById("listTabContentArea"); - var height = document.documentElement.clientHeight; - height -= myDiv.offsetTop; - height -= 105; - myDiv.style.height = height +"px"; - - var myDivScroll = document.getElementById("listScrollArea"); - var top = myDivScroll.offsetTop; - var scrollHeight = height - (top - myDiv.offsetTop); - myDivScroll.style.height = scrollHeight + "px"; -}; - /** * Shows the dialog to change the list settings. * From 1935d3def8e3095a1dcee99969f54db4bdc5b5a6 Mon Sep 17 00:00:00 2001 From: Roland Gruber Date: Sun, 28 Oct 2018 13:55:30 +0100 Subject: [PATCH 9/9] responsive account table --- lam/lib/types/dhcp.inc | 89 ++++++++++++++++++++++++---------------- lam/style/500_layout.css | 4 ++ 2 files changed, 57 insertions(+), 36 deletions(-) diff --git a/lam/lib/types/dhcp.inc b/lam/lib/types/dhcp.inc index 71da7382..7f80cf4c 100644 --- a/lam/lib/types/dhcp.inc +++ b/lam/lib/types/dhcp.inc @@ -178,12 +178,10 @@ class lamDHCPList extends lamList { } /** - * Prints the content of a cell in the account list for a given LDAP entry and attribute. - * - * @param array $entry LDAP attributes - * @param string $attribute attribute name + * {@inheritDoc} + * @see lamList::getTableCellContent() */ - public function listPrintTableCellContent(&$entry, &$attribute) { + public function getTableCellContent(&$entry, &$attribute) { // Fixed IPs if ($attribute=="fixed_ips") { // find all fixed addresses: @@ -197,48 +195,59 @@ class lamDHCPList extends lamList { $order[$i] = fixed_ip::extractIP($entries[$i]['dhcpstatements']); } } + $group = new htmlGroup(); natcasesort($order); - echo ""; - foreach ($order as $i => $sortval) { + for ($i = 0; $i < sizeof($order); $i++) { $dhcpstatements = array(); if (isset($entries[$i]['dhcpstatements'][0])) { $dhcpstatements = $entries[$i]['dhcpstatements']; } - $style = ''; + $cssClasses = array('nowrap'); if (!fixed_ip::isActive($dhcpstatements)) { - $style = 'style="text-decoration: line-through;"'; + $cssClasses[] = 'strike-through'; } - echo ""; - echo ""; $dhcphwaddress = explode(" ",$entries[$i]['dhcphwaddress'][0]); - echo ""; - echo ""; - echo ""; - } - echo "
" . fixed_ip::extractIP($dhcpstatements) . "".array_pop($dhcphwaddress)."".$entries[$i]['cn'][0]."
"; - } - } - // fixed ip address - elseif ($attribute=="dhcpstatements") { - // Search after the fixed ip entry - if (is_array($entry['dhcpstatements'])) { - foreach($entry['dhcpstatements'] AS $id => $value) { - - if (!is_array($value) && array_shift( explode(" ", $value) ) == "fixed-address") { - $ip = explode(" ", $value); - echo $ip['1']; + $ipAddress = fixed_ip::extractIP($dhcpstatements); + $ip = new htmlOutputText($ipAddress); + $ip->setCSSClasses($cssClasses); + $group->addElement($ip); + if (!empty($ipAddress)) { + $group->addElement(new htmlOutputText('
', false)); + } + $macAddress = array_pop($dhcphwaddress); + $mac = new htmlOutputText($macAddress); + $mac->setCSSClasses($cssClasses); + $group->addElement($mac); + if (!empty($macAddress)) { + $group->addElement(new htmlOutputText('
', false)); + } + $name = new htmlOutputText($entries[$i]['cn'][0]); + $name->setCSSClasses($cssClasses); + $group->addElement($name); + $group->addElement(new htmlOutputText('
', false)); + if ($i < (sizeof($order) - 1)) { + $group->addElement(new htmlOutputText('
', false)); } } + return $group; } } elseif ($attribute=="dhcprange") { // DHCP Range if (isset($entry['dhcprange'])) { - echo""; + $table = new htmlTable(); + $table->setCSSClasses(array('nowrap')); $ranges = array(); foreach($entry['dhcprange'] AS $id => $value) { if (!empty($value) && !is_numeric($value)) { $ex = explode(" ", $value); - $ranges[] = ""; + $row = new htmlTableRow( + array( + new htmlOutputText($ex[0]), + new htmlOutputText(' - '), + new htmlOutputText($ex[1]) + ) + ); + $ranges[$ex[0] . ' - ' . $ex[1]] = $row; } } $pooledRanges = searchLDAP($entry['dn'], '(objectclass=dhcpPool)', array('dhcprange')); @@ -249,18 +258,26 @@ class lamDHCPList extends lamList { foreach($pool['dhcprange'] AS $id => $value) { if (!empty($value) && !is_numeric($value)) { $ex = explode(" ", $value); - $ranges[] = ""; + $row = new htmlTableRow( + array( + new htmlOutputText($ex[0]), + new htmlOutputText(' - '), + new htmlOutputText($ex[1]) + ) + ); + $ranges[$ex[0] . ' - ' . $ex[1]] = $row; } } } - natcasesort($ranges); - echo implode('', $ranges); - echo"
".$ex[0]."
-
".$ex[1]."
".$ex[0]."
-
".$ex[1]."
"; + uksort($ranges, 'strnatcasecmp'); + foreach ($ranges as $text => $row) { + $table->addElement($row); + } + return $table; } } - else - { - parent::listPrintTableCellContent($entry, $attribute); + else { + return parent::getTableCellContent($entry, $attribute); } } diff --git a/lam/style/500_layout.css b/lam/style/500_layout.css index d2fbd317..347677e2 100644 --- a/lam/style/500_layout.css +++ b/lam/style/500_layout.css @@ -507,6 +507,10 @@ input.markOk { .sortableList li { margin: 0 3px 3px 3px; padding: 0.4em; padding-left: 1.5em; } .sortableList li span { position: absolute; margin-left: -1.3em; } +.strike-through { + text-decoration: line-through; +} + /** * table style for delete.php