2017-08-27 34 views
0

我使用impress.js作爲插件,我試圖在不更改impress.js本身的情況下覆蓋鍵碼定義(否則在下次更新期間更改將被覆蓋)在插件(impress.js)中覆蓋event.keycode而不更改插件中的代碼

這是鍵碼的定義如何在impress.js實現:

// KEYBOARD NAVIGATION HANDLERS 

    // Prevent default keydown action when one of supported key is pressed. 
    document.addEventListener("keydown", function(event) { 
     if (event.keyCode === 9 || 
      (event.keyCode >= 32 && event.keyCode <= 34) || 
      (event.keyCode >= 37 && event.keyCode <= 40)) { 
      event.preventDefault(); 
     } 
    }, false); 


     if (event.shiftKey || event.altKey || event.ctrlKey || event.metaKey) { 
      return; 
     } 

     if (event.keyCode === 9 || 
      (event.keyCode >= 32 && event.keyCode <= 34) || 
      (event.keyCode >= 37 && event.keyCode <= 40)) { 
      switch (event.keyCode) { 
       case 33: // Page up 
       case 37: // Left 
       case 38: // Up 
         api.prev(); 
         break; 
       case 9: // Tab 
       case 32: // Space 
       case 34: // Page down 
       case 39: // Right 
       case 40: // Down 
         api.next(); 
         break; 
      } 

      event.preventDefault(); 
     } 
    }, false); 

這是我正在試圖改寫它們的定義(在一個單獨的js文件,但代碼在impress.js啓動後執行):

  • 空格鍵應該調用暫停
  • 其他鍵應該沒有效果。

    //綁定鍵盤事件.. document.addEventListener( 'KEYUP',函數(事件){

    if (event.keyCode === 9 || (event.keyCode >= 32 && event.keyCode <= 34) || (event.keyCode >= 37 && event.keyCode <= 40)) { 
        switch (event.keyCode) { 
        // ..left key arrow, go to previous slide 
        case 37: 
         return deck.prev(); 
         break; 
         // ..right key arrow, go to previous slide 
        case 39: 
         return deck.next(); 
         break; 
        case 32: // Space 
         return deck.pause(); 
         break; 
        case 9: // Tab 
        case 33: // Page up 
        case 38: // Up 
        case 34: // Page down 
        case 40: // Down 
         return; 
        } 
    
        event.preventDefault(); 
    } 
    

    },假);

然而,鍵的功能沒有改變。

可以覆蓋密鑰,我該如何實現?

回答

1

addEventListener不覆蓋以前添加的事件偵聽器,這是使用on * event屬性/屬性的優勢之一。

爲了做你想做的事情,你需要添加你自己的impress:init事件監聽器,在通過impress添加之前,執行與庫相同的設置,更改需要更改的內容,然後調用stopImmediatePropagation()

stopImmediatePropagation將防止同類型的其他聽衆被執行,這意味着沒話說的impress:init事件監聽器不會被觸發。

//code executed before impress.js is loaded 
(function(document,window){ 
    "use strict"; 
    var throttle = function(fn, delay) { 
    var timer = null; 
    return function() { 
     var context = this, args = arguments; 
     clearTimeout(timer); 
     timer = setTimeout(function() { 
     fn.apply(context, args); 
     }, delay); 
    }; 
    }; 

    document.addEventListener("impress:init", function(event) { 
    event.stopImmediatePropagation(); 

    //parts of init code 

    document.addEventListener('keyup', function(event) { 
     if (event.keyCode === 9 || (event.keyCode >= 32 && event.keyCode <= 34) || (event.keyCode >= 37 && event.keyCode <= 40)) { 
     switch (event.keyCode) { 
      case 37: 
      return deck.prev(); 
      break; 
      case 39: 
      return deck.next(); 
      break; 
      case 32: // Space 
      return deck.pause(); 
      break; 
      case 9: // Tab 
      case 33: // Page up 
      case 38: // Up 
      case 34: // Page down 
      case 40: // Down 
      return; 
     } 
     event.preventDefault(); 
     } 
    }, false); 

    //other part of init code 
    }); 

})(document, window) 

演示

<script> 
 
