Javascript.RU

Создать новую тему Ответ
 
Опции темы Искать в теме
  #1 (permalink)  
Старый 21.10.2020, 06:37
Аспирант
Отправить личное сообщение для Aruta Посмотреть профиль Найти все сообщения от Aruta
 
Регистрация: 08.07.2019
Сообщений: 85

Срабатывает только только else...
Добрый день!
Задача:
- при нажатии на li или его дочерний <div class="filter__name filter__list"> блок li должен окрашивать границу в цвет activeColor
- при повторном нажатии style по-умолчанию цвет становится (в коде - для проверки пока код пишется - сделал черный цвет, чтобы в глаза бросалось сразу отрабатывает ли, но не отрабатывает)
- это справедливо для всех li, кроме последнего "CLEAR" - на нём ничего не происходит.

Не могу понять почему блок if-else отрабатывает не верно - он красит в нужный цвет при первом нажатии, но при повторном не снимает окраску границы.
Хочется понять в чем ошибка и узнать подсказки, а не готовое решение
Подскажите, пожалуйста!

P.S. если проще посмотреть на live версии, то могу залить

HTML:
<ul class="results__filter-inner dflex">
   <!-- Блок конкретного фильтра. Далее каждая группа фильтров обозначена li id="название фильтра" -->
    <li id="gender">
        <!--Блок названия группы фильтра и стрелочки -->
        <div class="filter__name filter__list">
             <div>Gender</div>
             <i class="arrow down"></i>
        </div>
        <!--Раскрывающийся список группы -->
        <div class="filter__name__list-wrap dflex" style="display: none;">
             <div class="name__list-inner">
                  <div class="name__list">
                       <input type="checkbox" id="chk_men" class="toggle" name="chk_men" value="Men">
                        <label for="chk_men" class="name__list-label">Men</label>
                  </div>
                  <div class="name__list">
                       <input type="checkbox" id="chk_women" class="toggle" name="chk_women" value="Women">
                       <label for="chk_women" class="name__list-label">Women</label>
                  </div>
             </div>
        </div>
    </li>
    <li id="priority">
        <div class="filter__name filter__list">
             <div>Priority</div>
                  <i class="arrow down"></i>
        </div>
        <div class="filter__name__list-wrap" style="display: none;">
             <div class="name__list-inner">
                  <div class="name__list">
                       <input type="checkbox" id="chk_color" class="toggle" name="chk_color" value="Color">
                       <label for="chk_color" class="name__list-label">Color</label>
                  </div>
                  <div class="name__list">
                       <input type="checkbox" id="chk_style" class="toggle" name="chk_style" value="Style">
                        <label for="chk_style" class="name__list-label">Style</label>
                  </div>
             </div>
        </div>
    </li>
    <li id="prod_type">
        <div class="filter__name filter__list">
             <div>Product type</div>
             <i class="arrow down"></i>
        </div>
        <div class="filter__name__list-wrap" style="display: none;">
             <div class="name__list-inner">
                  <div class="name__list">
                       <input type="checkbox" id="chk_shirt" class="toggle" name="chk_shirt" value="Shirt">
                       <label for="chk_shirt" class="name__list-label">Shirt</label>
                  </div>
                  <div class="name__list">
                       <input type="checkbox" id="chk_blouse" class="toggle" name="chk_blouse" value="Blouse">
                       <label for="chk_blouse" class="name__list-label">Blouse</label>
                  </div>
                  <div class="name__list">
                       <input type="checkbox" id="chk_top" class="toggle" name="chk_top" value="Top">
                       <label for="chk_top" class="name__list-label">Top, T-shirt, Sweatshirt</label>
                  </div>
                  <div class="name__list">
                       <input type="checkbox" id="chk_sweater" class="toggle" name="chk_sweater" value="Sweater">
                       <label for="chk_sweater" class="name__list-label">Sweater</label>
                  </div>                                                                                                                                                     
             </div>
        </div>
    </li>
    <li>
        <input type="checkbox" id="dublicate" class="toggle" name="dublicate">
        <label for="dublicate">Remove dublicate</label>
    </li>
    <li>
       <div class="filter__name clear">
           <div>Clear</div>
       </div>
    </li>
</ul>

JS:
const buttons = document.querySelectorAll('.results__filter-inner>li');
const subMenuAll = document.querySelectorAll('.filter__name__list-wrap');
let activeBorderColor ='#ff7bac';
let activeColor = '#220718';

