diff --git a/Assets/SEE/Controls/Actions/ShowLabel.cs b/Assets/SEE/Controls/Actions/ShowLabel.cs index 94e773a985..0aba08e383 100644 --- a/Assets/SEE/Controls/Actions/ShowLabel.cs +++ b/Assets/SEE/Controls/Actions/ShowLabel.cs @@ -181,9 +181,12 @@ private void On() /// private void Off() { - LabelAttributes settings = GetLabelSettings(nodeOperator.Node, nodeOperator.City); - nodeOperator.FadeLabel(0f, settings.AnimationFactor); - DisplayedLabelOperators.Remove(nodeOperator); + if (nodeOperator.Node != null) + { + LabelAttributes settings = GetLabelSettings(nodeOperator.Node, nodeOperator.City); + nodeOperator.FadeLabel(0f, settings.AnimationFactor); + DisplayedLabelOperators.Remove(nodeOperator); + } } /// diff --git a/Assets/SEE/Game/HolisticMetrics/WidgetsManager.cs b/Assets/SEE/Game/HolisticMetrics/WidgetsManager.cs index d5d5225751..e434f5f7eb 100644 --- a/Assets/SEE/Game/HolisticMetrics/WidgetsManager.cs +++ b/Assets/SEE/Game/HolisticMetrics/WidgetsManager.cs @@ -155,8 +155,8 @@ internal void Create(WidgetConfig widgetConfiguration) { ShowNotification.Error("Metric-board error", "There was an error when displaying the metric on the newly created " - + $"widget, this is the exception: {exception.Message}"); - throw exception; + + $"widget, this is the exception: {exception.Message}", log: false); + throw; } } } diff --git a/Assets/SEE/Game/LabelAttributes.cs b/Assets/SEE/Game/LabelAttributes.cs index 39261f966f..f4c9f1ca8d 100644 --- a/Assets/SEE/Game/LabelAttributes.cs +++ b/Assets/SEE/Game/LabelAttributes.cs @@ -14,6 +14,16 @@ namespace SEE.Game [HideReferenceObjectPicker] public class LabelAttributes { + /// + /// The default value for . + /// + public const float DEFAULT_FONT_SIZE = 0.4f; + + /// + /// The default value for . + /// + public const float DEFAULT_DISTANCE = 0.2f; + /// /// If true, a label with the node's SourceName will be displayed above each node. /// @@ -24,13 +34,13 @@ public class LabelAttributes /// The distance between the top of the node and its label. /// [Tooltip("The distance between the top of the node and its label.")] - public float Distance = 0.2f; + public float Distance = DEFAULT_DISTANCE; /// /// The font size of the node's label. /// [Tooltip("The font size of the label.")] - public float FontSize = 0.4f; + public float FontSize = DEFAULT_FONT_SIZE; /// /// How fast the label should (dis)appear. @@ -90,4 +100,4 @@ internal void Restore(Dictionary attributes, string label) } } } -} \ No newline at end of file +} diff --git a/Assets/SEE/Game/Operator/LabelOperator.cs b/Assets/SEE/Game/Operator/LabelOperator.cs index a3210735ca..fbffda5c79 100644 --- a/Assets/SEE/Game/Operator/LabelOperator.cs +++ b/Assets/SEE/Game/Operator/LabelOperator.cs @@ -60,7 +60,7 @@ private void PrepareLabel() Color textColor = UnityEngine.Color.white; Color lineColor = UnityEngine.Color.white; - string shownText = Node.SourceName; + string shownText = Node?.SourceName ?? gameObject.name; nodeLabel = transform.Find(labelPrefix + shownText)?.gameObject; if (nodeLabel == null) @@ -71,9 +71,10 @@ private void PrepareLabel() // First we create the label. // We define starting and ending positions for the animation. Vector3 startLabelPosition = gameObject.GetTop(); + float fontSize = Node != null ? City.NodeTypes[Node.Type].LabelSettings.FontSize : LabelAttributes.DEFAULT_FONT_SIZE; nodeLabel = TextFactory.GetTextWithSize(shownText, startLabelPosition, - City.NodeTypes[Node.Type].LabelSettings.FontSize, + fontSize, lift: true, textColor: textColor); nodeLabel.name = labelPrefix + shownText; @@ -132,7 +133,7 @@ private Vector3 DesiredLabelTextPosition if (labelAlpha.TargetValue > 0) { // Only put line and label up if the label should actually be shown. - endLabelPosition.y += City.NodeTypes[Node.Type].LabelSettings.Distance; + endLabelPosition.y += Node != null ? City.NodeTypes[Node.Type].LabelSettings.Distance : LabelAttributes.DEFAULT_DISTANCE; } return endLabelPosition; @@ -185,4 +186,4 @@ private Vector3 DesiredLabelEndLinePosition nodeLabel.transform.DOMove(position, duration).Play() }; } -} \ No newline at end of file +} diff --git a/Assets/SEE/Game/Operator/NodeOperator.cs b/Assets/SEE/Game/Operator/NodeOperator.cs index 4d6f94f33f..27b4b991ba 100644 --- a/Assets/SEE/Game/Operator/NodeOperator.cs +++ b/Assets/SEE/Game/Operator/NodeOperator.cs @@ -78,6 +78,8 @@ public partial class NodeOperator : GraphElementOperator /// /// The node to which this node operator belongs. + /// + /// Be aware that this may be null if the node operator is attached to an artificial node. /// public Node Node { @@ -461,7 +463,8 @@ Tween[] BlinkAction(int count, float duration) static Node GetNode(GameObject gameObject) { - if (!gameObject.TryGetComponent(out NodeRef nodeRef) || nodeRef.Value == null) + // We allow a null value for artificial nodes, but at least a NodeRef must be attached. + if (!gameObject.TryGetComponent(out NodeRef nodeRef)) { throw new InvalidOperationException($"NodeOperator-operated object {gameObject.FullName()} must have {nameof(NodeRef)} attached!"); } @@ -525,4 +528,4 @@ private void Update() } } } -} \ No newline at end of file +}