+
+ Examples
+ --------
+
+ >>> from .engine import CommandMessage
+
+ >>> root_path = os.path.sep + 'path'
+ >>> p = FilePlaylist(drivers=[],
+ ... path=os.path.join(root_path, 'to','playlist'))
+ >>> p.info['note'] = 'An example playlist'
+ >>> c = Curve(os.path.join(root_path, 'to', 'curve', 'one'))
+ >>> c.info['note'] = 'The first curve'
+ >>> p.append_curve(c)
+ >>> c = Curve(os.path.join(root_path, 'to', 'curve', 'two'))
+ >>> c.info['attr with spaces'] = 'The second curve\\nwith endlines'
+ >>> c.command_stack.extend([
+ ... CommandMessage('command A', {'arg 0':0, 'arg 1':'X'}),
+ ... CommandMessage('command B', {'arg 0':1, 'curve':c}),
+ ... ])
+ >>> p.append_curve(c)
+ >>> print p.flatten() # doctest: +REPORT_UDIFF
+ # Hooke playlist version 0.2
+ !!python/object/new:hooke.playlist.FilePlaylist
+ listitems:
+ - !!python/object:hooke.curve.Curve
+ info: {note: The first curve}
+ name: one
+ path: curve/one
+ - &id001 !!python/object:hooke.curve.Curve
+ command_stack: !!python/object/new:hooke.command_stack.CommandStack
+ listitems:
+ - !!python/object:hooke.engine.CommandMessage
+ arguments: {arg 0: 0, arg 1: X}
+ command: command A
+ explicit_user_call: true
+ - !!python/object:hooke.engine.CommandMessage
+ arguments:
+ arg 0: 1
+ curve: *id001
+ command: command B
+ explicit_user_call: true
+ info: {attr with spaces: 'The second curve
+ <BLANKLINE>
+ with endlines'}
+ name: two
+ path: curve/two
+ state:
+ _base_path: /path/to
+ info: {note: An example playlist}
+ name: playlist.hkp
+ path: /path/to/playlist.hkp
+ version: '0.2'
+ <BLANKLINE>
+ >>> p.relative_curve_paths = False
+ >>> print p.flatten() # doctest: +REPORT_UDIFF
+ # Hooke playlist version 0.2
+ !!python/object/new:hooke.playlist.FilePlaylist
+ listitems:
+ - !!python/object:hooke.curve.Curve
+ info: {note: The first curve}
+ name: one
+ path: /path/to/curve/one
+ - &id001 !!python/object:hooke.curve.Curve
+ command_stack: !!python/object/new:hooke.command_stack.CommandStack
+ listitems:
+ - !!python/object:hooke.engine.CommandMessage
+ arguments: {arg 0: 0, arg 1: X}
+ command: command A
+ explicit_user_call: true
+ - !!python/object:hooke.engine.CommandMessage
+ arguments:
+ arg 0: 1
+ curve: *id001
+ command: command B
+ explicit_user_call: true
+ info: {attr with spaces: 'The second curve
+ <BLANKLINE>
+ with endlines'}
+ name: two
+ path: /path/to/curve/two
+ state:
+ _base_path: /path/to
+ info: {note: An example playlist}
+ name: playlist.hkp
+ path: /path/to/playlist.hkp
+ relative_curve_paths: false
+ version: '0.2'
+ <BLANKLINE>
+ """
+ rcp = self._relative_curve_paths
+ self._relative_curve_paths = self.relative_curve_paths
+ self.update_curve_paths()
+ self._relative_curve_paths = rcp
+ digest = self._digest
+ self._digest = None # don't save the digest (recursive file).
+ yaml_string = yaml.dump(self, allow_unicode=True)
+ self._digest = digest
+ self.update_curve_paths()
+ return ('# Hooke playlist version %s\n' % self.version) + yaml_string
+
+ def save(self, path=None, makedirs=True):
+ """Saves the playlist to a YAML file.
+ """
+ self.set_path(path)
+ dirname = os.path.dirname(self.path) or '.'
+ if makedirs == True and not os.path.isdir(dirname):
+ os.makedirs(dirname)
+ with open(self.path, 'w') as f:
+ f.write(self.flatten())
+ self._digest = self.digest()
+
+
+def from_string(string):
+ u"""Load a playlist from a string.
+
+ Examples
+ --------
+
+ Minimal example.
+
+ >>> string = '''# Hooke playlist version 0.2
+ ... !!python/object/new:hooke.playlist.FilePlaylist
+ ... state:
+ ... version: '0.2'
+ ... listitems:
+ ... - !!python/object:hooke.curve.Curve
+ ... path: curve/one
+ ... - !!python/object:hooke.curve.Curve
+ ... path: curve/two
+ ... '''
+ >>> p = from_string(string)
+ >>> p.set_path('/path/to/playlist')
+ >>> for curve in p:
+ ... print curve.name, curve.path
+ one /path/to/curve/one
+ two /path/to/curve/two
+
+ More complicated example.
+
+ >>> string = '''# Hooke playlist version 0.2
+ ... !!python/object/new:hooke.playlist.FilePlaylist
+ ... listitems:
+ ... - !!python/object:hooke.curve.Curve
+ ... info: {note: The first curve}
+ ... name: one
+ ... path: /path/to/curve/one
+ ... - &id001 !!python/object:hooke.curve.Curve
+ ... command_stack: !!python/object/new:hooke.command_stack.CommandStack
+ ... listitems:
+ ... - !!python/object:hooke.engine.CommandMessage
+ ... arguments: {arg 0: 0, arg 1: X}
+ ... command: command A
+ ... - !!python/object:hooke.engine.CommandMessage
+ ... arguments:
+ ... arg 0: 1
+ ... curve: *id001
+ ... command: command B
+ ... info: {attr with spaces: 'The second curve
+ ...
+ ... with endlines'}
+ ... name: two
+ ... path: /path/to/curve/two
+ ... state:
+ ... _base_path: /path/to
+ ... _index: 1
+ ... info: {note: An example playlist}
+ ... name: playlist.hkp
+ ... path: /path/to/playlist.hkp
+ ... version: '0.2'
+ ... '''
+ >>> p = from_string(string)
+ >>> p.set_path('/path/to/playlist')
+ >>> p._index
+ 1
+ >>> p.info
+ {'note': 'An example playlist'}
+ >>> for curve in p:
+ ... print curve.name, curve.path
+ one /path/to/curve/one
+ two /path/to/curve/two
+ >>> p[-1].info['attr with spaces']
+ 'The second curve\\nwith endlines'
+ >>> type(p[-1].command_stack)
+ <class 'hooke.command_stack.CommandStack'>
+ >>> p[0].command_stack
+ []
+ >>> type(p[0].command_stack)
+ <class 'hooke.command_stack.CommandStack'>
+ >>> p[-1].command_stack # doctest: +NORMALIZE_WHITESPACE
+ [<CommandMessage command A {arg 0: 0, arg 1: X}>,
+ <CommandMessage command B {arg 0: 1, curve: <Curve two>}>]
+ >>> type(p[1].command_stack)
+ <class 'hooke.command_stack.CommandStack'>
+ >>> c2 = p[-1]
+ >>> c2.command_stack[-1].arguments['curve'] == c2
+ True
+ """
+ return yaml.load(string)
+
+def load(path=None, drivers=None, identify=True, hooke=None):
+ """Load a playlist from a file.
+ """
+ path = playlist_path(path, expand=True)
+ with open(path, 'r') as f:
+ text = f.read()
+ playlist = from_string(text)
+ playlist.set_path(path)
+ playlist._digest = playlist.digest()
+ if drivers != None:
+ playlist.drivers = drivers
+ playlist.set_path(path)
+ for curve in playlist:
+ curve.set_hooke(hooke)
+ if identify == True:
+ curve.identify(playlist.drivers)
+ return playlist
+
+
+class Playlists (NoteIndexList):
+ """A :class:`NoteIndexList` of :class:`FilePlaylist`\s.
+ """
+ pass