User Tools

Site Tools


en:user:gs3_sample_format_statements

Differences

This shows you the differences between two versions of the page.

Link to this comparison view

Both sides previous revisionPrevious revision
Next revision
Previous revision
en:user:gs3_sample_format_statements [2016/10/09 22:51] – [Using javascript to change the display] kjdonen:user:gs3_sample_format_statements [2023/03/13 01:46] (current) – external edit 127.0.0.1
Line 1: Line 1:
 +
 +
 +
  
 ====== Sample Greenstone3 Format Statements ====== ====== Sample Greenstone3 Format Statements ======
Line 154: Line 157:
  
  
-===== Linking metadata to a search =====+===== Handling multi-valued metadata ===== 
 + 
 +==== Displaying values in a bulleted list ==== 
 + 
 +Say we want to display all the authors of a document in a bulleted list. We can't just use <gsf:metadata name="dc.Creator"/> as it will put all the names out in a comma separated list. However, we can use the prefix and suffix options to put some HTML before and after each author. 
 + 
 +<code> 
 +<ul> 
 +<gsf:metadata name="dc.Creator" separator=""><prefix><gsf:html>&lt;li&gt;&lt;b&gt;</gsf:html></prefix> 
 +<suffix><gsf:html>&lt;/b&gt;&lt;/li&gt;</gsf:html></suffix></gsf:metadata> 
 +</ul> 
 +</code> 
 + 
 +This will produce output like: 
 + 
 +<ul><li><b>John Smith</b></li><li><b>Katherine Don</b></li><li><b>Cliff Richard</b></li></ul> 
 +==== Linking metadata to a search ==== 
 + 
 +How to link metadata values to a search for that value?
  
-How to link metadata values to a search for that value. 
 For example, say a document has several authors, stored as dc.Creator metadata. You can display a list of the authors, each one linked to a search of the dc.Creator index for that author. For example, say a document has several authors, stored as dc.Creator metadata. You can display a list of the authors, each one linked to a search of the dc.Creator index for that author.
  
Line 226: Line 246:
  
 ==== Adding javascript into a page ==== ==== Adding javascript into a page ====
 +
 +To add the javascript into an XSL file, you encase it in script tags. And because XSL will escape double quotes by default, you need to put it inside **<xsl:text disable-output-escaping="yes">** tags.
 +
 +<code>
 +<script type="text/javascript">
 +  <xsl:text disable-output-escaping="yes">
 +    function humanReadableFileSize(bytes)
 +    {
 +      var filesize = bytes + " bytes";
 +      if (bytes > 1048576) {
 +        filesize = Math.round(bytes / 1048576.0) + " MB";
 +      }
 +      else if (bytes > 1024) {
 + filesize = Math.round(bytes/1024.0)+ " KB";
 +      }
 +      return filesize;
 +    }
 +  </xsl:text>
 +</script>
 +
 +</code>
 +
 +There are multiple places you can use to add some javascript into your library.
 +
 +  * **All pages, all collections**
 +
 +**web/interfaces/default/transform/layouts/header.xsl** contains global templates used in the headers of all pages in the library. The **create-html-header** template sets up the header for each page. If you add your script element into here, it will appear in all pages in your library.
 +
 +  * **Only classifier pages, all collections**
 +
 +The **create-html-header** template calls an additional template **additionalHeaderContent**, which can be used to customise which pages get the extra javascript. For example, if we only want this function to be available for classifier pages, we can edit **web/interfaces/default/transform/pages/classifier.xsl**. Copy the **<xsl:template name="additionalHeaderContent">** element from the header.xsl file into the classifier.xsl file. Add the new script tag into it.
 +
 +  * **All pages, single collection**
 +
 +The **additionalHeaderContent** template calls further specifric templates, including **additionalHeaderContent-collection**. This template can be added into the collection's collectionConfig.xml file to modify the header just for that collection. If you want the javascript to be available for all pages in this collection, add the template to the global format statement. In GLI, select global. In the file, it is the top level <format> element.
 +
 +<code>
 +<xsl:template name="additionalHeaderContent-collection">
 +  <script type="text/javascript">
 +    <xsl:text disable-output-escaping="yes">
 +    function humanReadableFileSize(bytes)
 +    {
 +      .. function content here...
 +    }
 +    </xsl:text>
 +  </script>
 +</xsl:template>
 +</code>
 +
 +  * **single page, single collection**
 +
 +Say you just want to use this new javascript on the classifier pages, then add the template into the main classifier format element. Or add it into the format element of a specific classifier and it will only be available for that single classifier. 
  
 ==== Using the javascript in the format statement ==== ==== Using the javascript in the format statement ====
