• Status: Solved
  • Priority: Medium
  • Security: Public
  • Views: 488
  • Last Modified:

Displaying XSLT/XML javascript generated HTML

I am parsing an XML document with an xslt document and am also using variables in my xslt wich I change with a processor (all in firefox):

        var objDOMParser = new DOMParser();
        var xml = objDOMParser.parseFromString(navigator.XMLDocument, "text/xml");
        xml.async = false;
       
        var oProcessor = new XSLTProcessor();
        var xsl = navigator.XSLDocument;
        xsl.async = false;
       
        oProcessor.importStylesheet(xsl);
       
        oProcessor.setParameter(null, "id", id);
        oProcessor.setParameter(null, "mode", mode);
        var oResultDom = oProcessor.transformToDocument(xml);
       
        var serializer = new XMLSerializer();
        var str = serializer.serializeToString(oResultDom);

Works like a charm except for 1 thing, my output contains HTML and it is being diplayed as text:

<strong>hello world</strong>

I want it shown bold. How can I make this work?
0
frollo
Asked:
frollo
  • 7
  • 6
  • 2
1 Solution
 
Michel PlungjanIT ExpertCommented:
Show us the xsl.

For one you need
<xsl:output method="html" encoding="UTF-8"></xsl:output>

in the top
0
 
Geert BormansCommented:
The issue is likely in your XSLT
At the point where you output the text that contains the HTML tags,
you should disable the output escaping
                                           <xsl:value-of select="." disable-output-escaping="yes"/>

cheers

Geert
0
 
