User:PerfektesChaos/js/browserStorageManager/d.js

/// User:PerfektesChaos/js/browserStorageManager/d.js /// 2020-12-10 PerfektesChaos@de.wikipedia // Show and manipulate web storage and cookies. // ResourceLoader: compatible; //                 dependencies: //                    user, user.options, mediawiki.user, mediawiki.util /// Fingerprint: #0#0# /// @license GPL [//www.mediawiki.org/w/COPYING] (+GFDL, LGPL, CC-BY-SA) /// /* global window: false                                               */ /* jshint forin:false, bitwise:true, curly:true, eqeqeq:true, latedef:true, laxbreak:true, nocomma:true, strict:true, undef:true, unused:true          */

( function ( mw, $ ) {  "use strict";   var vsn  =  -2.3,       BSM  =  "browserStorageManager",       Max  =  100,       Bag  =  [ "localStorage", "sessionStorage", "cookies" ];

// Requires: JavaScript 1.4             ("in") //          ECMA        262-3 § 11.8.5  (string comparison operators)

// ///////////////////////////////////////////////////////////////////

function bb_mw { // Build functions for mediawiki environment, and execute // Precondition: // Uses: //   >  Bag //   >  Max //   >< BSM //    < domfuns // 2014-01-11     var config, domfuns, gui, lang, mod, prego, Key =  80; if ( typeof mw.libs[ BSM ] !==  "object"           ||   ! mw.libs[ BSM ] ) { mw.libs[ BSM ] =  { };

}     mw.libs[ BSM ].type  =  BSM; BSM                 =  mw.libs[ BSM ]; if ( BSM.vsn ) { return; }     BSM.vsn  =  vsn; config  =  { support: "User:PerfektesChaos/js/" + BSM.type }; gui     =  { }; lang    =  { }; mod     =  { }; BSM.doc =  "" + config.support + ""; domfuns =  [ "key", "length", "clear", "getItem",  "setItem",  "removeItem" ];

lang.texts  =  { // 2014-01-04 PerfektesChaos@de.wikipedia "#bytes":   {"en": "bytes", "de": "Bytes"}, "#chars":   {"en": "chars", "de": "Zeichen"}, "#content": {"en": "content...", "de": "Inhalt..."}, "#id":      {"en": "ID", "de": "ID"}, "!abort":   {"en": "abort", "de": "Abbruch"}, "!delete":  {"en": "delete entry", "de": "Eintrag löschen"}, "!edit":    {"en": "Modify text", "de": "Text bearbeiten"}, "!fresh":   {"en": "refresh table", "de": "Tabelle aktualisieren"}, "!new":     {"en": "new entry", "de": "Neuer Eintrag"}, "!save":    {"en": "save new text", "de": "Text speichern"}, "^show":    {"en": "Browser-Storage-Manager", "de": "Browser-Storage-Manager"}, "^suffix":  {"en": "&#8211; Show and manipulate" + " web/DOM storage and cookies.", "de": "&#8211; Zeige und bearbeite" + " Web/DOM Storage und Cookies."}, "^^key":    {"en": "Text height (default: "                              + Key + " %)", "de": "Schriftgröße (Vorgabe: "                             + Key + " %)"}, "^^max":    {"en": "Text length limit (default: "                              + Max + ")", "de": "Maximale Textlänge (Vorgabe: "                             + Max + ")"}, "^^portlet": {"en": "Create portlet link", "de": "Portlet-Link einfügen"} };  // lang.texts

lang.user =  { "de" :  "de", "als" : "de", "bar" : "de", "dsb" : "de", "frr" : "de", "gsw" : "de", "hsb" : "de", "ksh" : "de", "lb" :  "de", "nds" : "de", "pdc" : "de", "pdt" : "de", "pfl" : "de", "sli" : "de", "stq" : "de", "vmf" : "de" };  // lang.user   2012-12-19 PerfektesChaos@de.wikipedia

function fire { // Complete initialization after code loading // Uses: //   >  config.signature //   >  config.rLoader //    < config.link //    < gui.ltr //   config.fetch //   config.form //   mw.loader.state // Remark: May be used as event handler -- 'this' not accessed // 2020-12-10 PerfektesChaos@de.wikipedia config.fetch; if ( mw.config.get( "wgCanonicalSpecialPageName" )                                                     === "Blankpage" ) { if ( prego ) { config.form; }        } else { config.link =  true; }        gui.ltr  = ( $( "html" ).attr( "dir" )  !==  "rtl" ); if ( typeof config.rLoader !==  "object"              ||   ! config.rLoader ) { config.rLoader = { }; }        config.rLoader[ config.signature ] = "ready"; mw.loader.state( config.rLoader ); }  // fire

function first { // Start actions on current page // Uses: //   >  .key //   config.fence //   config.font //   config.fire //   mw.loader.using //   (config.firing) // 2015-09-29 PerfektesChaos@de.wikipedia var key =  false; if ( typeof BSM.key ===  "number" ) { key =  BSM.key; }        config.fence; config.font( key ); config.fire; mw.loader.using( [ "user",                           "user.options",                            "mediawiki.user",                            "mediawiki.util" ],                          config.firing ); }  // first

config.favorite =  function  { // Detect support page in user language // Uses: //   this //   >  lang.slang //   >  config.support //   lang.favorite // 2013-12-14 PerfektesChaos@de.wikipedia var r;        lang.favorite; switch ( lang.slang ) { case "de" : r =  "de.wikipedia.org"; break; default: r =  "en.wikipedia.org"; }  // switch .slang return "//" + r + "/wiki/" + this.support; };  // config.favorite

config.fence =  function ( apply ) { // Retrieve or check and memorize default text length // Precondition: //   apply  -- number with text length, to be stored, or nil // Postcondition: //   Returns valid number // Uses: //   this //   >  .max //   >  Max //   >< config.max // 2013-12-17 PerfektesChaos@de.wikipedia var n;        if ( typeof config.max  !==  "number" ) { if ( typeof BSM.max ===  "number" ) { if ( BSM.max >= 10 &&  BSM.max <= 1024 ) { config.max =  BSM.max; }           }            if ( typeof config.max  !==  "number" ) { config.max =  Max; }        }         if ( apply ) { switch ( typeof apply ) { case "number" : n =  apply; break; case "string" : n =  parseInt( apply, 10 ); break; default: n =  false; }  // switch typeof apply if ( n ) { if ( n >= 10 &&  n <= 1024 ) { config.max =  n;               } }        }         return config.max; };  // config.fence

config.fetch =  function  { // Retrieve preferences and overwrite presets // Uses: //   this //   >  config.supply //   >  .type //    < prego //    < gui.$link //   config.fence //   config.font //   gui.facility //   mw.libs.preferencesGadgetOptions.fetch // 2014-01-02 PerfektesChaos@de.wikipedia var link, vals; if ( typeof BSM.portlet ===  "boolean" ) { link =  BSM.portlet; } else { link =  true; }        if ( mw.user.isAnon ) { prego =  false; } else { prego =  mw.libs[ this.supply ]; }        if ( prego ) { vals  =  prego.fetch( BSM.type ); if ( vals  &&   typeof vals  ===  "object" ) { config.fence( vals.max ); config.font( vals.key ); if ( typeof vals.portlet ===  "boolean" ) { link =  vals.portlet; }           }         }         if ( link ) { gui.$link =  true; gui.facility( true ); }     };   // config.fetch

config.filled =  function ( assigned ) { // New preferences have been sent to server // Precondition: //   assigned  -- object with final form data, to be stored // Uses: //   config.fence //   gui.facility // Remark: May be used as event handler -- 'this' not accessed // 2013-12-17 PerfektesChaos@de.wikipedia if ( typeof assigned ===  "object"   &&   assigned ) { config.fence( assigned.max ); gui.facility( assigned.portlet ); }     };   // config.filled

config.fire =  function  { // Prepare ResourceLoader availability // Postcondition: //   loader.load requested, if not yet defined // Uses: //   this //    < config.supply //    < config.signature //    < config.rLoader //   mw.loader.getState //   mw.loader.state //   mw.loader.load // 2020-12-10 PerfektesChaos@de.wikipedia config.supply    =  "preferencesGadgetOptions"; config.signature =  "ext.gadget." + config.supply; if ( ! mw.loader.getState( config.signature ) ) { config.rLoader = { }; config.rLoader[ config.signature ] = "loading"; mw.loader.state( config.rLoader ); mw.loader.load( "https://en.wikipedia.org"                                  + "/w/index.php?title="                            + "User:PerfektesChaos/js/"                            + config.supply                            + "/r.js"                            + "&action=raw&bcache=1&maxage=604806"                            + "&ctype=text/javascript",                            "text/javascript" ); }     };   // config.fire

config.firing =  function  { // Intermediate loading process step // Precondition: //   MW ressources are available // Uses: //   >  config.supply //   mw.hook //   (fire) // Remark: Used as event handler -- 'this' is not config // 2015-09-29 PerfektesChaos@de.wikipedia mw.hook( config.supply + ".ready" ).add( fire ); };  // config.firing

config.font =  function ( apply ) { // Retrieve or check and memorize font size // Precondition: //   apply  -- number with font size, to be stored, or nil // Postcondition: //   Returns valid number // Uses: //   this //   >  Key //   >< config.key // 2013-12-17 PerfektesChaos@de.wikipedia var n;        if ( typeof config.key  !==  "number" ) { config.key =  Key; }        if ( apply ) { switch ( typeof apply ) { case "number" : n =  apply; break; case "string" : n =  parseInt( apply, 10 ); break; default: n =  false; }  // switch typeof apply if ( n ) { if ( n >= 65 &&  n <= 100 ) { config.key =  n;               } }        }         return config.key; };  // config.font

config.form =  function  { // Equip Special:Blankpage page with entry and form // Uses: //   >  .type //   >  lang.slang //   >  lang.texts //   >  .max //   >  gui.$link //   lang.favorite //   config.favorite //   prego.form //   (.config.filled) //   mw.libs.preferencesGadgetOptions.form // 2013-12-14 PerfektesChaos@de.wikipedia var dialog, sl, text   =  lang.texts; lang.favorite; sl =  lang.slang; dialog =  { script:  BSM.type, show:   text[ "^show" ][ sl ], support: this.favorite, suffix: text[ "^suffix" ][ sl ], filled: this.filled, opts:   [ { signature: "max", type:     "text", show:     text[ "^^max" ][ sl ], val:      config.fence },                                { signature: "portlet", type:     "checkbox", show:     text[ "^^portlet" ][ sl ], val:      ( gui.$link ? true                                                          : false ) },                                { signature: "key", type:     "text", show:     text[ "^^key" ][ sl ], val:      config.font }                              ] };         prego.form( dialog ); };  // config.form

gui.facility =  function ( add ) { // Remove previous portlet link, and create new one // Precondition: //   add  -- create new portlet link // Uses: //   this //   >< gui.$link //   gui.factory // 2013-12-17 PerfektesChaos@de.wikipedia if ( typeof this.$link ===  "object" ) { this.$link.hide; this.$link =  false; }        if ( add ) { $( this.factory ); }     };   // gui.facility

gui.factory =  function  { // Insert portlet link // Uses: //   >  lang.slang //   >  lang.texts //   >  .portlet //           -- object with portlet requirements //              .scope     -- container id         //               .show      -- label //              .shortcut  -- access key //              .stick     -- id to sort before in container //   >  .type //   >  .vsn //    < gui.$link //   lang.favorite //   jQuery.trim //   gui.facility //   mw.util.addPortletLink //   (gui.fiat) // Remark: May be used as event handler -- 'this' not accessed // 2013-12-17 PerfektesChaos@de.wikipedia var dom, s,            show, signal, scope    =  "p-tb", shortcut =  null, stick    =  null; lang.favorite; show =  lang.texts[ "^show" ][ lang.slang ]; if ( typeof BSM.portlet ===  "object"   &&   BSM.portlet ) { s =  BSM.portlet.scope; if ( typeof s ===  "string" ) { s =  $.trim( s ); if ( s.length ) { scope =  s;               } }           s  =  BSM.portlet.shortcut; if ( typeof s ===  "string" ) { s =  $.trim( s ); if ( s.length ) { shortcut =  s;               } }           s  =  BSM.portlet.show; if ( typeof s ===  "string" ) { s =  $.trim( s ); if ( s.length ) { show =  s;               } }           s  =  BSM.portlet.stick; if ( typeof s ===  "string" ) { s =  $.trim( s ); if ( s.length ) { stick =  s;               } }        }         signal  =  show + "\n" + BSM.type + " " + BSM.vsn; dom    =  mw.util.addPortletLink( scope,                                            "#",                                            show,                                            "t-" + BSM.type,                                            signal,                                            shortcut,                                            stick ); gui.$link =  $( dom ).find ( "a" ); gui.$link.click( gui.fiat ); };  // gui.factory

gui.fiat =  function  { // Equip current page with tables // Precondition: //   document ready // Uses: //   >  Bag //   >  .type //   >  config.key //   >  config.link //   >  prego //   >< gui.$wrapper //    < gui.$table //    < mod.makes //   gui.fresh //   lang.favorite //   prego.$button //   gui.folder //   jQuery.tablesorter //   gui.facility //   (gui.features) // Remark: May be used as event handler -- 'this' not accessed // 2014-01-29 PerfektesChaos@de.wikipedia var i, $btn, selector; if ( gui.$wrapper ) { for ( i = 0; i < 3;  i++ ) { gui.fresh( Bag[ i ] ); }  // for i         } else { selector =  "#" + BSM.type; lang.favorite; gui.$wrapper =  $( " " ); gui.$wrapper.attr( "id", selector ); gui.$wrapper.css( { "border":       "solid 2px #006400",                                "font-size":     config.key + "%",                                "margin-bottom": "2em",                                "padding":       "1em"                              } ); if ( config.link && prego ) { $btn =  prego.$button( BSM.type ); $btn.css( { "float"        : "right",                           "vertical-align": "top" } ); gui.$wrapper.prepend( $btn ); }           gui.$table  =  { }; mod.makes  =  { }; for ( i = 0; i < 3;  i++ ) { gui.folder( Bag[ i ] ); }  // for i            $( "#firstHeading" ).before( gui.$wrapper ); mw.loader.using( [ "jquery.tablesorter" ],                            function  {                                 for ( i = 0;  i < 3;  i++ ) {                                    gui.$table[ Bag[ i ] ].tablesorter;                                 }   // for i                             } ); gui.facility( false ); }     };   // gui.fiat

gui.folder =  function ( about ) { // Create initial table // Uses: //   >  gui.$wrapper //   >  lang.slang //   >  lang.texts //   >< gui.$table //   gui.furnish //   gui.fresh //   (mod.flip) //   (gui.fresh) // 2013-12-17 PerfektesChaos@de.wikipedia var s        =  ( about === "cookies"  ?  "#bytes"                                                 :  "#chars" ), $btn, $caption =  $( " " ), $span    =  $( " " ), $table   =  $( " " ), $tbody   =  $( " " ), $td      =  $( " " ), $tfoot   =  $( " " ), $th      =  $( " " ), $thead   =  $( " " ), $tr      =  $( " " ), $tf1     =  $td.clone, $tf2     =  $th.clone, $tf3     =  $td.clone, $th1     =  $th.clone, $th2     =  $th.clone, $th3     =  $th.clone, $trf     =  $tr.clone, $trh     =  $tr.clone; $table.attr( "class", "wikitable sortable" ); $caption.text( about ); $table.append( $caption ); $th1.text( lang.texts[ "#id" ][ lang.slang ] ); $th2.text( lang.texts[ s ][ lang.slang ] ); $th3.append( $span.clone ); $trh.append( $th1 ); $trh.append( $th2 ); $trh.append( $th3 ); $thead.append( $trh ); $table.append( $thead ); $table.append( $tbody ); $btn =  gui.furnish( "$btnNew" ); $btn.click( function {  mod.flip( about, -1, true );  } ); $tf1.append( $btn ); $tf2.css( { "font-family": "monospace",                    "text-align":  "right" } ); $tf2.append( $span ); $btn =  gui.furnish( "$btnRefresh" ); $btn.click( function {   gui.fresh( about );   } ); $tf3.append( $btn ); $trf.append( $tf1 ); $trf.append( $tf2 ); $trf.append( $tf3 ); $tfoot.append( $trf ); $table.append( $tfoot ); gui.$wrapper.append( $table ); gui.$table[ about ] =  $table; gui.fresh( about ); };  // gui.folder

gui.fresh =  function ( about ) { // Refill table body // Precondition: //   about  -- 1 of "localStorage", "sessionStorage", "cookies" // Postcondition: //   Returns Array with sorted assignments, or false // Uses: //   >  config.max //   >  lang.slang //   >  lang.texts //   >  gui.$table //   >  domfuns //   fresh //   jQuery.inArray //   gui.furnish //   (gui.fresh_1) //   (gui.fresh_2) // 2014-01-20 PerfektesChaos@de.wikipedia var el, i, m, n, $btn, $td1d, $td2d, $td3d, $trd, $txt, light  =  ( about === "cookies" ), r      =  fresh( about, config.max ), s      =  lang.texts[ "#content" ][ lang.slang ] + " (" + config.max + ")", $span  =  $( " " ), $table =  gui.$table[ about ], $tbody =  $table.children( "tbody" ), $tfoot =  $table.children( "tfoot" ), $thead =  $table.children( "thead" ), $td    =  $( " " ), $tr    =  $( " " ), $td1   =  $td.clone, $td2   =  $td.clone, $td3   =  $td.clone; $tbody.empty; $td1.css( { "font-family": "monospace" } ); $td2.css( { "font-family": "monospace",                    "text-align":  "right" } ); if ( r ) { m =  0; n =  r.length; for ( i = 0; i < n;  i++ ) { el =  r[ i ]; if ( light  ||                    $.inArray( el.id, domfuns )  <  0 ) { $td1d =  $td1.clone; $td2d =  $td2.clone; $td3d =  $td3.clone; $td1d.text( el.id ); $btn =  gui.furnish( "$btnDelete" ); $btn.on( "click",                          {  about: about,                              id:    el.id },                           gui.fresh_1 ); $td1d.append( $btn ); $td2d.text( el.n ); if ( el.n <= config.max ) { $txt =  $span.clone; $txt.text( el.v ); $td3d.append( $txt ); $btn =  gui.furnish( "$btnEdit" ); $btn.on( "click",                             { about: about,                                item: i,                                id:   el.id,                                val:  el.v },                              gui.fresh_2 ); $td3d.append( $btn ); } else { $td3d.text( el.v ); }                 $trd  =  $tr.clone; $trd.append( $td1d ); $trd.append( $td2d ); $trd.append( $td3d ); $tbody.append( $trd ); m +=  el.n;               } }  // for i         } else { m =  ""; }        $tr   =  $thead.children( "tr" ); $txt =  $tr.children( "th" ).eq( 2 ).children( "span" ); $txt.text( s ); $tr =  $tfoot.children( "tr" ); $tr.children( "td" ).children( "*" ).toggle( true ); $txt =  $tr.children( "th" ).children( "span" ); $txt.text( m ); mod.makes[ about ] =  0; return r;      };   // gui.fresh

gui.fresh_1 =  function ( event ) { // [delete] button has been clicked. // Precondition: //   event // Uses: //   mod.flush // 2013-12-17 PerfektesChaos@de.wikipedia mod.flush( event.data.about, event.data.id ); };  // gui.fresh_1

gui.fresh_2 =  function ( event ) { // [edit] button has been clicked. // Precondition: //   event // Uses: //   mod.flip // 2013-12-17 PerfektesChaos@de.wikipedia mod.flip( event.data.about,                  event.data.item,                   true,                   event.data.id,                   event.data.val ); };  // gui.fresh_2

gui.furnish =  function ( acquire ) { // Generate GUI elements. // Precondition: //   acquire  -- request //               "$btnAbort", //               "$btnDelete", //               "$btnEdit", //               "$btnNew", //               "$btnRefresh", //               "$btnStore"    -- button // Uses: //   this //   >  gui.ltr //   >  .type //   >  lang.slang //   lang.favorite // 2013-12-17 PerfektesChaos@de.wikipedia var show, $e, $v; if ( ! this[ acquire ] ) { lang.favorite; $e =  $( " " ); $e.attr( "type", "button" ); switch ( acquire ) { case "$btnAbort" : $e.css( { "color":      "#FF0000",                            "font-weight": "bolder",                            "float":       ( this.ltr ? "right" : "left" )                         } ); $e.attr( "class", BSM.type + "-tmp" ); $v =  $( " " ); $v.text( "X" ); show =  "!abort"; break; case "$btnDelete" : $e.css( { "color":      "#FF0000",                            "font-family": "sans-serif",                            "font-weight": "bolder",                            "float":       ( this.ltr ? "right" : "left" )                         } ); $e.css( ( this.ltr ? "margin-left" : "margin-right" ),                         "1em" ); $v =  $( " " ); $v.text( String.fromCharCode( 8722 ) ); show =  "!delete"; break; case "$btnEdit" : $e.css( { "color":      "#00A000",                            "font-weight": "bolder",                            "float":       ( this.ltr ? "right" : "left" )                         } ); $e.css( ( this.ltr ? "margin-left" : "margin-right" ),                         "1em" ); $v =  $( " " ); $v.text( String.fromCharCode( 8660 ) ); show =  "!edit"; break; case "$btnNew" : $e.css( { "color":      "#00A000",                            "font-size":   "150%",                            "font-weight": "bolder"                          } ); $v =  $( " " ); $v.text( "+" ); show =  "!new"; break; case "$btnRefresh" : $e.css( { "color":      "#00A000",                            "font-size":   "150%",                            "font-weight": "bolder",                            "float":       ( this.ltr ? "left" : "right" )                         } ); $v =  $( " " ); $v.text( "*" ); show =  "!fresh"; break; case "$btnSave" : $e.css( { "color":      "#00A000",                            "font-weight": "bolder",                            "float":       ( this.ltr ? "right" : "left" )                         } ); $e.attr( "class", BSM.type + "-tmp" ); $v =  $( " " ); $v.text( "+" ); show =  "!save"; break; }  // switch acquire $e.attr( "title", lang.texts[ show ][ lang.slang ] ); $e.append( $v ); this[ acquire ] =  $e; }        return  this[ acquire ].clone; };  // gui.furnish

lang.favorite =  function  { // Guess user language // Uses: //   this //   >  lang.user //   >< lang.slang //   mw.config.get // 2012-12-19 PerfektesChaos@de.wikipedia var s;        if ( ! this.slang ) { s =  mw.config.get( "wgUserLanguage" ).toLowerCase; if ( s.length > 4 ) {  // Remove RFC 1766 subtag from code if ( s.charCodeAt( 2 ) ===  45 ) {   // '-' s =  s.substr( 0, 2 ); }           }            s           =  this.user[ s ]; this.slang =  ( s ? s : "en" ); }     };   // lang.favorite

mod.flip =  function ( about, access, active, assign, alter ) { // [edit] or [new] button has been clicked; or saved/canceled. // Precondition: //   about   -- 1 of "localStorage","sessionStorage","cookies" //   access  -- number of item; -1 for new //   active  -- true: edit;  false: saved/canceled, restore //   assign  -- identifier //   alter   -- text to be changed, if any // Uses: //   >  config.max //   >  .type //   >< mod.makes //   gui.furnish //   (mod.flip) //   (mod.forward) // 2013-12-29 PerfektesChaos@de.wikipedia var start, $btnAbort, $btnSave, $eternity, $input, $lbl, $tbody, $td, $table =  gui.$table[ about ], $tfoot =  $table.children( "tfoot" ), $tr    =  $tfoot.children( "tr" ).children( "td" ), $new   =  $tr.eq( 0 ).children( "button" ), learn  =  ( access < 0 ), light  =  ( about === "cookies" ), slip   =  BSM.type + "-tmp"; if ( learn ) { $td =  $tr.eq( 1 ); $td.children( "button" ).toggle( ! active ); $td =  $tr.eq( 0 ); start =  ""; } else { $tbody =  $table.children( "tbody" ); $tr    =  $tbody.children( "tr" ).eq( access ); $td    =  $tr.children( "td" ).eq( 2 ); $td.children( "*" ).toggle( ! active ); start =  $td.children( "span" ).text; }        if ( active ) { mod.makes[ about ] =  mod.makes[ about ] + 1; $input =  $( " " ); $input.attr( { size: Math.ceil( config.max / 2 ),                           type:  "text" } ); $input.val( start ); $td.append( $input ); $btnAbort =  gui.furnish( "$btnAbort" ); $btnAbort.click( function {                                        mod.flip( about, access, false );                                         } ); $td.append( $btnAbort ); $btnSave =  gui.furnish( "$btnSave" ); $btnSave.click( function {   var life;                                            if ( learn && light ) {                                               life  =  $eternity.val;                                            } else {                                               life  =  false;                                            }                                            mod.forward( about, assign, $input.val, access, life );                                       } ); $td.append( $btnSave ); if ( learn && light ) { $eternity =  $( " " ); $eternity.attr( { "class": slip,                                "float": "right",                                 "id":    slip + "-eternity",                                 "type":  "checkbox" } ); $lbl =  $( " " ); $lbl.attr( { "class": slip,                           "float": "right"  ,                            "for":   slip + "-eternity" } ); $lbl.text( String.fromCharCode( 8734 ) ); $td.append( $lbl ); $td.append( $eternity ); }        } else { mod.makes[ about ] =  mod.makes[ about ] - 1; $td.children( "input" ).remove; $td.children( "." + slip ).remove; if ( typeof alter ===  "string" ) { $td.children( "span" ).text( alter ); $td =  $tr.children( "td" ).eq( 1 ); $td.text( alter.length ); }        }         $new.toggle( ! ( active  ||  mod.makes[ about ] ) ); };  // mod.flip

mod.flush =  function ( about, assign ) { // [delete] button has been clicked. // Precondition: //   about   -- 1 of "localStorage","sessionStorage","cookies" //   assign  -- identifier // Uses: //   jQuery.removeCookie  :: mediawiki.cookie //   gui.fresh // 2014-08-01 PerfektesChaos@de.wikipedia switch ( about ) { case "localStorage" : case "sessionStorage" : window[ about ].removeItem( assign ); break; case "cookies" : $.removeCookie( assign,                              { path: "/", expires: 0 } ); break; }  // switch about gui.fresh( about ); };  // mod.flush

mod.forward =  function ( about, assign, alter, access, ages ) { // [save] button has been clicked. // Precondition: //   about   -- 1 of "localStorage","sessionStorage","cookies" //   assign  -- identifier //   alter   -- text to be stored //   access  -- number of item; -1 for new //   ages    -- make cookie persistent // Uses: //   >  domfuns //   jQuery.trim //   jQuery.inArray //   jQuery.cookie //   gui.fresh //   mod.flip // 2014-01-20 PerfektesChaos@de.wikipedia var opts, story, subject =  assign, learn   =  ( access < 0 ), storage =  about; if ( learn ) { story   =  ""; subject =  $.trim( alter ); if ( subject === "" ) { storage =  ""; } else { switch ( storage ) { case "localStorage" : case "sessionStorage" : if ( window[ storage ].getItem( subject )  ||                          $.inArray( assign, domfuns )  >=  0 ) { storage =  ""; }                    break; case "cookies" : if ( mw.cookie.get( subject ) ) { storage =  ""; }                    break; }  // switch storage }        } else { story   =  alter; }        if ( storage !== "" ) { switch ( storage ) { case "localStorage" : case "sessionStorage" : window[ storage ].setItem( subject, story ); break; case "cookies" : opts =  { path: "/" }; if ( ages ) { opts.expires =  1000; }                 mw.cookie.set( subject, story, opts ); break; }  // switch storage mod.flip( storage, access, false, false, story ); if ( learn ) { gui.fresh( storage ); }        }      };   // mod.forward

BSM.fiat =  function  { // Equip current page with tables // Uses: //   mw.loader.using //   (gui.fiat) // 2013-12-17 PerfektesChaos@de.wikipedia mw.loader.using( [ "mediawiki.cookie" ],                         function  {                             $( gui.fiat );                          } ); };  // .fiat

BSM.fresh =  function ( about ) { // Rebuild table content // Precondition: //   about  -- 1 of "localStorage", "sessionStorage", "cookies" // Postcondition: //   Returns Array with sorted assignments, or false // Uses: //   >  gui.$wrapper //   >  config.max //   gui.fresh //   .fiat // Remark: May be used as event handler -- 'this' not accessed // 2013-12-28 PerfektesChaos@de.wikipedia var r;        if ( gui.$wrapper ) { r =  gui.fresh( about ); } else { BSM.fiat; r =  fresh( about, config.max ); }        return r;      };   // .fresh

first;

}  // bb_mw

// ///////////////////////////////////////////////////////////////////

function bb_nowiki { // Build functions for non-mediawiki environment, and execute // Uses: //   >  Bag //   >  BSM //   >  Max // 2013-12-17

function failure( all ) { // No console available // Precondition: //   all  -- object with all kinds of data // 2013-12-17        var k, s,             story  =  BSM + ": No console"; for ( k = 0; k < 2;  k++ ) { s     =  Bag[ k ]; story =  story + "\r\n" + s + ": " + figure( all[ s ] ); }  // for k         window.alert( story ); }  // failure

function fancy( all ) { // Try console tables // Precondition: //   all  -- object with all kinds of data // Uses: //   >  BSM // Throws: //   Unavailable // 2013-12-17        var k, o, s;         window.console.info( "== " + BSM + " ==" ); if ( window.opera ) { throw window.opera; }        if ( typeof window.console.table  ===  "object" ) { for ( k = 0; k < 3;  k++ ) { s =  Bag[ k ]; o =  all[ s ]; window.console.info( s + "  " + figure( o ) ); if ( o ) { window.console.table.call( window.console, o ); }           }   // for k         } else { throw { }; }     }   // fancy

function figure( assembly ) { // Retrieve total item count and character length of web storage // Precondition: //   assembly  -- Array with web storage info, or false // Postcondition: //   Returns string with numbers // 2013-12-17 PerfektesChaos@de.wikipedia var i, m, n, r;        if ( assembly ) { n =  assembly.length; m =  0; for ( i = 0; i < n;  i++ ) { m +=  assembly[ i ].n;            }   // for i            r  =  "#" + n + "   -> " + m;         } else { r =  "./."; }        return  r;      }   // figure

function fire { // Run on load // Uses: //   >  Bag //   >  Max //   fresh //   fancy //   flat //   failure // 2013-12-17 PerfektesChaos@de.wikipedia var i, s,            env  =  { }; for ( i = 0; i < 3;  i++ ) { s =  Bag[ i ]; env[ s ] =  fresh( s, Max ); }  // for i         if ( window.console ) { try { fancy( env ); } catch (e) { try { window.console.log( env ); } catch (ex) { flat( env ); }           }         } else { failure( env ); }     }   // fire

function flat( all ) { // console available, but no object log function // Precondition: //   all  -- object with all kinds of data // 2013-12-17        var e, i, k, n, o, s;         for ( k = 0;  k < 3;  k++ ) { s =  Bag[ k ]; o =  all[ s ]; n =  o.length; window.console.info( "=== " + s + " ===" ); for ( i = 0; i < n;  i++ ) { e =  o[ i ]; window.console.info( e.id + " = " + e.v ); }  // for i         }   // for k      }   // flat

fire;

}  // bb_nowiki

// ///////////////////////////////////////////////////////////////////

function fetch { // Retrieve cookies // Postcondition: //   Returns Array with cookie assignments, or false // 2013-12-17     var g, i, m, n, p, r, s, v;      if ( typeof window.document.cookie  ===  "string" ) { r =  [ ]; g =  window.document.cookie.split( "; " ); n =  g.length; for ( i = 0; i < n;  i++ ) { p =  g[ i ].split( "=" ); s =  decodeURIComponent( p[ 0 ] ); v =  p[ 1 ]; if ( v ) { m =  v.length; v =  decodeURIComponent( v ); } else { m =  0; v =  ""; }           r.push( { id: s,                      n:  m,                      v:  v } ); }  // for i      } else { r =  false; }     return  r;   }   // fetch

function find( access, allow ) { // Retrieve object with web storage // Precondition: //   access  -- either "localStorage" or "sessionStorage" //   allow   -- maximum number of characters // Postcondition: //   Returns Array with storage assignments, or false // 2013-12-17 PerfektesChaos@de.wikipedia var n, r, s, store, o =  window[ access ]; if ( typeof o ===  "object" ) { r =  [ ]; for ( s in o ) { store =  o.getItem( s ); if ( typeof store ===  "string" ) { n =  store.length; if ( n > allow ) { store =  store.substr( 0, allow ); }           } else { n     =  0; store =  ""; }           r.push( { id: s,                      n:  n,                      v:  store } ); }  // for s in o      } else { r =  false; }     return  r;   }   // find

function fresh( about, allow ) { // Rebuild content // Precondition: //   about   -- one of "localStorage", "sessionStorage", "cookies" //   allow   -- maximum number of characters // Uses: //   fetch //   find // Postcondition: //   Returns Array with sorted assignments, or false //           Each element is an object { id, n, v } //                               id  -- string //                               n   -- number of bytes/characters //                               v   -- truncated value // 2013-12-17 PerfektesChaos@de.wikipedia var r,         f  =  function( a,  b ) {   return  (   a.id.toLowerCase                                                < b.id.toLowerCase                                                ?  -1                                                :  +1 ); };     switch ( about ) { case "cookies" : r =  fetch; break; case "localStorage" : case "sessionStorage" : r =  find( about, allow ); break; default: r =  false; }  // switch about if ( r ) { r.sort( f ); }     return  r;   }   // fresh

if ( typeof mw ===  "object"   &&   $ ) { bb_mw; } else { bb_nowiki; }

}( window.mediaWiki, window.jQuery ) );

// Emacs // Local Variables: // coding: utf-8-dos // fill-column: 80 // End:

/// EOF  browserStorageManager/d.js