Open and close panels based on jQuery cookies - javascript

I have the following variables which store the value of a set of cookies:
var filterDate = $.cookie('filterDate');
var filterArea = $.cookie('filterArea');
var filterCategory = $.cookie('filterCategory');
var filterType = $.cookie('filterType');
var filterLevel = $.cookie('filterLevel');
var filterAge = $.cookie('filterAge');
var filterAttendance = $.cookie('filterAttendance');
The name of the cookies and variables are also the ids of some elements that are on the page so for example: <div id="filterDate"></div>
What I want to do is very minimally (i.e. less code as possible) is check if any have the value of open and if so then run the code inside.
if (filterDate == 'open' || filterArea == 'open' || filterCategory == 'open' || filterType == 'open' || filterLevel == 'open' || filterAge == 'open' || filterAttendance == 'open') {
$('#' + filter).find('.menuBox.nav ul').show();
$('#' + filter).find('.menuBox.nav p').hide();
$('#' + filter.find('h3 span').addClass('active');
}
How do I get the above to work as filter works for all the cookies without having to duplicate it per cookie and panel?

A compact solution may be:
//The array below allows you to easily add new filters
var filterNames = ["filterDate", "filterArea", ..., "filterAttendance"];
for (var i in filterNames) {
var filterName = filterNames[i];
var filterStatus = $.cookie(filterName);
if (filterStatus == 'open') {
$('#' + filterName).find('.menuBox.nav ul').show();
$('#' + filterName).find('.menuBox.nav p').hide();
$('#' + filterName.find('h3 span').addClass('active');
}
}

I wasn't clear if you were looking to trigger a different function based on the filter name. If so, you could store all the functions mapped to your cookies, then iterate over the names of the cookies, triggering the associated function if true: e.g.
var cookieList = ["filterDate", "filterArea"...];
var cookieMap = {"filterDate"=filterDateFn, "filterArea"=filterAreaFn...};
for (var i=0; i<numCookies; i++) {
if ($.cookie(cookieList[i]) == "open") {cookieMap[cookieList[i]]();}
if you only want to run one function, then you could skip making a cookieMap, and just run whatever success trigger you want, then break the for loop at that point.

Make an array of cookie names and then generate an object (map of key:pair values), where
the keys are the items from array and the values are the values of an appropriate cookies.
Then use loops to iterate through arrays/objects:
var filters = ['filterA', 'filterB', 'filterC'],
cookies1 = {},
cookies2 = {};
for(var i = 0, f; f = filters[i++];) {
// really here will be $.cookie(f); instead of 'open':
cookies1[f] = cookies2[f] = 'open';
}
// make one of second cookies set 'closed' for testing purpose:
cookies2['filterA'] = 'closed';
function allOpen(cookies) {
for(var i in cookies) {
if(cookies[i] != 'open') {
return false;
}
}
return true;
}
alert(allOpen(cookies1) + ', ' + allOpen(cookies2));
​

Related

Can't update javaScript global variable

Here I have global variable userId, and i want to update it inside signInUserFunction(), to use is in other function. I have tried to define it using var, window, But all these didn't help. This variable doesn't update. As i see its about AJAX async. So, what can i do with it?
And yes, I know that its not good to make authentication with JS, I am quite new to it. So, I am just creating random methods to improve.
var userId = 1;
function signInUser() {
$.getJSON('http://localhost:8887/JAXRSService/webresources/generic/getAllUsers', function(data) {
var items = [];
var i = 0;
$.each(data, function(firstname, value) {
var str = JSON.stringify(value);
data = JSON.parse(str);
var innerId;
for (p in data) {
innerId = data[p].id;
if ($('#nameSignIn').val() == data[p].first_name && $('#passwordSignIn').val() == data[p].password) { //
userId = innerId;
window.location.href = "content.html";
break;
} else {
i++;
if (i == data.length) {
alert("Ощибка в логине или пароле!")
}
}
}
});
});
}
How are you determining whether or not it has been set? It looks like immediately after you set it, you navigate to a different page. When you get to that page, you will have an entirely new window.
Try alerting the value before navigating away.
EDITED: Here is how you could pass it to the other page (but you shouldn't do this in a real app)
window.userId=innerId;
alert(window.userId);
//this isn't a very secure way to do this. I DON'T recommend this
window.location.href = "content.html?id=" + innerId ;
Then in the other page, you could access it off the document.location:
alert(document.location.toString().split("?id=")[1]);
After reading my comments, you may want to try this:
var userId = 1;
function signInUser(){
$.getJSON('http://localhost:8887/JAXRSService/webresources/generic/getAllUsers', function(data){
var items = [], actors = data.Actors, l = 0;
$.each(actors, function(i, o){
l++;
if($('#nameSignIn').val() === o.first_name && $('#passwordSignIn').val() === o.password){
userId = o.id;
// this will redirect before any other code runs -> location = 'content.html';
if(l === actors.length){
alert('End of Loop');
}
}
});
});
}
signInUser();
I would not store sensitive data in JSON such as passwords. Use a database. There is no need to get all the data at the same time either.
Using the idea #mcgraphix proposed (and giving you the same warning...this would certainly not be the way to transfer data like this in a production environment), here is one way to do it:
function signInUser() {
var url = 'http://localhost:8887/JAXRSService/webresources/generic/getAllUsers';
var userId;
$.getJSON(url, function(data) {
$.each(data.Actors, function(index, actor) {
// Cache the values of the #nameSignIn and #passwordSignIn elements
var name = $('#nameSignIn').val();
var password = $('#passwordSignIn').val();
if (actor.first_name === name && actor.password === password) {
// We have found the correct actor.
// Extract its ID and assign it to userId.
userId = actor.id;
window.location.href = "content.html?userId=" + userId;
}
});
// This alert should only be reached if none of the actor objects
// has a name and password that matches your input box values.
alert("Ощибка в логине или пароле!");
});
}
// On the next page...
// Top answer from http://stackoverflow.com/questions/2090551/parse-query-string-in-javascript
// This approach can handle URLs with more than one query parameter,
// which you may potentially add in the future.
function getQueryVariable(variable) {
var query = window.location.search.substring(1);
var vars = query.split('&');
for (var i = 0; i < vars.length; i++) {
var pair = vars[i].split('=');
if (decodeURIComponent(pair[0]) == variable) {
return decodeURIComponent(pair[1]);
}
}
console.log('Query variable %s not found', variable);
}
var userId = getQueryVariable('userId');
Thanks you for help.Ended it all with usage of:
sessionStorage.getItem('label')
sessionStorage.setItem('label', 'value')

Persist cookie form values across multiple pages

The setting: I have a form that captures$thisSearch.val(), saves it as a cookie, and pushes to an array. The form is an overlay triggered from a menu item in the header so this can appear on any page in the site.
The issue is that it only seems to save/persist the input values on/from that page it was entered on. I'm trying to collect all these values into one list.items() array that can be entered anywhere in the site.
I've tried pushing the string to the array myself instead of the add function and moved the dom around for the search form.
I can update question when I know what to specifically ask. Any pointers / concepts I should be aware of for this would be great.
var cookieList = function(cookieName) {
var cookie = $.cookie(cookieName);
var items = cookie ? cookie.split(/,/) : new Array();
return {
"add": function(val) {
items.push(val);
$.cookie(cookieName, items.join(','));
},
"items": function() {
return items;
}
}
}
var list = new cookieList("PreviousSearches");
$searchSubmit.on('click', function() {
var $thisSearch = $(this).prev().find($searchInput);
if( $thisSearch.val() == '' ) {
alert('Please enter a search term');
console.log( list );
return false;
} else {
searchTerm = $thisSearch.val()
list.add( searchTerm );
}
});
var searchTerms = list.items();
var total = searchTermsFiltered;
var searchTermsFiltered = searchTerms.filter(Boolean).slice( - 5 ).reverse();
var searchtermClean = searchTermsFiltered.join();
$.each($(searchTermsFiltered), function(i,v){
if (!window.location.origin)
window.location.origin = window.location.protocol+"//"+window.location.host;
var lastURLRaw = window.location.origin+'/bch/?s='+v;
var lastURL = lastURLRaw.replace(/ /g, '+');
listItem = '<li>'+v+'</li>';
$('.tags, .search-tags').append(listItem );
});
I found the path specifier from jquerys $.cookie in this top answer below.
$.cookie(cookieName, items.join(',') , { path: '/' }); from my code.
why are my jquery cookies not available across multiple pages?

How to Delete List Item in a Custom Page?

I have a custom Dashboard page (Dashboard.aspx) that I made - it is not located inside the list, rather inside Pages folder.
I created this Dashboard to replace SharePoint's default "AllItems.aspx".
However, I could not replicate the onClick event of "Delete Item" from the SharePoint default list view.
Can anyone provide code snippets of how to delete a list item from a custom page?
P.S.: My custom page already has the ID and List Name. I appreciate your responses!
The function provided by Microsoft is this one:
function DeleteListItem() {
ULSrLq: ;
if (!IsContextSet()) return;
var b = currentCtx,
e = currentItemID,
g = currentItemFSObjType,
c = L_STSRecycleConfirm_Text;
if (!b.RecycleBinEnabled || b.ExternalDataList) c = L_STSDelConfirm_Text;
if (b.HasRelatedCascadeLists && b.CascadeDeleteWarningMessage != null) c = b.CascadeDeleteWarningMessage + c;
if (confirm(c)) {
var h = L_Notification_Delete,
f = addNotification(h, true),
a = b.clvp;
if (b.ExternalDataList && a != null) {
a.DeleteItemCore(e, g, false);
a.pendingItems = [];
a.cctx.executeQueryAsync(function () {
ULSrLq: ;
if (typeof a.rgehs != "undefined") {
if (a.rgehs.length == 1 && a.rgehs[0].get_serverErrorCode() == SP.ClientErrorCodes.redirect) {
GoToPage(a.rgehs[0].get_serverErrorValue());
return
}
removeNotification(f);
a.ShowErrorDialog(RefreshOnDialogClose)
} else RefreshPage(SP.UI.DialogResult.OK)
}, function () {
ULSrLq: ;
removeNotification(f);
typeof a.rgehs != "undefined" && a.ShowErrorDialog()
})
} else {
var d = b.HttpPath + "&Cmd=Delete&List=" + b.listName + "&ID=" + e + "&NextUsing=" + GetSource();
if (null != currentItemContentTypeId) d += "&ContentTypeId=" + currentItemContentTypeId;
SubmitFormPost(d)
}
}
}
With that you should be able to find what you need for your case.
If you use some jQuery/JavaScript in your page, you may also want to check SharepointPlus that provides some useful functions (like to get data from a list or to delete an item).
I figured it out!
I have a JS library called "SPAPI_Lists", which is from SharePoint Services, I believe.
It provides a function called quickDeleteListItem(listName, listItemId).
Code looks like this:
var urlThatContainsList = 'http://www.samplesite.com/sample';
var listName = 'Sample List';
var listItemId = 3;
new SPAPI_Lists(urlThatContainsList).quickDeleteListItem(listName, listItemId);

How can I save javascript variables locally?

I am a beginner in Javascript/Jquery and I am making a mobile web app using jquery mobile and jquery and I can't figure out how to display all my inputs in one place. No matter how many data I enter into the form it always displays the last entered .Please, any help?
$(document).ready(function() {
if(localStorage['linrval'],localStorage['linrdate']){
$('#inrhist').prepend('<div class="inrval">'+localStorage['linrdate']+ ' ---- ' +localStorage['linrval']+ '</div>');
};
$('#inrbtn').click(function(){
var inrval=$('input[name=user]').val();
var inrdate=$('input[name=dateinr]').val();
localStorage.setItem('linrval',inrval);
localStorage.setItem('linrdate',inrdate);
$('#inrhist').prepend('<div class="inrval">'+inrdate+ ' ---- ' +inrval+ '</div>');
});
Couple of things need to change here every time you need to add into array instead of you update the item value with same property. localStorage only supports strings.
$(document).ready(function() {
//localStorage.removeItem("users");
var userStr = localStorage.getItem('users');
if (userStr != null && userStr != undefined) {
var jsonObj = JSON.parse(userStr);
console.log("onload value", jsonObj);
$.each(jsonObj.items, function(i, item) {
$('#inrhist').prepend('<div class="inrval">'+item.user +'--'+item.dateinr+'</div>');
});
}
$('#inrbtn').click(function () {
var dataItems = { items: [] };
var inrval = $('input[name=user]').val();
var inrdate = $('input[name=dateinr]').val();
var item = { user: inrval, dateinr: inrdate };
var usersList = localStorage.getItem('users');
var jsonObj;
if (usersList == null) {
dataItems.items.push(item);
jsonObj = JSON.parse(JSON.stringify(dataItems));
}
else {
jsonObj = JSON.parse(usersList);
jsonObj.items.push(item);
}
jsonStr = JSON.stringify(jsonObj);
console.log(jsonStr);
localStorage.setItem("users", jsonStr);
$('#inrhist').prepend('<div class="inrval">' + inrdate + '--' + inrval + '</div>');
});
});
LIVE DEMO
You have this:
if(localStorage['linrval'],localStorage['linrdate']){...}
Such expression is true if and only if localStorage['linrdate'] is true. The value for localStorage['linrval'] is basically ignored.
Perhaps you want this:
if( localStorage['linrval'] || localStorage['linrdate'] ){...}
^^
You're also overwriting your localStorage values:
localStorage.setItem('linrval',inrval);
localStorage.setItem('linrdate',inrdate);

Excel Type Filter popup for Jqgrid

I need to have a filter ( like in Excel spread Sheet) to embedded to the 'jquery' dialog popup. in this case i need to show all the unique values in the column and check box just before that value to select to the user. when user pressed filter button i need to filter only the values that user requested through the check boxes.
Can any one please let me any approach that i must follow.
Thanks in advance for your help and valuable time.
I was able to develop basic grid with excel kind of filter feature. any one who will come across this type of requirement can use this answer as a foundation.
I use this answer from 'Oleg' to embed the filter popup screen to the basic 'jqgrid'.
in the jqgrid page declare this array with the attributes (columns) that needs to display the filter screen popup.
var applyFilterColumnNames = ['Id','Type','custId','UserId'];
and the column model should be as follows -
colModel :[
{name:'Id', index:'Id',hidden: true,sortable: true},
{name:'custId', index:'custId', width:140,align:"left",sortable: true,search : false},
{name:'Type', index:'Type', width:120,align:"left",sortable: true,search : false},
{name:'UserId', index:'UserId', width:150,align:"left",sortable: true,search : false},
],
used that reference answer to embed the filter button function.
gr.closest("div.ui-jqgrid-view").find("div.ui-jqgrid-hdiv table.ui-jqgrid-htable tr.ui-jqgrid-labels > th.ui-th-column > div.ui-jqgrid-sortable")
.each(function () {
var idPrefix = "jqgh_" + gr[0].id + "_";
var idIndex = (this.id).substr(idPrefix.length,this.id.length) ;
if(includeInArray(applyFilterColumnNames,idIndex)){
jq('<button id=btn_'+idIndex+'>').css({float: "right", height: "17px"}).appendTo(this).button({
icons: {
primary: "ui-icon-gear"
},
text: false
}).click(function (e) {
var idPrefix = "jqgh_" + gr[0].id + "_";
// thId will be like "jqgh_list_name"
var thId = jq(e.target).closest('div.ui-jqgrid-sortable')[0].id ;
if (thId.substr(0, idPrefix.length) === idPrefix) {
var colName = thId.substr(idPrefix.length);
//alert('Clicked the button in the column "' + colName + '"');
constructFilter(colName);
return false;
}
});
//}
}
});
Below is the script i used to filter the jqgrid according to the filters
//Variables that use in filtering operation
var originalData = null;
var filteredData;
var selectedFilters = new Object();
var chkBoxElement;
var firstSortColumn;
function constructFilter(columnName){
// for the first initiation of the filter populate current grid data to an array
if(originalData == null || originalData == 'null'){
try{
// this array will hold the initail data set of the grid
originalData = gr.jqGrid('getGridParam','data');
// set the first sorting grid column
firstSortColumn = columnName;
// check if column is associated with a formatter. if so format the originalData values accordingly.
formatGridData(columnName);
}catch(e){}
}
var colData = new Array();
var filterDataSet;
// if current column is equal to initial sorted column set all posible values to the check boxes in the
// filter screen to select. ( since this is the master sorting column and other columns will filter according to that)
if(columnName == firstSortColumn){
filterDataSet = originalData;
}else{
// set current grid data set to show as checkboxes in the filter page
filterDataSet = gr.jqGrid('getCol',columnName,false);
}
for(key in filterDataSet){
// check box element object that will hold the checkbox label and its state ( true / false)
chkBoxElement = new Object();
chkBoxElement.id = getValueFromArray(filterDataSet[key],columnName);
if(typeof(chkBoxElement.id)== 'undefined'){
break;
}
// if this id is saved in previous filtering event checked option will set to true.
if(typeof(selectedFilters[columnName]) != 'undefined'){
if (includeInArray(selectedFilters[columnName],chkBoxElement.id)){
chkBoxElement.selected = true;
}else{
chkBoxElement.selected = false;
}
}
colData.push(chkBoxElement);
}
// removing duplicates
var uniqueValues = removeDuplicates(colData);
// sort the array without duplicate with the custom comparator
uniqueValues.sort(sortComparator);
// open the filter screen. return type will captured in the 'seletedElements' variable as pipe separated string
seletedElements = window.showModalDialog(filterUrl,uniqueValues,"dialogWidth:400px;dialogHeight:250px;center:yes;resizable:no;status:no;help:no;");
if(seletedElements != null && seletedElements != 'null'){
// get selected values to the array
selectedFilters[columnName] = seletedElements.split("|");
}else{
//user just close the popup (using close button) will return without doing anything
return;
}
if(columnName == firstSortColumn){
// refine filter with the non filtered data set
refillGrid(seletedElements,columnName,originalData);
}else{
// send current data set to refine
var currentDataSet = gr.jqGrid('getGridParam','data');
refillGrid(seletedElements,columnName,currentDataSet);
}
}
function formatGridData(columnName){
var isFormatter = gr.jqGrid("getColProp",columnName);
if(typeof isFormatter.formatter !== 'undefined') {
if(jq.isFunction( isFormatter.formatter ) ) {
for(key in originalData){
var plainValue = originalData[key][columnName];
var formattedVal = isFormatter.formatter.call(null,plainValue,null,null,null);
originalData[key][columnName] = formattedVal;
}
}
}
}
function resetFilters(){
for(key in applyFilterColumnNames){
jq("#btn_"+applyFilterColumnNames[key]).button("option", {
//icons: { primary: this.checked ? 'ui-icon-check' : 'ui-icon-closethick' }
icons: { primary: 'ui-icon-gear'}
});
}
gr.jqGrid("setCaption",gridCaption);
refreshGrid(originalData);
originalData = null;
firstSortColumn = null;
selectedFilters = new Object();
}
function refillGrid(seletedElements,columnName,filterDataSet){
var filteredData= new Array();
var elementsArray;
try{
elementsArray = seletedElements.split("|");
}catch(e){
// this exception happens when user simply open the filter screen
// do nothing and close it.
trace('Error in filter splitting -'+e);
return;
}
// When user de-select all check boxes from the popup screen
if(elementsArray == ""){
refreshGrid(originalData);
return;
}
// refine the grid data according to the filters
var mydata = filterDataSet;
for(i=0;i<elementsArray.length;i++){
var filterElement = elementsArray[i];
for(j = 0;j<mydata.length;j++){
if(filterElement==getValueFromArray(mydata[j],columnName)){
filteredData.push(mydata[j]);
}
}
}
// change the button icon to indicate that the column is filtered
changeButtonIcon(columnName);
// update the column header to indicate sort by column
changeGridCaption(columnName);
// fill the grid according to the passed array
refreshGrid(filteredData);
}
function changeGridCaption(columnName){
// get columns name array
var columnNames = gr.jqGrid('getGridParam','colNames');
// get column model array
var colModel = gr.jqGrid('getGridParam','colModel');
var colModelIndex=null;
if (firstSortColumn == columnName){
for(key in colModel){
try{
if (colModel[key].name == firstSortColumn){
colModelIndex = key;
break;
}
}catch(e){}
}
if(colModelIndex != null){
var columnName = columnNames[colModelIndex];
gr.jqGrid("setCaption",gridCaption + " - Filtered based on : "+columnName);
}
}
}
function changeButtonIcon(columnName){
//change the button Icon
jq("#btn_"+columnName).button("option", {
//icons: { primary: this.checked ? 'ui-icon-check' : 'ui-icon-closethick' }
icons: { primary: 'ui-icon-link'}
});
}
function getValueFromArray(obj,columnName){
if(obj !=null && typeof(obj)!='undefined'){
// if obj param is string just return it
if(typeof obj =='string'){
return obj;
}else{
return obj[columnName];
}
}
}
function sortComparator(a,b){
try{
var aId = a.id.toLowerCase();
var bId = b.id.toLowerCase();
if (aId < bId) {return 1}
if (aId > bId) {return -1}
}catch(e){
return 0;
}
}
function includeInArray(arr,obj) {
//alert(arr);
return (arr.indexOf(obj) != -1);
}
function refreshGrid(results) {
gr.jqGrid('clearGridData')
.jqGrid('setGridParam', { data: results })
.trigger('reloadGrid');
}
function removeDuplicates(valueArray){
var arr = {};
for ( i=0; i < valueArray.length; i++ ){
if(valueArray[i].id != null){
arr[valueArray[i].id] = valueArray[i];
}
}
valueArray = new Array();
for ( key in arr ){
valueArray.push(arr[key]);
}
return valueArray;
}
If something wrong here please let me know.this solution is working fine. but i really appreciate the comments in therms of performance and code best practices.

Categories

Resources