2013-06-19 12 views
0

n rows이 될 수있는 그리드를 만들고 있는데, leftChild와 rightChild의 두 가지보기로 구분됩니다. leftChild는 rightChild와 같은 양의 행을 가지고 있지만 leftChild는 그 위치에 있습니다. rightChild와의 유일한 차이점은 가로로 스크롤 할 수 있다는 것입니다. 내가 leftChild 또는 rightChild 요소 위로 마우스를 가져 가면 어떤 종류의 호버링 효과를 추가하고 싶습니다. 쉽습니다. 그러나 전체 행에 걸쳐 호버링 효과를 추가하고 싶습니다. 따라서 leftChild의 3 행 위로 마우스를 이동하면 rightChild의 3 행을 강조 표시합니다.CSS/JS : 요소 위에 마우스를 올리면 다른 요소가 강조 표시됩니다.

this과 비슷한 이상적인 CSS 솔루션이 마음에 들지만, 내 행이 서로 이어지는 것이 아니기 때문에 불가능합니다. 이 문제를 해결하는 또 다른 방법을 생각하려고 시도했지만 스트레이트 CSS에서는 불가능 해 보였습니다.

JavaScript를 입력하십시오. 다음 단계는 JavaScript를 CSS와 결합하는 것입니다. 행에 호버 효과를 추가 한 다음 JavaScript를 사용하여 다른 자식의 해당 행에 호버 클래스를 추가 할 수 있습니다. 이것은 jQuery로 매우 간단하지만 네이티브 JavaScript 접근 방식을 찾고 있습니다.

제가 생각하는 주요 접근 방식은 각 행 클래스 요소에 mouseentermouseleave을 추가하는 것입니다. 나는이 방법을 정말 좋아하지 않는다. 왜냐하면 각 행 요소에 2 개의 이벤트 리스너를 설정하고 있기 때문이다. 이것은 비효율적 인 것처럼 보인다. 어쨌든, 당신이 들어 왔을 때, 당신이 가지고 있던 것의 행 번호를 부여한 다음, hover 클래스를이 모든 행 번호 요소에 추가하십시오. 떠날 때, 당신은 단지 호버가있는 모든 요소를 ​​찾아 적절하게 제거합니다. 해당 코드는 다음과 같다 :

HTML

<body onload="loaded()"> 
    <div id="parent"> 
     <div id="leftChild"> 
      <div>left child</div> 
      <div class="row row1">some content</div> 
      <div class="row row2">other content</div> 
      <div class="row row3">more content</div> 
     </div> 
     <div id="rightChild"> 
      <div>right child</div> 
      <div class="row row1"> 
       <span class="col1">column 1 content</span> 
       <span class="col2">column 2 content</span> 
       <span class="col3">column 3 content</span> 
       <span class="col4">column 4 content</span> 
       <span class="col5">column 5 content some really long content to trigger scrolling just for the purpose of this example</span> 
      </div> 
      <div class="row row2"> 
       <span class="col1">column 1 content</span> 
       <span class="col2">column 2 content</span> 
       <span class="col3">column 3 content</span> 
       <span class="col4">column 4 content</span> 
       <span class="col5">column 5 content some really long content to trigger scrolling just for the purpose of this example</span> 
      </div> 
      <div class="row row3"> 
       <span class="col1">column 1 content</span> 
       <span class="col2">column 2 content</span> 
       <span class="col3">column 3 content</span> 
       <span class="col4">column 4 content</span> 
       <span class="col5">column 5 content some really long content to trigger scrolling just for the purpose of this example</span> 
      </div> 
     </div> 
    </div> 
</body> 

JS

function loaded() { 
    /*var parent = document.getElementById('parent'); 
    parent.onmouseenter = function(event) { 
     console.log(event.target); 
    }; 
    parent.onmouseleave = function(event) { 
     console.log(event.target); 
    };*/ 

    var rows = document.getElementsByClassName('row'); 
    for (var i = 0; i < rows.length; i++) { 
     rows[i].onmouseenter = function(event) { 
      var splits = event.target.className.split(" "); 
      var elems = document.getElementsByClassName(splits[splits.length - 1]); 
      for (var j = 0; j < elems.length; j++) { 
       elems[j].className += " hover"; 
      } 
     }; 

     rows[i].onmouseleave = function(event) { 
      var hovers = document.getElementsByClassName('hover'); 
      var len = hovers.length; 
      for (var j = 0; j < len; j++) { 
       hovers[0].className = hovers[0].className.replace(/\shover(\s|$)/, ''); 
      } 
     }; 
    } 
} 

CSS

.row:hover, .hover { 
    background-color: lightblue; 
} 

.row { 
    height: 50px; 
    padding: 5px; 
    white-space: nowrap; 
} 

.row > span { 
    display: inline-block; 
    border: 5px solid black; 
} 

#leftChild, #rightChild { 
    float: left; 
} 

