How to turn-off showing child items for selected Main Menu items in Umbraco CMS? - umbraco

In order to explain my issue easier, please first see this photo
On my template I have already configured Top navigation but problem is that I am trying to make new menu Item which will be called 'News' and thing is that I don't want that every out of 99 news items I will publish (in next two months), to be autmatically available as sumbenu child item under 'News'.
As I noticed, most of the configuration is under 'umbTopNavigation.xslt'
]>
xmlns:msxml="urn:schemas-microsoft-com:xslt"
xmlns:umbraco.library="urn:umbraco.library"
exclude-result-prefixes="msxml umbraco.library">
<xsl:output method="xml" omit-xml-declaration="yes" />
<xsl:param name="currentPage"/>
<!-- Input the documenttype you want here -->
<xsl:variable name="level" select="1"/>
<xsl:template match="/">
<ul id="topNavigation">
<li class="home">
<xsl:if test="$currentPage/#id = $currentPage/ancestor-or-self::* [#level=$level]/#id">
<xsl:attribute name="class">home current</xsl:attribute>
</xsl:if>
Home
</li>
<xsl:for-each select="$currentPage/ancestor-or-self::* [#level=$level]/* [#isDoc and string(umbracoNaviHide) != '1']"> <li>
<xsl:if test="#id = $currentPage/#id">
<xsl:attribute name="class">current</xsl:attribute>
</xsl:if>
<a class="navigation" href="{umbraco.library:NiceUrl(#id)}">
<span><xsl:value-of select="#nodeName"/></span>
</a> </li>
</xsl:for-each> </ul>
</xsl:template>
but I can't figure out what exactly I need to change?
Any help is appreciated and many thanks in advance!
MC2012
First macro
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE xsl:stylesheet [ <!ENTITY nbsp " "> ]>
<xsl:stylesheet
version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:msxml="urn:schemas-microsoft-com:xslt"
xmlns:umbraco.library="urn:umbraco.library"
exclude-result-prefixes="msxml umbraco.library">
<xsl:output method="xml" omit-xml-declaration="yes"/>
<xsl:param name="currentPage"/>
<xsl:template match="/">
<xsl:variable name="items" select="$currentPage/ancestor-or-self::* [#isDoc and #level = 2]/* [#isDoc and string(umbracoNaviHide) != '1']"/>
<!-- The fun starts here -->
<xsl:if test="count($items) > 0">
<ul>
<xsl:for-each select="$items">
<li>
<a href="{umbraco.library:NiceUrl(#id)}">
<xsl:value-of select="#nodeName"/>
</a>
</li>
</xsl:for-each>
</ul>
</xsl:if>
</xsl:template>
</xsl:stylesheet>
Second Macro
<?xml version="1.0" encoding="utf-8" ?>
<xsl:stylesheet
version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:umbraco.library="urn:umbraco.library"
exclude-result-prefixes="umbraco.library"
>
<xsl:output method="xml" indent="yes" omit-xml-declaration="yes" />
<xsl:param name="currentPage" />
<!-- Specify level of the top node for a language (usually 1) -->
<xsl:variable name="level" select="1" />
<!-- Grab the top node -->
<xsl:variable name="siteRoot" select="$currentPage/ancestor-or-self::*[#level = $level]" />
<xsl:template match="/">
<ul class="menu">
<!-- Create the Home link -->
<li>
<xsl:if test="$currentPage/#id = $siteRoot/#id">
<xsl:attribute name="class">sel</xsl:attribute>
</xsl:if>
<a href="{umbraco.library:NiceUrl($siteRoot/#id)}">
<xsl:value-of select="$siteRoot/#nodeName" />
</a>
</li>
<!-- Process all children of $siteRoot (if any) -->
<xsl:apply-templates select="$siteRoot/*[#isDoc][not(umbracoNaviHide = 1)]" />
</ul>
</xsl:template>
<!-- Generic template for all nav links -->
<xsl:template match="*[#isDoc]">
<li>
<xsl:if test="#id = $currentPage/#id">
<xsl:attribute name="class">sel</xsl:attribute>
</xsl:if>
<a href="{umbraco.library:NiceUrl(#id)}">
<xsl:value-of select="#nodeName" />
</a>
<!-- Render sub menu if necessary -->
<xsl:call-template name="submenu" />
</li>
</xsl:template>
<!-- Template for Inactive links -->
<xsl:template match="*[#isDoc][umbracoNaviInactive = 1]">
<li>
<xsl:if test="#id = $currentPage/#id">
<xsl:attribute name="class">sel</xsl:attribute>
</xsl:if>
<span>
<xsl:value-of select="#nodeName" />
</span>
<!-- Submenu? -->
<xsl:call-template name="submenu" />
</li>
</xsl:template>
<!-- Template checking for, and processing any submenu -->
<xsl:template name="submenu">
<xsl:variable name="subPages" select="*[#isDoc][not(umbracoNaviHide = 1)]" />
<xsl:if test="$subPages">
<ul>
<xsl:apply-templates select="$subPages" />
</ul>
</xsl:if>
</xsl:template>
</xsl:stylesheet>

