diff --git a/scs2-bullet-simulation/build.gradle.kts b/scs2-bullet-simulation/build.gradle.kts
index 8746d430..a630b684 100644
--- a/scs2-bullet-simulation/build.gradle.kts
+++ b/scs2-bullet-simulation/build.gradle.kts
@@ -17,10 +17,10 @@ mainDependencies {
api("us.ihmc:scs2-definition:source")
api("us.ihmc:scs2-shared-memory:source")
api("us.ihmc:scs2-session:source")
- api("us.ihmc:euclid-frame-shape:0.21.0")
+ api("us.ihmc:euclid-frame-shape:0.22.2")
api("us.ihmc:ihmc-messager:0.2.0")
- api("us.ihmc:ihmc-yovariables:0.12.2")
- api("us.ihmc:mecano-yovariables:17-0.18.1")
+ api("us.ihmc:ihmc-yovariables:0.13.3")
+ api("us.ihmc:mecano-yovariables:17-0.19.0")
apiBytedecoNatives("javacpp")
apiBytedecoNatives("bullet", "3.25-")
diff --git a/scs2-definition/build.gradle.kts b/scs2-definition/build.gradle.kts
index 96c163fe..545552ba 100644
--- a/scs2-definition/build.gradle.kts
+++ b/scs2-definition/build.gradle.kts
@@ -11,12 +11,12 @@ ihmc {
}
mainDependencies {
- api("us.ihmc:euclid:0.21.0")
- api("us.ihmc:euclid-shape:0.21.0")
- api("us.ihmc:euclid-frame:0.21.0")
- api("us.ihmc:ihmc-commons:0.32.0")
- api("us.ihmc:ihmc-yovariables:0.12.2")
- api("us.ihmc:mecano:17-0.18.1")
+ api("us.ihmc:euclid:0.22.2")
+ api("us.ihmc:euclid-shape:0.22.2")
+ api("us.ihmc:euclid-frame:0.22.2")
+ api("us.ihmc:ihmc-commons:0.34.0")
+ api("us.ihmc:ihmc-yovariables:0.13.3")
+ api("us.ihmc:mecano:17-0.19.0")
}
testDependencies {
diff --git a/scs2-definition/src/main/java/us/ihmc/scs2/definition/SCS2DefinitionTools.java b/scs2-definition/src/main/java/us/ihmc/scs2/definition/SCS2DefinitionTools.java
new file mode 100644
index 00000000..c24ba116
--- /dev/null
+++ b/scs2-definition/src/main/java/us/ihmc/scs2/definition/SCS2DefinitionTools.java
@@ -0,0 +1,52 @@
+package us.ihmc.scs2.definition;
+
+import us.ihmc.scs2.definition.collision.CollisionShapeDefinition;
+import us.ihmc.scs2.definition.robot.CrossFourBarJointDefinition;
+import us.ihmc.scs2.definition.robot.JointDefinition;
+import us.ihmc.scs2.definition.robot.RigidBodyDefinition;
+import us.ihmc.scs2.definition.robot.RobotDefinition;
+import us.ihmc.scs2.definition.visual.MaterialDefinition;
+import us.ihmc.scs2.definition.visual.VisualDefinition;
+
+import java.util.List;
+import java.util.function.Consumer;
+
+public class SCS2DefinitionTools
+{
+ public static void forEachRigidBodyDefinitionIncludingFourBars(RigidBodyDefinition start, Consumer rigidBodyConsumer)
+ {
+ RobotDefinition.forEachRigidBodyDefinition(start, body ->
+ {
+ rigidBodyConsumer.accept(body);
+ for (JointDefinition childrenJoint : body.getChildrenJoints())
+ {
+ if (childrenJoint instanceof CrossFourBarJointDefinition fourBarJointDefinition)
+ {
+ rigidBodyConsumer.accept(fourBarJointDefinition.getBodyBC());
+ rigidBodyConsumer.accept(fourBarJointDefinition.getBodyDA());
+ }
+ }
+ });
+ }
+
+ public static void addCollisionVisualsToRobot(RobotDefinition robotDefinition, MaterialDefinition material)
+ {
+ robotDefinition.forEachRigidBodyDefinition(rigidBody -> addCollisionVisualsToRigidBodyDefinition(rigidBody, material));
+ }
+
+ public static void addCollisionVisualsToRigidBodyDefinition(RigidBodyDefinition rigidBodyDefinition, MaterialDefinition material)
+ {
+ if (rigidBodyDefinition == null)
+ return;
+ List collisionShapeDefinitions = rigidBodyDefinition.getCollisionShapeDefinitions();
+ if (collisionShapeDefinitions == null)
+ return;
+
+ for (CollisionShapeDefinition collisionShapeDefinition : collisionShapeDefinitions)
+ {
+ rigidBodyDefinition.addVisualDefinition(new VisualDefinition(collisionShapeDefinition.getOriginPose(),
+ collisionShapeDefinition.getGeometryDefinition(),
+ material));
+ }
+ }
+}
diff --git a/scs2-definition/src/main/java/us/ihmc/scs2/definition/yoGraphic/SCS2YoGraphicHolder.java b/scs2-definition/src/main/java/us/ihmc/scs2/definition/yoGraphic/SCS2YoGraphicHolder.java
new file mode 100644
index 00000000..b75c6426
--- /dev/null
+++ b/scs2-definition/src/main/java/us/ihmc/scs2/definition/yoGraphic/SCS2YoGraphicHolder.java
@@ -0,0 +1,125 @@
+package us.ihmc.scs2.definition.yoGraphic;
+
+import us.ihmc.yoVariables.registry.YoRegistry;
+import us.ihmc.yoVariables.variable.YoVariable;
+import us.ihmc.scs2.definition.SCS2DefinitionTools;
+
+/**
+ * This interface was initially created to bind classes that can create SCS2 yoGraphics, such that:
+ *
+ * - they're easy to retrieve for refactoring purposes.
+ *
- Javadoc added here can spread around the codebase easily.
+ *
+ *
+ * SCS2 yoGraphic framework differs from SCS1 yoGraphic framework in a few aspects:
+ *
+ * - 2D vs 3D:
+ *
+ * - SCS1 uses {@link us.ihmc.graphicsDescription.yoGraphics.YoGraphic} for 3D graphics and {@link us.ihmc.graphicsDescription.plotting.artifact.Artifact} for 2D graphics. In this
+ * documentation, we abuse the term "yoGraphic" to refer to both the 2D and 3D types when referring
+ * to SCS1.
+ *
- SCS2 base class {@link YoGraphicDefinition} is extended into 2 branches:
+ * {@link YoGraphic3DDefinition} for 3D graphics and {@link YoGraphic2DDefinition} for 2D graphics.
+ *
+ * - Listing and grouping:
+ *
+ * - SCS1 uses {@link us.ihmc.graphicsDescription.yoGraphics.YoGraphicsListRegistry} to do both listing and grouping of yoGraphics.
+ * {@link us.ihmc.graphicsDescription.yoGraphics.YoGraphicsList} to represent a list of {@link us.ihmc.graphicsDescription.yoGraphics.YoGraphic} and {@link us.ihmc.graphicsDescription.yoGraphics.plotting.ArtifactList} for
+ * {@link us.ihmc.graphicsDescription.plotting.artifact.Artifact}. The grouping per say is done by attributing a name to a list or specifying a
+ * {@code listName} when registering a yoGraphic to the {@link us.ihmc.graphicsDescription.yoGraphics.YoGraphicsListRegistry}.
+ *
- SCS2 yoGraphic list is {@link YoGraphicListDefinition}. It is meant for convenience, because
+ * it implements {@link YoGraphicDefinition}, it can be passed around the same way a yoGraphic would
+ * be. For grouping, {@link YoGraphicGroupDefinition} should be used. You can think of it as a
+ * {@link YoRegistry} for yoGraphics, it has children (both regular graphics and other groups) and
+ * can be added to a parent group. A tree hierarchy of yoGraphics and groups can be created and will
+ * be reflected in the SCS2 GUI, see the menu YoGraphic > YoGraphic properties... all the
+ * yoGraphics will be under the group root:SessionVisualizer.
+ *
+ * - Internal data:
+ *
+ * - SCS1 yoGraphics are internally backed by {@link YoVariable} which makes them harder to
+ * serialize (so difficult to save to file and send over network) and also thread sensitive
+ * (yoVariables should not be shared across threads).
+ *
- SCS2 yoGraphics are only descriptions telling SCS2 what type of graphic should be created and
+ * what data (yoVariables or constants for instance) the graphic uses to notably change over time.
+ * For instance, the radius of a capsule (see {@link YoGraphicCapsule3DDefinition}) is not a
+ * yoVariable but a {@code String}. The {@code String} can be used to represent a {@code double}
+ * (constant value), or a yoVariable by setting it to either {@link YoVariable#getFullNameString()}
+ * or {@link YoVariable#getName()} (note that the former is preferable to account for non-uniqueness
+ * of yoVariable names), SCS2 then parses the field accordingly. This makes
+ * {@link YoGraphicDefinition} easier to serialize, save to file, and makes them thread-safe as no
+ * state is actually held.
+ *
+ * - Graphic handling:
+ *
+ * - SCS1 yoGraphics are queried regularly by the simulation thread to update their state such
+ * that the actual graphic can be updated. This is a non-trivial operation as yoGraphics often are
+ * created by a controller that runs on a different thread than the simulation thread, and they
+ * carry a state that is used by both the controller and simulation. To make things worse,
+ * {@link us.ihmc.graphicsDescription.plotting.artifact.Artifact} also implement the rendering.
+ *
- Because SCS2 yoGraphics do not actually carry any state, there is no such issue. This comes
+ * as the cost of making it way harder if not to say impossible to hack things around from the user
+ * side (outside SCS2 codebase). This often prevents implementing a workaround to a missing feature.
+ *
+ * - YoGraphics propagation to the GUI:
+ *
+ * - With SCS1 yoGraphics the typical workflow is: create a new registry
+ * {@link us.ihmc.graphicsDescription.yoGraphics.YoGraphicsListRegistry} in the main class where SCS is created, pass it down to the
+ * controller and any module running with the controller such that they can all create and register
+ * their {@link us.ihmc.graphicsDescription.yoGraphics.YoGraphic}/{@link us.ihmc.graphicsDescription.plotting.artifact.Artifact} to the registry, finally register the registry to SCS1
+ * or a {@code YoVariableServer}. In the case where a multithread controller is used, then 1
+ * registry per thread must be created and it should not be shared through threads.
+ *
- With SCS2 yoGraphics the intended workflow is: each class needing yoGraphics to be visualized
+ * should declare a getter that creates and returns {@code YoGraphicDefinition}s, the calling class
+ * then collects these yoGraphics and the yoGraphics of other classes it manages, and so on such
+ * that the yoGraphics can bubble all the way up to where the simulation is created. The intent
+ * behind that bubble up approach vs bubble down used for SCS1, is to reduce the number of
+ * constructor arguments and let classes higher in the hierarchy decide which yoGraphic to
+ * visualize.
+ *
+ * - Separation layer between yoGraphics and GUI rendering:
+ *
+ * - In SCS1, the yoGraphics are quite tightly connected to the rendered objects, so much that for
+ * {@link us.ihmc.graphicsDescription.plotting.artifact.Artifact}s the rendering actually happens inside the artifact class. This allows, when
+ * running simulation locally, for a certain scope of changes done on the yoGraphic to be reflected
+ * in the GUI even if the change is not reflected through the change in value of any yoVariable.
+ *
- In SCS2, the yoGraphics are only used at the initialization phase of the session as templates
+ * to create the graphical objects. Consequently, any changes done to a yoGraphic at runtime will
+ * not be reflected in the GUI.
+ *
+ *
+ *
+ *
+ * @author Sylvain Bertrand
+ */
+public interface SCS2YoGraphicHolder
+{
+ /**
+ * The intended implementation for this method is:
+ *
+ * - to create and return the yoGraphics to be visualized,
+ *
- to collect and return the yoGraphics from the classes managed by the class.
+ *
+ *
+ * Useful notes:
+ *
+ * - Use {@link YoGraphicGroupDefinition} to gather multiple yoGraphics and other groups into a
+ * single {@link YoGraphicDefinition}. The group will appear as a named registry in the SCS GUI.
+ * Including the name of the class in the group being created helps locating yoGraphics in the code.
+ *
- Use {@link YoGraphicListDefinition} if you do not want to create a group but still need to
+ * gather multiple yoGraphics into a single {@link YoGraphicDefinition}.
+ *
- Some helper classes:
+ *
+ * - {@link YoGraphicDefinitionFactory}: gather convenience methods to create
+ * {@link YoGraphicDefinition}s and other types needed to create yoGraphic.
+ *
- {@link us.ihmc.graphicsDescription.conversion.YoGraphicConversionTools}: for conversion tools between SCS1 and SCS2.
+ *
- {@link SCS2DefinitionTools}: for implementing that method that should have been
+ * implemented somewhere in {@code scs2-definition}.
+ *
+ *
+ *
+ *
+ * @return the yoGraphics to be visualized in the SCS GUI.
+ */
+ YoGraphicDefinition getSCS2YoGraphics();
+}
diff --git a/scs2-session-visualizer-jfx/build.gradle.kts b/scs2-session-visualizer-jfx/build.gradle.kts
index 88cbd6c2..e47ed48c 100644
--- a/scs2-session-visualizer-jfx/build.gradle.kts
+++ b/scs2-session-visualizer-jfx/build.gradle.kts
@@ -27,9 +27,9 @@ mainDependencies {
api(ihmc.javaFXModule("fxml", javaFXVersion))
api(ihmc.javaFXModule("swing", javaFXVersion))
- api("us.ihmc:euclid:0.21.0")
- api("us.ihmc:euclid-shape:0.21.0")
- api("us.ihmc:euclid-frame:0.21.0")
+ api("us.ihmc:euclid:0.22.2")
+ api("us.ihmc:euclid-shape:0.22.2")
+ api("us.ihmc:euclid-frame:0.22.2")
api("us.ihmc:ihmc-graphics-description:0.25.1")
api("us.ihmc:ihmc-video-codecs:2.1.6")
api("us.ihmc:ihmc-javafx-extensions:17-0.2.1")
@@ -218,4 +218,4 @@ fun addVSyncLinuxHackForJavaFXApp(sourceFolder: String, javafxappname: String)
launchScriptFile.delete()
launchScriptFile.writeText(originalScript)
-}
\ No newline at end of file
+}
diff --git a/scs2-shared-memory/build.gradle.kts b/scs2-shared-memory/build.gradle.kts
index 3da76831..07bbe49d 100644
--- a/scs2-shared-memory/build.gradle.kts
+++ b/scs2-shared-memory/build.gradle.kts
@@ -12,9 +12,9 @@ ihmc {
mainDependencies {
api("us.ihmc:scs2-definition:source")
- api("us.ihmc:euclid:0.21.0")
- api("us.ihmc:euclid-frame:0.21.0")
- api("us.ihmc:ihmc-yovariables:0.12.2")
+ api("us.ihmc:euclid:0.22.2")
+ api("us.ihmc:euclid-frame:0.22.2")
+ api("us.ihmc:ihmc-yovariables:0.13.3")
api("us.hebi.matlab.mat:mfl-core:0.5.7")
}
diff --git a/scs2-simulation/build.gradle.kts b/scs2-simulation/build.gradle.kts
index 72f61fbb..905bd784 100644
--- a/scs2-simulation/build.gradle.kts
+++ b/scs2-simulation/build.gradle.kts
@@ -14,9 +14,9 @@ mainDependencies {
api("us.ihmc:scs2-definition:source")
api("us.ihmc:scs2-shared-memory:source")
api("us.ihmc:scs2-session:source")
- api("us.ihmc:euclid-frame-shape:0.21.0")
+ api("us.ihmc:euclid-frame-shape:0.22.2")
api("us.ihmc:ihmc-messager:0.2.0")
- api("us.ihmc:mecano-yovariables:17-0.18.1")
+ api("us.ihmc:mecano-yovariables:17-0.19.0")
}
testDependencies {
diff --git a/scs2-symbolic/build.gradle.kts b/scs2-symbolic/build.gradle.kts
index a6823339..48bf49e8 100644
--- a/scs2-symbolic/build.gradle.kts
+++ b/scs2-symbolic/build.gradle.kts
@@ -14,9 +14,9 @@ mainDependencies {
api("us.ihmc:scs2-definition:source")
api("us.ihmc:scs2-shared-memory:source")
- api("us.ihmc:euclid:0.21.0")
- api("us.ihmc:euclid-frame:0.21.0")
- api("us.ihmc:ihmc-yovariables:0.12.2")
+ api("us.ihmc:euclid:0.22.2")
+ api("us.ihmc:euclid-frame:0.22.2")
+ api("us.ihmc:ihmc-yovariables:0.13.3")
}
testDependencies {