如何利用while循环制作动画和显示总计

时间:2018-09-27 00:28:17

标签: javascript animation while-loop

我正在尝试根据用户输入的动画总量。用户输入一些数字后,总数从0到总数动画。在阅读了各种书籍之后,我有些困惑,并认为StackOverflow将是练习JavaScript的最佳方法。请告诉我我的代码哪里出问题了。

代码如下:

<body>
<div>
    <label for="price">Price:</label>
    <input type="text" id="price" name="price">
    <br>
    <label for="Quantity">Quantity:</label>
    <input type="text" id="quantity" name="quantity">
    <br>
    <label for="Amount">Amount:</label>
    <input type="text" id="amount" name="amount">
</div>
<script>
var price = document.getElementById("price").value;
var quantity = document.getElementById("quantity").value;
var amount = price * quantity;
var length;

function updateAmount(){
  while(amount = 0; amount <= amount.length; amount++){
    document.getElementById("amount").value;
}

setInterval(updateAmount, 10);

从我的代码可以看出,我有点困惑。如果您能引导我朝正确的方向前进,我将不胜感激。

3 个答案:

答案 0 :(得分:1)

我建议您调查requestAnimationFrameeasing equations。在处理动画时,它们将有很大帮助。

我创建了一个示例JSFiddle,以向您显示requestAnimationFrame和缓动方程式。

HTML

<div>
    <label for="price">Price:</label>
    <input type="number" id="price" name="price">
    <label for="Quantity">Quantity:</label>
    <input type="number" id="quantity" name="quantity">
    <label for="Amount">Amount:</label>
    <div id="amount"></div>
</div>

JS

var priceInput = document.querySelector("#price");
var quantityInput = document.querySelector("#quantity");
var amountDiv = document.querySelector("#amount");

priceInput.addEventListener('keyup', update);
quantityInput.addEventListener('keyup', update);


var aid = null; // request animation id
var startTime = 0;
var duration = 1000; // in milliseconds
var amount = 0;
var begin = 0;
var change = 0;

function update() {
    if (aid !== null) {
        cancelAnimationFrame(aid);
    }

    var price = parseFloat(priceInput.value || 0);
    var quantity = parseInt(quantityInput.value || 0);
    startTime = performance.now();
    begin = amount;
    change = (price * quantity) - begin;
    aid = requestAnimationFrame(step);
}

function step(ts) {
    aid = requestAnimationFrame(step);
    var elapsed = ts - startTime;
    if (elapsed < duration) {
        amount = easeOutQuad(elapsed, begin, change, duration);
        amountDiv.innerHTML = amount.toFixed(2);
    }
    else {
        cancelAnimationFrame(aid);
        amountDiv.innerHTML = (begin + change).toFixed(2);
    }
}

// t = time
// b = begin
// c = change
// d = duration
function easeOutQuad(t, b, c, d) {
    return -c * (t /= d) * (t - 2) + b;
}

答案 1 :(得分:0)

您同时使用了while循环(它将同步运行直到完成而没有延迟)和setInterval。您将需要取消while循环部分。

var displayedAmount = 0;
var updateInterval = setInterval(updateAmount, 10)

function updateAmount() {
  if (displayedAmount >= amount) {
     clearInterval(updateInterval);
     return;
  }

  displayedAmount++;
  document.getElementById("amount").value = displayedAmount;
}

一种效果更好的更好方法是使用动画帧。确定所需的更改速率,例如:

const changePerMillisecond = 0.001; // 1 dollar? per second

...或:

const changePerMillisecond = total / 5000; // Animation always takes 5 seconds

...然后您可以使用此动画帧循环:

const startTime = Date.now();
let displayedAmount = 0;
function animateValue() {
  const timeTranspired = Date.now() - startTime;
  displayedAmount = Math.min(value, timeTranspired * changePerMillisecond);
  document.getElementById("amount").value = displayedAmount.toFixed(2);

  if (displayedAmount < amount) 
    requestAnimationFrame(animateValue);
}

requestAnimationFrame(animateValue);

答案 2 :(得分:0)

Option Explicit
'With Project ==================================================================
'  .Title: DueDateFWSLWL - Due Date: First Weekend Skip, Last Weekend Less
'  .Author: YMG
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'  With .Contents
'    Sub DueDateTester
'*** Function DueDateFWSLWL ***
'    Function WeekDayShifter
'  End With
'===============================================================================
'
'-------------------------------------------------------------------------------
Sub DueDateTester()
'
'Description
'  Practical use of the DueDateFWSLWL Function.
'Parameters
'  None
'Returns
'  Various outputs of dates as the result of the DueDateFWSLWL Function.
'
'-- Customize BEGIN --------------------
  Const Days As Long = 14
'-- Customize END ----------------------
'
  Debug.Print DueDateFWSLWL(Days)
  MsgBox DueDateFWSLWL(Days), vbInformation, "Due Date"
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'or
  Dim loF1 As Long
  Dim str1 As String
  str1 = "Due Date from 1 to 100"
  For loF1 = 1 To 100 Step 2
    str1 = str1 & vbCrLf & loF1 & Chr(9) & DueDateFWSLWL(loF1)
  Next
    Debug.Print str1
    MsgBox str1, vbInformation, "Due Date"
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
'or
'In Excel used as any other function e.g. type into cell A1 the number of days,
'and into another cell =DueDateFWSLWL(A1)
'etc.
'
End Sub
'
'-------------------------------------------------------------------------------
Function DueDateFWSLWL(Days As Long) As Date
'
'Description
'  Calculates a 'due' date after a specified number of days counting from today,
'  not counting the first weekend and shifting back to friday if it results on a
'  weekend.
'Parameters¸
'  cDays - The number of days.
'Returns
'  The 'due' date.
'Precendents
'  Function WeekDayShifter
'
  Dim Today As Date
  Dim iWD As Integer
  Dim iFirstWeekend As Integer
  Dim loDays As Long
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
  'Date Function: Returns a Variant (Date) containing the current system date.
  Today = Date
  iWD = WeekDayShifter(Weekday(Today))
  iFirstWeekend = 7 - iWD 'Results from 0-6
  If iFirstWeekend < Days + 2 Then
    Select Case iFirstWeekend
      Case 0 'It's a sunday.
        loDays = Days '+ 0 '0 for monday.
      Case 1 'It's a saturday.
        loDays = Days + 1 '1 for sunday.
      Case Else 'It's a workday.
        loDays = Days + 2 '2 for first weekend (Saturday & Sunday).
    End Select
   Else
'
'Time has run out. Sorry.
'
'This code might be wrong BEGIN ------------------------------------------------
'But its only here for some ridiculous inputs like 1 or 2 days, so I don't care.
    Select Case WeekDayShifter(Weekday(Today + Days))
      Case 0 'It's a sunday.
        loDays = Days - 2 '2 for sunday.
      Case 1 'It's a saturday.
        loDays = Days - 1 '1 for saturday.
      Case Else 'It's a workday
        loDays = Days '-0 '0 for workday.
    End Select
'This code might be wrong END --------------------------------------------------
'
  End If
''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''''
  DueDateFWSLWL = Today + loDays
  Select Case WeekDayShifter(Weekday(DueDateFWSLWL))
    Case 7 'Sunday
      DueDateFWSLWL = DueDateFWSLWL - 2
    Case 6 'Saturday
      DueDateFWSLWL = DueDateFWSLWL - 1
  End Select
'
End Function
'
'-------------------------------------------------------------------------------
Function WeekDayShifter(Weekday As Integer) As Integer
'
'Description
'  Shifts the results of the Weekday Function so that monday is the first day of
'  the week and sunday the last (7th).
'Parameters
'  Weekday - Default weekday from the Visual Basic Weekday Function.
'Returns
'  A 'shifted' weekday integer.
'Dependents
'  Function DueDateFWSLWL
'
  If Not IsNumeric(Weekday) Or Weekday < 1 Or Weekday > 7 Then Exit Function
  If Weekday <> 1 Then
    WeekDayShifter = Weekday - 1 'From monday to saturday
   Else
    WeekDayShifter = 7 'Sunday
  End If
'
''''''''''''''''''''''''''''''''''''''''
' Weekday Function: ' WeekDayShifter:  '
'  1 - Sunday *     '  1 - Monday      '
'  2 - Monday       '  2 - Tuesday     '
'  3 - Tuesday      '  3 - Wednesday   '
'  4 - Wednesday    '  4 - Thursday    '
'  5 - Thursday     '  5 - Friday      '
'  6 - Friday       '  6 - Saturday *  '
'  7 - Saturday *   '  7 - Sunday *    '
''''''''''''''''''''''''''''''''''''''''
'
End Function
'-------------------------------------------------------------------------------
'
'With Idea Source --------------------------------------------------------------
'  .Title: VBA - Add days with weekends, less the weekend of actual week
'  .TitleURL: https://stackoverflow.com/questions/52524316/vba-add-days-with-weekends-less-the-weekend-of-actual-week
'  .Author: L.Th
'  .AuthorURL: https://stackoverflow.com/users/10009861/l-th
'End With ----------------------------------------------------------------------
'
'End With ======================================================================

您忘记分配数量元素的值

function updateAmount(){
  while(amount = 0; amount <= amount.length; amount++){
    document.getElementById("amount").value;
}

如果要查看实际变化的数量,则在更新输入值时需要设置一个固定的时间间隔。像这样的东西:

document.getElementById("amount").value = amount;