Hover oraz click przy resize oraz ready

0

Czy może mi ktoś pomóc przy takim problemie. Mam menu, które ma mieć dwie funkcje. Przy rozdziałce poniżej 1000px ma byc działające rozwijanie na klika, ale na wyzszej na hover.
Jak to rozgryść? Napisałem takie cos i niestety przy skalowaniu okienka dalej działa resize mimo iż okienko ma mniej ni 1005 pikseli dlaczego? :

 jQuery(document).ready(myfunction);
jQuery(window).on('resize',myfunction);

function myfunction() {
    
	if (jQuery(window).width() > 1005) {
		
  jQuery(".menu-item-has-children").hover(function () { 
        jQuery(this).children("ul").stop().slideDown('fast');
    }, function () {
       jQuery(this).children("ul").stop().slideUp('slow');
    });
 
 
}
else {
	
	 jQuery(".menu-item-has-children").click(function (event) { 
	 	
	 	
	 	event.preventDefault();
	 	
		});
	
}

}
	
 
1

Even handler zakłada się raz, a nie w obsłudze innego zdarzenia,tak jak Ty to robisz. W efekcie jeśli chociaż raz okno ma zmieniony rozmiar w sposób taki, że szerokość przekroczy 1005px, to będziesz mieć założony (kolejny) handler i na kliknięcie, i na hover.
Załóż handler na kliknięcie i na hover, a potem w obsłudze tych zdarzeń sprawdzaj rozmiar.

0

chodzi o rozdzielenie tego tak? A nie można jakoś uspójnić ego aby nie powielać kodu dla resize i ready?

 jQuery(document).ready(function() {
    	
    	if (jQuery(window).width() > 1005) {
    	  jQuery(".menu-item-has-children").hover(function () { 
    	  	
        jQuery(this).children("ul").stop().slideDown('fast');
        
    }, function () {
    	
    	
       jQuery(this).children("ul").stop().slideUp('slow');
       
    });
    	
  } else {
  	
  	jQuery('.menu-item-has-children').unbind('mouseenter mouseleave');
  	
  	 jQuery(".menu-item-has-children").click(function () { 
	 	
		  jQuery(this).children("ul").stop().slideUp('slow');
		
	 	
		});
  } 	
    	
    });
	
	jQuery(window).resize(function() {
    	
    	if (jQuery(window).width() > 1005) {
    	  jQuery(".menu-item-has-children").hover(function () { 
    	  	
        jQuery(this).children("ul").stop().slideDown('fast');
        
    }, function () {
    	
    	
       jQuery(this).children("ul").stop().slideUp('slow');
       
    });
    	
  } else {
  	
  	jQuery('.menu-item-has-children').unbind('mouseenter mouseleave');
  	
  	 jQuery(".menu-item-has-children").click(function () { 
	 	
		jQuery(this).children("ul").stop().slideDown('fast');
		
	 	
		});
  } 	
    	
    }); 
0

OMG, kompletnie nie tak. Pisane z palca, raczej jako przykład niż dokładne odwzorowanie tego, co chcesz zrobić.

var performAction = function() { tu właściwa akcja };

var onClick = function() { if ($(window).width() < 1005) performAction(); };
var onHover = function() { if ($(window).width() >= 1005) performAction(); };

var attachHandlers = function() { attachOnClick(); attachOnHover(); }; // kod tych dwóch metod sobie sam dopisz
$(attachHandlers);
0

ale dlaczego wywołujesz tą samą funckje performAction(); dla klika i hovera?? Przecież one są inne? Dla hovera ma być powyzej 1005 a dla klika poniżej a tutaj dla tego i tego jest ta sama funkcja nie rozumiem tego

0

