public override VisualElement CreatePropertyGUI(SerializedProperty property) { var container = new VisualElement(); var keyProperty = property.FindPropertyRelative("key"); var targetProperty = keyProperty.FindPropertyRelative("target"); var itemContainer = new PropertyField(property.FindPropertyRelative("item")); var component = (Component)property.serializedObject.targetObject; var scene = component.gameObject.scene; var isInScene = scene.name != null && !EditorSceneManager.IsPreviewScene(scene); var messageType = isInScene ? MessageType.Error : MessageType.Warning; var localPlayerHelpBox = new IMGUIContainer(() => EditorGUILayout.HelpBox(LocalPlayerGimmickValidation.ErrorMessage, messageType)); void SwitchDisplayItem(GimmickTarget target) { itemContainer.SetVisibility(target == GimmickTarget.Item); localPlayerHelpBox.SetVisibility(!LocalPlayerGimmickValidation.IsValid(target, component)); } SwitchDisplayItem((GimmickTarget)targetProperty.enumValueIndex); var targetField = EnumField.Create( targetProperty.displayName, targetProperty, LocalPlayerGimmickValidation.IsLocalizable(component) ? LocalizableSelectables : ConsistentlySyncSelectables, (GimmickTarget)targetProperty.enumValueIndex, FormatTarget, SwitchDisplayItem); var keyField = new PropertyField(keyProperty.FindPropertyRelative("key")); container.Add(localPlayerHelpBox); container.Add(targetField); container.Add(keyField); container.Add(itemContainer); return(container); }
static VisualElement CreateConstantValuePropertyGUI(SerializedProperty property) { Assert.AreEqual(property.type, nameof(ConstantValue)); var container = new VisualElement { style = { flexDirection = new StyleEnum <FlexDirection>(FlexDirection.Row), flexGrow = new StyleFloat(9) } }; var boolValueProperty = property.FindPropertyRelative("boolValue"); Assert.AreEqual(boolValueProperty.propertyType, SerializedPropertyType.Boolean); var boolValueField = new Toggle { bindingPath = boolValueProperty.propertyPath, style = { flexGrow = new StyleFloat(9) } }; boolValueField.Bind(boolValueProperty.serializedObject); container.Add(boolValueField); var floatValueProperty = property.FindPropertyRelative("floatValue"); Assert.AreEqual(floatValueProperty.propertyType, SerializedPropertyType.Float); var floatValueField = new FloatField { bindingPath = floatValueProperty.propertyPath, style = { flexGrow = new StyleFloat(9) } }; floatValueField.Bind(floatValueProperty.serializedObject); container.Add(floatValueField); var integerValueProperty = property.FindPropertyRelative("integerValue"); Assert.AreEqual(integerValueProperty.propertyType, SerializedPropertyType.Integer); var integerValueField = new IntegerField { bindingPath = integerValueProperty.propertyPath, style = { flexGrow = new StyleFloat(9) } }; integerValueField.Bind(integerValueProperty.serializedObject); container.Add(integerValueField); var typeProperty = property.FindPropertyRelative("type"); var typeChoices = new List <ParameterType> { ParameterType.Bool, ParameterType.Float, ParameterType.Integer }; var currentType = (ParameterType)typeProperty.intValue; var selectingTarget = typeChoices.Contains(currentType) ? currentType : typeChoices[0]; var typeField = EnumField.Create(typeProperty, typeChoices, selectingTarget, SwitchField); container.Insert(0, typeField); void SwitchField(ParameterType type) { boolValueField.SetVisibility(type == ParameterType.Bool); floatValueField.SetVisibility(type == ParameterType.Float); integerValueField.SetVisibility(type == ParameterType.Integer); } SwitchField(selectingTarget); return(container); }
static VisualElement CreateExpressionPropertyGUI(SerializedProperty property, List <GimmickTarget> targetChoices, Func <GimmickTarget, string> formatTarget, int depth = 0) { Assert.AreEqual(property.type, nameof(Expression)); var container = new VisualElement { style = { marginLeft = new StyleLength(5) } }; var valueProperty = property.FindPropertyRelative("value"); var valueField = CreateValuePropertyGUI(valueProperty, targetChoices, formatTarget); container.Add(valueField); if (depth > 0) { return(container); } valueField.style.marginLeft = new StyleLength(5); var typeProperty = property.FindPropertyRelative("type"); var currentType = (ExpressionType)typeProperty.intValue; var operatorExpressionProperty = property.FindPropertyRelative("operatorExpression"); var operatorProperty = operatorExpressionProperty.FindPropertyRelative("operator"); var currentOperator = (Operator)operatorProperty.intValue; var operandsProperty = operatorExpressionProperty.FindPropertyRelative("operands"); var operandsContainer = new VisualElement(); container.Add(operandsContainer); const int ExpressionTypeValue = -1; var typeOperatorChoices = Enum.GetValues(typeof(Operator)).Cast <int>().Prepend(ExpressionTypeValue).ToList(); var typeOperatorDefaultIndex = typeOperatorChoices.IndexOf(currentType == ExpressionType.Value ? ExpressionTypeValue : (int)currentOperator); var typeOperatorField = new PopupField <int>(typeOperatorChoices, typeOperatorDefaultIndex, TypeOperatorFormat, TypeOperatorFormat); string TypeOperatorFormat(int value) { return(value == ExpressionTypeValue ? "=" : $"= {(Operator) value}"); } typeOperatorField.RegisterValueChangedCallback(e => { var type = e.newValue == ExpressionTypeValue ? ExpressionType.Value : ExpressionType.OperatorExpression; if (typeProperty.intValue != (int)type) { typeProperty.intValue = (int)type; typeProperty.serializedObject.ApplyModifiedProperties(); var operandsFirstProperty = operandsProperty.GetArrayElementAtIndex(0); switch (type) { case ExpressionType.Value: if (operandsFirstProperty != null) { CopyValueProperty(operandsFirstProperty.FindPropertyRelative("value"), valueProperty); } break; case ExpressionType.OperatorExpression: if (operandsFirstProperty == null) { operandsProperty.InsertArrayElementAtIndex(0); } CopyValueProperty(valueProperty, operandsFirstProperty.FindPropertyRelative("value")); break; } #if !UNITY_2019_3_OR_NEWER OnTypeChanged(type); #endif } if (type == ExpressionType.OperatorExpression && operatorProperty.intValue != e.newValue) { operatorProperty.intValue = e.newValue; operatorProperty.serializedObject.ApplyModifiedProperties(); #if !UNITY_2019_3_OR_NEWER OnOperatorChanged((Operator)e.newValue); #endif } }); container.Insert(0, typeOperatorField); var typeField = EnumField.CreateAsStringPopupField <ExpressionType>(typeProperty, newValue => { typeOperatorField.SetValueWithoutNotify(newValue == ExpressionType.Value ? ExpressionTypeValue : operatorProperty.intValue); OnTypeChanged(newValue); }); typeField.style.display = new StyleEnum <DisplayStyle>(DisplayStyle.None); container.Add(typeField); var operatorField = EnumField.CreateAsStringPopupField <Operator>(operatorProperty, newValue => { typeOperatorField.SetValueWithoutNotify(typeProperty.intValue == (int)ExpressionType.Value ? ExpressionTypeValue : (int)newValue); OnOperatorChanged(newValue); }); operatorField.style.display = new StyleEnum <DisplayStyle>(DisplayStyle.None); container.Add(operatorField); void OnOperatorChanged(Operator @operator) { operandsContainer.Unbind(); operandsContainer.Clear(); var requiredLength = @operator.GetRequiredLength(); if (requiredLength != operandsProperty.arraySize) { operandsProperty.arraySize = requiredLength; operandsProperty.serializedObject.ApplyModifiedProperties(); } var operandsField = CreateOperandsPropertyGUI(operandsProperty, targetChoices, formatTarget, depth); operandsContainer.Add(operandsField); } OnOperatorChanged(currentOperator); void OnTypeChanged(ExpressionType type) { valueField.SetVisibility(type == ExpressionType.Value); operandsContainer.SetVisibility(type == ExpressionType.OperatorExpression); } OnTypeChanged(currentType); return(container); }