Comments (3)
Ok, I added prest
in commit b4fba7e. It turns out adding it was easier than I was thinking it'd have to be. It should work as intended now but let me know if you come across any issues with it.
from cl-patterns.
I haven't gotten to look into it since the last time I tried implementing prest
but I think the clock changes I made in the process of implementing play-quant
/end-quant
should make it easier to implement prest
"the right way" (or at least, the way that feels right to me). Still probably need to do some restructuring of the way multichannel expansion works, though. In the meantime, I think something like this could work as a stopgap solution to embed rests in arbitrary pattern slots:
(pb :test
:instrument :default
:degree (pseq '((0 2) (1 3) (:rest 4) (3 :rest) 0 :rest 2 :rest) 1)
:embed (pf (let* ((key :degree)
(val (e key)))
(typecase val
(symbol (event :type :rest key 1))
(number (event :type :note))
(list (event :type (mapcar (lambda (i) (if (symbolp i) :rest :note)) val)
key (mapcar (lambda (i) (if (symbolp i) 1 i)) val))))))
:dur 1)
The :embed
pattern parses the :degree
and changes the event to a rest type if it detects a symbol. This should be usable for most keys, you just have to put it after the key you want to embed rests in, and then change the (key :degree)
so it refers to the name of the key in question. There are definitely some caveats to doing this, though (like how you can't do (prest 3)
to specify the numeric value the rest is replaced with) and it might not work for everything. But once prest
is actually implemented there shouldn't be as many of those sorts of caveats (ideally none).
from cl-patterns.
Oh, I missed the second line of your post when I read it initially, somehow. If you want to try adding it yourself, you're certainly welcome to give it a look! The way I attempted to add it before was by changing the raw-set-event-value
function defined in event.lisp. This is what I tried changing it to:
(defun raw-set-event-value (event key value)
"Set the value of KEY to VALUE in EVENT without running any conversion functions."
(with-slots (event-plist) event
(flet ((handle-prest (item)
(if (typep item 'prest)
(progn
(setf event-plist (plist-set event-plist :type :rest))
(slot-value item 'value))
item)))
(let ((value (if (listp value)
(mapcar #'handle-prest value)
(handle-prest value))))
(setf event-plist (plist-set event-plist (make-keyword key) value))))))
I defined the prest
class in patterns.lisp underneath
(defmethod as-pstream ((item pbind-pstream))
item)
like so:
;;; prest
(defclass prest ()
((value :initarg :value :initform 1)))
(defun prest (&optional (value 1))
"Make a prest object, which, when used in a `pbind' or similar event pattern, turns the current event into a rest and yields VALUE for the key's value.
Note that this is not a pattern; it is just a regular function that returns an object.
Example:
;; (next-upto-n (pbind :degree (pseq (list 0 1 (prest 2) 3) 1)))
;; ;=> ((EVENT :DEGREE 0) (EVENT :DEGREE 1) (EVENT :TYPE :REST :DEGREE 2) (EVENT :DEGREE 3))
See also: `pbind', `pbind''s :type key"
(make-instance 'prest :value value))
(defmethod rest-p ((prest prest))
t)
But there is definitely more restructuring that would be needed than just those two things. In particular the multichannel expansion; it will likely need to be moved either into pbind's next
method or better yet an :around next
method for pattern
or the like (so it applies to all patterns automatically without needing to be manually implemented for each, ideally)... At least, I think. Right now it's done in the clock-process
method with the code (split-event-by-lists (event-with-raw-timing event task))
.
The code should be able to pass these tests if prest
is implemented properly:
(test prest
"Test `prest'"
(is (equal (list nil t nil)
(mapcar #'rest-p (next-upto-n
(pbind :dur (pseq (list 1 (prest 2) 1) 1)
:dur (p+ (pk :dur) 1)))))
"prest does not work properly as a :dur value")
(is (equal (list 2 3 2)
(mapcar #'dur (next-upto-n
(pbind :dur (pseq (list 1 (prest 2) 1) 1)
:dur (p+ (pk :dur) 1)))))
"prest's value is not used as the value of the key it is used in")
(is (equal (list nil t nil)
(mapcar #'rest-p (next (pbind :freq (list 1 (prest 2) 1)
:freq (p+ (pk :freq) 1)))))
"prest does not work properly with multichannel expansion")
(is-true (rest-p (prest))
"`rest-p' is not true for prest"))
Good luck if you do decide to give it a try, and let me know if you have any questions. :) Otherwise I will probably get time to implement it soon.
from cl-patterns.
Related Issues (20)
- About *alsa-midi-instrument-map* HOT 3
- Error "There is no class named COMMON-LISP-USER::PBIND-PSTREAM." HOT 2
- Set default quant to 1
- pnary doesn't work with prest HOT 1
- stretch doesn't work HOT 2
- The lock in ipstream-stream is made a non-recursive, but is used as recursive
- Changing arguments interactively HOT 12
- Add 12-tone matrix generator HOT 16
- :tempo key HOT 1
- Plazy fails with repeats=1 HOT 1
- Some systems failed to build for Quicklisp dist HOT 1
- Some systems failed to build for Quicklisp dist HOT 2
- Instantaneous tempo changes HOT 3
- Saving output to file HOT 2
- Using print representation of symbols HOT 5
- Can't change tempo of running clock loop HOT 2
- None of the examples in the supercollider example work for me HOT 4
- Some systems failed to build for Quicklisp dist
- Can't build without xrandr HOT 3
- Some systems failed to build for Quicklisp dist HOT 4
Recommend Projects
-
React
A declarative, efficient, and flexible JavaScript library for building user interfaces.
-
Vue.js
🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.
-
Typescript
TypeScript is a superset of JavaScript that compiles to clean JavaScript output.
-
TensorFlow
An Open Source Machine Learning Framework for Everyone
-
Django
The Web framework for perfectionists with deadlines.
-
Laravel
A PHP framework for web artisans
-
D3
Bring data to life with SVG, Canvas and HTML. 📊📈🎉
-
Recommend Topics
-
javascript
JavaScript (JS) is a lightweight interpreted programming language with first-class functions.
-
web
Some thing interesting about web. New door for the world.
-
server
A server is a program made to process requests and deliver data to clients.
-
Machine learning
Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.
-
Visualization
Some thing interesting about visualization, use data art
-
Game
Some thing interesting about game, make everyone happy.
Recommend Org
-
Facebook
We are working to build community through open source technology. NB: members must have two-factor auth.
-
Microsoft
Open source projects and samples from Microsoft.
-
Google
Google ❤️ Open Source for everyone.
-
Alibaba
Alibaba Open Source for everyone
-
D3
Data-Driven Documents codes.
-
Tencent
China tencent open source team.
from cl-patterns.