1 | /* |
2 | * Copyright (C) 2012, Google Inc. All rights reserved. |
3 | * |
4 | * Redistribution and use in source and binary forms, with or without |
5 | * modification, are permitted provided that the following conditions |
6 | * are met: |
7 | * 1. Redistributions of source code must retain the above copyright |
8 | * notice, this list of conditions and the following disclaimer. |
9 | * 2. Redistributions in binary form must reproduce the above copyright |
10 | * notice, this list of conditions and the following disclaimer in the |
11 | * documentation and/or other materials provided with the distribution. |
12 | * |
13 | * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND ANY |
14 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED |
15 | * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE |
16 | * DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY |
17 | * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES |
18 | * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; |
19 | * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON |
20 | * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
21 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS |
22 | * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
23 | */ |
24 | |
25 | #pragma once |
26 | |
27 | #include "AudioScheduledSourceNode.h" |
28 | #include <wtf/Lock.h> |
29 | |
30 | namespace WebCore { |
31 | |
32 | class PeriodicWave; |
33 | |
34 | // OscillatorNode is an audio generator of periodic waveforms. |
35 | |
36 | class OscillatorNode final : public AudioScheduledSourceNode { |
37 | WTF_MAKE_ISO_ALLOCATED(OscillatorNode); |
38 | public: |
39 | // The waveform type. |
40 | enum class Type { |
41 | Sine, |
42 | Square, |
43 | Sawtooth, |
44 | Triangle, |
45 | Custom |
46 | }; |
47 | |
48 | static Ref<OscillatorNode> create(AudioContext&, float sampleRate); |
49 | |
50 | virtual ~OscillatorNode(); |
51 | |
52 | Type type() const { return m_type; } |
53 | ExceptionOr<void> setType(Type); |
54 | |
55 | AudioParam* frequency() { return m_frequency.get(); } |
56 | AudioParam* detune() { return m_detune.get(); } |
57 | |
58 | void setPeriodicWave(PeriodicWave*); |
59 | |
60 | private: |
61 | OscillatorNode(AudioContext&, float sampleRate); |
62 | |
63 | void process(size_t framesToProcess) final; |
64 | void reset() final; |
65 | |
66 | double tailTime() const final { return 0; } |
67 | double latencyTime() const final { return 0; } |
68 | |
69 | // Returns true if there are sample-accurate timeline parameter changes. |
70 | bool calculateSampleAccuratePhaseIncrements(size_t framesToProcess); |
71 | |
72 | bool propagatesSilence() const final; |
73 | |
74 | // One of the waveform types defined in the enum. |
75 | Type m_type { Type::Sine }; |
76 | |
77 | // Frequency value in Hertz. |
78 | RefPtr<AudioParam> m_frequency; |
79 | |
80 | // Detune value (deviating from the frequency) in Cents. |
81 | RefPtr<AudioParam> m_detune; |
82 | |
83 | bool m_firstRender; |
84 | |
85 | // m_virtualReadIndex is a sample-frame index into our buffer representing the current playback position. |
86 | // Since it's floating-point, it has sub-sample accuracy. |
87 | double m_virtualReadIndex; |
88 | |
89 | // This synchronizes process(). |
90 | mutable Lock m_processMutex; |
91 | |
92 | // Stores sample-accurate values calculated according to frequency and detune. |
93 | AudioFloatArray m_phaseIncrements; |
94 | AudioFloatArray m_detuneValues; |
95 | |
96 | RefPtr<PeriodicWave> m_periodicWave; |
97 | |
98 | // Cache the wave tables for different waveform types, except CUSTOM. |
99 | static PeriodicWave* s_periodicWaveSine; |
100 | static PeriodicWave* s_periodicWaveSquare; |
101 | static PeriodicWave* s_periodicWaveSawtooth; |
102 | static PeriodicWave* s_periodicWaveTriangle; |
103 | }; |
104 | |
105 | String convertEnumerationToString(OscillatorNode::Type); // In JSOscillatorNode.cpp |
106 | |
107 | } // namespace WebCore |
108 | |
109 | namespace WTF { |
110 | |
111 | template<> struct LogArgument<WebCore::OscillatorNode::Type> { |
112 | static String toString(WebCore::OscillatorNode::Type type) { return convertEnumerationToString(type); } |
113 | }; |
114 | |
115 | } // namespace WTF |
116 | |