在加载不起作用时,div中的动画和图像淡入

时间:2017-01-24 14:35:58

标签: javascript html css dom

我试图在div中制作动画,每个内部都有1个透明图像。一旦图像被加载,我希望它逐渐将不透明度从0改为1.我使其大部分工作但仍然某些代码是错误的,因为图像根本没有任何变化。

是否有人知道错误或如何解决问题。

如果代码snipplet不适合你,这里链接到jsfiddle

var items = document.querySelectorAll(".item"),
  t = 0;

items.forEach(function(i) {
  i.style.animationDelay = t + "s";
  t = t + 0.05;
});

var imgs = [];

items.forEach(function(itm) {
  imgs.push(itm.children[0]);
});


for (var i = 0; i < imgs.length; i++) {
  imgs[i].onload = () => {imgs[i].style.opacity = "1";};
}
body {
  background: #212121;
}

.list {
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
}

.item {
  transform: scale(0);
  width: 150px;
  height: 210px;
  margin: 1%;
  box-shadow: 0px 2px 10px rgba(0, 0, 0, 0.7);
  background: #191919;
  cursor: pointer;
  border-radius: 2px;
  animation: 0.2s loadInItems ease forwards;
}

.item img {
  opacity: 0;
  height: 100%;
  width: 100%;
  border-radius: 2px;
}

@keyframes loadInItems {
  from {
    opacity: 0;
    transform: scale(0);
  }
  to {
    opacity: 1;
    transform: scale(1);
  }
}

@keyframes fadeIn {
  to {
    opacity: 1
  }
}
<div class="list">
  <div class="item">
    <img src="https://bo3li.files.wordpress.com/2011/05/drive-angry-movie-cover.jpg">
  </div>

  <div class="item">
    <img src="http://www.tolkienlibrary.com/press/images/movie-tie-in-The-hobbit.jpg">
  </div>

  <div class="item">
    <img src="http://netdna.webdesignerdepot.com/uploads/2011/02/jurassicpark.jpg">
  </div>

  <div class="item">
    <img src="http://posterwire.com/wp-content/uploads/lord_of_war.jpg">
  </div>

  <div class="item">
    <img src="https://davebrendon.files.wordpress.com/2010/12/i-am-number-four-movie-poster.jpg">
  </div>

  <div class="item">
    <img src="http://gdj.gdj.netdna-cdn.com/wp-content/uploads/2011/12/grey-movie-poster.jpg">
  </div>

  <div class="item">
    <img src="https://s-media-cache-ak0.pinimg.com/originals/e2/81/9d/e2819de0653c516f0e242038770fa3b8.jpg">
  </div>

  <div class="item">
    <img src="http://netdna.webdesignerdepot.com/uploads/2011/02/inception.jpg">
  </div>

  <div class="item">
    <img src="https://bo3li.files.wordpress.com/2011/05/drive-angry-movie-cover.jpg">
  </div>

  <div class="item">
    <img src="http://www.tolkienlibrary.com/press/images/movie-tie-in-The-hobbit.jpg">
  </div>

</div>

Idk如果我解释得很好:

  1. 从一开始就有div和图像(但图像自然加载在div之后)
  2. div然后从缩放和不透明度0动画到两个1。
  3. 在加载每个图像时,图像从不透明度0变为1

2 个答案:

答案 0 :(得分:0)

正如here所解释的,当从浏览器缓存中检索图像时,onLoad事件可能会被提前触发。我采用了他为你的代码提出的hack,用它替换了最后一个for循环。

const onImageLoadHandler = () => {
    imgs[i].style.opacity = "1";
}

for (var i = 0; i < imgs.length; i++) {
  imgs[i].onload = onImageLoadHandler;
  if (imgs[i].complete) onImageLoadHandler()
}

fiddle

答案 1 :(得分:0)

所以,你的问题是你在onload事件上挂钩太晚了。发生这种情况是因为您的代码在创建DOM之后运行。可以这样考虑:评估代码时,浏览器已经评估了图像源属性,并且很可能已经触发了onload事件。

您只需使用自定义属性和getAttribute()即可解决此问题。因此,首先我们将src属性从您的图片更改为lazy-src。这样,浏览器就会知道有一个图像,但它的来源是未知的 - 因此它不会触发onload