#rightChild { 
    width: 300px; 
    overflow: auto; 
} 

#rightChild .row { 
    display: inline-block; 
} 

jsFiddle : Here

그래서 저는 몇 가지 사실을 알고 싶습니다.

  1. 바로 CSS로 가능합니까?
  2. 그렇지 않은 경우 어떻게하면보다 효율적으로 접근 할 수 있습니까?
  3. 하나의 이벤트 핸들러 또는 여러 이벤트 핸들러를 갖는 것이 더 효율적입니까?

내가 많이 묻는 이유는 알고 있지만 여러 가지 질문을하는 것이 싫지만, 특히 나 자신을 반복해야하는 경우. 나는 어떤 도움을 주셔서 감사합니다. 감사!

+0

엄 .. 표를 사용합니까? :/ –

+0

나는 차라리 그렇지 않고, SlickGrid (divs/span을 사용)를 사용하려고합니다 ... 이것은 단지 장난감 문제 일뿐입니다. – incutonez

답변

0

, 직선 자바 스크립트 접근 방식을 유지하는 I 하이브리드 접근법이 가장 빠른 속도로 진행되고 있습니다. JS 접근 방식에 매우 가깝습니다. (거의 완전히) jQuery 접근 방식은 마지막 단계에 있으며, 다른 방식과 비교해 볼 때 매우 느립니다. 둘.

이들 모두는 this jsFiddle에서 볼 수 있습니다.

JS

// Native JS approach... fastest (according to my jsPerf http://jsperf.com/removeclass-vs-native-js-remove-class/2) 
function loaded() { 
    var rows = document.getElementsByClassName('row'); 
    for (var i = 0; i < rows.length; i++) { 
     rows[i].onmouseenter = function(event) { 
      var row = this.className.match(/row-[\d]+/); 
      var elems = document.getElementsByClassName(row[0]); 
      for (var j = 0; j < elems.length; j++) { 
       elems[j].className += " hover"; 
      } 
     }; 

     rows[i].onmouseleave = function(event) { 
      var hovers = document.getElementsByClassName('hover'); 
      var len = hovers.length; 
      for (var j = 0; j < len; j++) { 
       hovers[0].className = hovers[0].className.replace(/\shover(\s|$)/, ''); 
      } 
     }; 
    } 
} 

// jQuery approach (slowest) 
/*$(document).ready(function() { 
    $('.row').on('mouseenter', function(event) { 
     var row = this.className.match(/row-[\d]+/); 
     $('.' + row).addClass('hover'); 
    }); 

    $('.row').on('mouseleave', function(event) { 
     $('.hover').removeClass('hover'); 
    }); 
});*/ 

// Hybrid approach (basically as fast as native JS approach) 
/*$(document).ready(function() { 
    var rows = document.getElementsByClassName('row'); 
    for (var i = 0; i < rows.length; i++) { 
    rows[i].onmouseenter = function(event) { 
     var row = this.className.match(/row-[\d]+/); 
     $('.' + row[0]).addClass('hover'); 
    }; 

     rows[i].onmouseleave = function(event) { 
      $('.hover').removeClass('hover'); 
     }; 
    } 
});*/ 
0
  1. 이 구조체의 CSS는 다음과 같습니다. no, CSS 레벨 4를 사용할 수 있기 전에.
  2. this를 사용하여 새 규칙은
  3. moouse 떠나 & 마우스를 유혹하면서 그것을에 추가 할 className 확인?

나는이 얻을 : JQuery와 통해,하지만 테스트를 위해 I 클래스 .row을 제거하고, 번호 하나 this jsPerf을 바탕으로

$("[class*='row']").hover(
    function() { 
     $('head').append('<style class="'+this.className+'" rel="stylesheet" > .'+this.className+' {background-color:lightblue;} </style>'); 
$(this).mouseleave(function() { $('style.'+this.className).remove();}); 
}); 

http://codepen.io/gcyrillus/pen/bhglr

+0

내 기본 JavaScript 접근 방식보다 효율적입니까? 나는 대답이 "아니오"라고 생각한다. 또한 전체 행을 강조 표시하지 않습니다 ... 분리 막대를 뛰어 넘습니다. – incutonez

+0

나는 이것이 서로 다른 두 가지 요소임을 보여주기 위해 다리 사이에 여백을 두었습니다. jQuery를 사용했기 때문에 CSS 스타일러스 선택기를 쉽게 사용할 수 있습니다. 물론, 귀하의 사이트에서이 유일한 기능을 위해 jQuery가 필요하다면, 브라우저 캐시에 아직없는 경우 방문자에게 한 번만 dir을 넘길 수 있습니다. –

+0

맞아요,하지만 jQuery가 약간의 오버 헤드를 추가하고 있습니다. 그래서 저는 직선적 인 JS 솔루션이 여전히 더 좋다고 생각합니다. 기본적으로 그리드가 상당히 커지면 기본적으로이 모든 것이 합산됩니다. – incutonez