(function(document, window) { 
 
    "use strict"; 
 
    var throttle = function(fn, delay) { 
 
     var timer = null; 
 
     return function() { 
 
      var context = this, args = arguments; 
 
      clearTimeout(timer); 
 
      timer = setTimeout(function() { 
 
       fn.apply(context, args); 
 
      }, delay); 
 
     }; 
 
    }; 
 

 
    document.addEventListener("impress:init", function(event) { 
 
     event.stopImmediatePropagation(); 
 
     var api = event.detail.api; 
 
     document.addEventListener("keydown", function(event) { 
 
      if (event.keyCode === 9 || 
 
       (event.keyCode >= 32 && event.keyCode <= 34) || 
 
       (event.keyCode >= 37 && event.keyCode <= 40)) { 
 
       event.preventDefault(); 
 
      } 
 
     }, false); 
 
     document.addEventListener("keyup", function(event) { 
 
      if (event.shiftKey || event.altKey || event.ctrlKey || event.metaKey) { 
 
       return; 
 
      } 
 

 
      if (event.keyCode === 9 || (event.keyCode >= 32 && event.keyCode <= 34) || (event.keyCode >= 37 && event.keyCode <= 40)) { 
 
       switch (event.keyCode) { 
 
       // ..left key arrow, go to previous slide 
 
       case 37: 
 
        //return deck.prev(); 
 
        console.log("deck.prev() would have been called"); 
 
        break; 
 
        // ..right key arrow, go to previous slide 
 
       case 39: 
 
        //return deck.next(); 
 
        console.log("deck.next() would have been called"); 
 
        break; 
 
       case 32: // Space 
 
        //return deck.pause(); 
 
        console.log("deck.pause() would have been called"); 
 
        break; 
 
       case 9: // Tab 
 
       case 33: // Page up 
 
       case 38: // Up 
 
       case 34: // Page down 
 
       case 40: // Down 
 
        return; 
 
       } 
 

 
       event.preventDefault(); 
 
      } 
 
     }, false); 
 

 
     document.addEventListener("click", function(event) { 
 
      var target = event.target; 
 
      while ((target.tagName !== "A") && 
 
        (target !== document.documentElement)) { 
 
       target = target.parentNode; 
 
      } 
 

 
      if (target.tagName === "A") { 
 
       var href = target.getAttribute("href"); 
 
       if (href && href[ 0 ] === "#") { 
 
        target = document.getElementById(href.slice(1)); 
 
       } 
 
      } 
 

 
      if (api.goto(target)) { 
 
       event.stopImmediatePropagation(); 
 
       event.preventDefault(); 
 
      } 
 
     }, false); 
 

 
     document.addEventListener("click", function(event) { 
 
      var target = event.target; 
 

 
      while (!(target.classList.contains("step") && 
 
         !target.classList.contains("active")) && 
 
         (target !== document.documentElement)) { 
 
       target = target.parentNode; 
 
      } 
 

 
      if (api.goto(target)) { 
 
       event.preventDefault(); 
 
      } 
 
     }, false); 
 

 
     document.addEventListener("touchstart", function(event) { 
 
      if (event.touches.length === 1) { 
 
       var x = event.touches[ 0 ].clientX, 
 
        width = window.innerWidth * 0.3, 
 
        result = null; 
 

 
       if (x < width) { 
 
        result = api.prev(); 
 
       } else if (x > window.innerWidth - width) { 
 
        result = api.next(); 
 
       } 
 

 
       if (result) { 
 
        event.preventDefault(); 
 
       } 
 
      } 
 
     }, false); 
 

 
     window.addEventListener("resize", throttle(function() { 
 
      api.goto(document.querySelector(".step.active"), 500); 
 
     }, 250), false); 
 
    
 
    }, false); 
 
})(document, window); 
 
</script> 
 
