PageSourceSearch

https://railsblocks.com/assets/controllers/clickable_animated_numb…390ae1950468f67f061f9d9b7247f30668d899cd.js

js railsblocks.com collected 2026-09-25 20:22:54 UTC 2,884 bytes, 78 lines download raw bytes

1import { Controller } from "@hotwired/stimulus";
2import "number-flow"; // Ensure number-flow is imported
3import { continuous } from "number-flow"; // For the slot machine effect
4
5export default class extends Controller {
6  static values = {
7    initial: { type: Number, default: 42 }, // Initial value
8    min: { type: Number, default: 0 }, // Minimum value
9    max: { type: Number, default: 999 }, // Maximum value
10    duration: { type: Number, default: 700 }, // Animation duration in ms
11  };
12
13  connect() {
14    this.element.innerHTML = "<number-flow></number-flow>";
15    this.flow = this.element.querySelector("number-flow");
16
17    // Configure spin and transform timings
18    this.flow.spinTiming = {
19      duration: this.durationValue,
20      easing: "ease-in-out",
21    };
22    this.flow.transformTiming = {
23      duration: this.durationValue,
24      easing: "ease-in-out",
25    };
26    this.flow.plugins = [continuous]; // Keep slot machine effect
27
28    // Store the target initial value
29    const targetInitialValue = this.initialValue;
30
31    // Set display to 0 initially without animation (or a very brief one if needed by number-flow)
32    // For number-flow, a direct update usually doesn't animate unless configured to.
33    // If it does, we might need to temporarily set duration to 0 for this first update.
34
35    // Temporarily set duration to 0 for the very first update to 0
36    const originalSpinDuration = this.flow.spinTiming.duration;
37    const originalTransformDuration = this.flow.transformTiming.duration;
38    this.flow.spinTiming.duration = 0;
39    this.flow.transformTiming.duration = 0;
40
41    this.flow.update(0); // Set to 0 without animation
42
43    // Restore original animation durations
44    this.flow.spinTiming.duration = originalSpinDuration;
45    this.flow.transformTiming.duration = originalTransformDuration;
46
47    // Set current value for future clicks
48    this.currentValue = targetInitialValue;
49
50    // Animate to the target initial value
51    // Use a timeout to ensure the "0" is rendered before animating
52    setTimeout(() => {
53      this.flow.update(targetInitialValue);
54    }, 50); // A small delay like 50ms should be enough
55  }
56
57  changeNumber() {
58    const oldVal = this.currentValue;
59    let newVal = Math.floor(Math.random() * (this.maxValue - this.minValue + 1)) + this.minValue;
60
61    // Ensure new value is different from the old one if possible within the range
62    if (this.maxValue > this.minValue) {
63      // only try to get a different number if range allows
64      while (newVal === oldVal) {
65        newVal = Math.floor(Math.random() * (this.maxValue - this.minValue + 1)) + this.minValue;
66      }
67    }
68
69    this.currentValue = newVal;
70    this.flow.update(this.currentValue);
71  }
72
73  disconnect() {
74    if (this.flow && typeof this.flow.destroy === "function") {
75      // this.flow.destroy(); // If number-flow has a destroy method
76    }
77  }
78};

Line numbers count LF bytes from the start of the resource, as the search results do. Vendor segments are library code the classifier recognised; they are stored but not indexed. Bytes are shown as Latin1 characters, one per byte.