Ok - you have two options. A quick hack or a full solution.
The quick hack is to update the second macro where the subnav is called and exclude the subnav being called where it's the news page (and you can include other pages in here too)
In this example I've used node ID 1107 to be the ID of your news page, but you will need to update this with your actual news page ID.
<?xml version="1.0" encoding="utf-8" ?>
<xsl:stylesheet
version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:umbraco.library="urn:umbraco.library"
exclude-result-prefixes="umbraco.library"
>
<xsl:output method="xml" indent="yes" omit-xml-declaration="yes" />
<xsl:param name="currentPage" />
<!-- Specify level of the top node for a language (usually 1) -->
<xsl:variable name="level" select="1" />
<!-- Grab the top node -->
<xsl:variable name="siteRoot" select="$currentPage/ancestor-or-self::*[#level = $level]" />
<xsl:template match="/">
<ul class="menu">
<!-- Create the Home link -->
<li>
<xsl:if test="$currentPage/#id = $siteRoot/#id">
<xsl:attribute name="class">sel</xsl:attribute>
</xsl:if>
<a href="{umbraco.library:NiceUrl($siteRoot/#id)}">
<xsl:value-of select="$siteRoot/#nodeName" />
</a>
</li>
<!-- Process all children of $siteRoot (if any) -->
<xsl:apply-templates select="$siteRoot/*[#isDoc][not(umbracoNaviHide = 1)]" />
</ul>
</xsl:template>
<!-- Generic template for all nav links -->
<xsl:template match="*[#isDoc]">
<li>
<xsl:if test="#id = $currentPage/#id">
<xsl:attribute name="class">sel</xsl:attribute>
</xsl:if>
<a href="{umbraco.library:NiceUrl(#id)}">
<xsl:value-of select="#nodeName" />
</a>
<!-- Render sub menu if necessary excluding the news pages -->
<xsl:if test="not(#id=1107)">
<xsl:call-template name="submenu" />
</xsl:if>
</li>
</xsl:template>
<!-- Template for Inactive links -->
<xsl:template match="*[#isDoc][umbracoNaviInactive = 1]">
<li>
<xsl:if test="#id = $currentPage/#id">
<xsl:attribute name="class">sel</xsl:attribute>
</xsl:if>
<span>
<xsl:value-of select="#nodeName" />
</span>
<!-- Submenu? -->
<xsl:call-template name="submenu" />
</li>
</xsl:template>
<!-- Template checking for, and processing any submenu -->
<xsl:template name="submenu">
<xsl:variable name="subPages" select="*[#isDoc][not(umbracoNaviHide = 1)]" />
<xsl:if test="$subPages">
<ul>
<xsl:apply-templates select="$subPages" />
</ul>
</xsl:if>
</xsl:template>
</xsl:stylesheet>
The proper way to do it would be to add a property to your document type to include a property to say do not list children or similar, and then test for that in the XSLT, but that's a much more involved fix, and for that I suggest you read up a bit more on how XSLTs work. Let me know if you want to go down that route and there are plenty of resources I can direct you to
thanks,

