0

下面的代码在整个屏幕上绘制正弦波,甚至更远。但是,我希望 x 永远不会超过(宽度)。此时,窗口应该被清除,并且应该再次绘制波浪,从 0 开始。我试过了

(set-state! :x (mod (seq->stream x) (width)))

但它没有用。我检查了一些示例,尝试了一些使用检查是否的代码(> x (width)),尝试将逻辑放入绘图函数中,但它们也不起作用。

我想在有限的显示器上绘制一个连续的波形(如心电图)。我将不胜感激任何帮助。

(ns soso.core
  (:require [quil.core :refer :all]
            [quil.helpers.seqs :refer [seq->stream range-incl]]))

(defn setup []
  (smooth)
  (frame-rate 100)
  (background 255)
  (let [x (range-incl)]
    (set-state! :x (seq->stream x))))

(defn draw []
  (stroke 0)
  (stroke-weight 2)
  (let [x ((state :x))
        y (round (* 100 (abs (sin x))))]
    (ellipse x y 4 4)))

编辑

当我尝试将逻辑放入draw函数时,我(set-state! :x 0)在setup函数中编写,并将以下代码放入draw函数中:

(let [x (if (> ((state :x)) 10)
            0
          (inc ((state :x))))])

但它不起作用,并且没有在任何 nrepl 缓冲区中引发任何错误。为了看看发生了什么,我在用户 repl 中尝试了这段代码:

(let [x 0]
  (take 20
        (if (> x 10)
            0
          (inc x))))

即使我通过将 if 语句包装在内部来尝试此代码(into '()),该代码仍抱怨:“IllegalArgumentException 不知道如何从 java.lang.Long clojure.lang.RT.seqFrom 创建 ISeq”。与以下内容相同:

(loop [x 0]
  (if (> x 10)
    0
    (recur (inc x))))

这个 if 语句有什么问题?clojure api 表示 if 测试测试条件,然后相应地评估并产生 then 或 else 分支。如果它产生了,它应该吐出那个整数,然后它会被添加到列表中,我认为它又应该由 take 函数列出。

4

1 回答 1

0

更像这样的东西似乎可以提供您正在寻找的效果。

(defn draw []
  (stroke 0)
  (stroke-weight 2)
  (let [x ((state :x))
        y (+ 100 (* 100 (sin (/ x 100))))]
    (ellipse (mod x (width)) y 4 4)))

您遇到的几个问题:

  1. sin 的输入是以弧度为单位的浮点值。我在这里除以 100 的技巧只是确保我们得到一个很好的连续输出。实际上,如果您想每 n 个像素循环一次,您需要使用 2 PI / n 来调整 x。
  2. 将值四舍五入会给你分数,因为罪的范围是 1 到 -1。在这里,我通过添加 100 进行调整。
  3. 你在哪里摆弄 x 将取决于确切的要求。在这里,我只是通过在绘图函数中取其模数来包装您的 x 值。

希望这可以帮助。

于 2014-05-02T21:31:58.297 回答