然后,当你循环你的项目;而不是将该项目推送到数组中,当您挂钩src以更改您的lazy-src时,将其onload属性更改为 var items = document.querySelectorAll(".item"), t = 0; items.forEach(function(i) { i.style.animationDelay = t + "s"; t = t + 0.05; }); var imgs = []; items.forEach(function(itm) { let image = itm.children[0] image.src = image.getAttribute('lazy-src'); image.onload = () => { image.style.opacity = "1"; }; });的值元素风格: (here's a link to your updated fiddle

body {
  background: #212121;
}

.list {
  display: flex;
  flex-wrap: wrap;
  justify-content: center;
}

.item {
  transform: scale(0);
  width: 150px;
  height: 210px;
  margin: 1%;
  box-shadow: 0px 2px 10px rgba(0, 0, 0, 0.7);
  background: #191919;
  cursor: pointer;
  border-radius: 2px;
  animation: 0.2s loadInItems ease forwards;
}

.item img {
  opacity: 0;
  height: 100%;
  width: 100%;
  border-radius: 2px;
}

@keyframes loadInItems {
  from {
    opacity: 0;
    transform: scale(0);
  }
  to {
    opacity: 1;
    transform: scale(1);
  }
}

@keyframes fadeIn {
  to {
    opacity: 1
  }
}
<div class="list">
  <div class="item">
    <img lazy-src="https://bo3li.files.wordpress.com/2011/05/drive-angry-movie-cover.jpg">
  </div>

  <div class="item">
    <img lazy-src="http://www.tolkienlibrary.com/press/images/movie-tie-in-The-hobbit.jpg">
  </div>

  <div class="item">
    <img lazy-src="http://netdna.webdesignerdepot.com/uploads/2011/02/jurassicpark.jpg">
  </div>

  <div class="item">
    <img lazy-src="http://posterwire.com/wp-content/uploads/lord_of_war.jpg">
  </div>

  <div class="item">
    <img lazy-src="https://davebrendon.files.wordpress.com/2010/12/i-am-number-four-movie-poster.jpg">
  </div>

  <div class="item">
    <img lazy-src="http://gdj.gdj.netdna-cdn.com/wp-content/uploads/2011/12/grey-movie-poster.jpg">
  </div>

  <div class="item">
    <img lazy-src="https://s-media-cache-ak0.pinimg.com/originals/e2/81/9d/e2819de0653c516f0e242038770fa3b8.jpg">
  </div>

  <div class="item">
    <img lazy-src="http://netdna.webdesignerdepot.com/uploads/2011/02/inception.jpg">
  </div>

  <div class="item">
    <img lazy-src="https://bo3li.files.wordpress.com/2011/05/drive-angry-movie-cover.jpg">
  </div>

  <div class="item">
    <img lazy-src="http://www.tolkienlibrary.com/press/images/movie-tie-in-The-hobbit.jpg">
  </div>

</div>
Declare @T table (id int,nameVal varchar(50),parentId int)
Insert into @T values 
(1   ,'A',   NULL),  
(2   ,'B',   NULL),  
(3   ,'C',   NULL),
(4   ,'D',   NULL),  
(5   ,'E',   NULL),  
(6   ,'A1',  1),  
(7   ,'A2',  6),  
(8   ,'A3',  1),  
(9   ,'A4',  7),  
(10  ,'B1',  2),  
(11  ,'B2',  2)  

Declare @Top    int         = null      --<<  Sets top of Hier Try 6
Declare @Nest   varchar(25) = '|-----'  --<<  Optional: Added for readability
Declare @Filter varchar(25) = '7'       --<<  Empty for All or try '7,10'

;with cteP as (
      Select Seq  = cast(10000+Row_Number() over (Order by nameVal) as varchar(500))
            ,ID
            ,parentId
            ,Lvl=1
            ,nameVal 
      From   @T 
      Where  IsNull(@Top,-1) = case when @Top is null then isnull(parentId,-1) else ID end
      Union  All
      Select Seq  = cast(concat(p.Seq,'.',10000+Row_Number() over (Order by r.nameVal)) as varchar(500))
            ,r.ID
            ,r.parentId
            ,p.Lvl+1
            ,r.nameVal
      From   @T r
      Join   cteP p on r.parentId = p.ID)
     ,cteR1 as (Select *,R1=Row_Number() over (Order By Seq) From cteP)
     ,cteR2 as (Select A.Seq,A.ID,R2=Max(B.R1) From cteR1 A Join cteR1 B on (B.Seq like A.Seq+'%') Group By A.Seq,A.ID )
     ,cte   as (
                Select A.R1  
                      ,B.R2
                      ,A.ID
                      ,A.parentId
                      ,A.Lvl
                      ,nameVal = Replicate(@Nest,A.Lvl-1) + A.nameVal
                 From cteR1 A
                 Join cteR2 B on A.ID=B.ID
               )
Select Distinct A.*
 From  cte A
 Join (
        Select A.R1,A.R2 
         From  cte A
         Join (Select R1 from cte Where IIF(@Filter='',1,0)+CharIndex(concat(',',ID,','),concat(',',@Filter+','))>0) B
           on B.R1 between A.R1 and A.R2
      ) B on A.R1 between B.R1 and B.R2
 Order By A.R1