|
1 /* This file is part of the KDE project. |
|
2 |
|
3 Copyright (C) 2009 Nokia Corporation and/or its subsidiary(-ies). |
|
4 |
|
5 This library is free software: you can redistribute it and/or modify |
|
6 it under the terms of the GNU Lesser General Public License as published by |
|
7 the Free Software Foundation, either version 2.1 or 3 of the License. |
|
8 |
|
9 This library is distributed in the hope that it will be useful, |
|
10 but WITHOUT ANY WARRANTY; without even the implied warranty of |
|
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
|
12 GNU Lesser General Public License for more details. |
|
13 |
|
14 You should have received a copy of the GNU Lesser General Public License |
|
15 along with this library. If not, see <http://www.gnu.org/licenses/>. |
|
16 */ |
|
17 |
|
18 #include "volumefadereffect.h" |
|
19 #include "common.h" |
|
20 #include <QtCore> |
|
21 |
|
22 QT_BEGIN_NAMESPACE |
|
23 |
|
24 namespace Phonon |
|
25 { |
|
26 namespace Gstreamer |
|
27 { |
|
28 |
|
29 VolumeFaderEffect::VolumeFaderEffect(Backend *backend, QObject *parent) |
|
30 : Effect(backend, parent, AudioSource | AudioSink) |
|
31 , m_fadeCurve(Phonon::VolumeFaderEffect::Fade3Decibel) |
|
32 , m_fadeTimer(0) |
|
33 , m_fadeDuration(0) |
|
34 , m_fadeFromVolume(0) |
|
35 , m_fadeToVolume(0) |
|
36 { |
|
37 m_effectElement = gst_element_factory_make ("volume", NULL); |
|
38 if (m_effectElement) |
|
39 init(); |
|
40 } |
|
41 |
|
42 VolumeFaderEffect::~VolumeFaderEffect() |
|
43 { |
|
44 if (m_fadeTimer) |
|
45 killTimer(m_fadeTimer); |
|
46 } |
|
47 |
|
48 GstElement* VolumeFaderEffect::createEffectBin() |
|
49 { |
|
50 GstElement *audioBin = gst_bin_new(NULL); |
|
51 |
|
52 // We need a queue to handle tee-connections from parent node |
|
53 GstElement *queue= gst_element_factory_make ("queue", NULL); |
|
54 gst_bin_add(GST_BIN(audioBin), queue); |
|
55 |
|
56 GstElement *mconv= gst_element_factory_make ("audioconvert", NULL); |
|
57 gst_bin_add(GST_BIN(audioBin), mconv); |
|
58 gst_bin_add(GST_BIN(audioBin), m_effectElement); |
|
59 |
|
60 // Link src pad |
|
61 GstPad *srcPad= gst_element_get_pad (m_effectElement, "src"); |
|
62 gst_element_add_pad (audioBin, gst_ghost_pad_new ("src", srcPad)); |
|
63 gst_object_unref (srcPad); |
|
64 |
|
65 // Link sink pad |
|
66 gst_element_link_many(queue, mconv, m_effectElement, (const char*)NULL); |
|
67 GstPad *sinkpad = gst_element_get_pad (queue, "sink"); |
|
68 gst_element_add_pad (audioBin, gst_ghost_pad_new ("sink", sinkpad)); |
|
69 gst_object_unref (sinkpad); |
|
70 return audioBin; |
|
71 } |
|
72 |
|
73 float VolumeFaderEffect::volume() const |
|
74 { |
|
75 gdouble val = 0.0; |
|
76 if (m_effectElement) |
|
77 g_object_get(G_OBJECT(m_effectElement), "volume", &val, (const char*)NULL); |
|
78 return (float)val; |
|
79 } |
|
80 |
|
81 void VolumeFaderEffect::setVolume(float volume) |
|
82 { |
|
83 g_object_set(G_OBJECT(m_effectElement), "volume", volume, (const char*)NULL); |
|
84 } |
|
85 |
|
86 Phonon::VolumeFaderEffect::FadeCurve VolumeFaderEffect::fadeCurve() const |
|
87 { |
|
88 return m_fadeCurve; |
|
89 } |
|
90 |
|
91 void VolumeFaderEffect::setFadeCurve(Phonon::VolumeFaderEffect::FadeCurve fadeCurve) |
|
92 { |
|
93 m_fadeCurve = fadeCurve; |
|
94 } |
|
95 |
|
96 void VolumeFaderEffect::fadeTo(float targetVolume, int fadeTime) |
|
97 { |
|
98 m_fadeToVolume = targetVolume; |
|
99 m_fadeDuration = fadeTime; |
|
100 m_fadeFromVolume = volume(); |
|
101 m_fadeStartTime.start(); |
|
102 |
|
103 if (m_fadeTimer) |
|
104 killTimer(m_fadeTimer); |
|
105 m_fadeTimer = startTimer(30); |
|
106 } |
|
107 |
|
108 void VolumeFaderEffect::updateFade() |
|
109 { |
|
110 double currVal = 0.0; |
|
111 float step = float(m_fadeStartTime.elapsed()) / float(m_fadeDuration); |
|
112 if (step > 1){ |
|
113 step = 1; |
|
114 if (m_fadeTimer) { |
|
115 killTimer(m_fadeTimer); |
|
116 m_fadeTimer = 0; |
|
117 } |
|
118 } |
|
119 // This is a very loose and interpretation of the API |
|
120 // But in fact when fading between arbitrary values, the decibel values make no sense |
|
121 // Note : seems like we will change the API to re-use names from QTimeline for this |
|
122 switch (fadeCurve()) { |
|
123 case Phonon::VolumeFaderEffect::Fade3Decibel: // Slow in the beginning |
|
124 currVal = step * step; |
|
125 break; |
|
126 case Phonon::VolumeFaderEffect::Fade6Decibel: // Linear fade |
|
127 currVal = step; |
|
128 break; |
|
129 case Phonon::VolumeFaderEffect::Fade9Decibel: // Fast in the beginning / Linear |
|
130 currVal = step * 0.5 + (1.0-(1.0-step)*(1.0-step)) * 0.5; |
|
131 break; |
|
132 case Phonon::VolumeFaderEffect::Fade12Decibel: // Fast in the beginning |
|
133 currVal = 1.0 - (1.0-step) * (1.0-step); |
|
134 break; |
|
135 default: |
|
136 break; |
|
137 } |
|
138 const double volume = (1.0 - currVal) * m_fadeFromVolume + currVal * m_fadeToVolume; |
|
139 setVolume(volume); |
|
140 } |
|
141 |
|
142 bool VolumeFaderEffect::event(QEvent *event) |
|
143 { |
|
144 switch (event->type()){ |
|
145 case QEvent::Timer: |
|
146 { |
|
147 QTimerEvent *timerEvent = static_cast<QTimerEvent *>(event); |
|
148 if (timerEvent->timerId() == m_fadeTimer) |
|
149 updateFade(); |
|
150 break; |
|
151 } |
|
152 default: |
|
153 break; |
|
154 } |
|
155 return QObject::event(event); |
|
156 } |
|
157 |
|
158 }} //namespace Phonon::Gstreamer |
|
159 |
|
160 QT_END_NAMESPACE |
|
161 |
|
162 #include "moc_volumefadereffect.cpp" |