>id=divisionname<< text can be hidden/shown >><< Necessary parameters: (:toggle id=divname:) Alternative: (:toggle divname:) Alternative with options: (:toggle hide divname:) initial hide (:toggle hide divname button:) initial hide, button (:toggle name1 name2:) toggle between name1 and name2 Optional parameters: id2=objname second object (div), for toggling betwen first and second object init=hide hides the division initially (default is show) show=labelname label of link or button when div is hidden (default is Show) hide=labelname label of link or button when div is shown (default is Hide) label=labelname label of link or button for both toggle states set=1 sets a cookie to remember toggle state button=1 display a button instead of a link group=classname on clicking show show div with associated id= (standard behaviour), but hide all other divs with class classname. ttshow=tooltiptext text that appears when the user hovers over the "show" link (default is Show) tthide=tooltiptext text that appears when the user hovers over the "hide" link (default is Hide) nojs=integer set to 1 or 2 will show toggle links/buttons if browser does not support javascript. Set to 2 will hide hidden divs via style in page head and not via javascript, so that for non-js browser initially hidden divs stay hidden. display=value what the display property of the specified div should be set to, when it's shown (block, inline-block, etc.; see https://www.w3schools.com/CSSref/pr_class_display.asp for details) */ # Version date $RecipeInfo['Toggle']['Version'] = '2021-11-18'; # declare $Toggle for (:if enabled Toggle:) recipe installation check global $Toggle; $Toggle = 1; # retrieve cookie global $CookiePrefix, $pagename; $current_page_group = PageVar($pagename, '$Group'); $current_page_name = PageVar($pagename, '$Name'); $toggle_cookie_name = "{$CookiePrefix}_toggle_{$current_page_group}_{$current_page_name}"; $toggle_cookie = json_decode($_COOKIE[$toggle_cookie_name],true); Markup('toggle', 'directives', '/\\(:toggle\\s*(.*?):\\)/i', "ToggleMarkup"); # all in one function function ToggleMarkup($m) { global $HTMLFooterFmt, $HTMLStylesFmt, $ToggleConfig, $ToggleLinks, $UploadUrlFmt, $UploadPrefixFmt, $toggle_cookie_name, $toggle_cookie; extract($GLOBALS['MarkupToHTML']); SDVA($ToggleConfig, array( 'init' => 'show', // initial state of element (visible) 'show' => XL("Show"), // link text 'Show' 'hide' => XL("Hide"), // link text 'Hide' 'ttshow' => XL("Show"), // tooltip text 'Show' 'tthide' => XL("Hide"), // tooltip text 'Hide' 'id' => '', // no default div name 'id2' => '', // no default div2 name 'group' => '', // no default group (class) name 'display' => 'block', // default to display:block; 'set' => false, // set no cookie to remember toggle state 'printhidden' => true, // hidden divs get printed 'nojs' => 0, // in no jsbrowser links are not shown, initial hidden divs are shown )); $HTMLStylesFmt['toggle'] = " @media print { .toggle { display: none; } } \n" . ".toggle img { border: none; } \n"; # javascript for toggling and cookie setting $HTMLFooterFmt['toggleobj'] = " \n"; $opt = ParseArgs($m[1]); // Get parameters without keys. if (is_array($opt[''])) { while (count($opt['']) > 0) { $parameter = array_shift($opt['']); if($parameter == 'button') $opt['button'] = 1; elseif($parameter == 'hide') $opt['init'] = 'hide'; elseif($parameter == 'show') $opt['init'] = 'show'; elseif(!isset($opt['id'])) $opt['id'] = $parameter; elseif(!isset($opt['id2'])) $opt['id2'] = $parameter; } } // Fill in un-specified parameters with defaults. $opt = array_merge($ToggleConfig, $opt); // Retrieve the ids of both the primary and (if specified) alternate elements. // (the 'div' options are for backwards compatibility with ShowHide and ToggleLink recipes) // The first version of these 2 lines is for PHP 5.3+; the second, for earlier versions // $id = $opt['div'] ?: $opt['id']; // $id2 = $opt['div2'] ?: $opt['id2']; $id = $opt['div'] ? $opt['div'] : $opt['id']; $id2 = $opt['div2'] ? $opt['div2'] : $opt['id2']; if ($id == '') return "//!Error:// no object id specified!"; // Verify that the ids of both elements do not contain special characters // which are forbidden in CSS identifiers. (Among other things, this forbids // quotation marks, which prevents Javascript injection attacks via ids.) $CSS_forbidden_characters_regex = "/[!\\\"#$%&'()*+,\\.\\/\\:;<=>?@[\\\\\]^`{|}~]/"; if (preg_match($CSS_forbidden_characters_regex, $id) || preg_match($CSS_forbidden_characters_regex, $id2)) return Keep("Invalid ID specified for element!"); // Value for the 'display' CSS property. Affects both the element and the alternate element. $display = $opt['display']; // Set labels for (both states of) the toggle link/button. $labels = array(); // The first version of these 2 lines is for PHP 5.3+; the second, for earlier versions // $labels['show'] = $opt['label'] ?: ($opt['lshow'] ?: $opt['show']); // $labels['hide'] = $opt['label'] ?: ($opt['lhide'] ?: $opt['hide']); $labels['show'] = $opt['label'] ? $opt['label'] : ($opt['lshow'] ? $opt['lshow'] : $opt['show']); $labels['hide'] = $opt['label'] ? $opt['label'] : ($opt['lhide'] ? $opt['lhide'] : $opt['hide']); // Transform label text into image tags, if appropriate. // (since we won't be putting the label text through pmwiki markup // processing, which would normally process image attach links) // (but maybe we should? TODO: investigate this) // Also encode apostrophes (for non-images). $ipat = "/\.png|\.gif|\.jpg|\.jpeg|\.ico/"; foreach($labels as $k => $val) { if(preg_match($ipat, $val)) { // Check for image, make image tag $prefix = (strstr($val, '/')) ? '/' : $UploadPrefixFmt; $path = FmtPageName($UploadUrlFmt.$prefix, $pagename); $labels[$k] = ""; $opt['button'] = ''; } else { // Apostrophe encoding $labels[$k] = str_replace("'","’",$val); } } // If the element is part of a defined group, then hide it, unless it's explicitly set to be initially-shown. if ($opt['group'] != '' && $opt['init'] != 'show') $opt['init'] = 'hide'; // If set=1 (i.e. cookie setting enabled), then check if a cookie is set; // if it is, read the element's initial state from the cookie. if($opt['set'] == 1) // The first version of this line is for PHP 5.3+; the second, for earlier versions // $opt['init'] = $toggle_cookie[$id] ?: $opt['init']; $opt['init'] = $toggle_cookie[$id] ? $toggle_cookie[$id] : $opt['init']; /* OPTION RETRIEVAL ENDS; NOW PROCESSING BEGINS */ // Set initial state, and update labels and target state // (for when user clicks the toggle/link button). $display_property_value = ($opt['init'] == 'show') ? $display : 'none'; if ($toggle_cookie[$id2] == false) $alternate_element_display_property_value = ($opt['init'] == 'show') ? 'none' : $display; $label = ($opt['init'] == 'show') ? $labels['hide'] : $labels['show']; $tooltip = ($opt['init'] == 'show') ? $opt['tthide'] : $opt['ttshow']; $state_to_toggle_to = ($opt['init'] == 'show') ? 'hide' : 'show'; // Open script block. $HTMLFooterFmt[] = "\n"; // Construct toggle link or button (later it is modified with javascript). $out = ""; if ($opt['button'] == 1) { $out .= ($opt['nojs'] == 0) ? "" : ""; } else { $out .= ($opt['nojs'] == 0) ? "{$label}" : "{$label}"; } $out .= ""; return Keep($out); } #EOF