OscillatorNode

Baseline Widely available

This feature is well established and works across many devices and browser versions. It’s been available across browsers since July 2015.

Giao diện OscillatorNode đại diện cho một dạng sóng tuần hoàn, chẳng hạn như sóng sine. Đây là một mô-đun xử lý âm thanh AudioScheduledSourceNode tạo ra tần số của sóng nhất định, thực chất là một âm thanh liên tục.

EventTarget AudioNode AudioScheduledSourceNode OscillatorNode
Số đầu vào 0
Số đầu ra 1
Chế độ đếm kênh max
Số kênh 2 (không dùng trong chế độ đếm mặc định)
Giải thích kênh speakers

Hàm khởi tạo

OscillatorNode()

Tạo một đối tượng OscillatorNode mới, tùy chọn cung cấp một đối tượng chỉ định giá trị mặc định cho các thuộc tính của nút. Thay thế, bạn có thể dùng phương thức factory BaseAudioContext.createOscillator(); xem Tạo AudioNode.

Thuộc tính phiên bản

Cũng kế thừa các thuộc tính từ đối tượng cha, AudioScheduledSourceNode.

OscillatorNode.frequency

Một AudioParam a-rate đại diện cho tần số dao động tính bằng hertz (mặc dù AudioParam trả về là chỉ đọc, giá trị mà nó đại diện thì không). Giá trị mặc định là 440 Hz (nốt La trung bình).

OscillatorNode.detune

Một AudioParam a-rate đại diện cho độ chỉnh âm của dao động tính bằng cents (mặc dù AudioParam trả về là chỉ đọc, giá trị mà nó đại diện thì không). Giá trị mặc định là 0.

OscillatorNode.type

Một chuỗi chỉ định hình dạng dạng sóng để phát; đây có thể là một trong số các giá trị tiêu chuẩn, hoặc custom để dùng PeriodicWave mô tả dạng sóng tùy chỉnh. Các dạng sóng khác nhau sẽ tạo ra âm thanh khác nhau. Các giá trị tiêu chuẩn là "sine", "square", "sawtooth", "triangle""custom". Mặc định là "sine".

Phương thức phiên bản

Cũng kế thừa các phương thức từ đối tượng cha, AudioScheduledSourceNode.

OscillatorNode.setPeriodicWave()

Đặt PeriodicWave mô tả dạng sóng tuần hoàn để dùng thay vì một trong các dạng sóng tiêu chuẩn; gọi hàm này sẽ đặt type thành custom.

AudioScheduledSourceNode.start()

Chỉ định thời điểm chính xác để bắt đầu phát âm thanh.

AudioScheduledSourceNode.stop()

Chỉ định thời điểm để dừng phát âm thanh.

Sự kiện

Cũng kế thừa các sự kiện từ đối tượng cha, AudioScheduledSourceNode.

Ví dụ

Sử dụng OscillatorNode

Ví dụ dưới đây cho thấy cách sử dụng cơ bản của AudioContext để tạo oscillator node và bắt đầu phát âm thanh trên nó. Để xem ví dụ được áp dụng, hãy xem Violent Theremin demo (xem app.js để biết mã liên quan).

js
// create web audio api context
const audioCtx = new AudioContext();

// create Oscillator node
const oscillator = audioCtx.createOscillator();

oscillator.type = "square";
oscillator.frequency.setValueAtTime(440, audioCtx.currentTime); // value in hertz
oscillator.connect(audioCtx.destination);
oscillator.start();

Các loại oscillator node khác nhau

Bốn loại oscillator types tích hợp là sine, square, trianglesawtooth. Chúng là hình dạng của dạng sóng được tạo ra bởi oscillator. Thực tế thú vị: Đây là các giá trị mặc định cho hầu hết các synth vì chúng là các dạng sóng dễ tạo ra về mặt điện tử. Ví dụ này trực quan hóa các dạng sóng cho các loại khác nhau ở các tần số khác nhau.

