【问题标题】:Animated GIF breaking when changed更改时动画 GIF 中断
【发布时间】:2022-12-06 02:26:28
【问题描述】:

我遇到了一个看似非常简单的问题,但我在修复它时遇到了一些问题。我正在尝试使用 Javascript 在我的页面上创建一个交互式 cat 对象,它基本上执行以下预期行为:

  • 首次加载页面时,猫躺在屏幕中间睡觉 (cat-sleeping.gif)
  • 当您将指针(自定义为看起来像鼠标)稍微靠近猫时,它会坐起来并开始梳理自己 (cat-sitting.gif)
  • 当您将指针移得更近时,猫开始追逐光标 (cat-chasing.gif)

为了处理检测鼠标接近度和追逐行为,我使用了一个在初始设置调用后从 window.requestAnimationFrame 调用的循环。追逐 + 鼠标接近按预期工作,但不断变化的动画状态不是。虽然当猫被激活时图像会按预期发生变化,但动画 gif 会变成静态图像。如果重要的话,我正在使用 Google Chrome 进行测试。

这是循环的 sn-p(请注意,此功能尚未完全完成,但到目前为止所有应该工作的东西都可以工作,除了动画)

function loop() {
  const { pointerEvent, pointerStatic, catActive } = state;
  const { cat, cursor } = settings;

  // Calculate distance between cat and pointer
  const distance = Math.sqrt(
    Math.pow(pointerEvent.x - cat.element.offsetLeft, 2) +
      Math.pow(pointerEvent.y - cat.element.offsetTop, 2)
  );

  // Normalize the distance
  const distanceNorm = scale(distance, 0, 1000);

  // Activate the cat after the pointer gets close enough
  if (distanceNorm < 0.1) {
    updateState({ catActive: true });
  }

  // Flip the cursor left or right depending on the direction of movement
  if (pointerEvent.movementX < 0) {
    cursor.element.style.transform = "scaleX(-1)";
  } else {
    cursor.element.style.transform = "scaleX(1)";
  }

  // Make the cat turn from left to right when the pointer is moving
  if (pointerEvent.x < cat.element.offsetLeft + cat.width / 2) {
    cat.element.style.transform = "scaleX(-1)";
  } else {
    cat.element.style.transform = "scaleX(1)";
  }

  // If the cat is active, chase the pointer
  if (catActive) {
    cat.element.src = "cat-walk.gif";
    cat.element.style.left = `${toAbsolute(
      distanceNorm,
      cat.element.offsetLeft,
      pointerEvent.x - 80
    )}px`;
    cat.element.style.top = `${toAbsolute(
      distanceNorm,
      cat.element.offsetTop,
      pointerEvent.y - 35
    )}px`;
  }

  window.requestAnimationFrame(loop);
}

【问题讨论】:

  • 只是为了排除问题,这个 gif 文件是否有循环设置?因为,这个 gif 可能有动画,但它可能缺少使它从第一帧重新开始的循环指令。
  • 另外,要排除的另一件事是,如果您有循环,是否会在每次迭代中重新加载 gif?您是否尝试在循环外加载 gif,然后影响其在循环内的行为?
  • .gif 是一个循环动画,之前在循环内部交互时工作正常。这是我最初在组合循环功能时使用的图像,所以在我开始尝试替换图像之前它一直运行良好。有没有可能是图像在每一帧都被循环加载,所以它永远停留在第一帧?
  • 嗯。我对此表示怀疑。然而,也许这需要不同的方法。有一个数组怎么样,其中每个元素指向不同的gif。然后,将 cat 变量从常量更改为常规变量,这样您就可以使用该数组中适合您的任何元素重新分配它?
  • 好的。请随时通知我。我很好奇它是怎么回事。

标签: javascript


【解决方案1】:

更改我的状态函数解决了这个问题——我专门为猫创建了一个单独的更改状态函数,因为我意识到由于与 PointerElement 事件共享数据,随着指针移动,状态在每帧都被更新。但是,我不是 100% 确定为什么这实际上有效 - 为了使其发挥作用,我需要从我的 catState 对象直接访问 catActive,而不是使用它的解构变体。我将此作为答案发布,以便我可以共享代码,但我想了解为什么这实际上有效,以便我学习而不是通过反复试验生存!

function updateCatState(newState) {
  let { catActive, cat, catForm } = catState;
  catState = { ...catState, ...newState };

  if (catState.catActive && cat.element.src !== catForm[1]) {
    console.log("catActive");
    cat.element.src = catForm[1];
  } else {
    cat.element.src = catForm[0];
  }
}

【讨论】:

    猜你喜欢
    • 2015-07-20
    • 2013-12-29
    • 2015-12-09
    • 2014-09-25
    • 1970-01-01
    • 2015-05-04
    • 2011-11-20
    • 2019-11-03
    • 1970-01-01
    相关资源
    最近更新 更多