Related

How to access variable defined under for-each loop/If condition in another for each loop

I have to generate the output in sequence and so I wanted to know how to access the variable defined under For-each loop/If condition and then value of select inside another for loop.
As per my example how to access partn and date3? Please help and suggest.
what is the concept for achieving the same..I have tried with-param as well, but didn't work for me.
XSLT:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:func="myfunc"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
xmlns:fn="http://www.w3.org/2005/xpath-functions" >
<xsl:output method="text" encoding="utf-8" />
<xsl:output omit-xml-declaration="yes" />
<xsl:param name="break" select="'
'" />
<xsl:template match="ZGS/ID">
<xsl:for-each select="E1">
<xsl:if test="PA = 'CE'">
<xsl:variable name="partn" select="PAN"/>
</xsl:if>
</xsl:for-each>
<xsl:for-each select="E13">
<xsl:if test="ID = 033">
<xsl:variable name="date3"
select="substring(DAT,3,8)"/>
</xsl:if>
</xsl:for-each>
<xsl:for-each select="E1E">
<xsl:text>823</xsl:text>
<xsl:text>03</xsl:text>
<xsl:for-each select="E1ED">
<xsl:if test="QU = 012 ">
<xsl:value-of select="BEL"/>
</xsl:if>
</xsl:for-each>
<xsl:value-of select="$partn"/>
<xsl:value-of select="$date3"/>
</xsl:for-each>
</xsl:template>
INPUT:
<?xml version='1.0' encoding='utf-8'?>
<ZGS>
<ID BEGIN="1">
<E1 SEGMENT="1">
<PA>AG</PA>
<NAME>ABC</NAME>
<SP>E</SP>
<AND>0004</AND>
</E1>
<E1 SEGMENT="1">
<PA>RE</PA>
<PAN>IUIOP</PAN>
<NAME>ABC1</NAME>
<SP>EQ</SP>
<AND>0005</AND>
<EKA3 SEGMENT="1">
<QU>009</QU>
</EKA3>
</E1>
<E1 SEGMENT="1">
<PA>CE</PA>
<PAN>PODW</PAN>
<NAME>ABC2</NAME>
<SP>EP</SP>
<AND>0006</AND>
</E1>
<E13 SEGMENT="1">
<ID>001</ID>
<DAT>20190329</DAT>
</E13>
<E13 SEGMENT="1">
<ID>002</ID>
<DAT>20190429</DAT>
</E13>
<E13 SEGMENT="1">
<IDD>033</IDD>
<DAT>20190529</DAT>
</E13>
<E1E>
<E1ED>
</E1ED>
<E1ED>
</E1ED>
</E1E>
In XSLT, variables once declared/defined, they cannot be changed. And exists only in the loop they are defined.
You might not need the xsl:for-each loop here. Instead the variables can be globally defined, so that you can use them where you want in your xslt.
You can try the following:
<?xml version="1.0" encoding="UTF-8"?>
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:func="myfunc"
xmlns:xs="http://www.w3.org/2001/XMLSchema" xmlns:fn="http://www.w3.org/2005/xpath-functions">
<xsl:output method="text" encoding="utf-8" />
<xsl:output omit-xml-declaration="yes" />
<xsl:param name="break" select="'
'" />
<xsl:variable name="partn" select="/ZGS/ID/E1[PA = 'CE']/PAN" />
<xsl:variable name="date3" select="substring(/ZGS/ID/E13[ID = '033']/DAT,3,8)" />
<xsl:template match="ZGS/ID">
<xsl:for-each select="E1E">
<xsl:text>823</xsl:text>
<xsl:text>03</xsl:text>
<xsl:for-each select="E1ED">
<xsl:if test="QU = 012 ">
<xsl:value-of select="BEL" />
</xsl:if>
</xsl:for-each>
<xsl:value-of select="$partn" />
<xsl:value-of select="$date3" />
</xsl:for-each>
</xsl:template>
</xsl:stylesheet>
https://xsltfiddle.liberty-development.net/jyRYYiu
Using xsl:param, it can be achieved as
<xsl:param name="partn" select="/ZGS/ID/E1[PA = 'CE']/PAN" />
<xsl:param name="date3" select="substring(/ZGS/ID/E13[ID = '033']/DAT,3,8)" />
<xsl:template match="ZGS/ID">
<xsl:for-each select="E1E">
<xsl:text>823</xsl:text>
<xsl:text>03</xsl:text>
<xsl:for-each select="E1ED">
<xsl:if test="QU = 012 ">
<xsl:value-of select="BEL" />
</xsl:if>
</xsl:for-each>
<xsl:for-each select="$partn">
<xsl:value-of select="." />
</xsl:for-each>
<xsl:value-of select="$date3" />
</xsl:for-each>
</xsl:template>
https://xsltfiddle.liberty-development.net/jyRYYiu/1