Line 234: Line 306:
  
 <code> <code>
-      <gsf:template match="documentNode"> +<gsf:template match="documentNode"> 
- <td valign="top"> +  <td valign="top"> 
-   <gsf:link type="document"> +    <gsf:link type="document"> 
-     <gsf:icon type="document"/> +      <gsf:icon type="document"/> 
-   </gsf:link> +    </gsf:link> 
- </td> +  </td> 
- <td valign="top"> +  <td valign="top"> 
-          <gsf:metadata name="dc.Title"/> +    <gsf:metadata name="dc.Title"/> 
- </td> +  </td> 
-        <td> +  <td> 
-          <gsf:metadata name="FileSize"/> +    <gsf:metadata name="FileSize"/> 
-        </td> +  </td> 
-      </gsf:template>+</gsf:template>
 </code> </code>
  
 We will modify the third <td> element to display a human readable form. We will modify the third <td> element to display a human readable form.
  
-During development, we can use the simple document.write() method to output the result:+During development, we can use the simple **document.write()** method to output the result:
  
 <code> <code>
 <td> <td>
-<script type="text/javascript">document.write(humanReadableFileSize(<gsf:metadata name="FileSize"/>));</script>+<script type="text/javascript">document.write(humanReadableFileSize(<gsf:metadata name="FileSize"/>)); 
 +</script>
 </td> </td>
 </code> </code>
  
 +This lets us check that our function is correct and we are getting the right metadata. However, using "document.write" is not considered good practice. And if you are adding this in a classifier which has bookshelves, then it ends up replacing the entire page with the filesize!
 +
 +Instead, we will need to add to the html of the td element. This means we need to give the td element an id so we can find it again. 
 +
 +If the <td> we are adding the filesize to contains only the filesize, then we can use the element.innerHTML() method to set the content. 
 +<code>
 +<td>
 +  <xsl:attribute name="id"><gsf:OID/>-fs</xsl:attribute>
 +  <script type="text/javascript"> 
 +    document.getElementById(<gsf:html>"</gsf:html><gsf:OID/>-fs<gsf:html>"</gsf:html>).innerHTML= humanReadableFileSize(<gsf:metadata name="FileSize"/>);
 +  </script>
 +</td>
 +</code>
 +
 +However, if this <td> element already has content, then we need to append the filesize, using element.appendChild() and document.createTextNode(). For example:
 +
 +<code>
 +<td>
 +  <xsl:attribute name="id"><gsf:OID/>-fs</xsl:attribute>
 +  ...other content here...
 +  <script type="text/javascript"> 
 +    document.getElementById(<gsf:html>"</gsf:html><gsf:OID/>-fs<gsf:html>"</gsf:html>).appendChild(document.createTextNode(humanReadableFileSize(<gsf:metadata name="FileSize"/>)));
 +  </script>
 +</td>
 +</code>
 +
 +Element ids need to be unique, so in this case we will use the document id (**<gsf:OID/>**) with **-fs** just in case the OID has been used as an id elsewhere in the page. Because we are not assigning a simple string to the id attribute, we need to use the **<xsl:attribute>** element. We cannot write
 +**<td id="<gsf:OID/>">**.
 +
 +To set an element's text, we use **document.getElementById("id").innerHTML = "xxx"**.
 +**document.getElementById** finds the specified element, and **element.innerHTML = "xxx"** sets its text.
 +
 +We set the text to be the result of calling our function on the filesize metadata.
 +
 +To add to an element's content, we find the node using **document.getElementById("id")**, we create a text node using **document.createTextNode("xxx")** and append it to the element using **element.appendChild(node)**.
 +
 +One further tricky part. We want to write **document.getElementById("<gsf:OID/>-fs")**. However, the XSL transform process will escape the double quotes with &quot; and then the javascript will be invalid. To get around this, we use **<xsl:text disable-output-escaping="yes">"</xsl:text>**.
  
 +i.e. **document.getElementById(<xsl:text disable-output-escaping="yes">"</xsl:text><gsf:OID/>-fs<xsl:text disable-output-escaping="yes">"</xsl:text>)**
  
 +Greenstone provides a shorthand: **<gsf:html>"</gsf:html>**, which gets resolved to <xsl:text> with the disable-output-escaping attribute set. 
  
  
  
  
en/user/gs3_sample_format_statements.1476053474.txt.gz · Last modified: 2016/10/09 22:51 by kjdon