Python: module boodle.generator

boodle.generator | index boodle/generator.py

`generator: A module containing various workhorse classes, used deep
in the heart of Boodler.
Generator -- stores the internal state of Boodler sound generation
Channel -- for creating hierarchical trees of sounds and agents
FrameCount -- represents a time (or duration) measured in sound frames
run_agents() -- the big function that does everything`

Modules
`` |  |
StringIO bisect boodle | boodle.listen logging boodle.sample | boodle.stereo sys traceback |

Classes
`` |  | boodle.BoodlerError(exceptions.Exception) BoodleInternalError ChannelError ScheduleError Channel FrameCount Generator
class BoodleInternalError(boodle.BoodlerError)
`` | `BoodleInternalError: Represents an internal sanity check going wrong.`
| Method resolution order: BoodleInternalError boodle.BoodlerError exceptions.Exception exceptions.BaseException __builtin__.object Data descriptors inherited from boodle.BoodlerError: __weakref__ `list of weak references to the object (if defined)` Methods inherited from exceptions.Exception: __init__(...) `x.__init__(...) initializes x; see x.__class__.__doc__ for signature` Data and other attributes inherited from exceptions.Exception: __new__ = <built-in method __new__ of type object> `T.__new__(S, ...) -> a new object with type S, a subtype of T` Methods inherited from exceptions.BaseException: __delattr__(...) `x.__delattr__('name') <==> del x.name` __getattribute__(...) `x.__getattribute__('name') <==> x.name` __getitem__(...) `x.__getitem__(y) <==> x[y]` __getslice__(...) `x.__getslice__(i, j) <==> x[i:j] Use of negative indices is not supported.` __reduce__(...) __repr__(...) `x.__repr__() <==> repr(x)` __setattr__(...) `x.__setattr__('name', value) <==> x.name = value` __setstate__(...) __str__(...) `x.__str__() <==> str(x)` Data descriptors inherited from exceptions.BaseException: __dict__ args message `exception message`
class Channel
`` | `Channel: a class for creating hierarchical trees of sounds and agents. Channel objects should be created via Agent.new_channel() and destroyed with the channel.stop() method. Public methods and fields: parent -- the parent of the channel (None if root) get_root_channel() -- return the root channel of the tree set_volume() -- change the volume of the channel set_pan() -- change the channel to a new pan position stop() -- stop the channel immediately get_prop() -- get a property from this channel has_prop() -- see whether this channel has a given property set_prop() -- set a property on this channel del_prop() -- delete a property from this channel Internal methods: realstop() -- do the work of stopping the channel close() -- shut down the channel addnote() -- note that a note has been added to the channel remnote() -- note that a note has been removed from the channel Class method: compare() -- compare two channels in deepest-to-root order`
| Methods defined here: __init__(self, parent, gen, createagent, startvol, pan) __str__(self) addnote(self) `addnote() -> None Note that a note has been added to the channel. Internal method. (Called from sample.queue_note.)` close(self) `close() -> None Shut down the channel. This presumes that all notes, agents, and subchannels have already been deleted. Internal method. (This is called both from the explicit stop list, and from the regular check for channels with no more stuff scheduled.)` del_prop(self, key) `del_prop(key) -> None Delete a property from this channel. If none is set, this has no effect. Note that this does not affect parent channels. So get_prop(key) may still return a value after del_prop(key).` get_prop(self, key, default=None) `get_prop(key, default=None) -> any Get a property from this channel. If none is set, see if one is inherited from the parent. If there is no inherited value either, return None, or the given default. Note that None is a legal property value. To distinguish between no property and a property set to None, use has_prop().` get_root_channel(self) `get_root_channel() -> channel Return the root channel of the tree.` has_prop(self, key) `has_prop(key) -> bool See whether this channel has a given property. If none is set, see if one is inherited from the parent.` realstop(self) `realstop() -> None Do the work of stopping the channel. This deletes all notes in the channel (and its subchannels), and all agents, and then closes all the subchannels. Finally it closes the channel itself. Internal method. (The stop() method queues this up in stoplist.)` remnote(self) `remnote() -> None Note that a note has been removed from the channel. Internal method. (Called from the callback to cboodle.create_note.)` set_pan(self, newpan, interval=0.5) `set_pan(newpan, interval=0.5) -> None Change the channel to a new pan position. This affects all notes in the channel and any subchannels. The position is specified relative to the parent. A value of 0 (or None, or stereo.default()) places the channel in the same position as its parent. A positive number shifts it to the right of the parent; a negative number shifts it left. The value may also be any object created by the stereo module. The change begins immediately, and occurs smoothly over the interval given (in seconds). If no value is given, the interval defaults to 0.5 (half a second). You should not use a shorter interval; it may not be rendered correctly, particularly for large changes. Due to the way the stereo code is written (a cheap and dirty hack), two stereo changes scheduled too close together on the same channel (within about one second) can interfere with each other. The earlier one may be ignored entirely in favor of the later. Therefore, you should not rely on rapid sequences of set_pan() calls for your sound effects. Set pan positions on individual notes instead, or else create several channels.` set_prop(self, key, val) `set_prop(key, val) -> None Set a property on this channel.` set_volume(self, newvol, interval=0.0050000000000000001) `set_volume(newvolume, interval=0.005) -> None Change the volume of the channel to a new level (0 means silence, 1 means full volume). This affects all notes in the channel and any subchannels. The volume change begins immediately, and occurs smoothly over the interval given (in seconds). If no value is given, the interval defaults to 0.005 (five milliseconds), which is short enough that it will sound instantaneous. (You should not use an interval shorter than 0.005; it can cause undesirable clicks and pops.) Due to the way the volume code is written (a cheap and dirty hack), two volume changes scheduled too close together on the same channel (within about one second) can interfere with each other. The earlier one may be ignored entirely in favor of the later. Therefore, you should not rely on rapid sequences of set_volume() calls for your sound effects. Set volumes on individual notes instead, or else create several channels.` stop(self) `stop() -> None Stop the channel immediately. All sounds playing in the channel (or any subchannels) are cut off; all sounds and agents scheduled to run are discarded. If any notes are playing with non-zero volume, their termination may cause undesirable clicks and pops. It is best to set the volume of a channel to zero before stopping it. (The FadeOutAgent class can be used for this.) Due to the way sound generation is buffered, when an agent calls channel.stop(), the channel may be stopped slightly later than it ought to be.` Static methods defined here: compare(ch1, ch2) `compare(ch1, ch2) -> int Compare two channels in depth order. Sorting a list of channels with this comparison function will put the deepest ones first, the root last.` Data and other attributes defined here: logger = None ordinal = 0
class ChannelError(boodle.BoodlerError)
`` | `ChannelError: Represents an invalid use of a channel.`
| Method resolution order: ChannelError boodle.BoodlerError exceptions.Exception exceptions.BaseException __builtin__.object Data descriptors inherited from boodle.BoodlerError: __weakref__ `list of weak references to the object (if defined)` Methods inherited from exceptions.Exception: __init__(...) `x.__init__(...) initializes x; see x.__class__.__doc__ for signature` Data and other attributes inherited from exceptions.Exception: __new__ = <built-in method __new__ of type object> `T.__new__(S, ...) -> a new object with type S, a subtype of T` Methods inherited from exceptions.BaseException: __delattr__(...) `x.__delattr__('name') <==> del x.name` __getattribute__(...) `x.__getattribute__('name') <==> x.name` __getitem__(...) `x.__getitem__(y) <==> x[y]` __getslice__(...) `x.__getslice__(i, j) <==> x[i:j] Use of negative indices is not supported.` __reduce__(...) __repr__(...) `x.__repr__() <==> repr(x)` __setattr__(...) `x.__setattr__('name', value) <==> x.name = value` __setstate__(...) __str__(...) `x.__str__() <==> str(x)` Data descriptors inherited from exceptions.BaseException: __dict__ args message `exception message`
class FrameCount
`` | `FrameCount: Represents a time (or duration) measured in a fixed number of sound frames. A frame is a group of values, one for each channel. (For a mono sound file, therefore, a frame is the same as a sample value.) When you see a sound rate like 44100 Hz, that's measuring frames per second. FrameCount objects can be passed as the delay (or duration) value for sched_note(), etc. However, you should only do this when you need exact-frame scheduling. A soundscape which uses FrameCount values will come out different on different computers, because not all audio devices play at the same frame rate. Boodler normally compensates for this, but if you use FrameCounts, you are bypassing that compensation. FrameCount(frames) -- constructor. The argument should be an integer (or long) number of frames. No range-checking is done at constructor-time.`
| Methods defined here: __init__(self, frames)
class Generator
`` | `Generator: A class that stores the internal state of Boodler sound generation. Everything in this class is private to Boodler. Interesting fields: (Note that sets are implemented as dicts, where only the keys are significant. It may be worth changing to Python sets, or it may not.) queue -- list of [runtime, agent, handler] lists. Sorted by runtime (and, insignificantly, by the other list values). These are not tuples because we have to update the runtime in place occasionally. rootchannel -- the root channel object channels -- set of channels in existence allhandlers -- set of all active handler objects listeners -- list of sources of external events postqueue -- list of events received from external sources. These are handled at the beginning of the next run cycle loader -- the package loader Internal methods: close() -- shut down the generator object select_time() -- determine the schedule time represented by a value select_duration() -- determine the duration represented by a value set_stats_interval() -- set the interval at which stats are dumped addagent() -- put an agent on the schedule queue remagent() -- remove an agent from the schedule queue addhandler() -- add a Handler object to the system remhandlers() -- remove a list of Handler objects from the system sendevent() -- process an event on the given channel dump_stats() -- write statistical information to the given file`
| Methods defined here: __init__(self, basevolume=0.5, stdinlisten=False, netlisten=False, listenport=None, loader=None) addagent(self, ag, chan, runtime, handle) `addagent(ag, chan, runtime, handle) -> None Put an agent on the schedule queue. The arguments are the channel, the scheduled time to run, and the function to call at that time. (handle is commonly ag.run.) A given agent can only be on the queue once.` addhandler(self, han) `addhandler(han) -> None Add a Handler object to the system. This sets up listening (and channel holds) as described by the Handler.` close(self) `close() -> None Shut down the generator object and any resources it has open. (This does not, however, shut down the cboodle module. The caller must do that.)` dump_stats(self, fl=None) `dump_stats(fl=sys.stdout) -> None Write statistical information to the given file or stream.` remagent(self, ag) `remagent(ag) -> None Remove an agent from the schedule queue. This does not check whether it's on the queue first. (When agents reach the front of the queue and are played, they aren't removed through this method. That's separate code in run_agents().)` remhandlers(self, hans) `remhandlers(hans) -> None Remove a list of Handler objects from the system. This shuts down listening and releases held channels. It is safe for a Handler to appear more than once in the list.` select_duration(self, duration) `select_duration(duration) -> long Determine the duration represented by a value. Typically this is a number (in seconds). It may also be a FrameCount object. This should only be called from Agent methods used by agent run() code. Raises ScheduleError for illegal values.` select_time(self, delay) `select_time(delay) -> long Determine the schedule time represented by a value. Typically this is a number (in seconds), measured from the current agentruntime. It may also be a FrameCount object. This should only be called from Agent methods used by agent run() code. (Outside of run() time, the agentruntime is not set.) Raises ScheduleError for illegal values.` sendevent(self, ev, chan) `sendevent(ev, chan) -> None Process an event on the given channel. This invokes all the listeners which are paying attention to the event.` set_stats_interval(self, val) `set_stats_interval(val) -> None Set the interval (in seconds) at which stats are dumped to the logger. Pass None to turn stats off.`
class ScheduleError(boodle.BoodlerError)
`` | `ScheduleError: Represents an invalid use of the scheduler.`
| Method resolution order: ScheduleError boodle.BoodlerError exceptions.Exception exceptions.BaseException __builtin__.object Data descriptors inherited from boodle.BoodlerError: __weakref__ `list of weak references to the object (if defined)` Methods inherited from exceptions.Exception: __init__(...) `x.__init__(...) initializes x; see x.__class__.__doc__ for signature` Data and other attributes inherited from exceptions.Exception: __new__ = <built-in method __new__ of type object> `T.__new__(S, ...) -> a new object with type S, a subtype of T` Methods inherited from exceptions.BaseException: __delattr__(...) `x.__delattr__('name') <==> del x.name` __getattribute__(...) `x.__getattribute__('name') <==> x.name` __getitem__(...) `x.__getitem__(y) <==> x[y]` __getslice__(...) `x.__getslice__(i, j) <==> x[i:j] Use of negative indices is not supported.` __reduce__(...) __repr__(...) `x.__repr__() <==> repr(x)` __setattr__(...) `x.__setattr__('name', value) <==> x.name = value` __setstate__(...) __str__(...) `x.__str__() <==> str(x)` Data descriptors inherited from exceptions.BaseException: __dict__ args message `exception message`

Functions
`` |  | run_agents(starttime, gen) `run_agents(starttime, gen) -> None The big function that does everything. This is called regularly from inside the cboodle module. Its task is to push notes into the note queue, and also manage everything required to do that -- agents, channels, listeners, etc. Raises StopGeneration when the soundscape is over (i.e., when all channels have expired).`

Data
`` |  | TRIMOFFSET = 13230000 TRIMTIME = 26460000 UNLOADAGE = 10000000 UNLOADTIME = 1323000 cboodle = <boodle.DummyDriver>