Subtraction by decimal number

I have a to subtract the amount -1 based on the condition.Please any one help.
Input:
<JD>
<GP xmlns="">
I xmlns="">
<PK>40</PK>
<A/>
<AMNT>11659650.15</AMNT>
<B/>
<C/>
</I>
<I xmlns="">
<PK>50</PK>
<A/>
<AMNT>11659650.15</AMNT>
<B/>
<C/>
</I>
</GP>
</JD>
Tried with below XSLT and got 1.165964915E7 for 50.
<xsl:for-each select="JD/mo:GP/I">
<xsl:if test="PK='40'">
<xsl:variable name="a" select="AMNT"/>
<xsl:element name="AMT">
<xsl:value-of select="$a"/>
</xsl:element>
</xsl:if>
<xsl:if test="PK='50'">
<xsl:variable name="a" select="AMNT"/>
<xsl:element name="AMT">
<xsl:value-of select="$a - 1"/>
</xsl:element>
</xsl:if>
Considering your given input as following:
<?xml version="1.0" encoding="UTF-8"?>
<Root>
<JD>
<GP>
<I>
<PK>40</PK>
<A />
<AMNT>11659650.15</AMNT>
<B />
<C />
</I>
<I>
<PK>50</PK>
<A />
<AMNT>11659650.15</AMNT>
<B />
<C />
</I>
</GP>
</JD>
</Root>
In XSLT 2.0, you can try it using xs:decimal as below:
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform" xmlns:xs="http://www.w3.org/2001/XMLSchema"
exclude-result-prefixes="xs">
<xsl:output omit-xml-declaration="yes" indent="yes" />
<xsl:strip-space elements="*" />
<xsl:template match="/Root">
<xsl:for-each select="JD/mo:GP/I">
<xsl:if test="PK='40'">
<xsl:variable name="a" select="AMNT" />
<xsl:element name="AMT">
<xsl:value-of select="$a" />
</xsl:element>
</xsl:if>
<xsl:if test="PK='50'">
<xsl:variable name="a" select="AMNT" />
<xsl:element name="AMT">
<xsl:value-of select="xs:decimal($a) - 1" />
</xsl:element>
</xsl:if>
</xsl:for-each>
</xsl:template>
In XSLT 1.0, Use the format-number() function:
<xsl:template match="/Root">
<xsl:for-each select="JD/mo:GP/I">
<xsl:if test="PK='40'">
<xsl:variable name="a" select="AMNT" />
<xsl:element name="AMT">
<xsl:value-of select="$a" />
</xsl:element>
</xsl:if>
<xsl:if test="PK='50'">
<xsl:variable name="a" select="AMNT" />
<xsl:element name="AMT">
<xsl:value-of select="format-number($a - 1, '0.##')" />
</xsl:element>
</xsl:if>
</xsl:for-each>
</xsl:template>

Aggregate nodes based on conditon under new parent

