문제

목표

사이트 전체의 페이지에서 이벤트 처리기를 일부 DIV에 동적으로 할당하고 싶습니다.

내 방법

jQuery를 사용하여 익명 기능을 선택한 DIV 이벤트의 핸들러로 바인딩합니다.

문제

코드는 DIV 이름 및 관련 URL 배열을 반복합니다. DIV 이름은 바인딩 대상을 설정하는 데 사용됩니다. 즉,이 이벤트 핸들러를이 DIV 이벤트에 첨부합니다.

이벤트 핸들러는 각 DIV 이벤트에 성공적으로 결합되지만 해당 이벤트 핸들러에 의해 트리거 된 작업은 배열의 마지막 항목 만 타겟팅합니다.

따라서 아이디어는 사용자가 주어진 DIV를 통해 마우스를 사용하면 해당 DIV에 대한 슬라이드 아웃 애니메이션을 실행해야한다는 것입니다. 그러나 대신, Div1 (Rangetaball)을 통해 Mousing은 Div4 (Rangetabthm)의 슬라이드 아웃 애니메이션을 트리거합니다. Divs 2, 3 등에 대해서도 마찬가지입니다. 순서는 중요하지 않습니다. 배열 요소를 변경하면 이벤트는 배열의 마지막 요소 인 Div4를 대상으로합니다.

내 코드 - (jQuery 사용)

var curTab, curDiv;
var inlineRangeNavUrls=[['rangeTabAll','range_all.html'],['rangeTabRem','range_remedial.html'],
                ['rangeTabGym','range_gym.html'],['rangeTabThm','range_thermal.html']];
        for (var i=0;i<inlineRangeNavUrls.length;i++)
        {
            curTab=(inlineRangeNavUrls[i][0]).toString();
            curDiv='#' + curTab;
            if  ($(curDiv).length)
            {
                $(curDiv).bind("mouseover", function(){showHideRangeSlidingTabs(curTab, true);} );
                $(curDiv).bind("mouseout", function(){showHideRangeSlidingTabs(curTab, false);} );
            }
        }

내 이론

맹목적으로 명백한 구문 오류 또는 기준 문제에 의한 패스가 보이지 않습니다. 처음에 나는 curtab의 값을 설정하기 위해 다음과 같은 진술을했습니다.

curTab=inlineRangeNavUrls[i][0];

그래서 문제가 발생했을 때 나는 (루프 반복을 통해) Curtab에 대한 참조를 변경하면서 실제로 바꾸다 이전의 모든 익명 기능 이벤트 핸들러에 대한 참조도 새로운 Curtab 값에 대한 참조 .... 이벤트 처리기가 항상 마지막 Div를 목표로 삼았습니다.

그래서 내가 정말로해야 할 일은 Curtab을 통과하는 것이 었습니다. 익명의 기능 이벤트 처리기에게 Curtab이 아닙니다 물체 참조.

그래서 나는 생각했다 :

curTab=(inlineRangeNavUrls[i][0]).toString();

문제를 해결하지만 그렇지 않습니다. 같은 거래. 그래서 분명히 문제에 관한 몇 가지 열쇠, 아마도 매우 기본적인 지식이 빠져 있습니다. 감사.

도움이 되었습니까?

해결책

루프를 통해 각 패스에 새 변수를 만들어 이벤트 핸들러를 위해 작성한 클로저에서 캡처되도록해야합니다.

그러나 변수 선언을 루프로 옮기는 것만으로도이를 달성하지 못합니다. JavaScript는 임의의 블록에 대한 새로운 범위를 도입하지 않습니다.

새로운 범위의 도입을 강요하는 쉬운 방법 중 하나는 다른 익명 기능을 사용하는 것입니다.

for (var i=0;i<inlineRangeNavUrls.length;i++)
{
  curDiv='#' + inlineRangeNavUrls[i][1];
  if ($(curDiv).length)
  {
    (function(curTab)
    {
      $(curDiv).bind("mouseover", function(){showHideRangeSlidingTabs(curTab, true);} );
      $(curDiv).bind("mouseout", function(){showHideRangeSlidingTabs(curTab, false);} );
    })(inlineRangeNavUrls[i][0]); // pass as argument to anonymous function - this will introduce a new scope
  }
}

Jason이 제안한 것처럼, 당신은 실제로 jQuery의 내장을 사용하여 이것을 약간 정리할 수 있습니다. hover() 기능:

for (var i=0;i<inlineRangeNavUrls.length;i++)
{
  (function(curTab) // introduce a new scope
  {
  $('#' + inlineRangeNavUrls[i][1])
    .hover(
      function(){showHideRangeSlidingTabs(curTab, true);},
      function(){showHideRangeSlidingTabs(curTab, false);} 
    );
  // establish per-loop variable by passsing as argument to anonymous function
  })(inlineRangeNavUrls[i][0]); 
}

다른 팁

여기서 일어나는 일은 당신의 anonmymous 기능이 폐쇄를 형성하고 외부 범위를 취하고 있다는 것입니다. 즉, 당신이 당신의 변칙적 인 함수 내에서 curtab을 참조 할 때, 이벤트 핸들러가 그 기능을 실행할 때, 그것은 현재의 외부 범위에서 쿠 타브의 값. 그것은 당신이 Curtab에 마지막으로 할당 한 모든 것입니다. (기능을 묻을 때 할당 된 내용이 아닙니다)

당신이해야 할 일은 이것을 바꾸는 것입니다.

$(curDiv).bind("mouseover", function(){showHideRangeSlidingTabs(curTab, true);} );

이에:

$(curDiv).bind("mouseover", 
    (function (mylocalvariable) { 
        return function(){
            showHideRangeSlidingTabs(mylocalvariable, true);
        } 
    })(curTab) 
);

이것은 curtab의 값을 외부 함수의 범위로 복사하여 내부 기능이 가져갈 것입니다. 이 복사는 내부 기능을 이벤트 핸들러에 바인딩하는 동시에 발생하므로 "mylocalvariable"은 그 당시 Curtab의 값을 반영합니다. 그런 다음 다음 번 루프 주변에서 새로운 범위가 새겨진 새로운 외부 기능이 생성되고 Curtab의 다음 값이 복사됩니다.

Shog9의 대답은 기본적으로 같은 것을 달성하지만 그의 코드는 조금 더 엄격합니다.

다소 복잡하지만 생각하면 말이됩니다. 폐쇄는 이상합니다.

편집 : 죄송합니다. 내부 기능을 반환하는 것을 잊었습니다. 결정된.

나는 당신이 이것을 필요로하는 것보다 더 복잡하게 만들고 있다고 생각합니다. 당신이하고있는 모든 것이 마우스 오버/아웃에 슬라이딩 효과를 할당하는 것입니다. 호버 jQuery와의 효과.

$("#mytab").hover(function(){
    $(this).next("div").slideDown("fast");},
  function(){
    $(this).next("div").slideUp("fast");
});

전체 HTML을 게시하면 정확히 어떻게 해야하는지 알려줄 수 있습니다 :)

변수의 값을 기존 태그가 아닌 태그에 넣을 수 있으며 나중에 거기에서 읽을 수 있습니다. 이 스 니펫은 루프 바디의 일부입니다.

 s = introduction.introductions[page * 6 + i][0]; //The variables content
 $('#intro_img_'+i).attr('tag' , s);              //Store them in a tag named tag
 $('#intro_img_'+i).click( function() {introduction.selectTemplate(this, $(this).attr('tag'));}  );  //retrieve the stored data
라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top