将 Jquery 转换为 Vanilla JS - 浮动元素

Converting Jquery to Vanilla JS - floating elements

    //First function -> Makes a heading float when scrolled past it
    if (window.matchMedia('(min-width: 767px)').matches) {
    $(function(){
var topBlockheight=$('.site-header').height();
        // Check the initial Position of the fixed_nav_container
        var stickyHeaderTop = $('.float-h2').offset().top;
        var stopFloat = $('#stop-float').offset().top;
        $(window).scroll(function(){
                if( (  $(window).scrollTop() > stickyHeaderTop-topBlockheight && $(window).scrollTop() < stopFloat-topBlockheight )) {
                        $('.float-h2').css({position: 'fixed', top: '200px'});  
                }
                else {
                        $('.float-h2').css({position: 'relative', top: '0px'});
                }
        });
  });
}

// Adds Hover effect for boxes
if (window.matchMedia('(min-width: 767px)').matches) {
$(document).ready(function(){
$(".thumb-cta").mouseover(function(){
    max_value=4;
    random_value= Math.floor((Math.random() * max_value) + 1);
    $(this).attr("data-random",random_value);
});
})
}

这是我网站 jQuery 中仅有的两个功能,我决定尝试用 vanilla JS 重写。做出这个决定的原因是因为我不想为 2 个基本功能(基本但仍然做不到,是的我知道)加载一个 90kb 的文件(jquery 主文件)。

我尝试使用 http://youmightnotneedjquery.com and https://www.workversatile.com/jquery-to-javascript-converter 重新编写它们,最后我得到了这段代码,它在控制台中没有任何错误,但仍然不起作用:((

            let el = document.getElementById("masthead");
            let topBlockheight = parseFloat(getComputedStyle(el, null).height.replace("px", ""))

            var rect = document.getElementById("float-h2").getBoundingClientRect();

            var offset = { 
                            top: rect.top + window.scrollY, 
                            left: rect.left + window.scrollX, 
                        };


                        var brect = document.getElementById("stop-float").getBoundingClientRect();

            var boffset = { 
                            top: rect.top + window.scrollY, 
                            left: rect.left + window.scrollX, 
                        };

                    window.scroll(function(){
                            if( (  window.scrollTop() > rect-topBlockheight && window.scrollTop() < stopFloat-topBlockheight )) {
                                    document.getElementById("float-h2").css({position: 'fixed', top: '200px'});  
                            }
                            else {
                                    document.getElementById("float-h2").css({position: 'relative', top: '0px'});
                            }
                    });

关于我如何继续前进的任何想法,因为我真的被困住了

  • 希望这对你有用
if (window.matchMedia('(min-width: 767px)').matches) {
      //Note: if "site-header" is more than one element remove [0] and create a loop
         var topBlockheight=document.getElementsByClassName('site-header')[0].offsetHeight
        var stickyHeaderTop = document.getElementsByClassName('float-h2')[0].offsetTop;
        var stopFloat = document.getElementById('stop-float').offsetTop;
        window.addEventListener("scroll", function(){
                if( (  window.scrollY > stickyHeaderTop-topBlockheight && window.scrollY < stopFloat-topBlockheight )) {
                        document.getElementsByClassName('float-h2')[0].style.position = 'fixed'
                  document.getElementsByClassName('float-h2')[0].style.top = '200px'
                }
                else {
                        document.getElementsByClassName('float-h2')[0].style.position = 'relative'
                  document.getElementsByClassName('float-h2')[0].style.top = 0
                }
        });
}

// Adds Hover effect for boxes
if (window.matchMedia('(min-width: 767px)').matches) {
document.onreadystatechange = function(){
if(document.readyState === "interactive") {
     document.getElementsByClassName('thumb-cta')[0].addEventListener("mouseover", function(){
    max_value=4;
    random_value= Math.floor((Math.random() * max_value) + 1);
      this.setAttribute("data-random",random_value);
    });
  }
 }
}