//функция HIDE всех нужных блоков по классу
const dnoneStyle = () => {	
	subMenuAll.forEach((dnone) => {
		dnone.style.display = "none";
	});
}
//Сброс цвета активного фильтра на "по-умолчанию" неактивный
const resetColorBorder = () =>{
	buttons.forEach((el) => {
				el.style.removeProperty('border-color');	
			})
} 

//Закрытие меню при клике вне меню
const close = () => {
	document.addEventListener('click', e => {
		if(!buttons.target) {
			subMenuAll.forEach((e) => {
				dnoneStyle();	
			})		
		}
	})
}

// Открытие/закрытие подменю при нажатии на название фильтра
buttons.forEach((elem) => {	
	let subMenu = elem.querySelector('.filter__name__list-wrap');
	let clear = elem.querySelector('.clear');
	subMenuAll.forEach( (chbx) => {		 
		let inputs = chbx.querySelectorAll('input');		
		for (let i=0; i<inputs.length; i++){
			inputs[i].onchange = () =>{
				let inputParent = chbx.parentNode;    //обращаемся к родителю элемента
				if (inputs[i].checked){		
					inputParent.style.borderColor = activeBorderColor;
					inputParent.style.color = activeColor;
				} else {
					inputParent.style.removeProperty('border-color');
					inputParent.style.removeProperty('color');
				}
			}
		}
	})	
	//этот блок не работает - срабатывает только условие else почему-то. 
	const notClear = () =>{
		if (!clear){
			if (elem.style.borderColor == activeBorderColor){
				console.log('on')
				elem.style.borderColor='black';
				elem.style.removeProperty('color');
			} else {
				console.log('off')
				// filterButtons();
				elem.style.borderColor = activeBorderColor;
				elem.style.color = activeColor;				
			}
		}
	}
	//конец плохо работающего блока

	elem.addEventListener('click', (subElem) => {		
			// elem.style.borderColor = activeBorderColor;
			const filterButtons = () => {
			subElem.stopPropagation();
			if (subMenu){	//если имеется выпадающий список у фильтра
				if (subMenu.style.display != "block"){
					dnoneStyle();
					subMenu.style.display = "block";
					//перебор checkbox, чтобы отмечался только один в фильтре
					let inputs= elem.getElementsByTagName('input');
					for (var i = inputs.length-1; i >= 0; -- i) {
						inputs[i].onclick = function () {
							for (var j = inputs.length-1; j >= 0; -- j) {
								if (inputs[j] != this) inputs[j].checked = false;
							}
						}
					}
					activeFilter();
					notClear();
					//запрет на всплытие клика выше выпадающего списка, т.е. не будет срабатывать на родителе.
					subMenu.addEventListener('click', (g) => {
						g.stopPropagation();
					});
				} else {
					dnoneStyle();
				}
			} else {	//если нет выпадающего списка у фильтра
				notClear();
				return;
			}
		}
		filterButtons();
		
	});
});

close();

Последний раз редактировалось Aruta, 21.10.2020 в 07:55.
Ответить с цитированием
  #2 (permalink)  
Старый 21.10.2020, 07:32
Аватар для рони
Профессор
Отправить личное сообщение для рони Посмотреть профиль Найти все сообщения от рони
 
Регистрация: 27.05.2010
Сообщений: 33,118

Aruta,
менять надо класс элемента, а не стили элемента!!!
Сообщение от Aruta
этот блок не работает -
потому-что if (elem.style.borderColor == activeBorderColor)
activeBorderColor не содержит нужный цвет, строки 3 и 4, нужно вычислять, писать функцию которая вернёт нужный "цвет", браузеры устанавливают цвет параметра в своих единицах измерения, независимо что было в параметре установки (строка 40 и 59)!!!

поэтому лучше проверять класс элемента elem.classList.contains(), а ещё лучше не проверять а менять сразу elem.classList.toggle() и будет одна строка вместо строк 50 - 63.
Ответить с цитированием
  #3 (permalink)  
Старый 21.10.2020, 07:44
Аспирант
Отправить личное сообщение для Aruta Посмотреть профиль Найти все сообщения от Aruta
 
Регистрация: 08.07.2019
Сообщений: 85

рони,
Сообщение от рони
ctiveBorderColor не содержит нужный цвет
Почему не содержит? Он же присваивает этот цвет при первом клике и присваивает его, когда чекбоксы активные имеются.
Сообщение от рони
поэтому лучше проверять класс элемента elem.classList.contains(), а ещё лучше не проверять а менять сразу elem.classList.toggle() и будет одна строка вместо строк 50 - 63.
Зачем тут elem.classList.contains() ? не понял...
у меня же не все elem идут с классами - 2 шт без класса