<link rel="styleshee" href="https://cdn.rawgit.com/impress/impress.js/master/css/impress-demo.css"> 
 

 
<div id="impress"> 
 
    <div id="bored" class="step slide" data-x="-1000" data-y="-1500"> 
 
     <q>Aren’t you just <b>bored</b> with all those slides-based presentations?</q> 
 
    </div> 
 
    <div class="step slide" data-x="0" data-y="-1500"> 
 
     <q>Don’t you think that presentations given <strong>in modern browsers</strong> shouldn’t <strong>copy the limits</strong> of ‘classic’ slide decks?</q> 
 
    </div> 
 
    <div class="step slide" data-x="1000" data-y="-1500"> 
 
     <q>Would you like to <strong>impress your audience</strong> with <strong>stunning visualization</strong> of your talk?</q> 
 
    </div> 
 
    <div id="title" class="step" data-x="0" data-y="0" data-scale="4"> 
 
     <span class="try">then you should try</span> 
 
     <h1>impress.js<sup>*</sup></h1> 
 
     <span class="footnote"><sup>*</sup> no rhyme intended</span> 
 
    </div> 
 
    <div id="its" class="step" data-x="850" data-y="3000" data-rotate="90" data-scale="5"> 
 
     <p>It’s a <strong>presentation tool</strong> <br/> 
 
     inspired by the idea behind <a href="http://prezi.com">prezi.com</a> <br/> 
 
     and based on the <strong>power of CSS3 transforms and transitions</strong> in modern browsers.</p> 
 
    </div> 
 
    <div id="big" class="step" data-x="3500" data-y="2100" data-rotate="180" data-scale="6"> 
 
     <p>visualize your <b>big</b> <span class="thoughts">thoughts</span></p> 
 
    </div> 
 
    <div id="tiny" class="step" data-x="2825" data-y="2325" data-z="-3000" data-rotate="300" data-scale="1"> 
 
     <p>and <b>tiny</b> ideas</p> 
 
    </div> 
 
    <div id="ing" class="step" data-x="3500" data-y="-850" data-rotate="270" data-scale="6"> 
 
     <p>by <b class="positioning">positioning</b>, <b class="rotating">rotating</b> and <b class="scaling">scaling</b> them on an infinite canvas</p> 
 
    </div> 
 
    <div id="imagination" class="step" data-x="6700" data-y="-300" data-scale="6"> 
 
     <p>the only <b>limit</b> is your <b class="imagination">imagination</b></p> 
 
    </div> 
 
    <div id="source" class="step" data-x="6300" data-y="2000" data-rotate="20" data-scale="4"> 
 
     <p>want to know more?</p> 
 
     <q><a href="http://github.com/bartaz/impress.js">use the source</a>, Luke!</q> 
 
    </div> 
 
    <div id="one-more-thing" class="step" data-x="6000" data-y="4000" data-scale="2"> 
 
     <p>one more thing...</p> 
 
    </div> 
 
    <div id="its-in-3d" class="step" data-x="6200" data-y="4300" data-z="-100" data-rotate-x="-40" data-rotate-y="10" data-scale="2"> 
 
     <p><span class="have">have</span> <span class="you">you</span> <span class="noticed">noticed</span> <span class="its">it’s</span> <span class="in">in</span> <b>3D<sup>*</sup></b>?</p> 
 
     <span class="footnote">* beat that, prezi ;)</span> 
 
    </div> 
 
    <div id="overview" class="step" data-x="3000" data-y="1500" data-scale="10"></div> 
 
</div> 
 

 
<script src="https://cdn.rawgit.com/impress/impress.js/master/js/impress.js"></script> 
 
<script>impress().init();</script>

1

更新以反映這一事實,這個功能是現在還在主impress.js分支。

在最近的impress.js版本中,您在這裏討論的關鍵導航代碼移至單獨的plugin src/plugins/navigation。如果你想禁用它並提供你自己的,你可以很容易地在build.js中做到這一點。

沒有運行時間的方式來禁用插件,但如果你想發送這樣的拉請求,我很樂意合併它。這可能採取以下形式:

<div id="impress" data-navigation="off" ... > 

最後,我還可以想象導航插件允許用戶指定鍵綁定。但是,因爲印象深刻。js目前不支持使用配置文件(並且它不會立即清楚它應該如何執行),因此每個演示文稿必須在演示文稿中指定其鍵綁定。

我希望你會發現這些選項比試圖從外部破解不可插入的上游版本更清潔。

+0

感謝您指出這一點!我很好奇,有沒有在這個叉子增加移動支持? – TheRed

+1

是的。我刪除了阻止在手機上加載的代碼。我整合了一個「touch」插件,可以讓你滑動下一個/上一個(而上游已經在左/右邊緣敲擊)。還有一個叫做「mobile」的插件,可以讓你隱藏所有的幻燈片,但是當前,上一個和下一個。這個想法是讓演示文稿更加輕鬆。 (這兩個實際上都是由他人完成的!) –