html
<div class="controls">
  <label for="type-select">
    Oscillator type
    <select id="type-select">
      <option>sine</option>
      <option>square</option>
      <option>triangle</option>
      <option>sawtooth</option>
    </select>
  </label>

  <label for="freq-range">
    Frequency
    <input
      type="range"
      min="100"
      max="800"
      step="10"
      value="250"
      id="freq-range" />
  </label>
  <button data-playing="init" id="play-button">Play</button>
</div>

<canvas id="wave-graph"></canvas>

Mã gồm hai phần: trong phần đầu tiên, chúng ta thiết lập phần âm thanh.

js
const typeSelect = document.getElementById("type-select");
const frequencyControl = document.getElementById("freq-range");
const playButton = document.getElementById("play-button");

const audioCtx = new AudioContext();
const osc = new OscillatorNode(audioCtx, {
  type: typeSelect.value,
  frequency: frequencyControl.valueAsNumber,
});
// Rather than creating a new oscillator for every start and stop
// which you would do in an audio application, we are just going
// to mute/un-mute for demo purposes - this means we need a gain node
const gain = new GainNode(audioCtx);
const analyser = new AnalyserNode(audioCtx, {
  fftSize: 1024,
  smoothingTimeConstant: 0.8,
});
osc.connect(gain).connect(analyser).connect(audioCtx.destination);

typeSelect.addEventListener("change", () => {
  osc.type = typeSelect.value;
});

frequencyControl.addEventListener("input", () => {
  osc.frequency.value = frequencyControl.valueAsNumber;
});

playButton.addEventListener("click", () => {
  if (audioCtx.state === "suspended") {
    audioCtx.resume();
  }

  if (playButton.dataset.playing === "init") {
    osc.start(audioCtx.currentTime);
    playButton.dataset.playing = "true";
    playButton.innerText = "Pause";
  } else if (playButton.dataset.playing === "false") {
    gain.gain.linearRampToValueAtTime(1, audioCtx.currentTime + 0.2);
    playButton.dataset.playing = "true";
    playButton.innerText = "Pause";
  } else if (playButton.dataset.playing === "true") {
    gain.gain.linearRampToValueAtTime(0.0001, audioCtx.currentTime + 0.2);
    playButton.dataset.playing = "false";
    playButton.innerText = "Play";
  }
});

Phần thứ hai, chúng ta vẽ dạng sóng trên canvas bằng cách dùng AnalyserNode đã tạo ở trên.

js
const dpr = window.devicePixelRatio;
const w = 500 * dpr;
const h = 300 * dpr;
const canvasEl = document.getElementById("wave-graph");
canvasEl.width = w;
canvasEl.height = h;
const canvasCtx = canvasEl.getContext("2d");

const bufferLength = analyser.frequencyBinCount;
const dataArray = new Uint8Array(bufferLength);
analyser.getByteTimeDomainData(dataArray);

// draw an oscilloscope of the current oscillator
function draw() {
  analyser.getByteTimeDomainData(dataArray);

  canvasCtx.fillStyle = "white";
  canvasCtx.fillRect(0, 0, w, h);

  canvasCtx.lineWidth = 4.0;
  canvasCtx.strokeStyle = "black";
  canvasCtx.beginPath();

  const sliceWidth = (w * 1.0) / bufferLength;
  let x = 0;

  for (let i = 0; i < bufferLength; i++) {
    const v = dataArray[i] / 128.0;
    const y = (v * h) / 2;
    if (i === 0) {
      canvasCtx.moveTo(x, y);
    } else {
      canvasCtx.lineTo(x, y);
    }
    x += sliceWidth;
  }

  canvasCtx.lineTo(w, h / 2);
  canvasCtx.stroke();

  requestAnimationFrame(draw);
}

draw();

Warning: Ví dụ này tạo ra tiếng ồn!

Thông số kỹ thuật

Specification
Web Audio API
# OscillatorNode

Tương thích trình duyệt

Xem thêm