Click to item for Callback/Event functionality
-
I have been enjoying JSCAD so far.
One function that would be very useful is to be able to click on an object and receive a js callback to the object in code.
I have just taken a screenshot of the example app for reference.
The JSCAD app creates a number of solids that are fed back to the viewer and the viewer renders them.
What would be very handy is to have the ability to select on of these top level objects and then be able to in code be able to do modifications to that selected object.
The level of interaction can be coursely-grained. No edge or face selection needs to be provided initially.
Typically, the use case might be to click on a particular object and then in code in a callback change the colour, position, scale or other properties.
-
@z3dev said in Click to item for Callback/Event functionality:
the focus of JSCAD is still 3D printing
Yes, that aligns with what I am doing.
The reason that I was querying this capability is that in the above picture of a drill-tray example, made from a photo-scan, I want to put in different options for the hinge and lid made by clicking on the parts in the jscad ui.
It's no big deal if it's not easy to achieve (as explained by @hrgdavor) in jscad at this point in time. I can resolve this some other way. I just thought it might be easy*
Interestingly, I was able to find that there is a component that does what I need for gltf but I haven't been able to locate an Open-Source equivalent just yet. https://iconscout.com/gltf-3d-editor provides a simple click+transform+rotate component for their platform that does what I was looking for.
-
@hrgdavor the focus of JSCAD is still 3D printing, but there have already been lots of innovative projects built. So, the only feedback that I can provide is... there has to be at least one UI that allows simple designs to be created via JS scripts (This includes the CLI as well.)
If someone wants to build a fully interactive CAD application, then they have to build and maintain. I'm sure that this kind of application can be created.
-
@hrgdavor said in Click to item for Callback/Event functionality:
I need to ask @z3dev to confirm this is not something in scope of jscad
No problem. It's 'obvious now that it would be a huge upgrade.
https://www.youtube.com/watch?v=y0MPVDRaP8E
However, from the research I've just done on this in the last week it seems that Solidworks has had the Click-Item and Animation capabilities for years.
I've just worked out for my own project that I do "need" these capabilities for "Sales" related reasons.
I also found another framework that has a JS animations API where a bit of work has gone into it: https://docs.metroui.org.ua/m4q-animation.html
They've gone through and thought out how to simplify the movement of objects from in the API with methods.
var el = $("#demo-cube-2"); var startPos = parseInt(el.style("left")); var maxLeft = startPos === 0 ? el.parent().width() - 62 : 0; btn.disabled = true; $.animate(el, { left: maxLeft }, 3000, function(){ btn.disabled = false; });
From my point of view, my use case would be to be able to click on a top-level entity, and then inside the callback fire off the animation routine and display the items moving.
My own practical use is that I have some boxes, and I'd like the lids to open. And other movements related to that.
Since it's Javascript and they already support Events and animations anyway, I'm hoping that the functionality wouldn't be out of place.
-
@DavidLyon66 that is something I really want to imeplement, but I need to ask @z3dev to confirm this is not something in scope of jscad itself ... at least for now. I would need to experiment with it in jscadui.
I have made some progress there that will be usable for jscad, but it takes years with time am able to put aside for it.
making an extension that goes beyond exporting main method would allow to keep the current principle for jscad, and that principle serves well many users and many use cases.
I would go about it by requiring an interactive script like you would like to create to export a different method, for example:
export function interactive(){...}
. There we could experiment with script doing more that just generating models without braking existing scripts and without confusing users that do not need such interactivity. -
@hrgdavor said in Click to item for Callback/Event functionality:
Said like that it is not too hard but it opens a pandora box and a can of worms.
You call them worms, somebody else calls it Pasta.
who receives the callback,
The name of the callback-function would be passed into the dictionary. So specifically, it has to be supplied by the Creator.
Eg:
return [ [colorize([0.65, 0.25, 0.8], outer),{'onclick':outerclick}], colorize([0.7, 0.7, 0.1], inner), ]
do you need also moseover event
Probably. Somebody is going to ask for it. It might look like this:
[ [colorize([0.7, 0.7, 0.1], inner],{'mouseover':'innerhover'}]),how do you highlight the selected element ?
The caller can do it in the callback. For example with the built in method 'colorise'. A reference to the object is passed to the callback.
what types of highlights would you need
Only existing JSCAD CSG (modelling) methods such as Transform (make it bigger), colorize (change color) etc.
what would you do with the selected item afterwards
Nothing - leave the object changed. Konva is another 2D JS framework and they have all the events worked out. If the item needs to be deselected if another item is clicked, that can be done in the callback code.
index is fragile, objects should have a unique id for callback
Most callbacks (for eg on Konva) give a pointer/reference to the object for the callback. ie
function outerclick(obj) { return(colorize([0.15, 0.35, 0.33], obj)) }
script is in the worker, renderer is on main thread
ok
how to send granular updates instead of re-render whole script (exponentional complication)
Just update the single object, and then do a refresh. On Konva for example, you have to update the Frame-Buffer yourself to see the change. But their use case is complex.
function outerclick(ref) {
return(colorize([0.15, 0.35, 0.33], ref))
}@z3dev said in Click to item for Callback/Event functionality:
@DavidLyon66 The design is assembled via a call to main(), which can accept a single dictionary of parameters (This is what happens for the parameters). The interactive parameters are converted to a dictionary.
That makes it easier to specify the name of a callback function. Just add it to the dictionary.
It might be worth looking at the Solidworks Animator. I was shown it by a CAD Operator at a place that I worked at once where they used it to show a machine design to a client to help motivate them to pay for the job.
https://www.youtube.com/watch?v=CwklwnqzbVU
Adding a Timeline isn't as hard as it seems. I'm not asking for it. I'm only mentioning it as this is the complete use-case. To be able to watch some sort of CAD Design in operation or action. Which is often what the client wants.
i don't need the animation in my use case.
-
@DavidLyon66 The design is assembled via a call to main(), which can accept a single dictionary of parameters (This is what happens for the parameters). The interactive parameters are converted to a dictionary.
-
@DavidLyon66 said in Click to item for Callback/Event functionality:
I would have thought that a callback with an index for the item on selection might not have been that hard.
Said like that it is not too hard but it opens a pandora box and a can of worms.
- who receives the callback,
- do you need also moseover event
- how do you highlight the selected element ?
- what types of highlights would you need
- what would you do with the selected item afterwards
- index is fragile, objects should have a unique id for callback
- script is in the worker, renderer is on main thread
- how to send granular updates instead of re-render whole script (exponentional complication)
Other contributors might disagree with me here, but I think this is something a separate project should do by using jscad.
-
@hrgdavor wrote:
it would take me at least a year
Thanks for the response. I wouldn't ask that you do that.
I will look for a workaround in this case.
I'm surprised that there isn't some sort API call available deep down inside the original code to accomplish this. Obviously I haven't checked it myself.
Using an example:
const jscad = require('@jscad/modeling') const { intersect, subtract } = jscad.booleans const { colorize } = jscad.colors const { cube, sphere } = jscad.primitives function main() { const outer = subtract( cube({ size: 10 }), sphere({ radius: 6.8 }) ) const inner = intersect( sphere({ radius: 4 }), cube({ size: 7 }) ) return [ colorize([0.65, 0.25, 0.8], outer), colorize([0.7, 0.7, 0.1], inner), ] } module.exports = { main
The above has two objects being returned:
return [ colorize([0.65, 0.25, 0.8], outer), colorize([0.7, 0.7, 0.1], inner), ]
I would have thought that a callback with an index for the item on selection might not have been that hard.
Thanks for the reply. At least I can proceed on the assumption that Callback-Events might not be available for the next few months
-
@DavidLyon66 said in Click to item for Callback/Event functionality:
be able to in code be able to do modifications to that selected object.
in my opinion, this sentence alone makes it much more complicated than blender or ultimaker cura.
If someone would implement what you are suggesting in jscad I would very happy and impressed at the same time.
I am one of few developers that are still active on the project (although little by little, and much less I would like). Even if were to work on this full time my guess is it would take me at least a year, and even then I am not sure to what extent it would match your expectations (or at least what I imagine your expectations are here).
btw, Blender has much more people smarter than me working there full time.
TLDR;
This looks huge to me and I would not dare to even start it, I would not mind if somebody would do it though. -
@hrgdavor I'm not sure that it's a huge amount of work.
I believe that it is only a matter of tweaking the existing code. Since 'everyone else has done it'. It's in everything from Blender to Ultimaker Cura where you can select top-level meshes, split, then move them around for printing in different places.
Here is a practical example of it being used elsewhere in an example: https://aframe.io/examples/showcase/responsiveui/
The idea is that you can select an object from the top level and have some simple level of control for it.
-
@DavidLyon66 That would be a huge undertaking.
Just the step to mark all entities during execution with code line numbers is difficult and requires code transformation. then taking cursor to that file location would be relatively easy to implement.
but intercepting editor changes to re-evaluate the script to only modify changed entity would be exponentionally more difficult. I would love to have time to develop something like that, but sadly I do not.
One thing that is doable is to perform faster render for parameter changes.. One thing that a developer writing the script can do is cache resulting objects baed on parameter values. and return the cached results for those objects that were not affected by parameter changes.