palette/sndfile-palette [ Classes ]

[ Top ] [ palette ] [ Classes ]

NAME

 sndfile-palette

 File:             sndfile-palette.lsp

 Class Hierarchy:  named-object -> linked-named-object -> sclist -> 
                   circular-sclist -> assoc-list -> recursive-assoc-list ->
                   palette -> sndfile-palette

 Version:          1.0.7

 Project:          slippery chicken (algorithmic composition)

 Purpose:          Implementation of the sndfile-palette class, which is a
                   simple palette that checks that all the sound files given
                   in a list for each id exist.  See comments in methods for
                   limitations and special features of this class.

 Author:           Michael Edwards: m@michael-edwards.org

 Creation date:    18th March 2001

 $$ Last modified: 10:35:19 Thu Feb 25 2016 GMT

 SVN ID: $Id: sndfile-palette.lsp 5891 2016-07-02 09:11:42Z medward2 $

sndfile-palette/analyse-followers [ Methods ]

[ Top ] [ sndfile-palette ] [ Methods ]

DESCRIPTION

 Using the followers slots of each sndfile in the palette, go through each
 sndfile in the palette and generate a large number of following sounds,
 i.e. emulate the max-play.  The results of the follow-on process are then
 analysed and a warning will be issued if any sndfile seems to dominate
 (defined as being present at least twice as many times as its 'fair share',
 where 'fair share' would mean an even spread for all the sound files in the
 palette).

ARGUMENTS

 - The sndfile-palette object.

OPTIONAL ARGUMENTS

 How many times to repeat the generation process.  Default = 1000.

RETURN VALUE

 T or NIL depending on whether the analysis detects an even spread or not.

SYNOPSIS

