BlazorBabylonJs icon indicating copy to clipboard operation
BlazorBabylonJs copied to clipboard

Define A Goal (for the project)

Open ADefWebserver opened this issue 5 years ago • 11 comments

Description

This thread is primarily directed at @SQL-MisterMagoo but everyone is welcome to participate in this discussion.

History

I created this project because I wanted to see if I could get the BabylonJs 3D framework to work with Blazor. I got that working and then parameterized the sample code in an attempt to make it generic.

@SQL-MisterMagoo then got a hold of the project and introduced a radically different structure that among other things allows you to use declarative syntax. Essentially the Blazor C# code allows you to call JavaScript methods on this file.

I can't stress how powerful this is and what possibilities it opens up. The question is now, where do we go from here?

Proposed Features

ADefWebserver avatar May 15 '20 01:05 ADefWebserver

They all sound like good features.

As far as the code goes, I would probably propose that we have a JavaScript (or TypeScript) module for the actual interop - with a corresponding C# api so from code we could do things like

var myBabylon = BabylonBlazor.WithDefaults().WithLights(MySetOfLights);
myBabylon.Cameras.Add(new Camera(...));
var textMesh = MeshWriter.Create("Hello World");
myBabylon.LoadMesh(textMesh);

I would see these sorts of API calls being pretty much a gateway to the JS library - like any JSInterop library - but perhaps there could be some batching of operations or even some caching/recording (undo/redo?) of operations.

But these apis would also be the basis of declarative components, like in the current demo.

<BabylonCanvas>
 <Light PropertyX="1"/>
 <Camera LookAt="SomeMeshId"/>
 <Mesh Source="MeshWriter.Create("Hello World")/>
</BabylonCanvas>

SQL-MisterMagoo avatar May 15 '20 10:05 SQL-MisterMagoo

@SQL-MisterMagoo Two Issues:

  1. No one loves Typescript as much as I do, but, NPM, for this project, is a non-starter for me (I have had too many nightmares where programmers on my team got stuck because of 'NPM Hell'). Do you think we can we use Typescript without NPM (or some other 'extra technology' that could potentially be a 'roadblock' for neophytes)?

Meaning, I would rather just continue to code in JavaScript so that a neophyte could just pull this project down and it-just-works 😜

  1. I love this As-The-"Goal" 💖:
var myBabylon = BabylonBlazor.WithDefaults().WithLights(MySetOfLights);
myBabylon.Cameras.Add(new Camera(...));
var textMesh = MeshWriter.Create("Hello World");
myBabylon.LoadMesh(textMesh);
<BabylonCanvas>
 <Light PropertyX="1"/>
 <Camera LookAt="SomeMeshId"/>
 <Mesh Source="MeshWriter.Create("Hello World")/>
</BabylonCanvas>

If you also agree then we can close this issue and I will move the other features to their own issues, so they can be addressed in the future.

So, for the main goal, what is the first step?

ADefWebserver avatar May 15 '20 12:05 ADefWebserver

🤣

I only included TypeScript as an option - I am personally just as comfortable with plain JS.

I'm happy for us to have a set of issues as you suggest.

My initial thoughts would be that the C# api (calling into JS) is the key - if we get that right, so the end user of the package doesn't have to see any JS then it's a win.

Wrapping components around that C# API should then be a very simple job.

SQL-MisterMagoo avatar May 15 '20 13:05 SQL-MisterMagoo

Where do we start and what can I do?

ADefWebserver avatar May 15 '20 13:05 ADefWebserver

I think - as you suggested - a set of issues listing the basic requirements for the api...

I feel like we need to figure out the "how" of doing this - the reason I picked up that web-component was because it made life easier - we need to make life easier still...

How do we plan to build a scene - is it a case of setting up a load of configuration and saying "build" and then it's static? probably not - we want to be more dynamic I think - adding and removing objects from the scene, switching scenes, saving/loading scenes?