I have an given XML and I want to convert it in new xml and want to aggregate nodes based on status and orderId.
<?xml version="1.0" encoding="utf-8"?>
<OrderStatusUpdate>
<OrderStatusEvents>
<OrderStatusEvent>
<StoreCode>store1</StoreCode>
<OrderId>Order1</OrderId>
<ItemId>Item1</ItemId>
<OrderStatusDetails>
<OrderStatusDetail>
<OrderStatusEventTimeStamp>2017-03-19 03:37:05</OrderStatusEventTimeStamp>
<StatusName>Cancelled</StatusName>
</OrderStatusDetail>
</OrderStatusDetails>
</OrderStatusEvent>
<OrderStatusEvent>
<StoreCode>Store1</StoreCode>
<OrderId>Order1</OrderId>
<ItemId>Item2</ItemId>
<OrderStatusDetails>
<OrderStatusDetail>
<OrderStatusEventTimeStamp>2017-03-19 03:48:35</OrderStatusEventTimeStamp>
<StatusName>Cancelled</StatusName>
</OrderStatusDetail>
</OrderStatusDetails>
</OrderStatusEvent>
<OrderStatusEvent>
<StoreCode>Store1</StoreCode>
<OrderId>Order1</OrderId>
<ItemId>Item3</ItemId>
<OrderStatusDetails>
<OrderStatusDetail>
<OrderStatusEventTimeStamp>2017-03-19 03:48:35</OrderStatusEventTimeStamp>
<StatusName>Shipped</StatusName>
</OrderStatusDetail>
</OrderStatusDetails>
</OrderStatusEvent>
<OrderStatusEvent>
<StoreCode>Store1</StoreCode>
<OrderId>Order2</OrderId>
<ItemId>Item1</ItemId>
<OrderStatusDetails>
<OrderStatusDetail>
<OrderStatusEventTimeStamp>2017-03-19 03:48:35</OrderStatusEventTimeStamp>
<StatusName>Cancelled</StatusName>
</OrderStatusDetail>
</OrderStatusDetails>
</OrderStatusEvent>
</OrderStatusEvents>
</OrderStatusUpdate>
And I want an output like this. Here I am grouping elements based on status and orderId.
<Orders>
<group name="CANCELLED">
<STATUS ID="CANCELLED" DESCRIPTION="Goods Cancelled">
<ORDER ID="Order1">
<ORDER_ITEM item="item1" />
<ORDER_ITEM item="item2" />
</ORDER>
</STATUS>
<STATUS ID="CANCELLED" DESCRIPTION="Goods Cancelled">
<ORDER ID="Order2">
<ORDER_ITEM item="item1" />
</ORDER>
</STATUS>
</group>
<group name="SHIPPED">
<STATUS ID="SHIPPED" DESCRIPTION="Goods SHIPPED">
<ORDER ID="Order1">
<ORDER_ITEM item="item3" />
</ORDER>
</STATUS>
<group>
</Orders>
I am using the following xslt and it is working fine. Is there any way to improve this.
<xsl:stylesheet version="2.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output omit-xml-declaration="yes" indent="yes" />
<xsl:template match="OrderStatusUpdate/OrderStatusEvents">
<Orders>
<xsl:for-each-group select="OrderStatusEvent" group-by="OrderStatusDetails/OrderStatusDetail/StatusName">
<xsl:variable name="group-name" select="current-grouping-key()" />
<group name="{current-grouping-key()}">
<xsl:for-each-group select="current-group()" group-by="OrderId">
<xsl:variable name="order-id" select="current-grouping-key()" />
<xsl:element name="STATUS">
<xsl:attribute name="ID"><xsl:value-of select="$group-name" /></xsl:attribute>
<xsl:attribute name="DESCRIPTION">Goods <xsl:value-of select="$group-name" /></xsl:attribute>
<xsl:element name="ORDER">
<xsl:attribute name="ID"><xsl:value-of select="$order-id" /></xsl:attribute>
<xsl:for-each select="current-group()">
<xsl:if test="$group-name = 'Shipped'">
<xsl:call-template name="Shipped">
<xsl:with-param name="nodes">
<xsl:copy-of select="." />
</xsl:with-param>
</xsl:call-template>
</xsl:if>
<xsl:if test="$group-name = 'Cancelled'">
<xsl:call-template name="Cancelled">
<xsl:with-param name="nodes">
<xsl:copy-of select="." />
</xsl:with-param>
</xsl:call-template>
</xsl:if>
</xsl:for-each>
</xsl:element>
</xsl:element>
</xsl:for-each-group>
</group>
</xsl:for-each-group>
</Orders>
</xsl:template>
<xsl:template name="Shipped">
<xsl:param name="nodes">
</xsl:param>
<xsl:element name="ORDER_ITEM">
<xsl:attribute name="ID"><xsl:value-of select="$nodes/OrderStatusEvent/ItemId" /></xsl:attribute>
</xsl:element>
</xsl:template>
<xsl:template name="Cancelled">
<xsl:param name="nodes"></xsl:param>
<xsl:element name="ORDER_ITEM">
<xsl:attribute name="ID"><xsl:value-of select="$nodes/OrderStatusEvent/ItemId" /></xsl:attribute>
</xsl:element>
</xsl:template>
</xsl:stylesheet>
It is easier to use literal result elements and attribute value templates as long as you don't need to compute element or attribute names at run-time and I don't think you need the two templates and call-template, it suffices to use
<xsl:stylesheet xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
exclude-result-prefixes="xs"
version="2.0">
<xsl:output omit-xml-declaration="yes" indent="yes" />
<xsl:template match="OrderStatusUpdate/OrderStatusEvents">
<Orders>
<xsl:for-each-group select="OrderStatusEvent" group-by="OrderStatusDetails/OrderStatusDetail/StatusName">
<xsl:variable name="group-name" select="current-grouping-key()" />
<group name="{current-grouping-key()}">
<xsl:for-each-group select="current-group()" group-by="OrderId">
<xsl:variable name="order-id" select="current-grouping-key()" />
<STATUS ID="{$group-name}" DESCRIPTION="Goods {$group-name}">
<ORDER ID="{$order-id}">
<xsl:apply-templates select="current-group()"/>
</ORDER>
</STATUS>
</xsl:for-each-group>
</group>
</xsl:for-each-group>
</Orders>
</xsl:template>
<xsl:template match="OrderStatusEvent">
<ORDER_ITEM ID="{ItemId}"/>
</xsl:template>
</xsl:stylesheet>

