public IEnumerator EnsureChangesToUXMLMadeExternallyAreReloaded() { const string testLabelName = "externally-added-label"; CreateTestUXMLFile(); yield return(LoadTestUXMLDocument(k_TestUXMLFilePath)); var assetCount = builder.document.visualTreeAsset.visualElementAssets.Count; yield return(AddTextFieldElement()); Assert.AreEqual(assetCount + 1, builder.document.visualTreeAsset.visualElementAssets.Count); // Save builder.document.SaveUnsavedChanges(k_TestUXMLFilePath, false); var vtaCopy = builder.document.visualTreeAsset.DeepCopy(); var newElement = new VisualElementAsset(typeof(Label).ToString()); VisualTreeAssetUtilities.InitializeElement(newElement); newElement.AddProperty("name", testLabelName); vtaCopy.AddElement(vtaCopy.GetRootUXMLElement(), newElement); var vtaCopyUXML = vtaCopy.GenerateUXML(k_TestUXMLFilePath, true); File.WriteAllText(k_TestUXMLFilePath, vtaCopyUXML); AssetDatabase.ImportAsset(k_TestUXMLFilePath, ImportAssetOptions.ForceUpdate); yield return(UIETestHelpers.Pause(1)); // Make sure the UI Builder reloaded. var label = builder.documentRootElement.Q <Label>(testLabelName); Assert.NotNull(label); }
internal static VisualElementAsset AddElement( this VisualTreeAsset vta, VisualElementAsset parent, VisualElement visualElement, int index = -1) { var fullTypeName = visualElement.GetType().ToString(); var vea = new VisualElementAsset(fullTypeName); VisualTreeAssetUtilities.InitializeElement(vea); visualElement.SetProperty(BuilderConstants.ElementLinkedVisualElementAssetVEPropertyName, vea); visualElement.SetProperty(BuilderConstants.ElementLinkedBelongingVisualTreeAssetVEPropertyName, vta); var overriddenAttributes = visualElement.GetOverriddenAttributes(); foreach (var attribute in overriddenAttributes) vea.AddProperty(attribute.Key, attribute.Value); return VisualTreeAssetUtilities.AddElementToDocument(vta, vea, parent); }
bool ParseAttributes(XElement elt, VisualElementAsset res, VisualTreeAsset vta, VisualElementAsset parent) { bool startedRule = false; foreach (XAttribute xattr in elt.Attributes()) { string attrName = xattr.Name.LocalName; // start with special cases switch (attrName) { case "class": res.AddProperty(xattr.Name.LocalName, xattr.Value); res.classes = xattr.Value.Split(' '); continue; case "content-container": case "contentContainer": res.AddProperty(xattr.Name.LocalName, xattr.Value); if (attrName == "contentContainer") { } if (vta.contentContainerId != 0) { logger.LogError(ImportErrorType.Semantic, ImportErrorCode.DuplicateContentContainer, null, Error.Level.Fatal, elt); continue; } vta.contentContainerId = res.id; continue; case k_SlotDefinitionAttr: logger.LogError(ImportErrorType.Syntax, ImportErrorCode.SlotsAreExperimental, null, Error.Level.Warning, elt); if (String.IsNullOrEmpty(xattr.Value)) { logger.LogError(ImportErrorType.Semantic, ImportErrorCode.SlotDefinitionHasEmptyName, null, Error.Level.Fatal, elt); } else if (!vta.AddSlotDefinition(xattr.Value, res.id)) { logger.LogError(ImportErrorType.Semantic, ImportErrorCode.DuplicateSlotDefinition, xattr.Value, Error.Level.Fatal, elt); } continue; case k_SlotUsageAttr: logger.LogError(ImportErrorType.Syntax, ImportErrorCode.SlotsAreExperimental, null, Error.Level.Warning, elt); var templateAsset = parent as TemplateAsset; if (templateAsset == null) { logger.LogError(ImportErrorType.Semantic, ImportErrorCode.SlotUsageInNonTemplate, parent, Error.Level.Fatal, elt); continue; } if (string.IsNullOrEmpty(xattr.Value)) { logger.LogError(ImportErrorType.Semantic, ImportErrorCode.SlotUsageHasEmptyName, null, Error.Level.Fatal, elt); continue; } templateAsset.AddSlotUsage(xattr.Value, res.id); continue; case "style": res.AddProperty(xattr.Name.LocalName, xattr.Value); ExCSS.StyleSheet parsed = new Parser().Parse("* { " + xattr.Value + " }"); if (parsed.Errors.Count != 0) { logger.LogError( ImportErrorType.Semantic, ImportErrorCode.InvalidCssInStyleAttribute, parsed.Errors.Aggregate("", (s, error) => s + error.ToString() + "\n"), Error.Level.Warning, xattr); continue; } if (parsed.StyleRules.Count != 1) { logger.LogError( ImportErrorType.Semantic, ImportErrorCode.InvalidCssInStyleAttribute, "Expected one style rule, found " + parsed.StyleRules.Count, Error.Level.Warning, xattr); continue; } m_Builder.BeginRule(-1); startedRule = true; foreach (Property prop in parsed.StyleRules[0].Declarations) { m_Builder.BeginProperty(prop.Name); VisitValue(prop.Term); m_Builder.EndProperty(); } // Don't call m_Builder.EndRule() here, it's done in LoadXml to get the rule index at the same time ! continue; } res.AddProperty(xattr.Name.LocalName, xattr.Value); } return(startedRule); }
public static void SetAttributeValue(this VisualElementAsset vea, string attributeName, string attributeValue) { vea.AddProperty(attributeName, attributeValue); }
private static bool ParseAttributes(XElement elt, VisualElementAsset res, StyleSheetBuilder ssb, VisualTreeAsset vta, VisualElementAsset parent) { // underscore means "unnamed element but it would not look pretty in the project window without one" res.name = "_" + res.GetType().Name; bool startedRule = false; foreach (XAttribute xattr in elt.Attributes()) { string attrName = xattr.Name.LocalName; // start with special cases switch (attrName) { case "name": res.name = xattr.Value; continue; case "text": res.text = xattr.Value; continue; case "class": res.classes = xattr.Value.Split(' '); continue; case "contentContainer": if (vta.contentContainerId != 0) { logger.LogError(ImportErrorType.Semantic, ImportErrorCode.DuplicateContentContainer, null, Error.Level.Fatal, elt); continue; } vta.contentContainerId = res.id; continue; case k_SlotDefinitionAttr: if (String.IsNullOrEmpty(xattr.Value)) { logger.LogError(ImportErrorType.Semantic, ImportErrorCode.SlotDefinitionHasEmptyName, null, Error.Level.Fatal, elt); } else if (!vta.AddSlotDefinition(xattr.Value, res.id)) { logger.LogError(ImportErrorType.Semantic, ImportErrorCode.DuplicateSlotDefinition, xattr.Value, Error.Level.Fatal, elt); } continue; case k_SlotUsageAttr: var templateAsset = parent as TemplateAsset; if (!(templateAsset != null)) { logger.LogError(ImportErrorType.Semantic, ImportErrorCode.SlotUsageInNonTemplate, parent, Error.Level.Fatal, elt); continue; } if (string.IsNullOrEmpty(xattr.Value)) { logger.LogError(ImportErrorType.Semantic, ImportErrorCode.SlotUsageHasEmptyName, null, Error.Level.Fatal, elt); continue; } templateAsset.AddSlotUsage(xattr.Value, res.id); continue; case "style": ExCSS.StyleSheet parsed = new Parser().Parse("* { " + xattr.Value + " }"); if (parsed.Errors.Count != 0) { logger.LogError( ImportErrorType.Semantic, ImportErrorCode.InvalidCssInStyleAttribute, parsed.Errors.Aggregate("", (s, error) => s + error.ToString() + "\n"), Error.Level.Warning, xattr); continue; } if (parsed.StyleRules.Count != 1) { logger.LogError( ImportErrorType.Semantic, ImportErrorCode.InvalidCssInStyleAttribute, "Expected one style rule, found " + parsed.StyleRules.Count, Error.Level.Warning, xattr); continue; } ssb.BeginRule(-1); startedRule = true; StyleSheetImportErrors errors = new StyleSheetImportErrors(); foreach (Property prop in parsed.StyleRules[0].Declarations) { ssb.BeginProperty(prop.Name); StyleSheetImporterImpl.VisitValue(errors, ssb, prop.Term); ssb.EndProperty(); } // Don't call ssb.EndRule() here, it's done in LoadXml to get the rule index at the same time ! continue; case "pickingMode": if (!Enum.IsDefined(typeof(PickingMode), xattr.Value)) { Debug.LogErrorFormat("Could not parse value of '{0}', because it isn't defined in the PickingMode enum.", xattr.Value); continue; } res.pickingMode = (PickingMode)Enum.Parse(typeof(PickingMode), xattr.Value); continue; } res.AddProperty(xattr.Name.LocalName, xattr.Value); } return(startedRule); }
private static bool ParseAttributes(XElement elt, VisualElementAsset res, StyleSheetBuilder ssb, VisualTreeAsset vta, VisualElementAsset parent) { res.name = "_" + res.GetType().Name; bool result = false; foreach (XAttribute current in elt.Attributes()) { string localName = current.Name.LocalName; switch (localName) { case "name": res.name = current.Value; continue; case "text": res.text = current.Value; continue; case "class": res.classes = current.Value.Split(new char[] { ' ' }); continue; case "contentContainer": if (vta.contentContainerId != 0) { UIElementsViewImporter.logger.LogError(ImportErrorType.Semantic, ImportErrorCode.DuplicateContentContainer, null, UIElementsViewImporter.Error.Level.Fatal, elt); continue; } vta.contentContainerId = res.id; continue; case "slot-name": if (string.IsNullOrEmpty(current.Value)) { UIElementsViewImporter.logger.LogError(ImportErrorType.Semantic, ImportErrorCode.SlotDefinitionHasEmptyName, null, UIElementsViewImporter.Error.Level.Fatal, elt); } else if (!vta.AddSlotDefinition(current.Value, res.id)) { UIElementsViewImporter.logger.LogError(ImportErrorType.Semantic, ImportErrorCode.DuplicateSlotDefinition, current.Value, UIElementsViewImporter.Error.Level.Fatal, elt); } continue; case "slot": { TemplateAsset templateAsset = parent as TemplateAsset; if (templateAsset == null) { UIElementsViewImporter.logger.LogError(ImportErrorType.Semantic, ImportErrorCode.SlotUsageInNonTemplate, parent, UIElementsViewImporter.Error.Level.Fatal, elt); continue; } if (string.IsNullOrEmpty(current.Value)) { UIElementsViewImporter.logger.LogError(ImportErrorType.Semantic, ImportErrorCode.SlotUsageHasEmptyName, null, UIElementsViewImporter.Error.Level.Fatal, elt); continue; } templateAsset.AddSlotUsage(current.Value, res.id); continue; } case "style": { StyleSheet styleSheet = new Parser().Parse("* { " + current.Value + " }"); if (styleSheet.Errors.Count != 0) { UIElementsViewImporter.logger.LogError(ImportErrorType.Semantic, ImportErrorCode.InvalidCssInStyleAttribute, styleSheet.Errors.Aggregate("", (string s, StylesheetParseError error) => s + error.ToString() + "\n"), UIElementsViewImporter.Error.Level.Warning, current); continue; } if (styleSheet.StyleRules.Count != 1) { UIElementsViewImporter.logger.LogError(ImportErrorType.Semantic, ImportErrorCode.InvalidCssInStyleAttribute, "Expected one style rule, found " + styleSheet.StyleRules.Count, UIElementsViewImporter.Error.Level.Warning, current); continue; } ssb.BeginRule(-1); result = true; StyleSheetImportErrors errors = new StyleSheetImportErrors(); foreach (Property current2 in styleSheet.StyleRules[0].Declarations) { ssb.BeginProperty(current2.Name); StyleSheetImporterImpl.VisitValue(errors, ssb, current2.Term); ssb.EndProperty(); } continue; } case "pickingMode": if (!Enum.IsDefined(typeof(PickingMode), current.Value)) { Debug.LogErrorFormat("Could not parse value of '{0}', because it isn't defined in the PickingMode enum.", new object[] { current.Value }); continue; } res.pickingMode = (PickingMode)Enum.Parse(typeof(PickingMode), current.Value); continue; } res.AddProperty(current.Name.LocalName, current.Value); } return(result); }