详情

  1. jQuery
  • in jQuery to select elements by className or tagName 写 $('.element') or $('tag') 就足够了,但是在 Vanillajs to select elements 你可以使用document.getElementsByClassName('elements') or document.getElementsByTagName('elements') which return found elements sharing the same className or tagName in array 如果你想 select 只有一个元素你可以写元素索引像 document.getElementsByClassName('elements')[0] 但如果你想 select 所有元素,你将需要创建一个循环
var el = document.getElementsByClassName('elements')
for(var i = 0; i < el.length; i++) {
  el[i].style.padding = '25px';
  el[i].style.background = 'red';
}

并且由于 id 是元素的唯一名称,您不需要任何额外的步骤就可以 select 它直接 select 就像 document.getElementById('id')

那是关于 selecting 元素

  • height() 使用获取元素高度的方法 - 在 Vanillajs js 中获取元素高度可以使用 offsetHeight 属性 或 getComputedStyle(element, pseudo|null).cssProp

例子 element.offsetHeightparseInt(getComputedStyle(element, null).height)

  • offset() 方法使用 return 元素的坐标此方法在 Vanillajs 中有 2 个属性 top, left 来获取元素offset top 你可以像element.offsetTop

    一样直接使用offsetTop属性
  • jQuery 提供了一个类似于 css() 的原型方法,它提供了一种简单易读的方式来为普通对象中的元素设置样式 propery: value - 在 Vanillajs 中为元素设置样式您将需要使用 style 对象,例如 element.style.prop = 'value' ,并且每次添加新的 css 属性 时都需要重复此行

el.style.padding = '25px';
el.style.background = 'red';
//and they will repeated as long as you add new property

如果你不想在你的项目中包含jQuery并且需要使用这个方法你可以将它定义为HTMLElement,HTMLMediaElement[=59=的原型方法]

Example 1: for styling one element

//for html elements
HTMLElement.prototype.css = function(obj) {
  for(i in obj) {
    this.style[i] = obj[i]
  }
}
//for media elements like video, audio
HTMLMediaElement.prototype.css = function(obj) {
  for(i in obj) {
    this.style[i] = obj[i]
  }
}
//Usage
var el = document.getElementsByClassName('elements')[0]
el.css({
  'padding': '25px',
  'background-color': 
})

如果你想为多个元素添加这个样式你可以将它定义为 Array

的原型方法

Example 2: for multiple elements

Array.prototype.css = function(obj) {
  for(i = 0; i < this.length; i++) {
    if (this[i] instanceof HTMLElement) {
      for(r in obj) {
        this[i].style[r] = obj[r]
      }
    }
  }
}
//Usage
var el1 = document.getElementsByClassName('elements')[0]
var el2 = document.getElementsByClassName('elements')[1]
[el1, el2].css({
  'background-color': 'red',
  padding: '25px'
})
  • jQuery 允许您在 selecting 像 $('.element').click(callback) 这样的元素时直接添加事件,但在 Vanillajs 中,您可以使用 addEventListener()oneventdocument.getElementById('id').addEventListener('click', callback) , document.getElementById('id').onclick = callback

    这样的属性
  • $(document).ready(callback) 这个方法用来让你的代码在加载库后开始工作,其他的事情是给 lib 足够的时间来加载以避免错误 - 在 Vanilla js 中你可以使用具有 3 个值 loadinginteractivecomplete

    onreadystatechange 事件和 document.readyState 属性

Example

document.onreadystatechange = function () {
  if (document.readyState === 'interactive') {
    //your code here
  }
}
  1. 你的隐藏代码
  • 在这一行 parseFloat(getComputedStyle(el, null).height.replace("px", "")) 你不需要替换任何东西因为 parseInt(), parseFloat 会忽略它
  • element.css() id 不知道当此方法未定义时您如何在控制台中没有收到任何错误您将需要按上面的方式定义它才能使其工作
  • scroll 事件未定义你将需要使用 window.onscroll = callback 像上面的例子