MCPcopy Create free account
hub / github.com/bspaans/python-mingus / play_Bars

Method play_Bars

mingus/midi/sequencer.py:236–312  ·  view source on GitHub ↗

Play several bars (a list of Bar objects) at the same time. A list of channels should also be provided. The tempo can be changed by providing one or more of the NoteContainers with a bpm argument.

(self, bars, channels, bpm=120)

Source from the content-addressed store, hash-verified

234 return {"bpm": bpm}
235
236 def play_Bars(self, bars, channels, bpm=120):
237 """Play several bars (a list of Bar objects) at the same time.
238
239 A list of channels should also be provided. The tempo can be changed
240 by providing one or more of the NoteContainers with a bpm argument.
241 """
242 self.notify_listeners(
243 self.MSG_PLAY_BARS, {"bars": bars, "channels": channels, "bpm": bpm}
244 )
245 qn_length = 60.0 / bpm # length of a quarter note
246 tick = 0.0 # place in beat from 0.0 to bar.length
247 cur = [0] * len(bars) # keeps the index of the NoteContainer under
248 # investigation in each of the bars
249 playing = [] # The NoteContainers being played.
250
251 while tick < bars[0].length:
252 # Prepare a and play a list of NoteContainers that are ready for it.
253 # The list `playing_new` holds both the duration and the
254 # NoteContainer.
255 playing_new = []
256 for (n, x) in enumerate(cur):
257 (start_tick, note_length, nc) = bars[n][x]
258 if start_tick <= tick:
259 self.play_NoteContainer(nc, channels[n])
260 playing_new.append([note_length, n])
261 playing.append([note_length, nc, channels[n], n])
262
263 # Change the length of a quarter note if the NoteContainer
264 # has a bpm attribute
265 if hasattr(nc, "bpm"):
266 bpm = nc.bpm
267 qn_length = 60.0 / bpm
268
269 # Sort the list and sleep for the shortest duration
270 if len(playing_new) != 0:
271 playing_new.sort()
272 shortest = playing_new[-1][0]
273 ms = qn_length * (4.0 / shortest)
274 self.sleep(ms)
275 self.notify_listeners(self.MSG_SLEEP, {"s": ms})
276 else:
277 # If somehow, playing_new doesn't contain any notes (something
278 # that shouldn't happen when the bar was filled properly), we
279 # make sure that at least the notes that are still playing get
280 # handled correctly.
281 if len(playing) != 0:
282 playing.sort()
283 shortest = playing[-1][0]
284 ms = qn_length * (4.0 / shortest)
285 self.sleep(ms)
286 self.notify_listeners(self.MSG_SLEEP, {"s": ms})
287 else:
288 # warning: this could lead to some strange behaviour. OTOH.
289 # Leaving gaps is not the way Bar works. should we do an
290 # integrity check on bars first?
291 return {}
292
293 # Add shortest interval to tick

Callers 4

play_TracksMethod · 0.95
play_BarsFunction · 0.45
test_playbarsMethod · 0.45

Calls 5

notify_listenersMethod · 0.95
play_NoteContainerMethod · 0.95
sleepMethod · 0.95
stop_NoteContainerMethod · 0.95
sortMethod · 0.80

Tested by 2

test_playbarsMethod · 0.36