No edit summary |
Update links, examples, and people |
||
Line 16: | Line 16: | ||
* '''Influenced by''': F#, Elm, Python, Haskell, VHDL, Odin, Go | * '''Influenced by''': F#, Elm, Python, Haskell, VHDL, Odin, Go | ||
* '''Showcase World''': https://go.resonite.com/world/U-1O4IcGhlKSm/R-2045c574-dda6-4a7e-9955-56d2ca002d78 | * '''Showcase World''': https://go.resonite.com/world/U-1O4IcGhlKSm/R-2045c574-dda6-4a7e-9955-56d2ca002d78 | ||
* [https://flux-sdk.samsmucny.com/ Documentation] | |||
== Who Should Use ProtoGraph? == | == Who Should Use ProtoGraph? == | ||
Line 39: | Line 40: | ||
# Import the <code>.brson</code> file into Resonite | # Import the <code>.brson</code> file into Resonite | ||
# Inspect the generated ProtoFlux under the corresponding slot | # Inspect the generated ProtoFlux under the corresponding slot | ||
=== Flux UI === | |||
The [https://flux-sdk.samsmucny.com/UI/Flux-SDK-UI.html Flux UI] can be used in Resonite to link up the sources and drives from generated ProtoFlux. | |||
== Examples == | == Examples == | ||
== Cross Product Module == | == Cross Product Module == | ||
This is a simple pure module that transforms input data into outputs.<syntaxhighlight lang="fsharp" line="1"> | This is a simple pure module that transforms input data into outputs.<syntaxhighlight lang="fsharp" line="1"> | ||
/// Multiplies two 3D vectors using a cross product | |||
module CrossProduct | module CrossProduct | ||
/// The first vector | |||
in A: float3 | in A: float3 | ||
/// The second vector | |||
in B: float3 | in B: float3 | ||
/// The result of (A X B) | |||
out this: float3 | out this: float3 | ||
where { | where { | ||
// Inputs | // Inputs | ||
Ax, Ay, Az = Unpack_Float3(A); | Ax, Ay, Az = Unpack_Float3(A); | ||
Bx, By, Bz = Unpack_Float3(B); | Bx, By, Bz = Unpack_Float3(B); | ||
// Computations | // Computations | ||
Cx = (Ay * Bz) - (Az * By); | Cx = (Ay * Bz) - (Az * By); | ||
Cy = (Az * Bx) - (Ax * Bz); | Cy = (Az * Bx) - (Ax * Bz); | ||
Cz = (Ax * By) - (Ay * Bx); | Cz = (Ax * By) - (Ay * Bx); | ||
// Final result | // Final result | ||
Pack_Float3(Cx, Cy, Cz); | Pack_Float3(Cx, Cy, Cz); | ||
} | } | ||
</syntaxhighlight> | </syntaxhighlight> | ||
Line 67: | Line 75: | ||
== Counter Object == | == Counter Object == | ||
This shows how you can write an object that maintains internal state and exposes methods to be called.<syntaxhighlight lang="fsharp" line="1"> | This shows how you can write an object that maintains internal state and exposes methods to be called.<syntaxhighlight lang="fsharp" line="1"> | ||
/// A simple object state machine that can count up and down | |||
module Counter | module Counter | ||
/// The current value of the counter | |||
out this: int | |||
// Public | /// Public method to count up | ||
out Increment: Impulse | out Increment: Impulse | ||
/// Public method to count down | |||
out Decrement: Impulse | out Decrement: Impulse | ||
/// Public method that sets counter to 0 | |||
out Reset: Impulse | out Reset: Impulse | ||
where { | where { | ||
// Variables are not shared with other nodes, they are private | // Variables are not shared with other nodes, they are private | ||
sync CounterVar: int; | sync CounterVar: int; | ||
// out impulses are methods on the object that send it messages | // out impulses are methods on the object that send it messages | ||
// to do different actions | // to do different actions | ||
Reset = CounterVar <- 0; | Reset = CounterVar <- 0; | ||
Increment = CounterVar <- ValueInc(CounterVar); | Increment = CounterVar <- ValueInc(CounterVar); | ||
Decrement = CounterVar <- ValueDec(CounterVar); | Decrement = CounterVar <- ValueDec(CounterVar); | ||
// We can also expose normal data. This is like a getter. | // We can also expose normal data. This is like a getter. | ||
CounterVar; | CounterVar; | ||
} | } | ||
</syntaxhighlight> | </syntaxhighlight> |
Revision as of 12:57, 2 September 2025
ProtoGraph is a declarative programming language designed to work with ProtoFlux in the Resonite ecosystem. It allows creators to write logic in a clean, readable text format that compiles directly into ProtoFlux nodes—making it easier to build, test, and maintain complex systems.
Overview
- Paradigm: Dataflow
- Family: ML: Caml: OCaml: F#
- Designers: Papaltine, Kittysquirrel
- Developers: Papaltine, Kittysquirrel
- Stable Release: N/A (Currently in Beta)
- License: AGPLv3
- Target Platform: Resonite (via ProtoFlux)
- File Extension:
.pg
- Compiler Tool:
flux-sdk
- Repository: Flux SDK
- Nuget: Papaltine.FluxSDK
- Compiled Format:
.brson
(Resonite Record) - Influenced by: F#, Elm, Python, Haskell, VHDL, Odin, Go
- Showcase World: https://go.resonite.com/world/U-1O4IcGhlKSm/R-2045c574-dda6-4a7e-9955-56d2ca002d78
- Documentation
Who Should Use ProtoGraph?
- Creators who want to move beyond visual scripting
- Developers building modular, reusable systems
- Teams collaborating on large-scale Resonite projects
Benefits
- Readable: Clean syntax that mirrors ProtoFlux
- Modular: Encourages reusable and easy to refactor code
- Reliable: Compiler checks help catch errors early
- Accessible: Friendly to those familiar with ProtoFlux as a first programming language
Building and Using in Resonite
- Write your
.pg
file - Compile it:
flux-sdk build MyModule.pg
- Import the
.brson
file into Resonite - Inspect the generated ProtoFlux under the corresponding slot
Flux UI
The Flux UI can be used in Resonite to link up the sources and drives from generated ProtoFlux.
Examples
Cross Product Module
This is a simple pure module that transforms input data into outputs.
/// Multiplies two 3D vectors using a cross product
module CrossProduct
/// The first vector
in A: float3
/// The second vector
in B: float3
/// The result of (A X B)
out this: float3
where {
// Inputs
Ax, Ay, Az = Unpack_Float3(A);
Bx, By, Bz = Unpack_Float3(B);
// Computations
Cx = (Ay * Bz) - (Az * By);
Cy = (Az * Bx) - (Ax * Bz);
Cz = (Ax * By) - (Ay * Bx);
// Final result
Pack_Float3(Cx, Cy, Cz);
}
Counter Object
This shows how you can write an object that maintains internal state and exposes methods to be called.
/// A simple object state machine that can count up and down
module Counter
/// The current value of the counter
out this: int
/// Public method to count up
out Increment: Impulse
/// Public method to count down
out Decrement: Impulse
/// Public method that sets counter to 0
out Reset: Impulse
where {
// Variables are not shared with other nodes, they are private
sync CounterVar: int;
// out impulses are methods on the object that send it messages
// to do different actions
Reset = CounterVar <- 0;
Increment = CounterVar <- ValueInc(CounterVar);
Decrement = CounterVar <- ValueDec(CounterVar);
// We can also expose normal data. This is like a getter.
CounterVar;
}