{"size": 1904, "ext": "js", "max_stars_repo_path": "src/patterns/InfinityCycle/index.js", "max_stars_repo_name": "edwardsCam/generative", "max_stars_repo_stars_event_min_datetime": "2017-11-02T22:08:26.000Z", "max_stars_repo_stars_event_max_datetime": "2018-12-06T07:20:45.000Z", "max_issues_repo_path": "src/patterns/InfinityCycle/index.js", "max_issues_repo_name": "edwardsCam/generative", "max_issues_repo_issues_event_min_datetime": "2021-10-05T23:26:56.000Z", "max_issues_repo_issues_event_max_datetime": "2022-02-26T12:22:12.000Z", "max_forks_repo_path": "src/patterns/InfinityCycle/index.js", "max_forks_repo_name": "edwardsCam/generative", "max_forks_repo_forks_event_min_datetime": "2017-11-02T22:08:42.000Z", "max_forks_repo_forks_event_max_datetime": "2017-11-02T22:08:42.000Z"}
{"max_stars_count": 2, "max_issues_count": 3, "max_forks_count": 1, "avg_line_length": 26.0821917808, "max_line_length": 72, "alphanum_fraction": 0.6234243697}
import { interpolateSmooth } from 'utils/Math'
import {
  BufferGeometry, BufferAttribute,
  Line, LineBasicMaterial,
} from 'three'
import { buildColorFromProps } from 'utils/Color'
import clearScene from 'utils/ClearScene'

export default function InfinityCycle(scene, initialProps) {
  let numPoints
  let timeBuff
  let g
  let points
  let line
  reset()

  function animate(time, delta, props) {
    const {
      maxPoints,
      vertical,
      growthTime,
      drawTime,
      pointDistance,
      likeWhoa,
      rotateSpeed,
    } = props

    timeBuff += delta
    numPoints = Math.min(numPoints, maxPoints)
    while (numPoints < maxPoints && timeBuff > drawTime) {
      timeBuff -= drawTime
      numPoints++
    }

    g.setDrawRange(0, numPoints)
    line.material.color = buildColorFromProps(props)
    line.material.needsUpdate = true

    const isVert = vertical
    const domain = [0, growthTime]
    const width = interpolateSmooth(
      { domain, range: isVert ? [4, 2] : [2, 5], value: time },
    )
    const height = interpolateSmooth(
      { domain, range: isVert ? [1, 4] : [4, 3], value: time },
    )
    for (let i = 0; i < numPoints; i++) {
      const j = time * rotateSpeed - (i * pointDistance)
      points[i * 3] = width * Math.sin((isVert ? likeWhoa : 1) * j)
      points[i * 3 + 1] = height * Math.sin((isVert ? 1 : likeWhoa) * j)
    }
    g.attributes.position.needsUpdate = true
    return Promise.resolve()
  }

  function reset() {
    return clearScene(scene).then(() => {
      numPoints = 0
      timeBuff = 0
      g = new BufferGeometry()
      points = new Float32Array(15000) // max points of 5000, *3 for xyz
      g.addAttribute('position', new BufferAttribute(points, 3))

      line = new Line(g, new LineBasicMaterial({
        color: buildColorFromProps(initialProps),
      }))
      scene.add(line)
    })
  }

  return { animate, reset }
}