frolloAuthor Commented:
<?xml version="1.0" encoding="utf-16"?>
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
  <xsl:param name="sortfield" select="'FunctieNaam'" />
  <xsl:param name="filter" select="''" />
  <xsl:param name="filterfield" select="''" />
  <xsl:param name="id" select="''" />
  <xsl:param name="mode" select="''" />

  <xsl:template match="/ArrayOfVacature">
    <table border="1">
      <xsl:choose>
        <xsl:when test="$id">
          <xsl:apply-templates select="Vacature[VacatureID=$id]" mode="detail">
          </xsl:apply-templates>
        </xsl:when>
        <xsl:when test="$filter">
          <xsl:apply-templates select="Vacature[BrancheID=$filter]">
          </xsl:apply-templates>
        </xsl:when>
        <xsl:otherwise>
          <xsl:apply-templates select="Vacature">
            <!--<xsl:sort select="$sortfield" order="ascending" />-->
            <xsl:sort select="*[name(.)=$sortfield]" order="ascending" />
          </xsl:apply-templates>
        </xsl:otherwise>
      </xsl:choose>
    </table>
  </xsl:template>

  <xsl:template match="Vacature">
    <table width="750" border="0" cellspacing="0" cellpadding="0">
      <tr>
        <td>
          <span id="VacatureBankKop">
            <xsl:value-of select="FunctieNaam"/>
          </span>
          <br/>
          <br/>
        </td>
      </tr>
      <tr>
        <td>
          <span id="Intro">
            <xsl:value-of select="Intro" disable-output-escaping="yes"/>
          </span>
          <br/>
          <br/>
        </td>
      </tr>
      <tr>
        <td align="right">
          <a href="javascript:void(0);" onclick="DetailVacature('{VacatureID}', 'detail');">Lees verder...</a>
        </td>
        <br/>
      </tr>
      <tr>
        <td>
          <br/>
          <hr />
        </td>
      </tr>
    </table>
  </xsl:template>

  <xsl:template match="Vacature" mode="detail">
    <table width="700" border="0" cellspacing="0" cellpadding="0">
      <tr>
        <td width="150" align="left" class="HoofdPunt">Vacaturenummer:</td>
        <td width="550" align="left">
          <xsl:value-of select="VacatureNummer" />
        </td>
      </tr>
      <tr>
        <td width="150" align="left" class="HoofdPunt">Opleidingsniveau:</td>
        <td width="550" align="left">
          <xsl:variable name="ActiveOpleidingsniveauID" select="OpleidingsNiveauID" />
          <xsl:for-each select="/ArrayOfVacature/Opleidingsniveau">
            <xsl:choose>
              <xsl:when test="OpleidingsniveauID = $ActiveOpleidingsniveauID">
                <xsl:value-of select="OpleidingsNaam" />
              </xsl:when>
            </xsl:choose>
          </xsl:for-each>
        </td>
      </tr>
      <tr>
        <td width="150" align="left" class="HoofdPunt">Branche:</td>
        <td width="550" align="left">
          <xsl:variable name="ActiveBrancheID" select="BrancheID" />
          <xsl:for-each select="/ArrayOfVacature/Branche">
            <xsl:choose>
              <xsl:when test="BrancheID = $ActiveBrancheID">
                <xsl:value-of select="BrancheNaam" />
              </xsl:when>
            </xsl:choose>
          </xsl:for-each>
        </td>
      </tr>
      <tr>
        <td width="150" align="left" class="HoofdPunt">Provincie:</td>
        <td width="550" align="left">
          <xsl:value-of select="Provincie" />
        </td>
      </tr>
      <tr>
        <td width="150" align="left" class="HoofdPunt">Startersfunctie:</td>
        <td width="550" align="left">
          <xsl:choose>
            <xsl:when test="Startersfunctie = 'true'">
              Ja
            </xsl:when>
            <xsl:otherwise>
              Nee
            </xsl:otherwise>
          </xsl:choose>
        </td>
      </tr>
      <tr>
        <td width="150" align="left" class="HoofdPunt">Aantal uren per week:</td>
        <td width="550" align="left">
          <xsl:value-of select="AantalUren" />
        </td>
      </tr>
      <tr>
        <td colspan="2">
          <hr />
        </td>
      </tr>
      <tr>
        <td colspan="2" align="left">
          <xsl:value-of select="Intro" disable-output-escaping="yes"/>
          <br/>
          <br/>
        </td>
      </tr>
      <tr>
        <td colspan="2" align="left" class="Functie">
          <xsl:value-of select="FunctieNaam" />
          <br/>
        </td>
      </tr>
      <tr>
        <td colspan="2" align="left">
          (<xsl:value-of select="AantalUren" /> uren per week)
          <br/>
          <br/>
        </td>
      </tr>
      <tr>
        <td colspan="2" align="left">
          <xsl:value-of select="Beschrijving" disable-output-escaping="yes"/>
        </td>
        <br/>
        <br/>
      </tr>
      <tr>
        <td colspan="2">
          <hr />
        </td>
      </tr>
      <tr>
        <td colspan="2" align="left">
          <b>Reageren?</b>
          <br/>
          <br/>
          Mail je CV en motivatie z.s.m. of uiterlijk voor <span id="datumtot">
            <xsl:value-of select="DatumTot" />
          </span> naar info@arbeidsplan.nl of reageer
          <br/>
          via onderstaande mogelijkheden.
        </td>
      </tr>
      <tr>
        <td colspan="2">
          <hr />
        </td>
      </tr>
      <tr>
        <td colspan="2" align="left" class="FooterFuncties">
          <img src="images/Dot.gif"></img>&#xa0;<a href="DirectReageren.aspx?Reageerdirect=Ik ben geinteresseerd in de functie:{FunctieNaam} met vacaturenummer:{VacatureNummer}">Ik wil direct reageren</a>
        </td>
      </tr>
      <tr>
        <td colspan="2" align="left" class="FooterFuncties">
          <img src="images/Dot.gif" border="0" />&#xa0;<a href="javascript:void(0);" onclick="PrintVacature('{VacatureID}','detail');">Ik wil deze vacature printen</a>
        </td>
      </tr>
      <!--<tr>
        <td colspan="2" align="left" class="FooterFuncties">
          <img src="images/Dot.gif"></img> Ik wil deze vacature doorsturen naar een vriend
        </td>
      </tr>-->
      <tr>
        <td colspan="2" align="left" class="FooterFuncties">
          <img src="images/Dot.gif" border="0" />&#xa0;<a href="javascript:void(0);" onclick=" HideWindow();">Ik wil terug naar lijst</a>
        </td>
      </tr>
    </table>
  </xsl:template>


  <xsl:template match="/ArrayOfBranche">
    Branche:
    <xsl:element name="select">
      <xsl:attribute name="id">cmbBranche</xsl:attribute>
      <xsl:attribute name="onchange">SetHuidigeBranche();Filter(cmbBranche.value);</xsl:attribute>
      <option value="Kies een branche" selected="selected">Kies een branche</option>
      <xsl:for-each select="Branche">
        <xsl:element name="option">
          <xsl:attribute name="value">
            <xsl:value-of select="BrancheID" />
          </xsl:attribute>
          <xsl:value-of select="BrancheNaam"/>
        </xsl:element>
      </xsl:for-each>
    </xsl:element>
  </xsl:template>

</xsl:stylesheet>
0
VIDEO: THE CONCERTO CLOUD FOR HEALTHCARE

Modern healthcare requires a modern cloud. View this brief video to understand how the Concerto Cloud for Healthcare can help your organization.

 
Michel PlungjanIT ExpertCommented:
Now add
<xsl:output method="html" />

to the top before the params
0
 
frolloAuthor Commented:
I already had the:
<xsl:value-of select="." disable-output-escaping="yes"/>

Now added:
<xsl:output method="html" />

Still no result onfortunately
0
 
Geert BormansCommented:
Can you pinpoint where the part with the strong comes from?
Is a literal string in the XML (possibly in a CDATA textnode or a real child)
(If it is a real child, you need to use copy-of)
or do you generate it with the javascript on the page eventually

cheers

Geert
0
 
frolloAuthor Commented:
The xml part that does not get displayed wel look like this:

<beschrijving>;nbsp;&amp;nbsp; sem pulvinar venenatis. Proin arcu libero, rhoncus eu, aliquet nec&lt;/FONT&gt;<beschrijving>

I want to display the value beschrijving tag as HTML
0
 