UPD. понял идею про classList, но он не подойдёт, т.к. если граница окрашены через функцию в 34 строке, то toggle будет их игнорировать и менять окраску, а этого не должно быть.

Последний раз редактировалось Aruta, 21.10.2020 в 08:01.
Ответить с цитированием
  #4 (permalink)  
Старый 21.10.2020, 08:11
Аватар для рони
Профессор
Отправить личное сообщение для рони Посмотреть профиль Найти все сообщения от рони
 
Регистрация: 27.05.2010
Сообщений: 33,118

Сообщение от Aruta
Он же присваивает этот цвет при первом клике
нет!!!
он присваивает свой цвет а не ваш.
Ответить с цитированием
  #5 (permalink)  
Старый 21.10.2020, 08:14
Аватар для рони
Профессор
Отправить личное сообщение для рони Посмотреть профиль Найти все сообщения от рони
 
Регистрация: 27.05.2010
Сообщений: 33,118

Сообщение от Aruta
но он не подойдёт, т.к. если граница окрашены через функцию в 34 строке,
убрать присвоение стилей во всех функциях(забыть что так можно) и сделать через установку классов.
Ответить с цитированием
  #6 (permalink)  
Старый 21.10.2020, 08:31
Аватар для рони
Профессор
Отправить личное сообщение для рони Посмотреть профиль Найти все сообщения от рони
 
Регистрация: 27.05.2010
Сообщений: 33,118

Aruta,
фокус-покус
<!DOCTYPE html>

<html>
<head>
  <title>Untitled</title>
  <meta charset="utf-8">
</head>

<body>
<div id="elem"></div>
<script>
let activeColor = '#220718';
elem.style.color = activeColor;
elem.innerHTML = elem.style.color;
</script>
</body>
</html>
Ответить с цитированием
  #7 (permalink)  
Старый 21.10.2020, 09:27
Аспирант
Отправить личное сообщение для Aruta Посмотреть профиль Найти все сообщения от Aruta
 
Регистрация: 08.07.2019
Сообщений: 85

Сообщение от рони
убрать присвоение стилей во всех функциях(забыть что так можно) и сделать через установку классов.
Спасибо. Попробую сделать так
Ответить с цитированием
  #8 (permalink)  
Старый 21.10.2020, 09:37
Аспирант
Отправить личное сообщение для Aruta Посмотреть профиль Найти все сообщения от Aruta
 
Регистрация: 08.07.2019
Сообщений: 85

Сообщение от рони Посмотреть сообщение
Aruta,
фокус-покус
<!DOCTYPE html>

<html>
<head>
  <title>Untitled</title>
  <meta charset="utf-8">
</head>

<body>
<div id="elem"></div>
<script>
let activeColor = '#220718';
elem.style.color = activeColor;
elem.innerHTML = elem.style.color;
</script>
</body>
</html>
У меня в браузер так же цвет выводится
Это к тому что должен выводиться именно #220718 а не RGB?
Ответить с цитированием
  #9 (permalink)  
Старый 21.10.2020, 10:09
Аватар для рони
Профессор
Отправить личное сообщение для рони Посмотреть профиль Найти все сообщения от рони
 
Регистрация: 27.05.2010
Сообщений: 33,118

Сообщение от Aruta
Это к тому что должен выводиться именно #220718 а не RGB?
это пример, как браузер преобразует все иные форматы(red, #FFF, и прочее) в один, в тот что выбрали авторы браузера.
Ответить с цитированием
  #10 (permalink)  
Старый 21.10.2020, 10:33
Аспирант
Отправить личное сообщение для Aruta Посмотреть профиль Найти все сообщения от Aruta
 
Регистрация: 08.07.2019
Сообщений: 85

Сообщение от рони Посмотреть сообщение
это пример, как браузер преобразует все иные форматы(red, #FFF, и прочее) в один, в тот что выбрали авторы браузера.
Спасибо
Ответить с цитированием
Ответ



Опции темы Искать в теме
Искать в теме:

Расширенный поиск


Похожие темы
Тема Автор Раздел Ответов Последнее сообщение
mouseover срабатывает только для первого тега Julia1991 jQuery 4 23.06.2019 20:16
Listener's - срабатывает только последний __Alex__ Events/DOM/Window 7 31.08.2018 18:04
setInterval срабатывает только по клику yaparoff Общие вопросы Javascript 2 16.01.2018 16:03
Событие срабатывает только 1 раз mazahaler Events/DOM/Window 4 24.12.2017 13:00
Событие click срабатывает только при повторном нажатии (через ON) loko jQuery 8 16.01.2014 10:35