Xslt for splitting a url in parts and combing them again

I want to build a sort of breadcrumb. I have link for example
http://server/site1/site2/site3
and want to build something like
http://serverhttp://server/site1...
How can I do this with xslt?
This can be accomplished with a recursive template:
<xsl:stylesheet version="1.0" xmlns:xsl="http://www.w3.org/1999/XSL/Transform">
<xsl:output method="xml" indent="yes"/>
<xsl:variable name="urlSample" select="'http://server/site1/site2/site3'" />
<xsl:template match="/">
<xsl:call-template name="UrlLinks">
<xsl:with-param name="url" select="$urlSample" />
</xsl:call-template>
</xsl:template>
<xsl:template name="UrlLinks">
<xsl:param name="url" />
<xsl:call-template name="UrlLinksIter">
<xsl:with-param name="portionSoFar" select="concat(substring-before($url, '://'), '://')" />
<xsl:with-param name="remainder" select="concat(substring-after($url, '://'), '/')" />
</xsl:call-template>
</xsl:template>
<xsl:template name="UrlLinksIter">
<xsl:param name="portionSoFar" />
<xsl:param name="remainder" />
<xsl:variable name="nextPart" select="substring-before($remainder, '/')" />
<xsl:variable name="nextRemainder" select="substring-after($remainder, '/')" />
<xsl:if test="normalize-space($nextRemainder) or normalize-space($nextPart)">
<xsl:variable name="url" select="concat($portionSoFar, $nextPart)"/>
<xsl:if test="normalize-space($nextPart)">
<!-- $nextPart could be empty if there are multiple slashes in a row-->
<a href="{$url}">
<xsl:value-of select="$url"/>
</a>
</xsl:if>
<xsl:call-template name="UrlLinksIter">
<xsl:with-param name="portionSoFar" select="concat($url, '/')" />
<xsl:with-param name="remainder" select="$nextRemainder" />
</xsl:call-template>
</xsl:if>
</xsl:template>
</xsl:stylesheet>
When this is run on any input (since the sample value is in a variable here) this produces:
http://server
http://server/site1
http://server/site1/site2
http://server/site1/site2/site3