Źle Cię zrozumiałem, chciałeś mieć ten sam kod dla ready i resize, a nie hover i click (chociaż to co napisałeś świadczy o tym, że kompletnie nie rozumiesz jak działa obsługa zdarzeń w js, nie mówiąc już o tym, jak działa mój powyższy kod - bo zadziała prawidłowo w przeciwieństwie do Twojego, mój dla >= 1005px wykona performAction po najechaniu myszką, a dla < 1005px po kliknięciu, a obsługa resize, skopana u Ciebie, u mnie jest w ogóle zbędna). Ale zasada jest taka sama - wyciągasz wspólny kod do osobnej funkcji i ją wywołujesz z obu miejsc.
BTW zastanów się nad jakością swojego kodu - nadużywasz funkcji anonimowych, deklarując funkcję anonimową w funkcji anonimowej, co zaciemnia kod. Ponadto znowu zakładasz wiele razy ten sam handler: w obsłudze resize (wykonywanej wiele razy! przecież onresize jest wykonywane przy każdej zmianie rozmiaru okna, a nie tylko raz na cały czas życia strony!) dajesz jQuery(".menu-item-has-children").hover(function () { ...., czyli USTAWIASZ handler. Handler zostaje już na zawsze, chyba że ręcznie go odczepisz albo usunies element z DOM, ale tego nie robisz. Teraz jeśli ktoś miał 1920px szerokości okna, z taką szerokością załadował Twoją stronę, a potem zmienił rozmiar na 720px, to handler na hover POZOSTAJE USTAWIONY. Czyli będziesz mieć mniej niż 1005px, a najechanie myszką będzie nadal coś tam otwierać. Ponadto handler będzie podczepiany NIE RAZ, a kilka, kilkaset razy (przy każdym zdarzeniu resize - czyli przy zmianie szerokości myszką), więc i będzie się kilkaset razy wykonywać. Nie muszę chyba Ci mówić, jak to wpłynie na wydajność kodu...

0

Zresztą popatrz jak działa mój oryginalny kod i wyciągnij wnioski (1005px uzyskasz rozciągając część okna zawierającą szary kwadrat): https://jsfiddle.net/sfzgapn0/

0

ok dzieki poprawiłem ael mam jeszcze jeden problem. Super to pokazałeś ale dla 1 elementu a ja mam menu i teraz jak ja mam dla funkcji performAction odwoływać się do this?



 var performAction = function(e) { 
 	
 	if (e.type == "click") {
 	 
 	
 	 
 	 
 	 } 
 	else {
 		
 		
 		
 	}  
 	
 	
 	};
 
 
 
var onClick = function(e) { if (jQuery(window).width() < 1005) performAction(e); };
var onHover = function(e) { if (jQuery(window).width() >= 1005) performAction(e); };

var attachOnClick = function() { jQuery(".menu-item-has-children").click(onClick); };
var attachOnHover = function() { jQuery(".menu-item-has-children").on("mouseenter", onHover); };

var attachHandlers = function() { attachOnClick(); attachOnHover(); };
jQuery(attachHandlers);
   

 
1

e.target. Nie zastanowiło Cię, że funkcja dostaje parametr e i tam może się coś czaić? Od tego tylko krok do użycia debugera, albo chociaż console.log() i konsoli js przeglądarki (F12->Console) i zaraz byś zobaczył co siedzi w evencie.
Poza tym możesz przekazać this jako drugi argument tej funkcji.
Myśl twórczo i dokształć się w temacie eventów :-)

0

hej juz do tego doszedłem tylko jeszcze jeden mały problem. Ogromne dzieki za pomoc własnie troche zczaiłem już i zaczynam czytać o eventach:)

Mój kod wyglada tak. Na klika działa suuuper. Ale na hovera nie nie łapie mi dziecka jak zjezdzam na ul to chowa sie:(

Po zdebugowaniu jest tak, że dla clicka widzi to co jest podane czyli .menu-item-has-children a dla overa widzi link, który jest obok, dlaczego tak widzi?

struktura wyglada tak:

<ul>
<a href=""></a>
<ul  class="menu-item-has-children"> /ul>

</ul> 

 var performAction = function(e) { 
 	
 	if (e.type == "click") {
 	 
 	
 	jQuery(e.currentTarget).children("ul").toggle();
 	 
 	 } 
 	else {
 		
 	jQuery(e.currentTarget).children("ul").stop(true, true).slideToggle('fast');
 	
 	
 	}  
 	
 	
 	};
 
 
 
var onClick = function(e) { if (jQuery(window).width() < 1005) performAction(e); };
var onHover = function(e) { if (jQuery(window).width() >= 1005) performAction(e); };

var attachOnClick = function() { jQuery(".menu-item-has-children").click(onClick); };
var attachOnHover = function() { jQuery(".menu-item-has-children, .sub-menu").on("mouseover", onHover); };

var attachHandlers = function() { attachOnClick(); attachOnHover(); };
jQuery(attachHandlers);
   

 

1 użytkowników online, w tym zalogowanych: 0, gości: 1