Can we define an api that lets us - from code initially - create a scene, display it, modify it and destroy it. How does that look? Is it a "builder" pattern like above or some other ?

If you could have a think about how you would like that api to look and map out some high level goals as issues I think it would be a good start.

SQL-MisterMagoo avatar May 15 '20 13:05 SQL-MisterMagoo

Sounds perfect. Give me a day to think on this and write down some ideas.

ADefWebserver avatar May 15 '20 15:05 ADefWebserver

I thought about it, I think we need to first agree on some basic Assumptions?

  1. There is only one engine (we make it for you)
  2. You can build and control a scene using declarative markup
  3. You can have multiple scenes on a page
  4. You can call any unsupported BabylonJS feature, from Blazor, using C# code

ADefWebserver avatar May 15 '20 17:05 ADefWebserver

steve

Quick note to anyone wanting to catch up on how Blazor works with JavaScript, this YouTube video by @SteveSandersonMS offers a good overview.

https://youtu.be/QnBYmTpugz0?t=137

However, this project implements most of the suggestions covered, plus, additional advanced architecture.

ADefWebserver avatar May 17 '20 01:05 ADefWebserver

Can we define an api that lets us - from code initially - create a scene, display it, modify it and destroy it. How does that look? Is it a "builder" pattern like above or some other ?

Create a Scene

<BabylonCanvas>
 <Scene ="@Scene1"/>
</BabylonCanvas>
@code {
Scene Scene1 = new BabylonBlazor.Scene();
Camera Camera1 = new BabylonBlazor.Camera { LookAt="SomeMeshId" };

Scene1.Cameras.Add(Camera1);

var textMesh = MeshWriter.Create("Hello World");
Scene1.LoadMesh(textMesh);
}

ADefWebserver avatar May 17 '20 01:05 ADefWebserver

I then had a thought, what if we created C# classes for the TypeScript classes in BabylonJS? I then looked to see if anyone else did that and found the Retyped/BabylonJsDemo.

They use a Bridge.NET Compiler and even have a Retyped.babylon NuGet package.

They end up with C# code like this:

using Retyped;

using static Retyped.babylon_js.BABYLON;

namespace BabylonJsDemo.SceneProviders
{
    /// <summary>
    /// Original sources: http://www.babylonjs-playground.com/#12S23Y
    /// </summary>
    public class Scene1Provider : AbstractSceneProvider
    {
        public override Scene CreateScene(dom.HTMLCanvasElement canvas, Engine engine)
        {
            // This creates a basic Babylon Scene object (non-mesh)
            var scene = new Scene(engine);

            // This creates and positions a free camera (non-mesh)
            var camera = new FreeCamera("camera1", new Vector3(0, 5, -10), scene);

            // This targets the camera to scene origin
            camera.setTarget(Vector3.Zero());

            // This attaches the camera to the canvas
            camera.attachControl(canvas, true);

            // This creates a light, aiming 0,1,0 - to the sky (non-mesh)
            var light = new HemisphericLight("light1", new Vector3(0, 1, 0), scene);

            // Default intensity is 1. Let's dim the light a small amount
            light.intensity = 0.7;

            // Our built-in 'sphere' shape. Params: name, subdivs, size, scene
            var sphere = Mesh.CreateSphere("sphere1", 16, 2, scene);

            // Move the sphere upward 1/2 its height
            sphere.position.y = 1;

            // Our built-in 'ground' shape. Params: name, width, depth, subdivs, scene
            var ground = Mesh.CreateGround("ground1", 6, 6, 2, scene);

            return scene;
        }
    }
}

Is this something that could help us?

For now I created this task for myself: Try to use the Retyped.babylon NuGet package

ADefWebserver avatar May 17 '20 13:05 ADefWebserver

... For now I created this task for myself: Try to use the Retyped.babylon NuGet package

This so didn't work :( Could not get the thing to compile. They don't provide the source code so I can't diagnose what is wrong.

ADefWebserver avatar Jun 03 '20 02:06 ADefWebserver