diff --git a/MainForm.cs b/MainForm.cs index c23e62a..c7701bb 100644 --- a/MainForm.cs +++ b/MainForm.cs @@ -636,70 +636,8 @@ namespace XSDDiagram ShowEnumerate(annotated); // Attributes enumeration - List listAttributes = new List(); - if (annotated is XMLSchema.element) - { - XMLSchema.element element = annotated as XMLSchema.element; + List listAttributes = DiagramHelpers.GetAnnotatedAttributes(this.schema, annotated, nameSpace); - if (element.Item is XMLSchema.complexType) - { - XMLSchema.complexType complexType = element.Item as XMLSchema.complexType; - listAttributes.AddRange(ShowAttributes(complexType, nameSpace)); - } - else if (element.type != null) - { - //XSDObject xsdObject = this.schema.ElementsByName[QualifiedNameToFullName("type", element.type)] as XSDObject; - //if (xsdObject != null) - XSDObject xsdObject; - if (this.schema.ElementsByName.TryGetValue(QualifiedNameToFullName("type", element.type), out xsdObject) && xsdObject != null) - { - XMLSchema.annotated annotatedElement = xsdObject.Tag as XMLSchema.annotated; - if (annotatedElement is XMLSchema.complexType) - { - XMLSchema.complexType complexType = annotatedElement as XMLSchema.complexType; - listAttributes.AddRange(ShowAttributes(complexType, nameSpace)); - } - else - { - } - } - else - { - } - } - else - { - } - } - else if (annotated is XMLSchema.complexType) - { - XMLSchema.complexType complexType = annotated as XMLSchema.complexType; - listAttributes.AddRange(ShowAttributes(complexType, nameSpace)); - } - //RC++ Original code - //else - //{ - //} - - //this.listViewAttributes.Items.Clear(); - //foreach (XSDAttribute attribute in listAttributes) - // this.listViewAttributes.Items.Add(new ListViewItem(new string[] { attribute.Name, attribute.Type, attribute.Use, attribute.DefaultValue })).Tag = attribute; - //RC-- - - //Adrian++ - //This part i modify - else if (annotated is XMLSchema.simpleType) - { - XMLSchema.attribute attr = new XMLSchema.attribute(); - XMLSchema.localSimpleType def = new XMLSchema.localSimpleType(); - def.Item = (annotated as XMLSchema.simpleType).Item; - attr.simpleType = def; - string type = ""; - if (def.Item is XMLSchema.restriction) type = (def.Item as XMLSchema.restriction).@base.Name; - XSDAttribute XSDattr = new XSDAttribute("filename", (annotated as XMLSchema.simpleType).name, "namespace", type, false, "", "", attr); - listAttributes.Add(XSDattr); - - } //This part i modify this.listViewAttributes.Items.Clear(); listAttributes.Reverse(); @@ -725,245 +663,6 @@ namespace XSDDiagram } } - private List ShowAttributes(XMLSchema.complexType complexType, string nameSpace) - { - List listAttributes = new List(); - ParseComplexTypeAttributes(nameSpace, listAttributes, complexType, false); - return listAttributes; - } - - private void ParseComplexTypeAttributes(string nameSpace, List listAttributes, XMLSchema.complexType complexType, bool isRestriction) - { - if (complexType.ItemsElementName != null) - { - for (int i = 0; i < complexType.ItemsElementName.Length; i++) - { - switch (complexType.ItemsElementName[i]) - { - case XMLSchema.ItemsChoiceType4.attribute: - { - XMLSchema.attribute attribute = complexType.Items[i] as XMLSchema.attribute; - ParseAttribute(nameSpace, listAttributes, attribute, false); - } - break; - case XMLSchema.ItemsChoiceType4.attributeGroup: - { - XMLSchema.attributeGroup attributeGroup = complexType.Items[i] as XMLSchema.attributeGroup; - ParseAttributeGroup(nameSpace, listAttributes, attributeGroup, false); - } - break; - case XMLSchema.ItemsChoiceType4.anyAttribute: - XMLSchema.wildcard wildcard = complexType.Items[i] as XMLSchema.wildcard; - XSDAttribute xsdAttribute = new XSDAttribute("", "*", wildcard.@namespace, "", false, null, null, null); - listAttributes.Add(xsdAttribute); - break; - case XMLSchema.ItemsChoiceType4.simpleContent: - case XMLSchema.ItemsChoiceType4.complexContent: - XMLSchema.annotated annotatedContent = null; - if (complexType.Items[i] is XMLSchema.complexContent) - { - XMLSchema.complexContent complexContent = complexType.Items[i] as XMLSchema.complexContent; - annotatedContent = complexContent.Item; - } - else if (complexType.Items[i] is XMLSchema.simpleContent) - { - XMLSchema.simpleContent simpleContent = complexType.Items[i] as XMLSchema.simpleContent; - annotatedContent = simpleContent.Item; - } - if (annotatedContent is XMLSchema.extensionType) - { - XMLSchema.extensionType extensionType = annotatedContent as XMLSchema.extensionType; - //XSDObject xsdExtensionType = this.schema.ElementsByName[QualifiedNameToFullName("type", extensionType.@base)] as XSDObject; - //if (xsdExtensionType != null) - XSDObject xsdExtensionType; - if (this.schema.ElementsByName.TryGetValue(QualifiedNameToFullName("type", extensionType.@base), out xsdExtensionType) && xsdExtensionType != null) - { - XMLSchema.annotated annotatedExtension = xsdExtensionType.Tag as XMLSchema.annotated; - if (annotatedExtension != null) - { - if (annotatedExtension is XMLSchema.complexType) - ParseComplexTypeAttributes(extensionType.@base.Namespace, listAttributes, annotatedExtension as XMLSchema.complexType, false); - } - } - if (extensionType.Items != null) - { - foreach (XMLSchema.annotated annotated in extensionType.Items) - { - if (annotated is XMLSchema.attribute) - { - ParseAttribute(nameSpace, listAttributes, annotated as XMLSchema.attribute, false); - } - else if (annotated is XMLSchema.attributeGroup) - { - ParseAttributeGroup(nameSpace, listAttributes, annotated as XMLSchema.attributeGroup, false); - } - } - } - } - else if (annotatedContent is XMLSchema.restrictionType) - { - XMLSchema.restrictionType restrictionType = annotatedContent as XMLSchema.restrictionType; - //XSDObject xsdRestrictionType = this.schema.ElementsByName[QualifiedNameToFullName("type", restrictionType.@base)] as XSDObject; - //if (xsdRestrictionType != null) - XSDObject xsdRestrictionType; - if (this.schema.ElementsByName.TryGetValue(QualifiedNameToFullName("type", restrictionType.@base), out xsdRestrictionType) && xsdRestrictionType != null) - { - XMLSchema.annotated annotatedRestriction = xsdRestrictionType.Tag as XMLSchema.annotated; - if (annotatedRestriction != null) - { - if (annotatedRestriction is XMLSchema.complexType) - ParseComplexTypeAttributes(restrictionType.@base.Namespace, listAttributes, annotatedRestriction as XMLSchema.complexType, false); - } - } - if (restrictionType.Items1 != null) - { - foreach (XMLSchema.annotated annotated in restrictionType.Items1) - { - if (annotated is XMLSchema.attribute) - { - ParseAttribute(nameSpace, listAttributes, annotated as XMLSchema.attribute, true); - } - else if (annotated is XMLSchema.attributeGroup) - { - ParseAttributeGroup(nameSpace, listAttributes, annotated as XMLSchema.attributeGroup, true); - } - } - } - } - break; - } - } - } - else - { - } - } - - private XSDAttribute ParseAttribute(string nameSpace, List listAttributes, XMLSchema.attribute attribute, bool isRestriction) - { - bool isReference = false; - string filename = ""; - string name = attribute.name; - string type = ""; - if (attribute.@ref != null) - { - object o = null; - this.schema.AttributesByName.TryGetValue(QualifiedNameToFullName("attribute", attribute.@ref), out o); - if (o is XSDAttribute) - { - XSDAttribute xsdAttributeInstance = o as XSDAttribute; - XSDAttribute refXSDAttribute = ParseAttribute(nameSpace, listAttributes, xsdAttributeInstance.Tag, isRestriction); - if(refXSDAttribute != null) - { - // Override the "use" field with - refXSDAttribute.Use = attribute.use.ToString(); - } - return null; - } - else // Reference not found! - { - type = QualifiedNameToAttributeTypeName(attribute.@ref); - name = attribute.@ref.Name; - nameSpace = attribute.@ref.Namespace; - isReference = true; - } - } - else if (attribute.type != null) - { - type = QualifiedNameToAttributeTypeName(attribute.type); - nameSpace = attribute.type.Namespace; - } - else if (attribute.simpleType != null) - { - XMLSchema.simpleType simpleType = attribute.simpleType as XMLSchema.simpleType; - if (simpleType.Item is XMLSchema.restriction) - { - XMLSchema.restriction restriction = simpleType.Item as XMLSchema.restriction; - type = QualifiedNameToAttributeTypeName(restriction.@base); - nameSpace = restriction.@base.Namespace; - } - else if (simpleType.Item is XMLSchema.list) - { - XMLSchema.list list = simpleType.Item as XMLSchema.list; - type = QualifiedNameToAttributeTypeName(list.itemType); - nameSpace = list.itemType.Namespace; - } - else - { - } - } - else - { - - } - if (string.IsNullOrEmpty(attribute.name) && string.IsNullOrEmpty(name)) - { - } - if (isRestriction) - { - if (attribute.use == XMLSchema.attributeUse.prohibited) - { - foreach (XSDAttribute xsdAttribute in listAttributes) - { - if (xsdAttribute.Name == name) - { - //listAttributes.Remove(xsdAttribute); - xsdAttribute.Use = attribute.use.ToString(); - break; - } - } - } - } - else - { - XSDAttribute xsdAttribute = new XSDAttribute(filename, name, nameSpace, type, isReference, attribute.@default, attribute.use.ToString(), attribute); - listAttributes.Insert(0, xsdAttribute); - return xsdAttribute; - - } - return null; - } - - private void ParseAttributeGroup(string nameSpace, List listAttributes, XMLSchema.attributeGroup attributeGroup, bool isRestriction) - { - if (attributeGroup is XMLSchema.attributeGroupRef && attributeGroup.@ref != null) - { - object o = null; - this.schema.AttributesByName.TryGetValue(QualifiedNameToFullName("attributeGroup", attributeGroup.@ref), out o); - if (o is XSDAttributeGroup) - { - XSDAttributeGroup xsdAttributeGroup = o as XSDAttributeGroup; - XMLSchema.attributeGroup attributeGroupInstance = xsdAttributeGroup.Tag; - - foreach (XMLSchema.annotated annotated in attributeGroupInstance.Items) - { - if (annotated is XMLSchema.attribute) - { - ParseAttribute(nameSpace, listAttributes, annotated as XMLSchema.attribute, isRestriction); - } - else if (annotated is XMLSchema.attributeGroup) - { - ParseAttributeGroup(nameSpace, listAttributes, annotated as XMLSchema.attributeGroup, isRestriction); - } - } - } - } - else - { - - } - } - - private static string QualifiedNameToFullName(string type, System.Xml.XmlQualifiedName xmlQualifiedName) - { - return xmlQualifiedName.Namespace + ':' + type + ':' + xmlQualifiedName.Name; - } - - private static string QualifiedNameToAttributeTypeName(System.Xml.XmlQualifiedName xmlQualifiedName) - { - return xmlQualifiedName.Name + " : " + xmlQualifiedName.Namespace; - } - private void ShowEnumerate(XMLSchema.attribute attribute) { this.listViewEnumerate.Items.Clear(); @@ -971,10 +670,10 @@ namespace XSDDiagram { if (attribute.type != null) { - //XSDObject xsdObject = this.schema.ElementsByName[QualifiedNameToFullName("type", attribute.type)] as XSDObject; + //XSDObject xsdObject = this.schema.ElementsByName[DiagramHelpers.QualifiedNameToFullName("type", attribute.type)] as XSDObject; //if (xsdObject != null) XSDObject xsdObject; - if (this.schema.ElementsByName.TryGetValue(QualifiedNameToFullName("type", attribute.type), out xsdObject) && xsdObject != null) + if (this.schema.ElementsByName.TryGetValue(DiagramHelpers.QualifiedNameToFullName("type", attribute.type), out xsdObject) && xsdObject != null) { XMLSchema.annotated annotatedElement = xsdObject.Tag as XMLSchema.annotated; if (annotatedElement is XMLSchema.simpleType) @@ -997,10 +696,10 @@ namespace XSDDiagram XMLSchema.element element = annotated as XMLSchema.element; if (element != null && element.type != null) { - //XSDObject xsdObject = this.schema.ElementsByName[QualifiedNameToFullName("type", element.type)] as XSDObject; + //XSDObject xsdObject = this.schema.ElementsByName[DiagramHelpers.QualifiedNameToFullName("type", element.type)] as XSDObject; //if (xsdObject != null) XSDObject xsdObject; - if (this.schema.ElementsByName.TryGetValue(QualifiedNameToFullName("type", element.type), out xsdObject) && xsdObject != null) + if (this.schema.ElementsByName.TryGetValue(DiagramHelpers.QualifiedNameToFullName("type", element.type), out xsdObject) && xsdObject != null) { XMLSchema.annotated annotatedElement = xsdObject.Tag as XMLSchema.annotated; if (annotatedElement is XMLSchema.simpleType) @@ -1081,49 +780,37 @@ namespace XSDDiagram return; } - foreach (object o in annotation.Items) - { - if (o is XMLSchema.documentation) - { - XMLSchema.documentation documentation = o as XMLSchema.documentation; - if (documentation.Any != null && documentation.Any.Length > 0 && documentation.Any[0].Value != null) - { - string text = documentation.Any[0].Value; - text = text.Replace("\n", " "); - text = text.Replace("\t", " "); - text = text.Replace("\r", ""); - text = Regex.Replace(text, " +", " "); - text = text.Trim(); - - //text = text.Replace(, " "); - - //text = text.Trim('\n', '\t', '\r', ' '); - //string[] textLines = text.Split(new char[] { '\n' }); - //for (int i = 0; i < textLines.Length; i++) - // textLines[i] = textLines[i].Trim('\n', '\t', '\r', ' '); - //text = string.Join("\r\n", textLines); - this.textBoxAnnotation.Text = text; - this.textBoxAnnotation.Visible = true; - if (this.webBrowserDocumentation != null) - this.webBrowserDocumentation.Visible = false; - } - else if (documentation.source != null) - { + bool isWebDocumentation = false; + Uri uriResult; + foreach (object o in annotation.Items) + { + if (o is XMLSchema.documentation) + { + XMLSchema.documentation documentation = o as XMLSchema.documentation; + if (documentation.Any != null && documentation.Any.Length > 0 && documentation.Any[0].Value != null) + { + } + else if (documentation.source != null && Uri.TryCreate(documentation.source, UriKind.Absolute, out uriResult) && (uriResult.Scheme == Uri.UriSchemeHttp || uriResult.Scheme == Uri.UriSchemeHttps)) + { if (this.webBrowserDocumentation != null) { + isWebDocumentation = true; this.textBoxAnnotation.Visible = false; this.webBrowserDocumentation.Visible = true; this.webBrowserDocumentation.Navigate(documentation.source); } - else - { - this.textBoxAnnotation.Text = documentation.source; - this.textBoxAnnotation.Visible = true; - } - } - break; - } - } + } + break; + } + } + + if(!isWebDocumentation) + { + this.textBoxAnnotation.Text = DiagramHelpers.GetAnnotationText(annotation); + this.textBoxAnnotation.Visible = true; + if (this.webBrowserDocumentation != null) + this.webBrowserDocumentation.Visible = false; + } } private void listViewAttributes_SelectedIndexChanged(object sender, EventArgs e) diff --git a/Options.cs b/Options.cs index 73da473..68a0e73 100644 --- a/Options.cs +++ b/Options.cs @@ -37,6 +37,7 @@ namespace XSDDiagram public static string Username { get; private set; } public static string Password { get; private set; } public static IList TextOutputFields { get; private set; } + public static bool DisplayAttributes { get; private set; } public static bool NoGUI { get; private set; } static Options() @@ -52,6 +53,7 @@ namespace XSDDiagram ForceHugeImageGeneration = false; RequestHelp = false; TextOutputFields = new List(); + DisplayAttributes = false; NoGUI = false; IsRunningOnMono = Type.GetType("Mono.Runtime") != null; @@ -157,6 +159,10 @@ namespace XSDDiagram TextOutputFields.Add(field.Trim()); } } + else if (string.Compare("-a", argument, true) == 0) + { + DisplayAttributes = true; + } else if (string.Compare("-no-gui", argument, true) == 0) { NoGUI = true; diff --git a/Program.cs b/Program.cs index 0dd8b6d..472413f 100644 --- a/Program.cs +++ b/Program.cs @@ -35,7 +35,7 @@ namespace XSDDiagram //static extern bool AllocConsole(); static string usage = @"XSD Diagram, version {0} -Usage: {1} [-o output.svg] [-os EXTENSION] [-r RootElement[@namespace]]* [-e N] [-d] [-z N] [-f PATH,NAME,TYPE,NAMESPACE,COMMENT] [-y] [-u USERNAME] [-p PASSWORD] [file.xsd or URL] +Usage: {1} [-o output.svg] [-os EXTENSION] [-r RootElement[@namespace]]* [-e N] [-d] [-z N] [-f PATH,NAME,TYPE,NAMESPACE,COMMENT] [-a] [-y] [-u USERNAME] [-p PASSWORD] [file.xsd or URL] -o FILE specifies the output image. '.png','.jpg', '.svg', '.txt', '.csv' ('.emf' on Windows) are allowed. @@ -58,6 +58,8 @@ Usage: {1} [-o output.svg] [-os EXTENSION] [-r RootElement[@namespace]]* [-e N] Work only with the '-o', '-os png' or '-os jpg' option. -f PATH,NAME,TYPE,NAMESPACE,COMMENT specifies the fields you want to output when rendering to a txt or csf file. +-a + outputs the attributes in text mode only (.txt and .csv). -y force huge image generation without user prompt. -u USERNAME @@ -90,7 +92,7 @@ Example 4: 'TotoRoot' and expanding the tree from the root until the 3rd level. Example 5: -> XSDDiagramConsole.exe -os txt -r TotoRoot -e 3 -f NAME,TYPE,COMMENT ./folder1/toto.xsd +> XSDDiagramConsole.exe -os txt -r TotoRoot -e 3 -f PATH,TYPE,COMMENT -a ./folder1/toto.xsd will write a textual representation in the standard output from a diagram with a root element 'TotoRoot' and expanding the tree from the root until the 3rd level. "; @@ -197,8 +199,10 @@ Example 5: DiagramExporter exporter = new DiagramExporter(diagram); IDictionary specificRendererParameters = new Dictionary() - { - { "TextOutputFields", Options.TextOutputFields } + { + { "TextOutputFields", Options.TextOutputFields }, + { "DisplayAttributes", Options.DisplayAttributes }, + { "Schema", schema } //For future parameters, {} }; if (Options.OutputOnStdOut) diff --git a/ReadMe.txt b/ReadMe.txt index d59a5ab..5816e31 100644 --- a/ReadMe.txt +++ b/ReadMe.txt @@ -1,6 +1,6 @@ XSD Diagram is a free xml schema definition diagram viewer (http://regis.cosnier.free.fr). -Version 1.2alpha Copyright (c) 2006-2016 Regis Cosnier, All Rights Reserved. +Version 1.2alpha Copyright (c) 2006-2017 Regis Cosnier, All Rights Reserved. This program is free software and may be distributed according to the terms of the GNU General Public License (GPL). @@ -39,7 +39,7 @@ COMMAND LINE USAGE: or on Windows use 'XSDDiagramConsole.exe' instead of 'XSDDiagram.exe' if you need the console: -> XSDDiagramConsole.exe [-o output.svg] [-os EXTENSION] [-r RootElement[@namespace]]* [-e N] [-d] [-z N] [-f PATH,NAME,TYPE,NAMESPACE,COMMENT] [-y] [-u USERNAME] [-p PASSWORD] [file.xsd or URL] +> XSDDiagramConsole.exe [-o output.svg] [-os EXTENSION] [-r RootElement[@namespace]]* [-e N] [-d] [-z N] [-f PATH,NAME,TYPE,NAMESPACE,COMMENT] [-a] [-y] [-u USERNAME] [-p PASSWORD] [file.xsd or URL] Options: @@ -63,6 +63,8 @@ Options: Work only with the '-o', '-os png' or '-os jpg' option. -f PATH,NAME,TYPE,NAMESPACE,COMMENT specifies the fields you want to output when rendering to a txt or csf file. +-a + outputs the attributes in text mode only (.txt and .csv). -y force huge image generation without user prompt. -u USERNAME @@ -96,7 +98,7 @@ Example 4: 'TotoRoot' and expanding the tree from the root until the 3rd level. Example 5: -> XSDDiagramConsole.exe -os txt -r TotoRoot -e 3 -f NAME,TYPE,COMMENT ./folder1/toto.xsd +> XSDDiagramConsole.exe -os txt -r TotoRoot -e 3 -f PATH,TYPE,COMMENT -a ./folder1/toto.xsd will write a textual representation in the standard output from a diagram with a root element 'TotoRoot' and expanding the tree from the root until the 3rd level. @@ -112,7 +114,6 @@ TODO LIST: - Add an icon "Go to Diagram" on tool bar, to help working with lot of includes (Majo). - Show/hide group elements in the settings (Mario M.). - Font look blurry on Windows, add default font size in the settings (Mario M.). -- Multi-(language) documentation (https://github.com/dgis/xsddiagram/issues/8) - Add the infer XSD file in the command line. - NoukNouk suggestions: + Add some display parameter like font type / size for tags / annotation... background color, vertical margin between tags... @@ -136,11 +137,14 @@ TODO LIST: CHANGES: -version 1.2alpha (2016-11-??) +version 1.2alpha (2017-02-??) - Add infer XSD from XML menu. - Fix a null reference exception in the documentation (Thanks Mario M.). - Add the namespace in the command line option -r (Thanks Kevin). - Add the option --no-gui to prevent the UI to be shown (Thanks Kevin). +- Add multi-(language) documentation (https://github.com/dgis/xsddiagram/issues/8). +- Fix the URL escaping in the import (https://github.com/dgis/xsddiagram/issues/11). +- Add the attributes of an element with the option -a for text output only. version 1.1 (2016-07-08) - Fix SVG page size. diff --git a/XSDDiagram.exe b/XSDDiagram.exe index 8dabf85..5fc2e2c 100644 Binary files a/XSDDiagram.exe and b/XSDDiagram.exe differ diff --git a/XSDDiagramConsole.exe b/XSDDiagramConsole.exe index 4295645..f5b987a 100644 Binary files a/XSDDiagramConsole.exe and b/XSDDiagramConsole.exe differ diff --git a/XSDDiagrams/DiagramHelpers.cs b/XSDDiagrams/DiagramHelpers.cs new file mode 100644 index 0000000..da9a942 --- /dev/null +++ b/XSDDiagrams/DiagramHelpers.cs @@ -0,0 +1,368 @@ +using System; +using System.Collections.Generic; +using System.Text; +using System.Text.RegularExpressions; + +namespace XSDDiagram +{ + /// + /// Helper functions to work with the diagram. + /// + public class DiagramHelpers + { + + /// + /// Gives the display string of a type. + /// + /// The type. + /// Name of the XML qualified. + /// + public static string QualifiedNameToFullName(string type, System.Xml.XmlQualifiedName xmlQualifiedName) + { + return xmlQualifiedName.Namespace + ':' + type + ':' + xmlQualifiedName.Name; + } + + private static string QualifiedNameToAttributeTypeName(System.Xml.XmlQualifiedName xmlQualifiedName) + { + return xmlQualifiedName.Name + " : " + xmlQualifiedName.Namespace; + } + + + private static void ParseComplexTypeAttributes(Schema schema, string nameSpace, List listAttributes, XMLSchema.complexType complexType, bool isRestriction) + { + if (complexType.ItemsElementName != null) + { + for (int i = 0; i < complexType.ItemsElementName.Length; i++) + { + switch (complexType.ItemsElementName[i]) + { + case XMLSchema.ItemsChoiceType4.attribute: + { + XMLSchema.attribute attribute = complexType.Items[i] as XMLSchema.attribute; + ParseAttribute(schema, nameSpace, listAttributes, attribute, false); + } + break; + case XMLSchema.ItemsChoiceType4.attributeGroup: + { + XMLSchema.attributeGroup attributeGroup = complexType.Items[i] as XMLSchema.attributeGroup; + ParseAttributeGroup(schema, nameSpace, listAttributes, attributeGroup, false); + } + break; + case XMLSchema.ItemsChoiceType4.anyAttribute: + XMLSchema.wildcard wildcard = complexType.Items[i] as XMLSchema.wildcard; + XSDAttribute xsdAttribute = new XSDAttribute("", "*", wildcard.@namespace, "", false, null, null, null); + listAttributes.Add(xsdAttribute); + break; + case XMLSchema.ItemsChoiceType4.simpleContent: + case XMLSchema.ItemsChoiceType4.complexContent: + XMLSchema.annotated annotatedContent = null; + if (complexType.Items[i] is XMLSchema.complexContent) + { + XMLSchema.complexContent complexContent = complexType.Items[i] as XMLSchema.complexContent; + annotatedContent = complexContent.Item; + } + else if (complexType.Items[i] is XMLSchema.simpleContent) + { + XMLSchema.simpleContent simpleContent = complexType.Items[i] as XMLSchema.simpleContent; + annotatedContent = simpleContent.Item; + } + if (annotatedContent is XMLSchema.extensionType) + { + XMLSchema.extensionType extensionType = annotatedContent as XMLSchema.extensionType; + //XSDObject xsdExtensionType = this.schema.ElementsByName[QualifiedNameToFullName("type", extensionType.@base)] as XSDObject; + //if (xsdExtensionType != null) + XSDObject xsdExtensionType; + if (schema.ElementsByName.TryGetValue(QualifiedNameToFullName("type", extensionType.@base), out xsdExtensionType) && xsdExtensionType != null) + { + XMLSchema.annotated annotatedExtension = xsdExtensionType.Tag as XMLSchema.annotated; + if (annotatedExtension != null) + { + if (annotatedExtension is XMLSchema.complexType) + ParseComplexTypeAttributes(schema, extensionType.@base.Namespace, listAttributes, annotatedExtension as XMLSchema.complexType, false); + } + } + if (extensionType.Items != null) + { + foreach (XMLSchema.annotated annotated in extensionType.Items) + { + if (annotated is XMLSchema.attribute) + { + ParseAttribute(schema, nameSpace, listAttributes, annotated as XMLSchema.attribute, false); + } + else if (annotated is XMLSchema.attributeGroup) + { + ParseAttributeGroup(schema, nameSpace, listAttributes, annotated as XMLSchema.attributeGroup, false); + } + } + } + } + else if (annotatedContent is XMLSchema.restrictionType) + { + XMLSchema.restrictionType restrictionType = annotatedContent as XMLSchema.restrictionType; + //XSDObject xsdRestrictionType = this.schema.ElementsByName[QualifiedNameToFullName("type", restrictionType.@base)] as XSDObject; + //if (xsdRestrictionType != null) + XSDObject xsdRestrictionType; + if (schema.ElementsByName.TryGetValue(QualifiedNameToFullName("type", restrictionType.@base), out xsdRestrictionType) && xsdRestrictionType != null) + { + XMLSchema.annotated annotatedRestriction = xsdRestrictionType.Tag as XMLSchema.annotated; + if (annotatedRestriction != null) + { + if (annotatedRestriction is XMLSchema.complexType) + ParseComplexTypeAttributes(schema, restrictionType.@base.Namespace, listAttributes, annotatedRestriction as XMLSchema.complexType, false); + } + } + if (restrictionType.Items1 != null) + { + foreach (XMLSchema.annotated annotated in restrictionType.Items1) + { + if (annotated is XMLSchema.attribute) + { + ParseAttribute(schema, nameSpace, listAttributes, annotated as XMLSchema.attribute, true); + } + else if (annotated is XMLSchema.attributeGroup) + { + ParseAttributeGroup(schema, nameSpace, listAttributes, annotated as XMLSchema.attributeGroup, true); + } + } + } + } + break; + } + } + } + else + { + } + } + + private static XSDAttribute ParseAttribute(Schema schema, string nameSpace, List listAttributes, XMLSchema.attribute attribute, bool isRestriction) + { + bool isReference = false; + string filename = ""; + string name = attribute.name; + string type = ""; + if (attribute.@ref != null) + { + object o = null; + schema.AttributesByName.TryGetValue(QualifiedNameToFullName("attribute", attribute.@ref), out o); + if (o is XSDAttribute) + { + XSDAttribute xsdAttributeInstance = o as XSDAttribute; + XSDAttribute refXSDAttribute = ParseAttribute(schema, nameSpace, listAttributes, xsdAttributeInstance.Tag, isRestriction); + if (refXSDAttribute != null) + { + // Override the "use" field with + refXSDAttribute.Use = attribute.use.ToString(); + } + return null; + } + else // Reference not found! + { + type = QualifiedNameToAttributeTypeName(attribute.@ref); + name = attribute.@ref.Name; + nameSpace = attribute.@ref.Namespace; + isReference = true; + } + } + else if (attribute.type != null) + { + type = QualifiedNameToAttributeTypeName(attribute.type); + nameSpace = attribute.type.Namespace; + } + else if (attribute.simpleType != null) + { + XMLSchema.simpleType simpleType = attribute.simpleType as XMLSchema.simpleType; + if (simpleType.Item is XMLSchema.restriction) + { + XMLSchema.restriction restriction = simpleType.Item as XMLSchema.restriction; + type = QualifiedNameToAttributeTypeName(restriction.@base); + nameSpace = restriction.@base.Namespace; + } + else if (simpleType.Item is XMLSchema.list) + { + XMLSchema.list list = simpleType.Item as XMLSchema.list; + type = QualifiedNameToAttributeTypeName(list.itemType); + nameSpace = list.itemType.Namespace; + } + else + { + } + } + else + { + + } + if (string.IsNullOrEmpty(attribute.name) && string.IsNullOrEmpty(name)) + { + } + if (isRestriction) + { + if (attribute.use == XMLSchema.attributeUse.prohibited) + { + foreach (XSDAttribute xsdAttribute in listAttributes) + { + if (xsdAttribute.Name == name) + { + //listAttributes.Remove(xsdAttribute); + xsdAttribute.Use = attribute.use.ToString(); + break; + } + } + } + } + else + { + XSDAttribute xsdAttribute = new XSDAttribute(filename, name, nameSpace, type, isReference, attribute.@default, attribute.use.ToString(), attribute); + listAttributes.Insert(0, xsdAttribute); + return xsdAttribute; + + } + return null; + } + + private static void ParseAttributeGroup(Schema schema, string nameSpace, List listAttributes, XMLSchema.attributeGroup attributeGroup, bool isRestriction) + { + if (attributeGroup is XMLSchema.attributeGroupRef && attributeGroup.@ref != null) + { + object o = null; + schema.AttributesByName.TryGetValue(QualifiedNameToFullName("attributeGroup", attributeGroup.@ref), out o); + if (o is XSDAttributeGroup) + { + XSDAttributeGroup xsdAttributeGroup = o as XSDAttributeGroup; + XMLSchema.attributeGroup attributeGroupInstance = xsdAttributeGroup.Tag; + + foreach (XMLSchema.annotated annotated in attributeGroupInstance.Items) + { + if (annotated is XMLSchema.attribute) + { + ParseAttribute(schema, nameSpace, listAttributes, annotated as XMLSchema.attribute, isRestriction); + } + else if (annotated is XMLSchema.attributeGroup) + { + ParseAttributeGroup(schema, nameSpace, listAttributes, annotated as XMLSchema.attributeGroup, isRestriction); + } + } + } + } + else + { + + } + } + + private static List GetComplexTypeAttributes(Schema schema, XMLSchema.complexType complexType, string nameSpace) + { + List listAttributes = new List(); + DiagramHelpers.ParseComplexTypeAttributes(schema, nameSpace, listAttributes, complexType, false); + return listAttributes; + } + + /// + /// Gets the annotated attributes. + /// + /// The schema. + /// The annotated. + /// The name space. + /// The list of all the attributes. + public static List GetAnnotatedAttributes(Schema schema, XMLSchema.annotated annotated, string nameSpace) + { + // Attributes enumeration + List listAttributes = new List(); + if (annotated is XMLSchema.element) + { + XMLSchema.element element = annotated as XMLSchema.element; + + if (element.Item is XMLSchema.complexType) + { + XMLSchema.complexType complexType = element.Item as XMLSchema.complexType; + listAttributes.AddRange(GetComplexTypeAttributes(schema, complexType, nameSpace)); + } + else if (element.type != null) + { + //XSDObject xsdObject = this.schema.ElementsByName[DiagramHelpers.QualifiedNameToFullName("type", element.type)] as XSDObject; + //if (xsdObject != null) + XSDObject xsdObject; + if (schema.ElementsByName.TryGetValue(DiagramHelpers.QualifiedNameToFullName("type", element.type), out xsdObject) && xsdObject != null) + { + XMLSchema.annotated annotatedElement = xsdObject.Tag as XMLSchema.annotated; + if (annotatedElement is XMLSchema.complexType) + { + XMLSchema.complexType complexType = annotatedElement as XMLSchema.complexType; + listAttributes.AddRange(GetComplexTypeAttributes(schema, complexType, nameSpace)); + } + else + { + } + } + else + { + } + } + else + { + } + } + else if (annotated is XMLSchema.complexType) + { + XMLSchema.complexType complexType = annotated as XMLSchema.complexType; + listAttributes.AddRange(GetComplexTypeAttributes(schema, complexType, nameSpace)); + } + else if (annotated is XMLSchema.simpleType) + { + XMLSchema.attribute attr = new XMLSchema.attribute(); + XMLSchema.localSimpleType def = new XMLSchema.localSimpleType(); + def.Item = (annotated as XMLSchema.simpleType).Item; + attr.simpleType = def; + string type = ""; + if (def.Item is XMLSchema.restriction) type = (def.Item as XMLSchema.restriction).@base.Name; + XSDAttribute XSDattr = new XSDAttribute("filename", (annotated as XMLSchema.simpleType).name, "namespace", type, false, "", "", attr); + listAttributes.Add(XSDattr); + + } + return listAttributes; + } + + + public static string GetAnnotationText(XMLSchema.annotation annotation) + { + string textDocumentation = ""; + foreach (object o in annotation.Items) + { + if (o is XMLSchema.documentation) + { + string text = ""; + XMLSchema.documentation documentation = o as XMLSchema.documentation; + if (documentation.Any != null && documentation.Any.Length > 0 && documentation.Any[0].Value != null) + { + text = documentation.Any[0].Value; + text = text.Replace("\n", " "); + text = text.Replace("\t", " "); + text = text.Replace("\r", ""); + text = Regex.Replace(text, " +", " "); + text = text.Trim(); + } + else if (documentation.source != null) + { + text = documentation.source; + } + if(!string.IsNullOrEmpty(textDocumentation)) + textDocumentation += "\r\n"; + textDocumentation += text; + if (!string.IsNullOrEmpty(documentation.lang) || !string.IsNullOrEmpty(documentation.source)) + { + textDocumentation += " ("; + if (!string.IsNullOrEmpty(documentation.lang)) + textDocumentation += documentation.lang; + if (!string.IsNullOrEmpty(documentation.lang) && !string.IsNullOrEmpty(documentation.source)) + textDocumentation += ", "; + if (!string.IsNullOrEmpty(documentation.source)) + textDocumentation += documentation.source; + textDocumentation += ")"; + } + } + } + + return textDocumentation; + } + } +} diff --git a/XSDDiagrams/Parsing/Schema.cs b/XSDDiagrams/Parsing/Schema.cs index b354f32..025e9c9 100644 --- a/XSDDiagrams/Parsing/Schema.cs +++ b/XSDDiagrams/Parsing/Schema.cs @@ -163,6 +163,8 @@ namespace XSDDiagram if (!string.IsNullOrEmpty(schemaLocation)) { + schemaLocation = Uri.UnescapeDataString(schemaLocation); + loadedFileName = basePath + Path.DirectorySeparatorChar + schemaLocation.Replace('/', Path.DirectorySeparatorChar); string url = schemaLocation.Trim(); @@ -260,7 +262,7 @@ namespace XSDDiagram { uri = new Uri(url); } - catch (UriFormatException) + catch (UriFormatException ex) { throw new Exception("Cannot read the URL '" + url + "'!"); } diff --git a/XSDDiagrams/Rendering/Diagram.cs b/XSDDiagrams/Rendering/Diagram.cs index 4e5a689..c6b6707 100644 --- a/XSDDiagrams/Rendering/Diagram.cs +++ b/XSDDiagrams/Rendering/Diagram.cs @@ -41,7 +41,7 @@ namespace XSDDiagram.Rendering private List _rootElements; private DiagramItem _selectedElement; - private XMLSchema.any _fakeAny; + private XMLSchema.any _fakeAny; #endregion diff --git a/XSDDiagrams/Rendering/DiagramExporter.cs b/XSDDiagrams/Rendering/DiagramExporter.cs index ca7e41e..953f009 100644 --- a/XSDDiagrams/Rendering/DiagramExporter.cs +++ b/XSDDiagrams/Rendering/DiagramExporter.cs @@ -68,10 +68,10 @@ namespace XSDDiagram.Rendering DiagramAlertHandler alerteDelegate, IDictionary specificRendererParameters) { string extension = Path.GetExtension(outputFilename).ToLower(); - if (string.IsNullOrEmpty(extension)) - { - extension = ".svg"; - outputFilename += extension; + if (string.IsNullOrEmpty(extension)) + { + extension = ".svg"; + outputFilename += extension; } using (FileStream stream = File.Create(outputFilename)) { @@ -97,10 +97,10 @@ namespace XSDDiagram.Rendering { _diagram.Scale = 1.0f; _diagram.Layout(referenceGraphics); - + IntPtr hdc = referenceGraphics.GetHdc(); - Metafile metafile = new Metafile(stream, hdc); - Graphics graphics = Graphics.FromImage(metafile); + Metafile metafile = new Metafile(stream, hdc); + Graphics graphics = Graphics.FromImage(metafile); graphics.SmoothingMode = SmoothingMode.HighQuality; _diagram.Layout(graphics); DiagramGdiRenderer.Draw(_diagram, graphics); @@ -117,13 +117,13 @@ namespace XSDDiagram.Rendering } } else if (extension.Equals(".png", StringComparison.OrdinalIgnoreCase) || - extension.Equals(".jpg", StringComparison.OrdinalIgnoreCase) || + extension.Equals(".jpg", StringComparison.OrdinalIgnoreCase) || extension.Equals(".jpeg", StringComparison.OrdinalIgnoreCase)) { Rectangle bbox = _diagram.ScaleRectangle(_diagram.BoundingBox); bool bypassAlert = true; if (alerteDelegate != null && (bbox.Width > 10000 || bbox.Height > 10000)) - bypassAlert = alerteDelegate("Huge image generation", + bypassAlert = alerteDelegate("Huge image generation", String.Format("Do you agree to generate a {0}x{1} image?", bbox.Width, bbox.Height)); if (bypassAlert) { @@ -153,8 +153,14 @@ namespace XSDDiagram.Rendering renderer.IsCSV = extension.CompareTo(".csv") == 0; IDictionary parameters = specificRendererParameters as IDictionary; object o; - if (parameters != null && parameters.TryGetValue("TextOutputFields", out o)) - renderer.TextOutputFields = o as IList; + if (parameters != null) { + if (parameters.TryGetValue("TextOutputFields", out o)) + renderer.TextOutputFields = o as IList; + if (parameters.TryGetValue("DisplayAttributes", out o) && o is bool) + renderer.DisplayAttributes = (bool)o; + if (parameters.TryGetValue("Schema", out o)) + renderer.Schema = o as Schema; + } renderer.Render(_diagram); } diff --git a/XSDDiagrams/Rendering/DiagramItem.cs b/XSDDiagrams/Rendering/DiagramItem.cs index 464dd07..3ed1727 100644 --- a/XSDDiagrams/Rendering/DiagramItem.cs +++ b/XSDDiagrams/Rendering/DiagramItem.cs @@ -490,28 +490,30 @@ namespace XSDDiagram.Rendering XMLSchema.annotated annotated = this.TabSchema as XMLSchema.annotated; if (annotated != null && annotated.annotation != null) { - foreach (object o in annotated.annotation.Items) - { - if (o is XMLSchema.documentation) - { - XMLSchema.documentation documentation = o as XMLSchema.documentation; - if (documentation.Any != null && documentation.Any.Length > 0 && documentation.Any[0].Value != null) - { - text = documentation.Any[0].Value; - text = text.Replace("\n", " "); - text = text.Replace("\t", " "); - text = text.Replace("\r", ""); - text = Regex.Replace(text, " +", " "); - text = text.Trim(); - } - else if (documentation.source != null) - { - text = documentation.source; - } + text = DiagramHelpers.GetAnnotationText(annotated.annotation); - break; - } - } + //foreach (object o in annotated.annotation.Items) + //{ + // if (o is XMLSchema.documentation) + // { + // XMLSchema.documentation documentation = o as XMLSchema.documentation; + // if (documentation.Any != null && documentation.Any.Length > 0 && documentation.Any[0].Value != null) + // { + // text = documentation.Any[0].Value; + // text = text.Replace("\n", " "); + // text = text.Replace("\t", " "); + // text = text.Replace("\r", ""); + // text = Regex.Replace(text, " +", " "); + // text = text.Trim(); + // } + // else if (documentation.source != null) + // { + // text = documentation.source; + // } + // + // break; + // } + //} } return text; diff --git a/XSDDiagrams/Rendering/DiagramTxtRenderer.cs b/XSDDiagrams/Rendering/DiagramTxtRenderer.cs index 5029c34..67da624 100644 --- a/XSDDiagrams/Rendering/DiagramTxtRenderer.cs +++ b/XSDDiagrams/Rendering/DiagramTxtRenderer.cs @@ -28,6 +28,8 @@ namespace XSDDiagram.Rendering private string _fieldSeparator; private IList _textOutputFields; private IList _finalTextOutputFields; + private bool _displayAttributes; + private Schema _schema; private static List fields = new List() { "PATH", "NAME", "TYPE", "NAMESPACE", "COMMENT" @@ -91,7 +93,30 @@ namespace XSDDiagram.Rendering } } - + public bool DisplayAttributes + { + get + { + return _displayAttributes; + } + set + { + _displayAttributes = value; + } + } + + public Schema Schema + { + get + { + return _schema; + } + set + { + _schema = value; + } + } + #endregion @@ -115,6 +140,10 @@ namespace XSDDiagram.Rendering { } + /// + /// Renders the specified diagram. + /// + /// The diagram. public override void Render(Diagram diagram) { _fieldSeparator = IsCSV ? "," : "\t"; @@ -137,6 +166,10 @@ namespace XSDDiagram.Rendering this.EndItemsRender(); } + /// + /// Renders the specified drawing item. + /// + /// The drawing item. public override void Render(DiagramItem drawingItem) { string type = ""; @@ -159,6 +192,7 @@ namespace XSDDiagram.Rendering parentElement = parentElement.Parent; } + // Get the comment/documentation string comment = ""; XMLSchema.annotated annotated = drawingItem.TabSchema as XMLSchema.annotated; if (annotated != null && annotated.annotation != null) @@ -187,6 +221,7 @@ namespace XSDDiagram.Rendering } } + // Output the item for (int i = 0; i < _finalTextOutputFields.Count; i++) { if (i > 0) @@ -204,6 +239,48 @@ namespace XSDDiagram.Rendering _writer.WriteLine(); + // Output the item attributes + if (this.Schema != null && this.DisplayAttributes) + { + string nameSpace = drawingItem.NameSpace; + if (annotated != null) + { + // Attributes enumeration + List listAttributes = DiagramHelpers.GetAnnotatedAttributes(this.Schema, annotated, nameSpace); + listAttributes.Reverse(); + for (int a = 0; a < listAttributes.Count; a++) + { + XSDAttribute xsdAttribute = listAttributes[a]; + if(xsdAttribute != null) + { + string commentAttribute = ""; + XMLSchema.attribute attribute = xsdAttribute.Tag; + if (attribute != null && attribute.annotation != null) + commentAttribute = DiagramHelpers.GetAnnotationText(attribute.annotation); + + for (int i = 0; i < _finalTextOutputFields.Count; i++) + { + if (i > 0) + _writer.Write(_fieldSeparator); + string field = _finalTextOutputFields[i]; + switch (field) + { + case "PATH": _writer.Write(path + "@" + xsdAttribute.Name); break; + case "NAME": _writer.Write(drawingItem.Name + "@" + xsdAttribute.Name); break; + case "TYPE": _writer.Write(xsdAttribute.Type); break; + case "NAMESPACE": _writer.Write(xsdAttribute.NameSpace); break; + case "COMMENT": _writer.Write(commentAttribute); break; + } + } + _writer.WriteLine(); + } + + //this.listViewAttributes.Items.Add(new ListViewItem(new string[] { attribute.Name, attribute.Type, attribute.Use, attribute.DefaultValue, s })).Tag = attribute; + } + } + } + + //// Draw the inheritor line //if (drawingItem.InheritFrom != null) //{ diff --git a/XSDDiagrams/XSDDiagrams2010.csproj b/XSDDiagrams/XSDDiagrams2010.csproj index 3575969..35a9501 100644 --- a/XSDDiagrams/XSDDiagrams2010.csproj +++ b/XSDDiagrams/XSDDiagrams2010.csproj @@ -61,6 +61,7 @@ + diff --git a/test.bat b/test.bat index b999183..9c51c42 100644 --- a/test.bat +++ b/test.bat @@ -12,6 +12,6 @@ start "" /wait XSDDiagramConsole.exe -o Tests\fileDoc.svg -r COLLADA -e 2 -d Tes XSDDiagramConsole.exe -os png -r COLLADA -e 3 -y Tests\COLLADASchema_141.xsd > Tests\stdout.png XSDDiagramConsole.exe -os jpg -r COLLADA -e 3 -y Tests\COLLADASchema_141.xsd > Tests\stdout.jpg XSDDiagramConsole.exe -os svg -r COLLADA -e 3 -y Tests\COLLADASchema_141.xsd > Tests\stdout.svg -XSDDiagramConsole.exe -os txt -r COLLADA -e 2 -f NAME,TYPE,COMMENT Tests\COLLADASchema_141.xsd +XSDDiagramConsole.exe -os txt -r COLLADA -e 2 -f NAME,TYPE,COMMENT -a Tests\COLLADASchema_141.xsd XSDDiagramConsole.exe -h @pause