2 # Copyright (C) 2009 Anton Khirnov <wyskas@gmail.com>
4 # Nephilim is free software: you can redistribute it and/or modify
5 # it under the terms of the GNU General Public License as published by
6 # the Free Software Foundation, either version 3 of the License, or
7 # (at your option) any later version.
9 # Nephilim 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 General Public License for more details.
14 # You should have received a copy of the GNU General Public License
15 # along with Nephilim. If not, see <http://www.gnu.org/licenses/>.
18 from PyQt4
import QtGui
, QtCore
19 from PyQt4
.QtCore
import QVariant
21 from ..common
import Button
22 from ..plugin
import Plugin
25 class wgPlayControl(QtGui
.QToolBar
):
26 """Displays controls for interacting with playing, like play, volume ..."""
43 class VolumeSlider(QtGui
.QSlider
):
45 def __init__(self
, parent
):
46 QtGui
.QSlider
.__init
__(self
, parent
)
47 self
.setOrientation(parent
.orientation())
49 self
.setToolTip('Volume control')
51 def paintEvent(self
, event
):
52 painter
= QtGui
.QPainter(self
)
53 painter
.eraseRect(self
.rect())
55 grad
= QtGui
.QLinearGradient(0, 0, self
.width(), self
.height())
56 grad
.setColorAt(0, self
.palette().color(QtGui
.QPalette
.Window
))
57 grad
.setColorAt(1, self
.palette().color(QtGui
.QPalette
.Highlight
))
58 if self
.orientation() == QtCore
.Qt
.Horizontal
:
59 rect
= QtCore
.QRect(0, 0, self
.width() * self
.value() / self
.maximum(), self
.height())
61 rect
= QtCore
.QRect(0, self
.height() * (1 - float(self
.value()) / self
.maximum()), self
.width(), self
.height())
62 painter
.fillRect(rect
, QtGui
.QBrush(grad
))
64 def __init__(self
, p
, parent
= None):
65 QtGui
.QToolBar
.__init
__(self
, p
.name
, parent
)
68 self
.logger
= p
.logger
69 self
.setObjectName(p
.name
)
71 self
.play_icon
= QtGui
.QIcon(':icons/media-playback-start.svg')
72 self
.pause_icon
= QtGui
.QIcon(':icons/media-playback-pause.svg')
74 self
.play_action
= self
.addAction(self
.play_icon
, 'play', self
.on_play_click
)
75 self
.stop_action
= self
.addAction(QtGui
.QIcon(':icons/media-playback-stop.svg'), 'stop', self
.on_stop_click
)
76 self
.prev_action
= self
.addAction(QtGui
.QIcon(':icons/media-skip-backward.svg'), 'previous', self
.on_prev_click
)
77 self
.next_action
= self
.addAction(QtGui
.QIcon(':icons/media-skip-forward.svg'), 'next', self
.on_next_click
)
80 self
.vol_slider
= self
.VolumeSlider(self
)
81 self
.vol_slider
.valueChanged
.connect(self
.onVolumeSliderChange
)
82 self
.addWidget(self
.vol_slider
)
85 self
.random
= self
.addAction(QtGui
.QIcon(':icons/media-playlist-shuffle.svgz'), 'random')
86 self
.random
.setCheckable(True)
87 self
.random
.toggled
.connect(self
.p
.mpclient
.random
)
88 self
.p
.mpclient
.random_changed
.connect(self
.random
.setChecked
)
90 self
.repeat
= self
.addAction(QtGui
.QIcon(':icons/media-playlist-repeat.svg'), 'repeat')
91 self
.repeat
.setCheckable(True)
92 self
.p
.mpclient
.repeat_changed
.connect(self
.repeat
.setChecked
)
93 self
.repeat
.toggled
.connect(self
.p
.mpclient
.repeat
)
95 self
.single
= self
.addAction(QtGui
.QIcon(':icons/single.png'), 'single mode')
96 self
.single
.setCheckable(True)
97 self
.p
.mpclient
.single_changed
.connect(self
.single
.setChecked
)
98 self
.single
.toggled
.connect(self
.p
.mpclient
.single
)
100 self
.consume
= self
.addAction(QtGui
.QIcon(':icons/consume.png'), 'consume mode')
101 self
.consume
.setCheckable(True)
102 self
.p
.mpclient
.consume_changed
.connect(self
.consume
.setChecked
)
103 self
.consume
.toggled
.connect(self
.p
.mpclient
.consume
)
105 self
.outputs_menu
= QtGui
.QMenu('Audio outputs')
106 outputs
= self
.addAction(QtGui
.QIcon(':icons/outputs.png'), 'Audio outputs')
107 outputs
.triggered
.connect(lambda : self
.outputs_menu
.popup(QtGui
.QCursor
.pos()))
108 self
.p
.mpclient
.connect_changed
.connect(self
.__update
_outputs
)
110 self
.orientationChanged
.connect(self
.vol_slider
.setOrientation
)
112 self
.p
.mpclient
.state_changed
.connect(self
.onStateChange
)
113 self
.p
.mpclient
.volume_changed
.connect(self
.onVolumeChange
)
115 def __update_outputs(self
):
116 self
.outputs_menu
.clear()
117 for output
in self
.p
.mpclient
.outputs
:
118 act
= self
.outputs_menu
.addAction(output
.name
)
119 act
.setCheckable(True)
120 act
.setChecked(output
.state
)
121 act
.toggled
.connect(output
.set_state
)
122 output
.state_changed
.connect(act
.setChecked
)
124 def onStateChange(self
, new_state
):
125 status
= self
.p
.mpclient
.status()
127 if new_state
== 'play':
128 self
.play_action
.setIcon(self
.pause_icon
)
129 self
.play_action
.setToolTip('pause')
130 elif new_state
== 'pause' or new_state
== 'stop':
131 self
.play_action
.setIcon(self
.play_icon
)
132 self
.play_action
.setToolTip('play')
134 def onVolumeChange(self
, new_vol
):
135 self
.vol_slider
.setValue(new_vol
)
137 def on_play_click(self
):
138 status
=self
.p
.mpclient
.status()
139 if status
['state']=='play':
140 self
.logger
.info('Toggling playback')
141 self
.p
.mpclient
.pause()
142 elif status
['state']=='stop':
143 self
.logger
.info('Pausing playback')
144 self
.p
.mpclient
.play(None)
146 self
.p
.mpclient
.resume()
147 def on_stop_click(self
):
148 self
.logger
.info('Stopping playback')
149 self
.p
.mpclient
.stop()
150 def on_prev_click(self
):
151 self
.logger
.info('Playing previous')
152 self
.p
.mpclient
.previous()
153 def on_next_click(self
):
154 self
.logger
.info('Playing next')
155 self
.p
.mpclient
.next()
156 def onVolumeSliderChange(self
, val
):
157 self
.p
.mpclient
.set_volume(val
)
159 class PlayControl(Plugin
):
161 info
= 'Controls playback.'
167 self
.o
= wgPlayControl(self
, None)
168 QtGui
.QApplication
.instance().main_win
.addToolBar(QtCore
.Qt
.TopToolBarArea
, self
.o
)
170 QtGui
.QApplication
.instance().main_win
.removeToolBar(self
.o
)