Umbraco outputting filesize

I'm trying to output the correct size for pdf files that has been uploaded.
But the only output is 0 - what am I doing wrong?
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE xsl:stylesheet [ <!ENTITY nbsp " "> ]>
<xsl:stylesheet
version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:msxml="urn:schemas-microsoft-com:xslt"
xmlns:umbraco.library="urn:umbraco.library" xmlns:Exslt.ExsltCommon="urn:Exslt.ExsltCommon" xmlns:Exslt.ExsltDatesAndTimes="urn:Exslt.ExsltDatesAndTimes" xmlns:Exslt.ExsltMath="urn:Exslt.ExsltMath" xmlns:Exslt.ExsltRegularExpressions="urn:Exslt.ExsltRegularExpressions" xmlns:Exslt.ExsltStrings="urn:Exslt.ExsltStrings" xmlns:Exslt.ExsltSets="urn:Exslt.ExsltSets" xmlns:umbraco.contour="urn:umbraco.contour"
exclude-result-prefixes="msxml umbraco.library Exslt.ExsltCommon Exslt.ExsltDatesAndTimes Exslt.ExsltMath Exslt.ExsltRegularExpressions Exslt.ExsltStrings Exslt.ExsltSets umbraco.contour ">
<xsl:output method="xml" omit-xml-declaration="yes" />
<xsl:param name="currentPage"/>
<xsl:variable name="documentTypeAlias" select="string('PdfItem')"/>
<xsl:variable name="size" select="#currentpage/data [#alias = 'umbracoBytes']" />
<xsl:variable name="sizeAndSuffix">
<xsl:choose>
<xsl:when test="$size >= 1073741824">
<xsl:value-of select="format-number($size div 1073741824,'#,###')"/>
<xsl:text>GB</xsl:text>
</xsl:when>
<xsl:when test="$size >= 1048576">
<xsl:value-of select="format-number($size div 1048576,'#,###')"/>
<xsl:text>MB</xsl:text>
</xsl:when>
<xsl:when test="$size >= 1024">
<xsl:value-of select="format-number($size div 1024,'#,###')"/>
<xsl:text>KB</xsl:text>
</xsl:when>
<xsl:when test="$size > 0 and $size < 1024">
<xsl:value-of select="format-number($size div 0,'#,###')"/>
<xsl:text> Bytes</xsl:text>
</xsl:when>
<xsl:otherwise>
<xsl:text>0 Bytes</xsl:text>
</xsl:otherwise>
</xsl:choose>
</xsl:variable>
<xsl:template match="/">
<xsl:for-each select="$currentPage/node [#nodeTypeAlias = $documentTypeAlias and string(data [#alias='umbracoNaviHide']) != '0']">
<div class="pdf">
<a>
<xsl:attribute name="class">pdfmenu</xsl:attribute>
<xsl:attribute name="href"><xsl:value-of select="umbraco.library:GetMedia(./data[#alias='pdf'], 0)/data [#alias = 'umbracoFile']"/></xsl:attribute>
<strong><xsl:value-of select="#nodeName"/><span>
(<xsl:value-of select="$sizeAndSuffix"/>)</span></strong>
<em><xsl:value-of select="data [#alias = 'PDFBeskrivelse']"/></em>
<img>
<xsl:attribute name="src"><xsl:value-of select="data [#alias = 'PDFBillede']"/></xsl:attribute>
<xsl:attribute name="alt"></xsl:attribute>
<xsl:attribute name="height">200</xsl:attribute>
<xsl:attribute name="width">141</xsl:attribute>
</img>
</a>
</div>
</xsl:for-each>
</xsl:template>
</xsl:stylesheet>
Alright, I've move the size variable into the for-each loop, as it varies per file and fixed a few typos:
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE xsl:stylesheet [
<!ENTITY nbsp " ">
]>
<xsl:stylesheet
version="1.0"
xmlns:xsl="http://www.w3.org/1999/XSL/Transform"
xmlns:msxml="urn:schemas-microsoft-com:xslt"
xmlns:umbraco.library="urn:umbraco.library" xmlns:Exslt.ExsltCommon="urn:Exslt.ExsltCommon" xmlns:Exslt.ExsltDatesAndTimes="urn:Exslt.ExsltDatesAndTimes" xmlns:Exslt.ExsltMath="urn:Exslt.ExsltMath" xmlns:Exslt.ExsltRegularExpressions="urn:Exslt.ExsltRegularExpressions" xmlns:Exslt.ExsltStrings="urn:Exslt.ExsltStrings" xmlns:Exslt.ExsltSets="urn:Exslt.ExsltSets" xmlns:umbraco.contour="urn:umbraco.contour"
exclude-result-prefixes="msxml umbraco.library Exslt.ExsltCommon Exslt.ExsltDatesAndTimes Exslt.ExsltMath Exslt.ExsltRegularExpressions Exslt.ExsltStrings Exslt.ExsltSets umbraco.contour ">
<xsl:output method="xml" omit-xml-declaration="yes" />
<xsl:param name="currentPage"/>
<xsl:variable name="documentTypeAlias" select="string('PdfItem')"/>
<xsl:template match="/">
<xsl:for-each select="$currentPage/node [#nodeTypeAlias = $documentTypeAlias and string(data [#alias='umbracoNaviHide']) != '0']">
<xsl:if test="string(data [#alias = 'pdf']) != ''">
<xsl:variable name="size" select="umbraco.library:GetMedia(data[#alias='pdf'], 0)/data [#alias = 'umbracoFile']" />
<xsl:variable name="sizeAndSuffix">
<xsl:choose>
<xsl:when test="$size >= 1073741824">
<xsl:value-of select="format-number($size div 1073741824,'#,###')"/>
<xsl:text>GB</xsl:text>
</xsl:when>
<xsl:when test="$size >= 1048576">
<xsl:value-of select="format-number($size div 1048576,'#,###')"/>
<xsl:text>MB</xsl:text>
</xsl:when>
<xsl:when test="$size >= 1024">
<xsl:value-of select="format-number($size div 1024,'#,###')"/>
<xsl:text>KB</xsl:text>
</xsl:when>
<xsl:when test="$size > 0 and $size < 1024">
<xsl:value-of select="format-number($size div 0,'#,###')"/>
<xsl:text> Bytes</xsl:text>
</xsl:when>
<xsl:otherwise>
<xsl:text>0 Bytes</xsl:text>
</xsl:otherwise>
</xsl:choose>
</xsl:variable>
<div class="pdf">
<a>
<xsl:attribute name="class">pdfmenu</xsl:attribute>
<xsl:attribute name="href">
<xsl:value-of select="umbraco.library:GetMedia(data[#alias='pdf'], 0)/data [#alias = 'umbracoFile']"/>
</xsl:attribute>
<strong>
<xsl:value-of select="#nodeName"/>
<span>
(<xsl:value-of select="$sizeAndSuffix"/>)
</span>
</strong>
<em>
<xsl:value-of select="data [#alias = 'PDFBeskrivelse']"/>
</em>
<img>
<xsl:attribute name="src">
<xsl:value-of select="data [#alias = 'PDFBillede']"/>
</xsl:attribute>
<xsl:attribute name="alt"></xsl:attribute>
<xsl:attribute name="height">200</xsl:attribute>
<xsl:attribute name="width">141</xsl:attribute>
</img>
</a>
</div>
</xsl:if>
</xsl:for-each>
</xsl:template>
</xsl:stylesheet>
That should do the trick.

Resources