У меня есть страница с блоками информации, которые вы можете включить и выключить. Чтобы узнать, какие блоки вы хотите показать, я сохранил их состояние в Угловом файле cookie.Персонализация страницы с использованием 1 углового файла cookie
HTML:
<block-toggle-btn block-ref="{{ id }}" climbnodes="3" mytarget=".block__content"></block-toggle-btn>
Угловая Директива:
myApp.directive('blockToggleBtn', ['$cookies', function($cookies) {
return {
restrict: 'E',
template:'-',
link: link,
scope: {
blockRef: '@',
mytarget: '@', // target .cssclass
climbnodes: '=' // Used to climb the dom
}
};
function link(scope, element, attr) {
var parent = element.parent();
for (var i = 0; i < scope.climbnodes; i++) {
parent = parent.parent();
}
var blockRef = scope.blockRef;
var blockToggleCookie = $cookies.get(blockRef);
scope.toggleVisibility = function() {
element.toggleClass('invisible');
parent.find(scope.mytarget).slideToggle();
if (element.hasClass('invisible')) {
element.html('+');
blockVisible = 'invisible';
scope.setBlockToggleCookie(blockRef, blockVisible);
} else {
element.html('-');
blockVisible = 'visible';
scope.setBlockToggleCookie(blockRef, blockVisible);
}
};
scope.setBlockToggleCookie = function(blockRef, blockVisible) {
var expireDate = new Date();
expireDate.setTime(2144232732000);
$cookies.put(blockRef, blockVisible, {'expires': expireDate});
};
// If cookie is set keep block closed
if (blockToggleCookie == 'invisible') {
scope.toggleVisibility();
}
element.bind('click', function(event) {
event.preventDefault();
scope.toggleVisibility();
});
}
}]);
Это отлично работает на данный момент, но он устанавливает куки для каждого "блока" информации я показываю. Мне нужно, вместо этого, переместить все это в один файл cookie, содержащий информацию о том, какие блоки показывать и что скрывать.
Я знаю, это звучит как большой вопрос, и это так, но я полагал, что было бы более полезно публиковать все это, а не каждую часть, с которой я борюсь, чтобы я мог лучше понять и собрать все это вместе. В настоящее время я сбился с кроличьей дыры, пытаясь понять, как создать массив объектов для хранения в Угловом $cookies.putObject
. Я получаю странные результаты, когда я пытаюсь сделать .push()
в массив объектов. Например, с помощью этой функции я попытался вызвать из события щелчка:
scope.buildCookieObj = function(blockRef, blockVisible) {
scope.cookieItems.push({blockRef: blockRef, blockVisible: blockVisible});
};
Я знаю, что это не является услугой написания кода, и я действительно пытался сделать этот шаг за шагом, но обнаружил, что потерял в сорняках , Я новичок в Angular и знаю, когда он его использует, или вставлять JQuery становится немного подавляющим. Поэтому даже любые советы о направлении принять это приветствуются.
EDIT:
Я думаю, что я сделал некоторый прогресс (хотя это уже поздно, так что я не совсем 100% это работает, но я так думаю). Это обновленный код, устанавливающий объект cookie. Теперь мне просто нужно извлечь и перебрать его, чтобы определить (из файла cookie), изначально блоки которых должны быть закрыты.
myApp.directive('blockToggleBtn', ['$cookies', function($cookies) {
var cookieItems = [];
return {
restrict: 'E',
template:'-',
link: link,
scope: {
blockRef: '@',
mytarget: '@', // target .cssclass
climbnodes: '=' // Used to climb the dom
}
};
function link(scope, element, attr) {
var parent = element.parent();
for (var i = 0; i < scope.climbnodes; i++) {
parent = parent.parent();
}
scope.toggleVisibility = function() {
element.toggleClass('invisible');
parent.find(scope.mytarget).slideToggle();
if (element.hasClass('invisible')) {
element.html('+');
blockVisible = 'invisible';
scope.buildCookieObj(blockRef, blockVisible);
} else {
element.html('-');
blockVisible = 'visible';
scope.buildCookieObj(blockRef, blockVisible);
}
};
scope.buildCookieObj = function(blockRef, blockVisible) {
// If that item already exists remove so we can replace with new visibility setting
$.each(cookieItems, function(i){
if(cookieItems[i].blockRef === blockRef) {
cookieItems.splice(i,1);
return false;
}
});
cookieItems.push({blockRef: blockRef, blockVisible: blockVisible});
scope.setBlockToggleCookie(cookieItems);
};
scope.setBlockToggleCookie = function(cookieItems) {
// Maximum value for cookie expiration, i.e. the closest thing to
// "never expire" is the year 2038. See:
// http://stackoverflow.com/questions/532635/javascript-cookie-with-no-expiration-date/532638#532638 and
// http://stackoverflow.com/questions/34586494/make-cookies-never-expire-with-angularjs
var expireDate = new Date();
expireDate.setTime(2144232732000);
$cookies.putObject('personalization', cookieItems, {'expires': expireDate});
};
element.bind('click', function(event) {
event.preventDefault();
scope.toggleVisibility();
});
}
}]);
Дальнейший прогресс, за исключением противоположности действительно:
Реализованных У меня есть дополнительная проблема настройки куки в том, что он получает перезаписан каждый раз, когда вы вновь открыть приложение и переключение блоков и выключение. Все еще пытаюсь продумать эту логику. Если я назову его чем-то зависимым от времени или сеанса, а что нет, не уверен, как я тогда извлечу это, чтобы перебрать его.
Что касается извлечения печенья и установив соответствующие блоки, которые будут включаться и выключаться, я сделал это, чтобы получить значения:
var personalizationCookie = $cookies.getObject('personalization');
console.log(personalizationCookie);
$.each(personalizationCookie, function(key, value) {
var blockRef = value.blockRef;
var blockVisible = value.blockVisible;
console.log(blockRef, blockVisible);
});
Но я не понял, как целевые блоки , Я подумал, что, возможно, просто JQuery .find()
, но я думаю, что dom еще не отображен, поэтому он ничего не находит. Обернуть его в $(document).ready()
не работает. Я предполагаю, потому что у нас есть экран загрузки, который будет «загружен», даже если элементы dom, которые я ищу, по-прежнему не являются. Но это может быть что-то особенное для нашего приложения. Я должен спросить начальных разработчиков. Просто подумал, что я обновляю здесь всю информацию.
EDIT # 2: Так что я придумал решение, которое работает, и я подумал о «отвечая» на мой вопрос здесь, но решение, которое я придумал еще нуждается в некоторой доработке. Вся логика находится в директиве, и я знаю, что это не так, как должно быть.Я сказал, что хотел бы опубликовать его здесь, если это было полезно для всех, а также потому, что я работаю над тем, чтобы переместить всю логику в сервисы и приветствовал бы любое направление с этим. (Я уже вниз службы против завода вопрос отверстие, и это достаточно сложная, даже начав реальную задачу!)
myApp.directive('blockToggleBtn', ['$cookies', function($cookies) {
var personalizationCookie = $cookies.getObject('personalization');
return {
restrict: 'E',
template:'-',
link: link,
scope: {
blockRef: '@',
mytarget: '@', // target .cssclass
climbnodes: '=' // Used to climb the dom
}
};
function link(scope, element, attr) {
var parent = element.parent();
for (var i = 0; i < scope.climbnodes; i++) {
parent = parent.parent();
}
var blockRef = scope.blockRef;
scope.toggleVisibility = function() {
element.toggleClass('invisible');
parent.find(scope.mytarget).slideToggle();
if (element.hasClass('invisible')) {
element.html('+');
blockVisibility = 'invisible';
scope.buildCookieObj(blockRef, blockVisibility);
} else {
element.html('-');
blockVisibility = 'visible';
scope.buildCookieObj(blockRef, blockVisibility);
}
};
scope.buildCookieObj = function(blockRef, blockVisibility) {
// If that item already exists remove so we can replace with new visibility setting
$.each(personalizationCookie, function(i){
if(personalizationCookie[i].blockRef === blockRef) {
personalizationCookie.splice(i,1);
return false;
}
});
personalizationCookie.push({blockRef: blockRef, blockVisibility: blockVisibility});
scope.setBlockToggleCookie(personalizationCookie);
};
scope.setBlockToggleCookie = function(personalizationCookie) {
// Maximum value for cookie expiration, i.e. the closest thing to
// "never expire" is the year 2038. See:
// http://stackoverflow.com/questions/532635/javascript-cookie-with-no-expiration-date/532638#532638 and
// http://stackoverflow.com/questions/34586494/make-cookies-never-expire-with-angularjs
var expireDate = new Date();
expireDate.setTime(2144232732000);
$cookies.putObject('personalization', personalizationCookie, {'expires': expireDate});
var personalizationCookie = $cookies.getObject('personalization');
};
// Check to see if there's a cookie for this element's block
// If yes, then toggle minus to plus and hide the block content the button refers to
$.each(personalizationCookie, function(key, value) {
if ((value.blockRef == scope.blockRef) && (value.blockVisibility == 'invisible')) {
parent.find(scope.mytarget).hide();
element.html('+').addClass('invisible');
}
});
element.bind('click', function(event) {
event.preventDefault();
scope.toggleVisibility();
});
}
}]);