(defmethod analyse-followers ((sfp sndfile-palette) &optional (depth 1000))

sndfile-palette/auto-cue-nums [ Methods ]

[ Top ] [ sndfile-palette ] [ Methods ]

DESCRIPTION

 Set the cue-num slot of every sndfile-ext object in the palette to be an
 ascending integer starting at 2. NB If a sndfile has it's :use slot set to
 NIL it won't be given a cue number.

ARGUMENTS

 - a sndfile-palette object.

RETURN VALUE

 The cue number of the last sndfile-ext object.

SYNOPSIS

(defmethod auto-cue-nums ((sfp sndfile-palette))

sndfile-palette/find-sndfile [ Methods ]

[ Top ] [ sndfile-palette ] [ Methods ]

DESCRIPTION

 Return the full directory path and file name of a specified sound file,
 from within the directories given in the PATHS slot.

ARGUMENTS

 - A sndfile-palette object.
 - The name of a sound file from within that object. This can be a string or
   a symbol. Unless it is given as a string, it will be handled as a symbol
   and will be converted to lowercase. Inclusion of the file extension is
   optional. 

RETURN VALUE

 Returns the full directory path and file name of the specified sound file
 as a string.

EXAMPLE

(let ((msfp (make-sfp 'sfp-test 
                      '((sndfile-group-1
                         (test-sndfile-1))
                        (sndfile-group-2
                         (test-sndfile-2 test-sndfile-3 
                          (test-sndfile-4 :frequency 261.61)))
                        (sndfile-group-3
                         ((test-sndfile-5 :start 0.006 :end 0.182) 
                          test-sndfile-6)))
                      :paths
                      '("/path/to/sndfiles-dir-1"
                        "/path/to/sndfiles-dir-2"))))
 (find-sndfile msfp 'test-sndfile-4))

=> "/path/to/sndfiles-dir-2/test-sndfile-4.aiff"

SYNOPSIS

(defmethod find-sndfile ((sfp sndfile-palette) sndfile)

sndfile-palette/get-nearest-by-freq [ Functions ]

[ Top ] [ sndfile-palette ] [ Functions ]

DATE

 October 1st 2015, Edinburgh

DESCRIPTION

 Given a frequency and a list of sndfile objects, return the sndfile from
 the list whose frequency is closest to the first argument.

ARGUMENTS

 - a frequency in Hertz (number)
 - a simple list of sndfile objects, such as that contained in the data slot
  of a sndfile-palette group.

RETURN VALUE

 the nearest sndfile object

SYNOPSIS

(defun get-nearest-by-freq (freq sflist)

sndfile-palette/get-snd-with-cue-num [ Methods ]

[ Top ] [ sndfile-palette ] [ Methods ]

DESCRIPTION

 Return the (first, but generally unique) sndfile object which has the
 given cue-num slot.

ARGUMENTS

 - the sndfile-palette object.
 - the cue number (integer).

RETURN VALUE

 The sndfile/sndfile-ext object with the given cue number or NIL if it can't
 be found.

SYNOPSIS

(defmethod get-snd-with-cue-num ((sfp sndfile-palette) cue-num)

sndfile-palette/get-sndfiles [ Functions ]

[ Top ] [ sndfile-palette ] [ Functions ]

DATE

 5th September 2015, Edinburgh

DESCRIPTION

 Return a list of the full paths of sound files in the given path. Files
 without the extensions aif, wav, aiff, and snd are ignore.

ARGUMENTS

 The full path to the folder where the sound files are, as a string

OPTIONAL ARGUMENTS

 - a list of folders to skip i.e. just the last folder name, not the
   complete path
 - A single pattern (string) or list of patterns that the sound
   file name must have--just the filename, excluding path/folders and
   extension. If a list then all patterns must be in the file name, not
   just one of them. Default = NIL.
 - Sim. to :insist except this/these are patterns none of which can
   be in the file name. Default = NIL.

RETURN VALUE

 A list of full paths as strings.

EXAMPLE

(get-sndfiles "/music/hyperboles/snd/cello/samples/"
              '("short-percussive" "weird"))
-->
("/music/hyperboles/snd/cello/samples/1/g4-III-4-001.aif"
 "/music/hyperboles/snd/cello/samples/1/g4-III-4-002.aif"
 "/music/hyperboles/snd/cello/samples/1/g4-III-4-003.aif"
 "/music/hyperboles/snd/cello/samples/1/g4-III-4-004.aif"
 "/music/hyperboles/snd/cello/samples/10/cs5-I-5-9-13-4-001.aif"
 ... 

SYNOPSIS

(defun get-sndfiles (folder &optional skip insist resist)

sndfile-palette/kontakt-to-sfp [ Functions ]

[ Top ] [ sndfile-palette ] [ Functions ]

DATE

 October 2nd 2015, Edinburgh
 
 DESCRIPTION This function is only available on Mac OSX 64bit Intel machines
 and requires the nki executable which since version 1.0.6 comes with
 slippery-chicken (in the bin directory).
 
 Using the public-domain C programme "nki tool" from the Linux Sampler
 project (http://www.linuxsampler.org/nkitool/), convert a Kontakt .nki
 sampler file to a sndfile-palette object. This will only include the sound
 file and the MIDI note number it is mapped to, but it will mean that the
 sndfile objects in the palette include the correct frequency. So using such
 a sndfile-palette makes it possible to have clm-play act as a traditional
 sampler, though of course much more is possible too.

 The nki file could of course map more than one sample to any MIDI note
 (e.g. for handling different velocities). By default all of these could be
 included in the sndfile-palette, and the :snd-selector function passed to
 clm-play could select the correct file based on velocity, for
 instance. However, you may want to filter out some sound files. This is
 where the :insist and :resist keyword arguments come in handy (see below).

 NB If you get the error message "zpipe: invalid or incomplete deflate data"
 then it's probably because the nki file is in Kontakt 4.2.2 (or higher)
 format so can't be converted with this tool. You could try "save as" in
 Kontakt 3 or 4 and rerunning this function, as those older programmes will
 probably save in the older format (worked for me at least once).

ARGUMENTS

 - the path to the .nki file to process
 - the path to the samples i.e. the sound files which the nki file uses

OPTIONAL ARGUMENTS

 Keyword arguments:
 :insist
 - :insist. A single pattern (string) or list of patterns that the sound
   file name must have--just the filename, excluding path/folders and
   extension. If a list then all patterns must be in the file name, not
   just one of them. Default = NIL i.e. accept all.
 - :resist. Sim. to :insist except this/these are patterns none of which can
   be in the file name. Default = NIL.
 - :group. The group ID that will be assigned to the sound files. Default =
   NIL whereby the name of the nki file will be used.
 - :converter. The path to the nki tool executable. Default =
   /path/to/slippery-chicken/bin/nki 

RETURN VALUE

EXAMPLE

SYNOPSIS

#+(and mac-osx X86-64)
(defun kontakt-to-sfp (nki samples-path
                       &key insist resist group
                         (converter
                          (concatenate 'string
                                       cl-user::+slippery-chicken-home-dir+
                                       "bin/nki")))

sndfile-palette/make-sfp [ Functions ]

[ Top ] [ sndfile-palette ] [ Functions ]

DESCRIPTION

 Make a sndfile-palette object. This object is a simple palette which checks
 to make sure that all of the sound files in a given list exist for each
 given ID.

 Sound files are given as as single names, without the path and without the
 extension. These can be given using the optional keyword arguments <paths>
 and <extensions>.

 NB Although this class is a palette and therefore a subclass of
 recursive-assoc-list, the sound lists in this case cannot be nested beyond
 a depth of two (as in example below).  

ARGUMENTS

 - An ID for the palette.
 - A list of lists that contains IDs for the names of one or more groups of
   sound files, each paired with a list of one or more names of existing
   sound files. The sound file names themselves can be paired with keywords
   from the sndfile class, such as :start, :end, and :frequency, to define
   and describe segments of a given sound file.

OPTIONAL ARGUMENTS

 keyword arguments:
 - :paths. A list of one or more paths to where the sound files are located.
 - :extensions. A list of one or more sound file extensions for the
   specified sound files. The default initialization for this slot of the
   sndfile-palette already contains ("wav" "aiff" "aif" "snd"), so this
   argument can often be left unspecified.
 - :warn-not-found. T or NIL to indicate whether a warning should be printed
   to the Lisp listener if the specified sound file cannot be found. 
   T = print warning. Default = T.

RETURN VALUE

 Returns NIL.

EXAMPLE

(let ((msfp (make-sfp 'sfp-test 
                      '((sndfile-group-1
                         (test-sndfile-1))
                        (sndfile-group-2
                         (test-sndfile-2 test-sndfile-3 
                          (test-sndfile-4 :frequency 261.61)))
                        (sndfile-group-3
                         ((test-sndfile-5 :start 0.006 :end 0.182) 
                          test-sndfile-6)))
                      :paths '("/path/to/sound-files-dir-1/"
                               "/path/to/sound-files-dir-2/")))))

SYNOPSIS

(defun make-sfp (id sfp &key paths (extensions '("wav" "aiff" "aif" "snd"))
                          auto-freq with-followers (warn-not-found t))

sndfile-palette/make-sfp-from-folder [ Functions ]

[ Top ] [ sndfile-palette ] [ Functions ]

DATE

 5th September 2015, Edinburgh

DESCRIPTION

 Makes a sndfile-palette object from the sound files found in a specific
 folder (directory) on the file system. Allows any arbitrary levels of
 subfolders with the proviso that they'll be converted to a flat list, using
 the subfolders as tags (e.g. dir/subdir1/subdir2 becomes
 dir-subdir1-subdir2).

 The folders can contain other files (they'll be ignored). Sound files are
 those with extensions .aif .wav .aiff and .snd

ARGUMENTS

 - the folder path, as a string.

OPTIONAL ARGUMENTS

 keyword arguments:
 - :skip. a list of folders to skip i.e. just the last folder name, not the
   complete path. Default = NIL.
 - :auto-freq. whether to do automatic frequency detection on the sound
   files. Default = NIL.
 - :insist. A single pattern (string) or list of patterns that the sound
   file name must have--just the filename, excluding path/folders and
   extension. If a list then all patterns must be in the file name, not
   just one of them. Default = NIL.
 - :resist. Sim. to :insist except this/these are patterns none of which can
   be in the file name. Default = NIL.

RETURN VALUE

 a sndfile-palette object

SYNOPSIS

EXAMPLE

(make-sfp-from-folder "/music/hyperboles/snd/cello/samples/"
                              '("short-percussive" "weird"))
-->
SNDFILE-PALETTE: paths: NIL
                 extensions: (wav aiff aif snd)
                 num-snds: 92
                 with-followers: NIL
                 next: NIL
PALETTE: 
RECURSIVE-ASSOC-LIST: recurse-simple-data: T
                      num-data: 16
                      linked: T
                      full-ref: NIL
ASSOC-LIST: warn-not-found T
CIRCULAR-SCLIST: current 0
SCLIST: sclist-length: 16, bounds-alert: T, copy: T
LINKED-NAMED-OBJECT: previous: NIL, this: NIL, next: NIL
NAMED-OBJECT: id: AUTO, tag: NIL, 
data: (
LINKED-NAMED-OBJECT: previous: NIL, this: (1), next: (10)
NAMED-OBJECT: id: 1, tag: NIL, 
data: (

SNDFILE-EXT: use: T, cue-num: 2, pitch: -1, pitch-curve: -1, bandwidth: -1, 
             bandwidth-curve: -1, continuity: -1, continuity-curve: -1, 
             weight: -1, weight-curve: -1, energy: -1, energy-curve: -1, 
             harmonicity: -1, harmonicity-curve: -1, volume: -1, 
             volume-curve: -1, loop-it: NIL, bitrate: 24, srate: 96000, 
             num-frames: 1719753, bytes: 5159314, group-id: (1)
             followers: NIL

SNDFILE: path: /music/hyperboles/snd/cello/samples/1/g4-III-4-004.aif, 
         snd-duration: 17.914093, channels: 1, frequency: 150.24414
         start: 0.0, end: 17.914093, amplitude: 1.0, duration 17.914093
         will-be-used: 0, has-been-used: 0
         data-consistent: T
...
|#
(defun make-sfp-from-folder (folder &key skip auto-freq insist resist
                                      (default-group 'default-group))

sndfile-palette/make-sfp-from-groups-in-wavelab-marker-file [ Functions ]

[ Top ] [ sndfile-palette ] [ Functions ]

DESCRIPTION

 Automatically generate a sndfile-palette object using the specified sound
 file from grouping defined in the specified wavelab marker file.

 The <marker-file> argument can be passed as a list of marker files, in
 which case these will first be concatenated.

ARGUMENTS

 - A string that is the name of the marker file, including the directory
   path and extension.
 - A string that is the name of the sound file. This can either be a full
   directory path, file name, and extension, or just a base file name. If
   the latter, values for the optional arguments :paths and :extensions must
   also be specified.

OPTIONAL ARGUMENTS

 - :paths. NIL or a list of strings that are the directory paths to the
   specified sound files. If the sound file is passed with the directory
   path, this must be set to NIL. NB: The paths given here apply only to the
   sound files, not to the marker files. Default = NIL.
 - :extensions. A list of strings that are the extensions to the given sound
   files. If the sound files are passed with their extensions, this must be
   set to NIL. Default = NIL.
 - :warn-not-found. T or NIL to indicate whether to print a warning to the
   listener if the specified sound file is not found. T = print a
   warning. Default = NIL.
 - :sampling-rate. An integer that is the sampling rate of the specified
   sound file. Changing this value will alter the start-times determined for
   each sound segment. Default = 44100.
 - :print. T or NIL to indicate whether feedback about the groups found and
   created should be printed to the listener. T = print. Default = T.

RETURN VALUE

 Returns NIL.

EXAMPLE

(make-sfp-from-groups-in-wavelab-marker-file 
 "/path/to/24-7.mrk"
 "24-7"
 :paths '("/path/to/sndfile/directory/")
 :sampling-rate 44100
 :extensions '("wav"))

=>
24 markers read from /path/to/24-7.mrk
Adding tapping: 2.753 -> 4.827
Adding tapping: 5.097 -> 6.581
Adding tapping: 6.763 -> 8.538
Adding splinter: 13.878 -> 15.993
Adding tapping: 16.338 -> 18.261
Adding splinter: 19.403 -> 25.655

tapping: 4 sounds
splinter: 2 sounds

SYNOPSIS

(defun make-sfp-from-groups-in-wavelab-marker-file (marker-file sndfile 
                                                    &key
                                                    paths
                                                    extensions
                                                    warn-not-found
                                                    (sampling-rate 44100)
                                                    (print t))

sndfile-palette/make-sfp-from-wavelab-marker-file [ Functions ]

[ Top ] [ sndfile-palette ] [ Functions ]

DESCRIPTION

 Automatically create a sndfile-palette object from the specified wavelab
 marker file and the specified sound file (from which the marker file must
 have been generated).

 The function will produce a sndfile-palette object with multiple groups,
 each of which consists of the number of sound file segments specified using
 the :snds-per-group argument (defaults to 8). By default the segments will
 be collected into the groups in chronological order. If the optional
 :random-every argument is given a value, every nth group will consist of
 random segments instead.

 The sound file segments of each group will correspond to the time points
 stored in the marker file. 

 The <marker-file> argument can consist of a list of marker files, in which
 case these would first be concatenated. 

 NB: Be aware that marker files created on operating systems differing from
     the one on which this function is called might trigger errors due to
     newline character mismatches.

ARGUMENTS

 - A string that is the name of the marker file, including the directory
   path and extension.
 - A string that is the name of the sound file. This can either be a full
   directory path, file name, and extension, or just a base file name. If
   the latter, values for the optional arguments :paths and :extensions must
   also be specified.

OPTIONAL ARGUMENTS

 keyword arguments:
 - :snds-per-group. An integer that is the number of sound file segments to
   include in each group. Default = 8.
 - :random-every. An integer to indicate that every nth group is to consist
   of random (rather than chronologically consecutive) sound file segments.
   Default = 999999 (i.e. essentially never) 
 - :paths. NIL or a list of strings that are the directory paths to the
   specified sound files. If the sound file is passed with the directory
   path, this must be set to NIL. NB: The paths given here apply only to the
   sound files, not to the marker files. Default = NIL.
 - :sampling-rate. An integer that is the sampling rate of the specified
   sound file. Changing this value will alter the start-times determined for
   each sound segment. Default = 44100.
 - :extensions. A list of strings that are the extensions to the given sound
   files. If the sound files are passed with their extensions, this must be
   set to NIL. Default = NIL.
 - :warn-not-found. T or NIL to indicate whether to print a warning to the
   listener if the specified sound file is not found. T = print a
   warning. Default = NIL.
 - :name. The name for the overall sndfile-palette and the base name for
    each group within (these will have a suffix that is an auto-incrementing
    number e.g. 'auto would become 'auto1 'auto2 etc.).  Default = 'auto.

RETURN VALUE

 A sndfile-palette object.

EXAMPLE

(make-sfp-from-wavelab-marker-file 
  "/path/to/24-7.mrk"
 "24-7"
 :snds-per-group 2
 :random-every 3
 :paths '("/path/to/sound-file/directory/")
 :sampling-rate 44100
 :extensions '("wav"))

=>
SNDFILE-PALETTE: paths: (/Volumes/JIMMY/SlipperyChicken/sc/test-suite/)
                 extensions: (wav)
PALETTE: 
RECURSIVE-ASSOC-LIST: recurse-simple-data: T
                      num-data: 8
                      linked: NIL
                      full-ref: NIL
ASSOC-LIST: warn-not-found NIL
CIRCULAR-SCLIST: current 0
SCLIST: sclist-length: 8, bounds-alert: T, copy: T
LINKED-NAMED-OBJECT: previous: NIL, this: NIL, next: NIL
NAMED-OBJECT: id: AUTO, tag: NIL, 
data: (
NAMED-OBJECT: id: "auto1", tag: NIL, 
data: (

SNDFILE: path: /Volumes/JIMMY/SlipperyChicken/sc/test-suite/24-7.wav, 
         snd-duration: 29.652811, channels: 2, frequency: 261.62555
         start: 0.09142857, end: 1.0361905, amplitude: 1.0, duration 0.94476193
         will-be-used: 0, has-been-used: 0
         data-consistent: T
LINKED-NAMED-OBJECT: previous: NIL, this: NIL, next: NIL
NAMED-OBJECT: id: "24-7", tag: NIL, 
data: /Volumes/JIMMY/SlipperyChicken/sc/test-suite/24-7.wav
[...]

SYNOPSIS

(defun make-sfp-from-wavelab-marker-file (marker-file sndfile 
                                          &key
                                          (snds-per-group 8)
                                          (random-every 999999) ;; i.e. never
                                          paths
                                          (sampling-rate 44100)
                                          extensions
                                          ;; MDE Fri Oct  5 14:04:08 2012 
                                          (name 'auto)
                                          warn-not-found)

sndfile-palette/max-play [ Methods ]

[ Top ] [ sndfile-palette ] [ Methods ]

DESCRIPTION

 This generates the data necessary to play the next sound in the current
 sound's followers list.  See the sndfile-ext method for details.

ARGUMENTS

 - The sndfile-palette object.
 - The fade (in/out) duration in seconds.
 - The maximum loop duration in seconds.
 - The time to trigger the next file, as a percentage of the current
   sndfile-ext's duration.

OPTIONAL ARGUMENTS

 - whether to print data to the listener as it is generated. Default = NIL.

RETURN VALUE

 A list of values returned by the sndfile-ext method.

SYNOPSIS

(defmethod max-play ((sfp sndfile-palette) fade-dur max-loop start-next
                     &optional print)

sndfile-palette/osc-send-cue-nums [ Methods ]

[ Top ] [ sndfile-palette ] [ Methods ]

DESCRIPTION

 Send via OSC the cue number of each sound file in a form that a Max sflist~
 can process and store.

ARGUMENTS

 - the sndfile-palette object.

RETURN VALUE

 The number of cue numbers sent.  NB This is not the same as the last cue
 number as cues start from 2.

SYNOPSIS

#+(and darwin sbcl)
(defmethod osc-send-cue-nums ((sfp sndfile-palette))

sndfile-palette/reset [ Methods ]

[ Top ] [ sndfile-palette ] [ Methods ]

DESCRIPTION

 Reset the followers' slot circular list to the beginning or to <where>

ARGUMENTS

 - the sndfile-palette object.

OPTIONAL ARGUMENTS

 - an integer to set the point at which to restart.  This can be higher than
   the number of followers as it will wrap.  Default = nil (which equates to
   0 lower down in the class hierarchy).
 - whether to issue a warning if <where> is greater than the number of
   followers (i.e. that wrapping will occur).  Default = T.

RETURN VALUE

 T

SYNOPSIS

(defmethod reset ((sfp sndfile-palette) &optional where (warn t))

sndfile-palette/set-frequency-from-filename [ Methods ]

[ Top ] [ sndfile-palette ] [ Methods ]

DATE

 October 1st 2015, Edinburgh

DESCRIPTION

 Set the frequency slot of every sound file object in the palate to a value
 extracted from the file name. This is intended but of course not restricted
 to palettes created from sample libraries, where, as is often the case, the
 file name of each sample contains the pitch of the file. For example, from
 the Akoustik Piano sample library we have the file
 Stein-R(A1)-V(220)-dB(2446)-T(MF)-M(123)-P(404-03-01).wav. In this case the
 A1 in the first parentheses indicate the pitch. By writing and passing a
 short parsing function to read the pitch out of such a file name we can
 easily process each sound file in the palette. See akoustik-piano-name
 below for an example of how to process such file names.

 See also make-sfp-from-folder.

ARGUMENTS

 - The sound file palette object

OPTIONAL ARGUMENTS

 Keyword arguments:
 - A single group or list of groups (IDs) for the sound files we wish to
   process.
 - The functionFor processing a single name. Of course the names must be
   consistent and each sound file must be able to be processed by this
   single function. NB for reasons of similar usage in get-spectra-al (see
   spectra.lsp) this function actually must return the MIDI note number (may
   be a floating point for microtonal applications), which is then converted
   by the sndfile class to a frequency in Hertz.
 - The function to be called when the name function cannot determine the
   frequency of the sound file. This could be #'error (the default), #'warn,
   or nil if nothing is to be done on failure.

RETURN VALUE

 The sndfile-palette object after processing.

SYNOPSIS

(defmethod set-frequency-from-filename
    ((sfp sndfile-palette)
     &key groups (name-fun #'akoustik-piano-name) (on-error #'error))