PageSourceSearch

https://arkansassiteselection.com/js/Views/Shared/Global.js?20260510045326

js arkansassiteselection.com collected 2026-10-05 21:42:09 UTC 21,598 bytes, 577 lines download raw bytes

1/// <reference path="../../jquery-1.10.2.intellisense.js" />
2
3var menu_close_timer = null; // Keeps track of mouse out delay timer to close user menu.
4var regex_valid_email = /^([a-zA-Z0-9_\.\-])+\@(([a-zA-Z0-9\-])+\.)+([a-zA-Z0-9]{2,4})+$/;
5
6$(function () {
7
8    $(document).on('sscevent:asynclogin', globalHandleLogin); // Attach to login event.
9
10    // Attach event to open User-Menu when UserName labeled Account Menu item is clicked.
11    $('#global_header').on('click', '.gh-account-menu', function () {
12        var $this = $(this);
13        var mpos = $this.position();
14
15        $('.gh-account-menu-select').css('top', mpos.top + $this.outerHeight()).css('right', $(window).width() - (mpos.left + $this.outerWidth())).fadeIn();
16    });
17
18    // Close account menu when any item inside is clicked.
19    $('#global_header').on('click', '.gh-account-menu-item', function () {
20        $('.gh-account-menu-select').fadeOut();
21    });
22
23    // Attach event to begin timer when mouse exits menu to fade menu out.
24    $('.gh-account-menu-select').on('mouseleave', function () {
25        menu_close_timer = window.setTimeout(closeMenu, 1250);
26    });
27
28    // Attach event to canel timer if they re-enter the  menu (so it doesn't close when they just temporarily cross out of the border while navigating).
29    $('.gh-account-menu-select').on('mouseenter', function () {
30        if (menu_close_timer)
31            window.clearTimeout(menu_close_timer);
32    });
33
34    function closeMenu() {
35        window.clearTimeout(menu_close_timer);
36        $('.gh-account-menu-select').fadeOut();
37    }
38
39    $(document).on('click', '.link-signout', function () {
40        $.ajax({
41            type: 'POST',
42            url: '/api/Security/LogOff',
43            success: function (msg) {
44                if (msg.Success) {
45                    window.location = '/' + (global_branding.URLPrefix ? global_branding.URLPrefix : '');
46                } else
47                    alert('LogOut Failed:\n\n' + msg.Msg);
48            },
49            error: function () {
50                alert('Network or Server Error Attempting to Log Out!');
51            }
52        });
53    });
54
55    makeAccountLinks();
56
57    $('.enter-nosubmit, .enter-nextinput').on('keydown', function (e) {
58
59        if (e.keyCode == 13) {
60
61            var $this = $(this);
62
63            // Cancel the default event if this is enter-nosubmit
64            if ($this.is('.enter-nosubmit'))
65                return false;
66
67            // Go up to the parent enter-nextinput-group and find the next enter-nextinput after the current one.
68            if ($this.is('.enter-nextinput')) {
69                var $current = $this, found_item = false;
70                $this.closest('.enter-nextinput-group').find('.enter-nextinput').each(function () {
71                    if (found_item) {
72                        $(this).focus();
73                        return false;
74                    }
75
76                    if ($(this).is($current))
77                        found_item = true;
78                });
79                return false;
80            }
81        }
82
83        return true;
84    });
85
86    $('.allow-positive-decimal').on('keypress', function (e) {
87
88        if ((e.which >= 48 && e.which <= 57) || e.which == 46) {
89            return true;
90        }
91
92        return false;
93    });
94
95    $('.button-cancel').on('click', function () {
96        window.history.back(); // Goes back, which should set the URL hash to users which should show the users list section
97        return false;
98    });
99
100    $('.warning-unobtrusive').on('mouseenter', function () {
101        var $this = $(this);
102        $this.stop();
103
104        if (window.timer_warning) {
105            window.clearTimeout(window.timer_warning);
106            window.timer_warning = null;
107        }
108
109        var bottom = parseFloat($this.css('bottom'));
110        if (bottom < 0) {
111            $this.animate({ 'bottom': 0 }, -(bottom / $this.outerHeight()) * 500);
112        }
113
114    }).on('mouseleave', function () {
115        window.timer_warning = window.setTimeout(hideWarning, 1500);
116    });
117
118});
119
120// This handles updating the header menus when a user logs in after loading the page.
121function globalHandleLogin(e, user_name) {
122    // Remove the join and sign-in links from the mobile & non-mobile
123    $('#li_join, #li_sign_in, #mobile_join, #mobile_sign_in').remove();
124
125    // Create the user-name drop-down menu button that holds the user links for non-mobile with the sign-out link
126    $('nav.top.hidden-mobile ul').append('<li><div class="dropdown" data-dropdown><a href="#" class="account-name" data-dropdown-toggle style="padding-right: 3em;">Menu <svg style="position: absolute;" viewBox="0 0 24 24"><path d="M3 18h18v-2H3v2zm0-5h18v-2H3v2zm0-7v2h18V6H3z"/></a><div class="dropdown-content account-nav right" data-dropdown-content><ul><li><a href="#" class="gh-account-menu-item sign-out link-signout">Sign Out</a></li></ul></div></div></li>');
127
128    // Create the account links and signout for the mobible nav
129    $('div.mobile-nav-panel div.account').append('<ul class="nav-secondary"></ul><a href="#" class="btn btn-small link-signout">Sign Out</a>');
130
131    makeAccountLinks();
132}
133
134function makeAccountLinks() {
135    if (account_links) {
136        $(account_links)
137            .each(function () {
138                if (this.Type == 'Item') {
139
140                    this.Text = $.trim(this.Text).toLowerCase() == 'account' ? elideEmailMiddle(window.username, 158) : this.Text;
141
142                    var $link_item = $('<a class="gh-account-menu-item"></a>').html(this.Text);
143                    if (this.Href) {
144                        if (this.BrandingPrefix && global_branding.URLPrefix) {
145                            if (this.Href.substr(0, 1) == '/') {
146                                this.Href = this.Href.replace(/^\//, '/' + global_branding.URLPrefix);
147                            }
148                        }
149
150                        $link_item.prop('href', this.Href);
151                    }
152                    if (this.ClientId) {
153                        $link_item.prop('id', this.ClientId);
154                    }
155                    if (this.ClientClass) {
156                        $link_item.addClass(this.ClientClass);
157                    }
158
159                    $('nav.top.hidden-mobile div.dropdown ul li:last').before($('<li></li>').append($link_item));
160
161                    if (!this.NoMobile) {
162                        $('div.mobile-nav-panel div.account ul.nav-secondary').append($('<li></li>').append($link_item.clone()));
163                    }
164                }
165            });
166    }
167
168    if ($('nav.top.hidden-mobile div.dropdown li span.inbox-unread-count').length) {
169        $('nav.top.hidden-mobile #header_unread').show().find('.inbox-unread-count').text($('nav.top.hidden-mobile div.dropdown li span.inbox-unread-count').text());
170    }
171}
172
173function elideEmailMiddle(email, width) {
174    var $tw = $('<div style="font-size:12.25px;display:none;"></div>');
175    $('body').prepend($tw);
176    $tw.html(email);
177    if ($tw.width() <= width) {
178        $tw.remove();
179        return email;
180    }
181
182    var lp = email.substr(0, email.indexOf('@') + 1);
183
184    $tw.html(lp);
185    if ($tw.width() > width) {
186        do {
187            lp = lp.substr(0, lp.length - 1);
188            $tw.html(lp + '&hellip;');
189        } while ($tw.width() > width)
190
191        $tw.remove();
192        return lp + '&hellip;';
193    }
194
195    var rp = email.substr(email.indexOf('@') + 1);
196    var rpl = rp.substr(0, (rp.length + 1) / 2);
197    var rpr = rp.substr((rp.length + 1) / 2);
198
199    $tw.html(lp + rpl + '&hellip;' + rpr)
200    var cut_right = true;
201    while ($tw.width() > width) {
202        if (cut_right) { rpr = rpr.substr(1); }
203        else { rpl = rpl.substr(0, rpl.length - 1); }
204        if (!rpl.length && !rpr.length) { $tw.remove(); return email; } // failsafe
205        cut_right = !cut_right;
206        $tw.html(lp + rpl + '&hellip;' + rpr)
207    }
208
209    $tw.remove();
210    return lp + rpl + '&hellip;' + rpr;
211}
212
213function modalCloseAll() {
214    $(document).trigger('close-modal-manual');
215}
216
217function modalOpen(modal_name) {
218    $(document).trigger('close-modal-manual');
219    $(document).trigger('open-modal-manual', [modal_name]);
220}
221
222function displayErrorMessage(msg) {
223    displayMessage('Error', msg);
224}
225
226function displaySuccessMessage(msg) {
227    displayMessage('Success', msg);
228}
229
230function displayMessage(title, msg) {
231    $('div[data-modal="generic-message"] div.modal-content-body').html((title ? '<h2>' + title + '</h2>' : '') + msg);
232    modalOpen('generic-message');
233}
234
235function parseJSONDateTime(json_datetime) {
236    if (json_datetime)
237        return new Date(parseInt(json_datetime.match(/\/Date\(([0-9]+)\)\//)[1]));
238    else
239        return null;
240}
241
242function getDateTimeString(date_val) {
243    if (date_val) {
244        return $.datepicker.formatDate('m/d/yy', date_val) + ' ' + date_val.getHours() + ':' + ('0' + date_val.getMinutes()).substr(-2);
245    }
246    else {
247        return 'Unknown';
248    }
249}
250
251function matchObject(obj, filter, fields) {
252
253    // Does it makes sense to combine all fields into one target string and search it just once (with regex?) Might need to use a funky char for a delimiter between the strings when combining them to prevent false positives being created.
254    if (fields) {
255        for (var i = 0; i < fields.length; i++) {
256            if (obj[fields[i]]) {
257                // TODO: Let's use case insensitive regex and try to support wildcards in the search.
258                if (obj[fields[i]].toString().toLowerCase().indexOf(filter) >= 0)
259                    return true;
260            }
261        }
262    }
263
264    return false;
265}
266
267// Call a webmethod without input or specific HTTP method-verb
268function loadGlobalData(data_array, key, url, callback, error_callback) {
269    loadGlobalDataInput(data_array, key, url, null, callback, error_callback);
270}
271
272// Call a webmethod with input, but without specific HTTP method-verb
273function loadGlobalDataInput(data_array, key, url, data, callback, error_callback) {
274    loadGlobalDataMethod(data_array, key, null, url, data, callback, error_callback);
275}
276
277// Call a web method with the appropriate HTTP method(verb), input data & URL, &
278// store the result in a data_array and call the callback. This will bypass the
279// ajax if the exisiting data is already loaded, and just call the call back, so
280// multiple methods that need the same data can all request it using this
281// method, but only the first one actually triggers the AJAX request, and the
282// following calls just use the cached data.
283// Parameters
284// data_array: The object (associative array) in which to place the received data if it is not already there.
285// key: The named index to use for the recieved/cached data.
286// method: The HTTP method to use most likely 'GET' or 'POST'. If null then GET is default.
287// url: The URL for the web-method endpoint.
288// data: Any input data to pass to the web-method.
289// callback: The method to call upon successful HTTP communication with web-method.
290// prev_request: This method returns the XHR object, so you can save it and pass it back the next time you make the same request.  If it's still running, it will cancel it before calling it again.
291function loadGlobalDataMethod(data_array, key, method, url, data, callback, error_callback, prev_request) {
292
293    // Kill any still pending request.
294    if (prev_request && prev_request.readyState != 4) {
295        prev_request.abort();
296    }
297
298    // If we already store something under that index, then just call the callback.
299    if (data_array[key] != null) {
300        callback();
301        return null;
302    }
303    else {
304        // Call the web-method.
305        return $.ajax({
306            type: (method ? method : 'GET'), url: url, dataType: "json", data: data,
307            success: function (msg) {
308                if (msg.Success) {
309                    // Store the data we recieved, then call the callback.
310                    // TODO: What about success=false in api result?
311                    data_array[key] = msg.Data;
312                    callback();
313                } else {
314                    if (!error_callback) {
315                        displayErrorMessage('Unexpected Error Loading Global Data of Type "' + key + '"');
316                    } else {
317                        error_callback(msg);
318                    }
319                }
320            },
321            error: function (response) {
322                // readyState=0 means unsent, which is probably because it was cancelled.
323                if (response.readyState > 0) {
324                    if (!error_callback) {
325                        // If a network error or server error happened, inform the user, but do not call the callback.
326                        displayErrorMessage('Network or Server Error Loading Global Data of Type "' + key + '"');
327                    } else {
328                        error_callback();
329                    }
330                }
331            }
332        });
333    }
334}
335
336function selectFirstTab(tabgroup) {
337    var tab_toggle = $($('a[data-tab-group="' + tabgroup + '"]').removeClass('active')[0]).addClass('active').data('tab-toggle');
338    $('.tab-content[data-tab-group="' + tabgroup + '"]').hide();
339    $('.tab-content[data-tab-group="' + tabgroup + '"][data-tab-pane="' + tab_toggle + '"]').show();
340}
341
342// Creates an English description of a number of minutes, in units of either min, hours, or days.
343function minutesDescription(minutes) {
344
345    if (minutes < 60)
346        return minutes + ' min';
347
348    if (minutes < (24 * 60))
349        return Math.round(minutes / 60) + ' hours';
350
351    return Math.round(minutes / 60 / 24) + ' days';
352}
353
354// Uses JavaScript's Localization to format the number for the Locale if available. This handles putting the thousands-separator and decimal appropriate for the local culture.
355function formatNumber(n) {
356    if (Number.prototype.toLocaleString && !isNaN(n)) {
357        return parseFloat(n).toLocaleString();
358    }
359
360    return n;
361}
362
363// Adds a single row with full table width and centered message. $table is a jQuery object holding the table element. Message can be HTML string
364function appendTableMessage($table, message, no_clear) {
365    var num_cols = $table.children('thead').find('th,td').length;
366    if (!no_clear) { $table.find('tbody').empty(); }
367    $table.find('tbody').append($('<tr>').append($('<td style="text-align: center;"></td>').prop('colspan', num_cols).html(message)));
368}
369
370// Parses any URL Query Parameters and puts them in an array
371function queryParams() {
372
373    var vars = [];
374    var q = document.URL.split('?')[1];
375    if (q != undefined) {
376        q = q.split('#')[0]; // Remove any hash fragment
377        q = q.split('&'); // split the variable pairs out
378        for (var i = 0; i < q.length; i++) {
379            var valpair = q[i].split('=');
380            vars.push(valpair[1]);
381            vars[valpair[0]] = valpair[1];
382        }
383    }
384
385    return vars;
386}
387
388function isValidEmail(email) { return regex_valid_email.test(email); }
389
390// Returns a string with the status of the property based on the input flags.
391// Truth Table (X=Don't Care)
392// Approved  | F | T | F | F |
393// Declined  | F | X | T | F |
394// Submitted | F | X | X | T |
395// ===========================
396// Result    | D | P | R | S |  Key: D=Draft, P=Published, R=Declined, S=Submitted
397function getListingStatus(approved, declined, submitted) {
398    if (approved) { return 'Published'; }
399    if (declined) { return 'Declined'; }
400    if (submitted) { return 'Submitted'; }
401    return 'Draft';
402}
403
404// Returns null if val is null, or empty/whitespace string, otherwise returns orig val.
405function nullEmpty(val) {
406    if (!val || $.trim(val) == '')
407        return null;
408    else
409        return val;
410}
411
412// Returns true if object member named 'member' is the only non-null value.
413function onlyValue(obj, member) {
414    // Make sure the member they are talking about has a value
415    if (!obj[member]) return false;
416
417    var keys = Object.keys(obj);
418    // Look for any members that have a value that aren't the member
419    var idx = keys.findIndex(function (key) {
420        return (obj[key] && key != this);
421    }, member);
422
423    // Return whether we found one
424    return idx < 0;
425}
426
427// Returns true if object members in array members are the only non-null values.
428function onlyValues(obj, members) {
429
430    // Make sure all the members asked for have values.
431    for (var i = 0; i < members.length; i++) {
432        if (!obj[members[i]]) return false;
433    }
434
435    var keys = Object.keys(obj);
436    // Look for any members that have a value that aren't in the members list
437    var idx = keys.findIndex(function (key) {
438        return (obj[key] && this.indexOf(key) < 0);
439    }, members);
440
441
442    // Return whether we found one
443    return idx < 0;
444}
445
446function getExtentVals() {
447
448    var default_extent_vals = [-97, -87.8, 28.8, 36.8];
449
450    if (global_branding && global_branding['MapInitialExtent']) {
451
452        var extent_vals = global_branding['MapInitialExtent'].split(',');
453        // There should be exactly 4 (bounding box corners)
454        if (extent_vals.length == 4) {
455            // Make sure all the extent values are valid floats
456            for (var evi = 0; evi < 4; evi++) {
457                if (!isNaN(extent_vals[evi])) {
458                    extent_vals[evi] = parseFloat(extent_vals[evi]);
459                }
460                else {
461                    return default_extent_vals;
462                }
463            }
464
465            return extent_vals;
466        }
467    }
468
469    return default_extent_vals;
470}
471
472function isNonNullEmpty(obj) {
473    if (obj != null && obj.length == 0)
474        return true;
475
476    return false;
477}
478
479// Takes a JavaScript function arguments object and creates a name value pair object from the variable names and the values passed.
480// See: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Functions/arguments
481function objectifyArguments(arg_list) {
482
483    // Extract the argument names from the text of the function itself. Remove newlines and spaces and extract the bit between the parens after the keyword function.
484    var arg_names_match = arg_list.callee.toString().replace(/\n/g, '').replace(/\s*/g, '').match(/^function\(([^)]+)\)/);
485    if (!arg_names_match)
486        return null;
487
488    // Create an empty object to store the name/values.
489    var values = {};
490
491    // Split the argument names (from the function text) and loop through them adding each as the name with it's value from the arg_list
492    var arg_names = arg_names_match[1].split(',');
493    for (var i = 0; i < arg_names.length; i++) {
494        values[arg_names[i]] = arg_list[i];
495    }
496
497    return values;
498}
499
500// Processes a string to make it suitable for a title by removing non-alpha-numeric chars and replacing space
500s with dashes as well as optionally limiting the lenth
501function makeURLTitle(text, len) {
502    return text.replace(/[^a-zA-Z0-9 ]/g, '').replace(/ +/g, '-').substr(0, len);
503}
504
505function setCookie(cname, cvalue, exdays) {
506    var d = new Date();
507    d.setTime(d.getTime() + (exdays * 24 * 60 * 60 * 1000));
508    var expires = "expires=" + d.toUTCString();
509    document.cookie = cname + "=" + cvalue + ";" + expires + ";path=/";
510}
511
512function getCookie(cname) {
513    var name = cname + "=";
514    var ca = document.cookie.split(';');
515    for (var i = 0; i < ca.length; i++) {
516        var c = ca[i];
517        while (c.charAt(0) == ' ') {
518            c = c.substring(1);
519        }
520        if (c.indexOf(name) == 0) {
521            return c.substring(name.length, c.length);
522        }
523    }
524    return "";
525}
526
527function isPasswordValid(password) {
528    if (!password) { return false; }
529
530    // Regular Exps don't have an AND operator, so it's difficult to write a regex that matches valid passwords, when validity is defined by something AND something else AND something else. But, regular expressions do have an OR operator, so just apply DeMorgan's theorem, and write a regex that matches invalid passwords
531    return !password.match('^(.{0,5}|[^0-9]*|[^A-Z]*|[^a-z]*)$');
532}
533
534function getRandom(length) {
535
536    return Math.floor(Math.pow(10, length - 1) + Math.random() * 9 * Math.pow(10, length - 1));
537
538}
539
540function countdownRedirect($counter) {
541
542    var cd = parseInt($counter.html());
543
544    if (cd <= 0) {
545        window.location = $counter.data('redirect-target');
546    }
547    else {
548        // If we are just starting, then don't decrement till after the 1st second.
549        if ($counter.is('.coundown-active')) {
550            cd--;
551            $counter.html(cd);
552        } else {
553            $counter.addClass('coundown-active');
554        }
555
556        window.setTimeout(function () { countdownRedirect($counter); }, 1000);
557    }
558}
559
560function formatFileSize(size) {
561    if (size < 1024) {
562        return size.toLocaleString() + " B";
563    }
564
565    if (size < 1024 * 1024) {
566        return (size / 1024).toFixed().toLocaleString() + " KB";
567    }
568
569    return (size / 1024 / 1024).toFixed(1).toLocaleString() + " MB";
570}
571
572function escapeHTML(html) {
573    var text = document.createTextNode(html);
574    var p = document.createElement('p');
575    p.appendChild(text);
576    return p.innerHTML;
577}

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.