getpath of a clip only with deferlow?
Clicking on a MIDI Clip [live.path] sends out an id which goes to [live.object] to get the path of the Clip. I don’t understand why it works only with [deferlow] right after [live.path]. Can anyone explain this?
I attached the device…
Quote from the docs (Live API Overview):
Note: changes to a Live Set and its contents are not possible from a notification. The error message in the Max Window is ‘Changes cannot be triggered by notifications’. In many cases putting a deferlow between the notification outlet and the actual change helps to resolve the issue.
Thanks, I know this quote. I should probably reframe my question: why is implemented this way?
I’d guess it’s for prevention of feedback loops.
(not sure if the developers want to discuss implementation details)
yeah maybe. But then I wonder why it’s not set to low priority in the first place? Oh, it seems to behave differently depending on where the live.object points at. It works with getting the path of a track f.e.
I think the whole deferlow thing is unclear – for me it’s a bit like if it doesn’t work, stick a couple of deferlows in.. If we understood why they are required, the mechanics behind it, it would be easier to program efficiently. Apologies if it actually is explained somewhere, I searched but couldn’t find it.
Here is an article that explains some relevant aspects of the Max execution model.
Thanks, I know this article as well. =)
I think I just considered getting the path of a MIDI Clip by clicking on it so basic that I didn’t expect it to be necessary to use any tricks. M4L ain’t easy to tame…
Here’s my understanding of deferlow – can you tell me if this is correct?
Everything below (and connected to) the deferlow object is executed with the lowest priority – effectively allowing other events to finish first, before the events below deferlow object.
in the case of M4L objects, what is that ‘thing’ or those events that need to finish first? what is that M4L object dependent on that requires it to be below a deferlow?
apologies if I completely misunderstood something!
[deferlow] puts the message it receives at the end of the low priority thread (there is high priority and low priority) unlike [defer] which puts it at the front of the low priority thing (This of course also affects the objects downstream of [deferlow] but they are not "deferlowed" per se). So [deferlow] is the strongest slow-down you can do.
In this case it’s the sending out the id of the MIDI Clip I clicked on that is put to the very end of the queue. Why it has to do this to give back the path of a Clip but f.e. not of the track this Clip is on I don’t understand.
I’d think that if I can deferlow it than it could also be built into the object so it "just works".
the thing about max is, whilst most of it is easy to learn and use, it wants to give you so much flexibility, individuality and level of control like no other app, that sometimes you run into these sort of issues (the perennial "scheduler" issue) that you wish "it just took care of it for me", but it cannot be that way, as then you would not have all that amazing control and uniqueness.
however, i do not think that this issue is particularly complex at all, and once you have been patching with max a while it starts to make more and more sense and becomes natural to take into account. even though the helpfiles explain it very well, here is my potentially nightmare explanation, i hope it helps a bit:
----------begin_max5_patcher---------- 4627.3oc2cstiiiak92U+Tvw6O5Y.pRgWDkDGjDfdw1AH.SlDjq6ht6sgJKV 1ZZYICI4p5JW1euOC4wKOIgTjRVpKeQVhh1sGzScQVkH0224b34b3gj+sWcy r6y9LuXF36AuCbyM+sWcyMUWRdgaz+9MyVE944IgEU21r4YqVwSKmcq5yJ4e tr55n5q7PVZ4Cgy4xqhZcsh3+p5ZPGn9xoaVEmlvKKZeuqy4EhFHrLNK8i47 4kpdGiF3vBXL1s.u.wS..0eA7g5FIew8p6E09yuU9qM2jnIy1TV2l0cj0gky WFmt3KZOWrKKHPzfT4iASpdXAsaRw6UZ3pp2qYuIONLoFEhiptV18+zcHWu1 n07rjr782Ok23+3UuR9kauvoDDhfcHdBNgJvHlEHEQKBajBFIoPOOjxxIlTB 78kcapO1FJIPrCymwBZZvgyG3yCePlZkDHqRy.Q8sgBRSqMRsCz4gMvStIKJ owjEh5ZEaVcZxQxKvqSdgQQJwVOqLzNzXDBgcsNLBxdVsjMFk3x7IFfPBlVB Ik+jncpaCwKhhOlmDO+S2U80WvUqABVbs3iBK4Q28CwOxeyu6We257r47hh6 dJtb4cIYgQE2k8vcyCSRJpeBIwo74YaTMg6tHW7tIWxNY.r9ppKU97ZtBYlM 6Vw+2fyGwYXWuJQBDF5PQhg9kthgOcZpw8qplimqgbMlKdLwI7G44EBwxVhq 2LKb85VW9lV+IRh5mTrs2sMWJNUcIXykx4OF27XUWTP+up9CqemwJQPZ03ot 9D02719lJjTVjjM+S7n1O+YYq4owosUq57wQ7GB2jT9wcSic+7Z85c9g6Diu Y1h73nrTYmnyeo7x0MmPWfpTta+xTcGogq2webg38XSw8g4Rf69DdKgIgXdV VR2OpgqDZRgowqDh8kwpNKF17PiWsNWq8zbMdZn3YrrXddVRRmGk5SdbGeRj fNmyeJNpbY0ypMTJt8300TvrFLJJdAunr60JCWTz8JcBMtsbVaSDct9Asc20 lPT6qtCa3GvN9dskeXGe7cjNGFHFyi3A2kQ8daXe+F22qOPtUZQDW2caa+vF NdgwC7WBo8vL+M0l5056S.mN+bxonyDmhYlgSQWlb58VmSoMbJV4JzYfSILi vovKSN02xbpGZKkF3YYJU3aVSi64YBZkcYxpTKypBGCqAVjav4iUQtTSvpAW lrpqss+x1NlJFirs82W15ikW8Oe7ZmPk6Rqwy1G8g2O8g2Kr1lXeQzsUAY7g i.70YutZfOUVnvvgh4tyLHJpdelMBYZhmRFh4uWw4SRJknFGgn87iV+0NOwV vAocmuVYuJTKCBSUHxdQIXOPIk2VtjdBRGTl6nBbDZPcVT5EFh+p.CwvJICW rIvv9n2hgrSBFQWVv3IfF2Glt3nvAkbZnAwJplmfErSxNj5ss2lgPDWa71dH uYpRyKH6AfNIvfhxMO7.XIOmCd2lBN34rM4f3UgKhSqzs9P6GSmzAi2ieQj8 LvJVfRPpOJv3zfRZSD2JlAIXjLWDUNVzNqvm13md1hO7lJuKmdu9YTyDhtAh QeaNjkRn6IkoUuNxOe2TVgPvedssNskZP2WpHdQoVsn08IzoAnN22x3nntIv Vky2BYFjU4p+fuDQ707TwSX9yebd37k5Nk9MudlBlUD9HO5ihdffc9XXYYd7 8aJUu7smFiEIY2GlnmiiFJoIGy6LK+CapA1QNs6wzEbfO5XyTwKyX9KR39q1 BxiZZ11l1b9C77jrmlcBSF1QmoysysEEtSu+183zGvqucNGZXbyjbR8vphzw AgXUUyDFd5SgVSs.zRkENsS67+KHtD7TbRB3M+ve4M+O+Avxv0BsEPXInbIG 71e7+RN5Vn3yk+ZYXwmJ.woheIt.nmvycN4l3cLa1XywwBTVgzBKmt6NYMmR AcvbBBTzlqquJTQISBgP4netmLSh8mM.NJQ3CgSkE0gH0CCbjCi36P7QdHTu Aj6yxiTyVKw4PSoOUEPsHTQIlqJYyVNm088mLyblHJRhi3+eyFvrku2J3Rnm pqxMjOU99LTCDEwKREh.GxLAB52p0pPu.AtggP7frRfLI1FKD3QmBzhOldIt x4cFdLlcaGn3tUXQMUMJSEyfuiOgUgwCARcMHjVBhAwCY3rdVaGRv41SCiPj JeKkZvnJSZCAinCAiDtPUJ7cXPV3URRdtiQRpSP1GClzEfL7KyUXWbv6hvzl 4rOEHrIYRyS3KAySFxPCSk7PiXiAM6xvqYS35aaYFsskQ44KZB87sGlfLkwD s3Ruri.YV1dJDRc77DblLbELcZspBIPGLzkQ8jtTiNNdvflV8vfQT1A6bCfS VHkcwMUrqj.Ge5PM6vPSmh0JQregK3ubPskwhXECiLnak5fObccmLnWZRqIZ dFbqd7oWxxLrcUsYDhS.S3XGc50raW3vTLqGJ1lLbku4NfmAEqXdLG+.gmNx .+QnoLjEFy0gfnUdUQ7qZEAqgbGrh8fbGW7xbuQsL1AA6k14whq43RfsPxZS jrWHA1OPzaaMqmKt4Rd9GU0kbSRkMULg0FEA2KfZv8lLcmrpTwP1yB6nK56t 2.EZLZqofaOAFoUhPID8725UMf4.Et8sqAzZHDilVamswIkj6QrcFLyfo5MX pWxWPEJ5SswR9hzBKUh9CcEFwNSq3K5TyGtDKxGd9lhOPvyzZU0cpIDelCCK LJJih.akkWOD55354x77jARDLNZ4JcAc2lVrixRWZYrZKjyCsDN4qydDwgJb PVMOtPqvKhfsgABdAI0PIiiWbuRWw8s4EaouzhWFs9B85byaggNnSrFd3d2W 5J6fIjId2zYD4LM.0TX.DexzlxTFpIhIWbvwCNvmbIjwTij0yVu5jfwmzSOx WWI8zDXHQo7qpdkgl3ROzrK6IXoSk5zGkDJ6JZV2Z+1q0SF0ztQ8mN8DCm.W SU3HTpiuuFAQtiNKrThcyBqgSkZG3PY5XnoRkh+ZJUpVHonApEwfZmYXboCk Bm8UzFMDQUNltParoN5RTRsT3XbA8bsIbsvNTAgAsHUPF01F34Zep6AKQEVY WbrlJPtihJNS46iaIpvJaVfZp.y7FEUblxwWjknBhmEoB+QkFb2yTZ8laIp. Ywgs0dGMXp3LkIu6sDU.s3v1X2wMrs204jPnoBbfEG1FiG2v19mGpvXkWfYA U8XKiLBgy0tBq+kMnNNe8m5c108ApdW1f537Zm3+Ud0rLIf5H8+l38UdEoLM f537jlP+JudRlFPcb9DStRq5fZ+SY1ndCpohw4SLg7UdgFLMf537tkfO6EKf olLS8LDnwiCNMlD30xb8ST5TT89G8XlleL05Se44dFfqQO13m72IbggsNLku sIWjlIdApNGE5hF8OHbUbwtPzIrOercas.cnHtgsBNTEMSGaRsArFGqyy1jF o13gvWNvith.lB3QALGAdBtvgGO5TAO5BI3vvC6BGdb8mH3QG50ggGL7BGd1 S45a.3wOnGvC5BGdPSkoYc3PGAdvW1vClMUll0gnbD3gbgCO9SkoYsy0GAdb O2vyHdQIX+96Ai2UvKZu7EgdE7h1KuJtBDc6k+AHxUvKZeFoGguBdQ6yX1nK UWZvpieCBFZ5Akpgm9LlMBdEHGzmQeMUbQ6sZxRij6foIYOAVmGmkGW9LnbY tr9g+kfeoI2jfb8ZJlZ5dJno9uh27gaeXLctRwCqzrCbMY4C+PtnMMLhNLXQ kBwgCKDSBK+bvOWfHYeRtw4tjmrVdZWBBExd4xTFxSmyAqCWvA2o2KciK.h+ w+75jv3Tdjb20Mm633XPARhuqJUq3wIKRXa2qc0xh5bMMfklUv0Bn2e3KPHy 5Ussa1j06ghd9lD8dZIWB.fWm8HOOJO9Q9qkvSVJHKGjlUBVE9IdAHDrbi.C ihenFSKyp1LnkGuAB6.uqJo3evArL6I4A75sx8GZQG3grb4FZ7W93eH9yBjO L4ovmks0sxGw7rM4EbmctQRSlTtQoanOAbwJdw8zW2bTSxK..3w2mJOfUeep 5mkeczGgvmN33yZ4MG8EGAD8Ca7M5hW4iRv3u+Ee4N0+o2cxExcUhmEyWxi1 jHDvExqQYs+a9X7NQyfoDMo0qRZ0lCoJehxC7ySs79XlDOq272yRSdFrlmK. uURzqndudWXjHE75h0gyUpugOFFmTsrt1EBRM3nWrp8yb+Q5HkdacSeNXpNr F8omrPLdJ.csQvcB6wkK25ckzBZkLcVkA6hxvsGJ4cveOyg+xiAVZO2HuOjQ DHtZaoWI1GTQFArSF+QlD+6345pvpiyf7Vqc6idPFPLnXNpBezAcNd4b0AAt h0N8Ct.rQcOaY7hk1GnOYQS0zJqVibC.xLpOY+GfewuP3fJe9FobBPEr8zVY U5iXr8bPoX1Z.hFzr.1kgxIQegeE0Qzc5UCTvYpDBC+xy9jI5XNwEoLdNRiv sfcLzcqg3ADAhQGHzahEsCzUbFzJ6HNFnjXCNSq90odMgiv5AjrwxnAo7s1c baKQAvqycERj9THFaQpXjZE9rqy8CRDUiNVgJ7na2kCG251wO35bifD4oUMn VlOFq9g+U5N.odlgcsxd+Hi4PoPHjL5gN78tR24G0GQo1YniV7wX0OtV2wGq xZMxyyJaAmtFX0a36dthWaQdVQQhJUZEwqVmD+PrbdHRi.xzTH9j3zzv4y2j GVxA47RdRh.AjyNgLwaOsLKgKmAIwkBuW.Y0S6Q0S3c0qKfOLpLaH7LCSXdP pYlqTO8o3b84AIUEhB8jy9YvDdZVNtyjRnuJGBaeGUKOBeGObfKJXWEbPfQS f9+5++e1as7gdTmp7O7jpgzct6A194PgCKA.hH4LI78eOwfmuZHKenSfTBgL F.TeHDMV7ynox9aiAeJM6oaAyyC+qOeK39MxiexkgOxAE773rMRadEbdJf+4 PgUOdgxhVb0o36ZdV0kTml0Ee2QsdM1SKFMpgHFfNX5.YQsWqlC4r50nSPoi iySbEATMIjxgZD+Xd7hE7bf5zEWOEkgkeeuGtvj1Sfz5wvCNsSJ3c5V.E4DP UGg8h3lpehn58i1S+n.znlm+we62.tC7iu8O+1eOHJSI3em7HuV78hxMqiUt .HvoBtPSnXZYj9apQuHvaAnT3PATiNmNbmENBDrZZgKyj0.x2OaZmgr.s3Z. bbi+Ue.Vqhk.MzZvAgcMaILUjH7+rTXldS57DdXtBaqmiX0wwtxvtzfhvdRV dYXZo1YTogb8sVUxNBYX0jGKu4tS.W0LKOoGV68lKvDXSIkUuieql.ygX.2y jDhdC9VM0awoKlY6okjIbVo97MSOs4HuA6sAyrBqRopeP3X+a9c+Zv2JGFS6 Vw2IEDE+Yhe7y2BBqDJWJ91pvzmAuddXRRwqqrzV8y2GN+SheONUWIYpnq9M ge9mIe1fhmKJ4qjWsfKa.wHlkwqjR6+rFZALOLUJvqqgh602nPMZwlvbg9Am GczRlZBrVIFPrhxb8cGo65xiM95QVqKPMksqSuHrPtFtXWe+rrk2JGQUvyEY qpqLEYQqcqvAznrzWWJnnbdk0r2OC7tmy1HHqUYEk5gieRYDKr7a.earC2AH kLphudar0JadhP1eVvvKRS0Qj2L8qe2GNZMCZE6YHnGywUcJhWm7v.1vJlPD AaVtR3nu.7yEn+B4.AKWI+UPJup.XEP76a1mqE7zu4O8G9i5Ac.u4W8GE7jp zYE2mTmW3yzCO.91eZifFabpsVkrYTn4xnPJ+tKCtgoNVJ0moqxBsoQqZ.bi Qq1iiwLRgegYlMIUEb+6jad9enCC8e91e0u82+1cQQspD+IA92q4OhBsIrQ5 slH5NW0ILt9LFBolM+APZtc7Xq5OtBTJTMUMGV0KpRXUGlrPvPyq2cNpO0PA a6CQ7hx3zJfn0Mgj6tU.TycsLNJhm19kNJtPVGkQ6e+wu2cH+NM0g5PPqzg9 x1Z28HFwhcHXe5PX6RYGWFBZODBQ6iPjbcXBvVrGA6UOBYodjau5QVTQC0Ka QeQ+dR6QPVu5QHKhQvd0ivVTNB0qdjM09Q8Firi1OqWif3YMDpxfM9X8G6o4 yB5C93aW7gbr9i8z5Y8QflYOMLORO5O91yiHJrG7km85O8xAMJzt3ywz2oVl uNl6YTe61eNFe4gr1Xpz93PMkYO7oO56xCMsA0e.e3U+iW8uAMc6B3C -----------end_max5_patcher-----------
by the way
"I’d think that if I can deferlow it than it could also be built into the object so it "just works"."
… usually, the reason one thing has to be deferlow-ed when another does not and you are not expecting it, is simply to do with bad patching practices and not following your execution orders exactly correctly. the problem with deferlow is that it ‘makes stuff work’ so it gets way overused, whereas ones use of it should not be frivilous but very exacting. if you need 10 in a simple patch then something is usually very wrong with the patch, not the execution / thread calling of Live/Max.
Wow nice patch – you must have a lot of time!
Did you have a look at my attached .amxd? Why does it need deferlow in this specific case? I can’t see any bad patching practice in it.
Pid – I completely agree, I’d want my patches to be defer low-free if possible. I build all my abstractions to Max object conventions like get triggered by the left-most input, and try to build my patches so that they execute in the right order just by design (left-to-right arrangement of objects etc), and use a lot of triggers to add control of execution order.
Which makes it so much more interesting to understand why m4l needs deferlows to operate! And not knowing why/when to use them and when not means you end up using many more than required, because at the end of the day you want it to work….
I’ll look at your patch when I get home, I hope it will clear things up for me!
regarding your track example: Do you get the same error/warning message as with the clip?
(right-click on the device title bar and select ‘Open Max window’).
I think your second example shows normal behavior because the path calculation is simple and thus can easily be performed in real time (high priority). In contrast, the path calculation of ‘detail_clip’ is much more complicated since the clip may reside anywhere in the set depending on user interaction (selection).
ok, broc is the expert, listen to her/him. however, i’ll add…
no, sorry, i did not look at your .amxd originally – i was just answering to the ‘deferlow’ issues. however, i have looked at your example device now and the answer is very simple and is a tricky part of the API that has always been there (and documented), namely: you cannot trigger processes based on observed notifications from the API.
this is one of the API ‘rules’. it is for this very reason that use of the [deferlow] object was envisioned, and its use here is perfect and correct and exactly as you had it. there was possibly confusion because [live.path] is not strictly an ‘observer’ object but, give it the argument you gave it to track straight to "detail_clip" and it becomes one.
therefore we ascertain that SOME parts of the API are slow, in terms of callbacks. as broc said, "the path calculation of ‘detailed_clip’ is much more complicated as the clip may reside anywhere in the set depending on user interaction".
i attach a .amxd device based on yours demonstrating this, although i am sure you get it… disclaimer: i am no API expert – i delve into it now and then.
Pid, thanks for the valuable comment. Apparently I’m not the only expert here if at all…
easy vs. complicated path calculation: OK, if this is what it is I can live with that. Is anywhere documented which calls are what?
so sending an id is an "observed notification from the API" and doesn’t work, but deferring the same to the end of the low priority thread works. uh…
I just tried one more thing which really baffles me: even when I [zl reg] the id for a second before passing it on to [live.object] it won’t work. So it’s somehow not about the time but the thread it is attached to. or so…
easy vs. complicated path calculation: OK, if this is what it is I can live with that. Is anywhere documented which calls are what?
No, unfortunately. But I’m not sure if a strict classification would be possible.
"So it’s somehow not about the time but the thread it is attached to. or so…"
- well done, you got it! as i demonstrated in my initial crazy patch-description of [defer] and [deferlow], with [defer] (or [delay], or [pipe], or [s]/[r] etc) it is not possible to pinpoint the exact execution order, but with [deferlow] it is. this is why it works to [deferlow] on an ‘observer notification’ from the live api because it is saying ‘do everything you need to do, when you have done that, let me know and i will execute’. it is nothing to do with ‘id’s in general – you can happily trigger as many as you want so long as not directly from a notification. with the tricky business of ‘you cannot start another process based on a live api observer,’ think of it like a digital audio feedback loop – it cannot be done like in the analog domain – you need a sample of delay (in gen~!) or a vector of delay (in msp).
re: "easy vs. complicated path calculation" – sort of; it is more about ‘possible to predict time scale of callback’ and ‘NOT possible to predict…’; but in general, yes. "No, unfortunately. But I’m not sure if a strict classification would be possible" – exactly. it is not about a ‘list’ of objects or api calls that always need [deferlow], it is more about realising general situations in which these things are needed. so no list. however, i do agree that the documentation on this could be better. e.g. there should be a discussion-chapter somewhere in the docs about ‘strategies for programming with the live api and fitting everything else in and around it’. or a snappier title of course. preferably not written by such a hacky douchebag as myself that does not really know what the hell he is talking about.
api calls in both live and max (and most other media software on the planet) happen in a slower, deferred, not as high priority and to some degree unpredictable thread, because the important stuff – audio (and video, but that is different again) – must never get interrupted or glitch. in fact live and max are two of the most amazing and robust softwares in this regard and it is one of the things that makes them special. letting ‘us’ in there, right in the guts of the software, to mess around and hack and create our own things, is very tricky and sometimes difficult. but that is what max is. i am constantly amazed that max even works at all with me abusing it all the time.
and yes, obviously, i had a pretty slow day today (!!), but i just got an email with some c++ stuff in it so i’ll be locked away this weekend doing that as i really suck at it.
p.s. broc is still the man! i learn loads from him!
Seriously helpful thread! I finally understand the language they’re using in the manuals.
the below may be obvious? let me know…
I think you can interpret the message "live.object: Setting the Id cannot be triggered by notifications" as follows:
1) because you clicked a different clip in Live, the live.path object had to send out a new path ID. this is a notification
2) the notification (the new path ID) was going to set the ID for the live.object BUT.. "Setting the Id cannot be triggered by notifications"
But not everything you do (even some possibly complicated stuff) is triggered by a ‘notification’ from live: eg if you trigger the path directly by clicking a message box with the path name. Maybe the attached device illustrates it. I changed from ‘getpath’ to ‘get name’ because it illustrates my point a bit better. It definitely means I can get rid of a lot of deferlows in my patches.
I think I learned more in 3 months on this forum than I have in the year before :-)
Awesome. I just was able to cut out 32 deferlows (see clipping) : not understanding when they were required, I had a deferlow after every live.path that was feeding an id into a live.object. Now I know when I need them and when I don’t!
----------begin_max5_patcher---------- 1727.3oc6blzbaaCE.9r7uBTc1ICdXgK4VmoyzlCc5kdqIiGJQDa1RQpRR4X 2L4+dI.WhrsjEn7ivhZ7AKaPRa7vGdq.f9aWLa9h76TkyIef7WjYy91EylYt j9ByZaOa9pn6VlFUZdr4KyWsRkUM+xl6Uotqxb8e+dRl5qj0QUKug7orORJT +6FUYEo5FEIKZkpjj+ER.YUzxh7RxcDAIVcaxRU4GHejrLJibsphTjDqeLNq 9leQUjl+0xepqqRSxTKy2jY5OQ6EShM8d9h+9c9AcO4Wxypzco4V+bQRTZ2c x1rJIKUUYFKP6EMxbR10WUnVV0vBfxkumdIwio+Dj8MHedq9nL4+L8Anep9N HeSUWOP0W76Wbg9iKe4.NOMtGvIY0DNJMo5dCg6wEIpPQVroHQESpelxMKL+ FphxcxQ9N3nOdbjK8dBFEAulX7WKTprsvkVMMoPEeY8OEu002jUSIUYYTw8y 2AiD3wHOvfENMT+MVngXLpKfTsEa8n4ILpiBc2noWptespQhmOuWz1hIdHZ+ IjTCEXFzHORjz0AKySyKZMr0+kn8e.5+jGA3Vo0LtV8DxoG0jOM+2TQ2dO4O 2rP8o46zriMLxFNPxxdFxBF0LNXXJPCLsFrmM.Qnoc7aFTCBJ9TDgRq5lu4a dFkDHvELYOVfoI2pde8MzR3vnBfOUBM7vGdYFgkQ2phupYLcUTUUQxhMUM4d LqGNyle055PUIkUprkpdn1PUjXaEYAIcuTcQT10yubezkguKNQvKgtrWcu9b 7PBqIAAFDLI85mlb8M0469.u9VBQAdVsLV3VoSz5f2MNyv0AumDQnzpY4wm5 N387vmJAh2bv2RWe78lIfosCdDi4wCNo8u+b1p0ila1O3tr8qcAPdHhIMva7 pGZ7i0pfMXBxwiMQqWqxh6VJGBkrNpndDVUaiSXCSQSHvmS9MK7fe3Qppcxn DIjH5XRHlNJQvvThjT74zYiRjDv1U9qfNzARB+WLJQj+Han4fKY3kXk+4QF3 RNdHoMz+zOAbo.cn7V928vUhdxlmLoe+bQ4nCTGzCcG4mNA4dIpOXV9Vy5nz r0Ub16kuxpOGuCq.zWbI.ZLpjSMOVOS7wmOspcB1PzAano9U4qe3wibsBnna +wwdsB5VgfQdsBH5e5px57ttMQ8URoJsdjUqsWUDs7eNtz28PL8cn47M.sVv 9u50.9RWjED2FBPzT3GqIy8SnhaPdek4HlJKH.dytEFNw2XYtDSpzpJIm708 v8FAr3+VkOc30eDbfwmB09LvkIlGfOnf.+yjk3igoZDSDdZFG732ocFhECAs aj0CC4MEWnOVHlToUq4LHjGcDvxag75wKLB9plDg7F3lZwY3CpynPdTLO2+B 9oYHuides.L8sSMC4yfHdfOlToUoY5GwCji.VdKhWOdEifqJ9Y3FbAb7A0IT DuWfJDlU+x3MVl9S8s3BSm4sPAXdusEWuyaD.KUdhtGWKt9.aSzvNNi3an1j ewQuWXSic4ByhBAAs4jXg1tbY9MM64xidqoMcu95Ojlk4aJV1Mt6NMvDnW.h UkUIYQUI4Ya8P5WkRxOjxaRhiUl62IfwIkQKRUw6+E+zV44Qc0tkG868jijG 8Kv1AkGuGBwmJOqRhWmmjUU18tVEpCtwa1hJI3225GcDdi.lEyvlgI3FhRsY FFb2LLyF4g5L4QezpOrEI2cVj91XAHcm7HsQd7bKe.ajG2Xe8ng9djGwv7Xw 7DFeTTulby86aMBdrdjx8dFA9taF1FODR2YAHAaz3NTLxGMC6IM0aAlL6D98 MFi4Wqje24w0ylHRR2ouIswih9XTNHKXoYoRC7LyrgFyYciQX9UZSDC8oUzU 7LzF4wc43pOx9GVdXCLmR+sbPqKpcDcPKsIEEovYg7j1Dv3QTeTkGaRQQ5tT 3j1jRfzcobKsoHOo6RgSZS..g7DiONrjDabXwCOs3ivc161Dui6t3KbavC2c teLc0gBWv8GV9pfvGLoxz9JfHj79liPHOtUywtyEA2lPLb24BkaSNqb2UEL2 lPd7AVEbuRVy+T7.I.8MGiUtylgf6VJTtMkAybWYRbahZyFXYR.SFr8Tr9eL ci3TL2lRgMCT2X1vroTIt6x7fayxuybWlGLqbyACLTFy2a6PYcpfiTnLabq. tK6.F0BjBhAhTpOcajRkrwDofMEfxbmYCXSB6f6bUCVoyIcKe.ajG231ErIa NXf6xXuReanL.niYnLaR3xcZb1TBjmSkFvB1LrDUZN+XTSNnf9LvJaaNByt1 3PwcU3ZSVSGa4+jOew2u3+I36zZE -----------end_max5_patcher-----------
I think your .amxd example illustrates the ‘notification’ aspect very well.
For clarity of the comparison, ‘getpath’ may be replaced by ‘b’ (purely cosmetic).
It would be nice to have examples like this in the documentation/tutorials of M4L.
Thanks broc, much appreciated.
agreed. I’ve actually learned so much in the past weeks I may gather it up and put it in a thread. (my dayjob is running a small technical training team in a big company, I don’t really want to take my work home!)
and yes my patch was a bit sloppy – (late night work) I like the [t getpath l] method, so much cleaner that using a message box: unfortunately it doesn’t work with ‘get name’!
@basvik "unfortunately it doesn’t work with ‘get name’"
it does – just not sure if it makes much sense ;)
----------begin_max5_patcher---------- 489.3ocuUF0aaCBDG+Y7mBDOmUYfr1z811Gh8xZkE1bMgIavxbIKcU869LX6 zjo3LuJ27fQh6vb+uebG7RBgk61CdF8KzePIjWRHjnofAR+bBqRsunT4iKik uEQmksnykcakaKVBXzIu2ZmI74ZnamY4J6ZF8wd20JrXiwtNqAJvtUHVd2Mo Kn2GFDoCiG9CiNFaW9O+D+yGEai8PnC1dMIILrXhohE9U6NNrcHrOJF1SMtJ +yU4tx+yr7hYnTtLjVqh44c2dwTTND3mbVzpphAf8cnQqrpi84M+N5iya2uO VpTZ1A2z5HjPyOV37N5rJNY0HbQbVt70Fipj9MWo9rnI87nQzazq1A5rtDKS gXiosBuqkfbfPDVVMz3MdDrEvAx1g14DvsDZCE2X7YZXmo.nEJqyZJTkY0pF vNB6kix9E8eSn4SJiv+d4EOC3y3Yv6o7rB7d0ZXNqAEKi23vWxOpTbL.La8l h4qzAoOvVCHMHmGXzQt2RbwhjIzjda5a8nid2U5GwcWwH01gX+62phhMX+Tn 4caaJFRugWMnuIXM3QiUgl1WxNZQ7SVzFiVCQ+C5qxnqcFK1KB5im8HbxZJD N9+RSoWWMImBmDWWMkNEMIutZRLAMIO478pfI9TN5duZpcxqI+gHP4Uh -----------end_max5_patcher-----------
To clarify, I meant replacing [t getpath l] by [t b l] as getpath is used here only to trigger the message [get name].
So the appearance of getpath could be confusing at first sight.
@ broc: understood: this was just because I made the patch from editing other ones, a slip-up. From a trying-explain-the-issue point of view, superconfusing, I agree
@pure: i did try that too. I think I did a test using pedant to compare a [trigger object with symbol + fromsymbol] patch with [triggering a message box], but in terms of performance it doesn’t matter much: the API calls are slow and their time varies a lot, compared to the rest of the objects. So I guess that’s a good argument to just make the patch the way it is most readable.. I vote for triggering a message box
Update – in case anyone reads this thread and finds it useful: I’ve been wrecking my head over the above: i think I figured out when and where I should use [deferlow] to prevent the "Setting the Id cannot be triggered by notifications" error messages, but M4L behaviour has been very inconsistent.
Turns out there is a BIG difference whether you have your device open for editing in Max (many more errors, and inconsistently: sometimes execution is fine, sometimes I get the error, and it seems to depend on how busy the system is whether or not you get the error). But when you have the M4L device running inside Live (ie _not_ open for editing) it behaves a lot more predictable
yeah this happens with many objects. then having to clutter the little space you have in live with a lot of prints and bangs for debugging is quite annoying…
In my experience, serious testing in edit mode is not possible. So in general I save (or even reload) the device and then look at the Max window in performance mode (open with right-click on the device title bar). Strictly speaking, interactive editing in M4L doesn’t really work as advertised.
unfortunately true :(
though, still trying to ignore this fact =)
Maybe we should gather up a few of those ‘gotcha’s ‘
I think I saw the posts that said you can’t really do interactive editing but I ignored them – because on the surface it seems to work ok: it’s the unpredictability that really causes the frustration.
Now I get it – and my devices work so much better! So actually, I"m pleased :-) Happy New Year btw
pid – if you cant make a call based off an observed value, then how can you make a call, like enter notes (sent by push) when the buttons are retrieved through an observer?
The example in this thread fails to take into account that the terminal node of a chain is executed first– for example, a chain of bang objects will execute from end to beginning, like this (second attachment)
Here is a revision of the first part of example that you can play with to get a better understanding.
The reverse chain of execution is odd, but once you know that , it’s easier to see what these objects are doing.
it’s been a while since this thread so I would need to reread to exactly recall what it was about. however, I ran your example patcher here and you will probably spot the interesting difference in behavior when you look at 2 and 3. shouldn’t be like that, no?
Actually, based on the idea that the end of the chain executes first, yours makes more sense. I thought it would end up that way, and that’s how I numbered it, but then it reversed the 3 and 2 so I reversed mine.. Strange!
I believe it’s supposed to work the way it did for you. Maybe some sort of glitch.. What version of max are you using? That test was done in 5.19