开发者

Preserve carriage returns when i write/read from xml file using asp.net

开发者 https://www.devze.com 2023-04-02 19:48 出处:网络
i have TextBox to take comment from user, comments will be saved into XML file the problem is when i write a text have enter key (new line ) it will save into the xml in the right way

i have TextBox to take comment from user, comments will be saved into XML file the problem is when i write a text have enter key (new line ) it will save into the xml in the right way like this

            <comment>
              sdagsg
               fag
                fdhfdhgf
              </comment>

but when i read from the xml 开发者_如何学运维looks like this " sdagsg fag fdhfdhgf"

           string strXstFile = Server.MapPath(@"~/TopicAndComments.xsl");
        XslCompiledTransform x = new XslCompiledTransform();

        // Load the XML 
        XPathDocument doc = new XPathDocument(Server.MapPath(@"~/TopicAndComments.xml"));

        // Load the style sheet.
        XslCompiledTransform xslt = new XslCompiledTransform();
        xslt.Load(strXstFile);

        MemoryStream ms = new MemoryStream();
        XmlTextWriter writer = new XmlTextWriter(ms, Encoding.ASCII);
        StreamReader rd = new StreamReader(ms);
        //Pass Topic ID to XSL file
        XsltArgumentList xslArg = new XsltArgumentList();
        xslArg.AddParam("TopicID", "", HiddenField_SelectedTopicID.Value.ToString());
        xslt.Transform(doc, xslArg, writer);

        ms.Position = 0;
        strHtml = rd.ReadToEnd();
        rd.Close();
        ms.Close();


There is nothing wrong with the read of the XML file. XML is not sensitive to white space.

When you want some parts in XML to not follow all the XML rules and be a bit special, you use a so-called CDATA section. This is what you should be using when "saving" the data of the user.

See one way of how to do it in C#. The way you write XML may have a different equivalent:
http://msdn.microsoft.com/en-us/library/system.xml.xmldocument.createcdatasection.aspx

And I think I agree with Davide Piras in his comment on the question. I think you are having the same issue as Escaping new-line characters with XmlDocument, and hence picked the favorite answer to me from there.


When your xml is parsed it gives the following DOM tree:

Original xml:

            <comment>
              sdagsg
               fag
                fdhfdhgf
              </comment>

Generated DOM tree:

|- NODE_DOCUMENT #document ""
  |- NODE_ELEMENT comment ""
    |- NODE_TEXT #text "\n              sdagsg\n               fag\n                fdhfdhgf\n              "

So the carriage returns are in the XML document.

When i use an MXXMLWriter to convert the XML back into text, i get following XML fragment:

<comment>
              sdagsg
               fag
                fdhfdhgf
              </comment>

So you can get your original XML, with all the embedded whitespace and linebreaks.

The issue you're having is that you want to display the XML as HTML. There are a number of issues with that.

If you blindly try to output the XML inside HTML:

<P><comment>
              sdagsg
               fag
                fdhfdhgf
              </comment></P>

Then nothing appears. The html parser doesn't recognize the <comment> element. Browsers are required to not render any elements they don't recognize.

The first fix one might try, is escape the < and > characters, as you are required to do, with &lt; and &gt;:

<P>&lt;comment&gt;
              sdagsg
               fag
                fdhfdhgf
              &lt;/comment&gt;</P>

This now renders in a browser, but renders as:

<comment> sdagsg fag fdhfdhgf </comment>

The reason for this is that the browser is required to collapse whitespace (e.g, tab, space, linebreak) into a single space.

There are two ways you can handle this. First is to put the "pre-formatted" xml into a preformatted (PRE) html element:

<PRE>&lt;comment&gt;
                  sdagsg
                   fag
                    fdhfdhgf
                  &lt;/comment&gt;</PRE>

This gives the output in HTML:

<comment>
                  sdagsg
                   fag
                    fdhfdhgf
                  </comment>

The other, more complicated, solution is to work with HTML, and present the HTML you wish. If you want to maintain all the whitespace (and not have the browser collapse it), then you must convert it explicitly into non-breaking space characters, by replacing "" with "&nbsp;":

<P>&lt;comment&gt;
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sdagsg
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fag
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fdhfdhgf
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&lt;/comment&gt;</P>

And you also must expliditely have line breaks by converting every "CRLF" into "<BR>":

<P>&lt;comment&gt;<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;sdagsg<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fag<BR>
&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;fdhfdhgf<BR>

And now you have HTML that preserves your spaces and carriage returns:

<comment>
                  sdagsg
                   fag
                    fdhfdhgf
                  </comment>


But can XSL do it?

i don't know.

XSL may be an NP Turing-complete language, but i don't know if it can:

String html = DocumentToString(xmlDocument);
html = StringReplace(html, "<", "&lt;");
html = StringReplace(html, ">", "&gt;");
html = StringReplace(html, " ", "&nbsp;");
html = StringReplace(html, "\r\n", "<BR>");


This transformation:

<xsl:stylesheet version="1.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>
 <xsl:strip-space elements="*"/>

 <xsl:template match="text()" name="replaceNL">
   <xsl:param name="pText" select="."/>

         <xsl:choose>
           <xsl:when test="not(contains($pText, '&#10;'))">
            <xsl:copy-of select="$pText"/>
           </xsl:when>
           <xsl:otherwise>
             <xsl:copy-of select="substring-before($pText, '&#10;')"/>
             <br />
             <xsl:call-template name="replaceNL">
               <xsl:with-param name="pText" select=
                "substring-after($pText, '&#10;')"/>
             </xsl:call-template>
           </xsl:otherwise>
         </xsl:choose>
 </xsl:template>
</xsl:stylesheet>

when applied on the provided XML document:

<comment>
   sdagsg
     fag
      fdhfdhgf
</comment>

produces an HTML result with the wanted properties:

<br/>   sdagsg<br/>     fag<br/>      fdhfdhgf<br/>

and it displays in the browser as:


sdagsg
fag
fdhfdhgf

and if you want to preserve even the whitespace, this can be done by a slight modification of the above transformation:

<xsl:stylesheet version="1.0"
 xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
 <xsl:output omit-xml-declaration="yes" indent="yes"/>
 <xsl:strip-space elements="*"/>

 <xsl:template match="text()" name="replaceNL">
   <xsl:param name="pText" select=
    "translate(., ' ', '&#160;')"/>

         <xsl:choose>
           <xsl:when test="not(contains($pText, '&#10;'))">
            <xsl:copy-of select="$pText"/>
           </xsl:when>
           <xsl:otherwise>
             <xsl:copy-of select="substring-before($pText, '&#10;')"/>
             <br />
             <xsl:call-template name="replaceNL">
               <xsl:with-param name="pText" select=
                "substring-after($pText, '&#10;')"/>
             </xsl:call-template>
           </xsl:otherwise>
         </xsl:choose>
 </xsl:template>
</xsl:stylesheet>

The result now has every space character replaced by a non-breaking space and in the browser it displays as:


   sdagsg
     fag
      fdhfdhgf


finally i found the solution the solution is to replace xml space to html space after html generated i add this

    strHtml = strHtml.Replace("&lt;br/&gt;", "<br/>");

at the end of the method before closing the stream reader

0

精彩评论

暂无评论...
验证码 换一张
取 消