Geert BormansCommented:
strange, the disable-output-escaping you have in the template for Beschrijving should cover this.
I can't see that you re-escape it afterwards
It could be that the "Beschrijving" element doesn't pass the template for Beschrijving and that it is output by the built-in template
I can only know that if I saw the full XML
I assume that the fact that your sample has smaller case for description instead of "Beschrijving" is caused by the fact that you made up a mock-up example?

cheers

Geert
0
 
frolloAuthor Commented:
<?xml version="1.0" encoding="utf-16"?><ArrayOfVacature xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:xsd="http://www.w3.org/2001/XMLSchema">
  <Vacature>
    <VacatureID>4</VacatureID>
    <WerkgeverID>12</WerkgeverID>
    <Actief>true</Actief>
    <AdminOK>true</AdminOK>
    <Doorzoekbaar>false</Doorzoekbaar>
    <DatumPlaatsing>2007-04-28</DatumPlaatsing>
    <DatumWijziging>2007-04-28</DatumWijziging>
    <Bekeken>0</Bekeken>
    <VacatureNummer>1234</VacatureNummer>
    <OpleidingsNiveauID>1</OpleidingsNiveauID>
    <Bedrijfsnaam>IC-Three</Bedrijfsnaam>
    <BrancheID>1</BrancheID>
    <FunctieCategorie />
    <Provincie>Overijssel</Provincie>
    <Startersfunctie>true</Startersfunctie>
    <Standplaats>Zwolle</Standplaats>
    <AantalUren>40</AantalUren>
    <ContractTypeID>1</ContractTypeID>
    <Intro>&lt;strong&gt;Lorem ipsum dolor sit amet, consectetuer adipiscing elit&lt;/strong&gt;. </Intro>
    <FunctieNaam>Ontwikkelaar</FunctieNaam>
    <Beschrijving>&lt;strong&gt;Lorem ipsum dolor sit amet, consectetuer adipiscing elit&lt;/strong&gt;. </Beschrijving>
    <Gevraagd />
    <Geboden />
    <DatumVan>2007-04-28</DatumVan>
    <DatumTot>2007-05-27</DatumTot><Featured>true</Featured>
  </Vacature>

0
 
frolloAuthor Commented:
I think I found the problem:

http://www.semiologic.com/2005/05/15/firefox-xslt-bug/

It should work, but it doesn't
0
 
Geert BormansCommented:
It works fine when I test it with an XSLT processor
... and then the bell rings
disable-output-escaping is not a mandatory functionality for XSLT processors,
some don't support it, the most important being FireFox
so it can't work with FireFox... you will need to find a way to unescape the &lt; after the XSLT has worked on it... seems a complex thing to do in regex
Try to unescape it in the XML beforehand and do an xsl:copy

cheers

Geert
0
 
Geert BormansCommented:
Seems you found a reference yourself.
Note that this isn't a bug. disable-output-escaping is a hacky feature
and a compliant XSLT processor don't necessarily has to support it.
Transformiix people decided not to suport it... ever
still they are compliant to the spec

best work around I can think of is to unescape the HTML with a slightly changed identity transform,
before you feed it to the browser XSLT
... you'd better pray that the embedded HTML is wellformed :-)

I can help you with the identity transform for preprocessing the XML if you want me to
If it is not wellformed, you might need an extra pass via TagSoup or so

Oh, if I only would have been awake at the start of the question, it would have saved us some posts :-)

cheers

Geert
0
 
frolloAuthor Commented:
Solved it:

function UnEscape(UnEscapeString)
{
    var intIndexOfMatch = UnEscapeString.indexOf("&nbsp");

    while (intIndexOfMatch != -1)
    {
        UnEscapeString = UnEscapeString.replace( "&nbsp", " " )
        intIndexOfMatch = UnEscapeString.indexOf( "&nbsp" );
    }
   
    intIndexOfMatch = UnEscapeString.indexOf( "&lt;" );

    while (intIndexOfMatch != -1)
    {
        UnEscapeString = UnEscapeString.replace( "&lt;", "<" )
        intIndexOfMatch = UnEscapeString.indexOf( "&lt;" );
    }
   
    intIndexOfMatch = UnEscapeString.indexOf( "&gt;" );

    while (intIndexOfMatch != -1)
    {
        UnEscapeString = UnEscapeString.replace( "&gt;", ">" )
        intIndexOfMatch = UnEscapeString.indexOf( "&gt;" );
    }

    return UnEscapeString;

}

Added the above function and am running the result html through it.

Thanks guys for the help, and thanks gertone for the inspiration to this sollution.
0
 
Geert BormansCommented:
welcome
0
 
frolloAuthor Commented:
PS. the HTML was not wellformed, but doesn't matter with the sollution I produced. Thanks again.
0

Featured Post

Free Tool: ZipGrep

ZipGrep is a utility that can list and search zip (.war, .ear, .jar, etc) archives for text patterns, without the need to extract the archive's contents.

One of a set of tools we're offering as a way to say thank you for being a part of the community.

  • 7
  • 6
  • 2
Tackle projects and never again get stuck behind a technical roadblock.
Join Now