[XSL-LIST Mailing List Archive Home] [By Thread] [By Date] [Recent Entries] [Reply To This Message]

Linear sequence of moves to rectangular board

Subject: Linear sequence of moves to rectangular board
From: Stuart Yeates <stuart.yeates@xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx>
Date: Thu, 12 May 2005 21:40:37 +0100 (BST)
linear sequence
I'm transforming a linear sequence of moves into the state of a rectangular board (initially in HTML, images to come, maybe in SVG later). The game I'm modelling is the game of, played with black and white stones on a rectangular grid. Stones can be added  and rarely removed. An empty state is sometimes in a transient state called "ko."

The attached xml2xhtml.xslt file transforms test1.go.xml into html, with the board in a table and calculates the number of moves and captures for black and white. By passing in different values of $moves, you can step through the moves in the game.

I'm aiming for maximum portability and maximum inter-operability. The XML file format is still flexible.

I have some questions about where to go from here:

(*) In real games $size is normally 19 (but potentially unbounded), and there are approximately 1/2 (size*size) moves per game. My recursive solution has a max depth of (2*size)+(1/2 (size*size)) ~= 200, is this likely to be a problem for any implementations? I'm particular thinking of transformations in browsers. 

(*) Maybe it's because I'm used to the gracefully recursion of scheme/lisp, but the recursion here feels rather clunky. Am I doing something wrong?

(*) I'd like to define calculate a value for $moves (commented out) and use it if no value is passed in on the command line/url, but I can't work out how. This doesn't work:

<xsl:if test="$moves = ''">
  <xsl:variable name="moves" select="count(//move) -1"/>
</xsl:if>

as the variable has the wrong scope, and $move access is an error if undefined. So how do I make it robust in the face of bad/missing input from the commandline or url?

(*) Currently I'm using explicit "order" attribute. The attribute seems redundant (and potentially error prone), is there a better way to do this?

(*) I would like to represent variations, moving from a linear sequence to a sparse tree, as shown in test2.go.xml and test3.go.xml. The desired behavour would be to display at each moves the possible moves following and provide a way to generate the board state for that move, much as incrementing $move does currently. I'm not sure whether restructuring the XML (which is not yet fixed) format would help.

Looking at other code and the manuals I have access to the ancestor axis seems like it should be the solution, but I can't quite seem to join up the dots. I can can see that one approach could be to transform test3.go.xml into a format like test1.go.xml, and then to html, but I'm not sure how portable two step transformations are.

(*) There are some rather obscure Unicode characters for representing go stones (on the same code-page as the chess pieces). I'm extremely doubtful about their support in a range of browsers, is there a good way to find out how widely they're used? I'm particularly interested in support for them amoung far-east localised windows versions, since this is where most go players are. 

cheers
stuart

---------

<?xml version='1.0'?>
<!-- xml2xhtml.xslt -->
<xsl:stylesheet version="1.0"
  xmlns:xsl="http://www.w3.org/1999/XSL/Transform">

  <xsl:output method="xml" indent="yes"/>

  <xsl:variable name="size" select="//@dimensiony"/>

  <!--<xsl:variable name="moves" select="count(//move) -1"/>-->

	<!-- do the rows -->

    <xsl:template name="tablerow">
        <xsl:param name="rownumber"/>
         <tr>

        <xsl:call-template name="tablecolumn">
            <xsl:with-param name="columnnumber" select="$size -1"/>
            <xsl:with-param name="rownumber" select="$rownumber"/>
        </xsl:call-template>

        </tr>

       <xsl:if test="$rownumber &gt; 0">
          <xsl:call-template name="tablerow">
            <xsl:with-param name="rownumber"> 
 		<xsl:value-of select="$rownumber - 1"/>
            </xsl:with-param>
          </xsl:call-template>
        </xsl:if>
    </xsl:template>


	<!-- do the columns -->	

    <xsl:template name="tablecolumn">
        <xsl:param name="rownumber"/>
        <xsl:param name="columnnumber"/>
         <td>

          <xsl:call-template name="tablecell">
            <xsl:with-param name="rownumber"> 
 		<xsl:value-of select="$rownumber"/>
            </xsl:with-param>
            <xsl:with-param name="columnnumber"> 
 		<xsl:value-of select="$columnnumber"/>
            </xsl:with-param>
          </xsl:call-template>

        </td>
       <xsl:if test="$columnnumber  &gt; 0">
          <xsl:call-template name="tablecolumn">
            <xsl:with-param name="rownumber"> 
 		<xsl:value-of select="$rownumber"/>
            </xsl:with-param>
            <xsl:with-param name="columnnumber"> 
 		<xsl:value-of select="$columnnumber - 1"/>
            </xsl:with-param>
          </xsl:call-template>
        </xsl:if>
    </xsl:template>

	<!-- do a single cell -->	

    <xsl:template name="tablecell">
        <xsl:param name="rownumber"/>
        <xsl:param name="columnnumber"/>

          <xsl:call-template name="tablecellmove">
            <xsl:with-param name="rownumber"> 
 		<xsl:value-of select="$rownumber"/>
            </xsl:with-param>
            <xsl:with-param name="columnnumber"> 
 		<xsl:value-of select="$columnnumber"/>
            </xsl:with-param>
            <xsl:with-param name="status">empty</xsl:with-param>
            <xsl:with-param name="move"> 
 		<xsl:value-of select="0"/>
            </xsl:with-param>
          </xsl:call-template>

    </xsl:template>

    <xsl:template name="tablecellmove">
        <xsl:param name="rownumber"/>
        <xsl:param name="columnnumber"/>
        <xsl:param name="status"/>
        <xsl:param name="move"/>

        <!-- <xsl:value-of select="$status"/> -->

        <xsl:choose>

          <xsl:when test="$move = $moves">
            <xsl:value-of select="$status"/>
          </xsl:when>

          <xsl:when test="//move[@order=$move]/ko/vertex[@x=$rownumber][@y=$columnnumber]">
            <xsl:call-template name="tablecellmove">
              <xsl:with-param name="rownumber"> 
 		<xsl:value-of select="$rownumber"/>
              </xsl:with-param>
              <xsl:with-param name="columnnumber"> 
 	        <xsl:value-of select="$columnnumber"/>
              </xsl:with-param>
              <xsl:with-param name="status">ko</xsl:with-param>
              <xsl:with-param name="move"> 
 		<xsl:value-of select="$move + 1"/>
              </xsl:with-param>
            </xsl:call-template>
          </xsl:when>

          <xsl:when test="//move[@order=$move]/remove/vertex[@x=$rownumber][@y=$columnnumber]">
            <xsl:call-template name="tablecellmove">
              <xsl:with-param name="rownumber"> 
 		<xsl:value-of select="$rownumber"/>
              </xsl:with-param>
              <xsl:with-param name="columnnumber"> 
 	        <xsl:value-of select="$columnnumber"/>
              </xsl:with-param>
              <xsl:with-param name="status">empty</xsl:with-param>
              <xsl:with-param name="move"> 
 		<xsl:value-of select="$move + 1"/>
              </xsl:with-param>
            </xsl:call-template>
          </xsl:when>
          
          <xsl:when test="//move[@order=$move]/vertex[@x=$rownumber][@y=$columnnumber]">
            <xsl:call-template name="tablecellmove">
              <xsl:with-param name="rownumber"> 
 		<xsl:value-of select="$rownumber"/>
              </xsl:with-param>
              <xsl:with-param name="columnnumber"> 
 	        <xsl:value-of select="$columnnumber"/>
              </xsl:with-param>
              <xsl:with-param name="status">
                <xsl:value-of select="//move[@order=$move]/@colour"/>
              </xsl:with-param>
              <xsl:with-param name="move"> 
 		<xsl:value-of select="$move + 1"/>
              </xsl:with-param>
            </xsl:call-template>
          </xsl:when>

          <xsl:when test="$status = 'ko'">
            <xsl:call-template name="tablecellmove">
              <xsl:with-param name="rownumber"> 
 		<xsl:value-of select="$rownumber"/>
              </xsl:with-param>
              <xsl:with-param name="columnnumber"> 
 	        <xsl:value-of select="$columnnumber"/>
              </xsl:with-param>
              <xsl:with-param name="status">empty</xsl:with-param>
              <xsl:with-param name="move"> 
 		<xsl:value-of select="$move + 1"/>
              </xsl:with-param>
            </xsl:call-template>
          </xsl:when>
          
          <xsl:when test="//move[@order=$move]">
            <xsl:call-template name="tablecellmove">
              <xsl:with-param name="rownumber"> 
 		<xsl:value-of select="$rownumber"/>
              </xsl:with-param>
              <xsl:with-param name="columnnumber"> 
 	        <xsl:value-of select="$columnnumber"/>
              </xsl:with-param>
              <xsl:with-param name="status"> 
 		<xsl:value-of select="$status"/>
              </xsl:with-param>
              <xsl:with-param name="move"> 
 		<xsl:value-of select="$move + 1"/>
              </xsl:with-param>
            </xsl:call-template>
          </xsl:when>

          <xsl:otherwise>
            <xsl:value-of select="$status"/>
          </xsl:otherwise>
	</xsl:choose>
	
    </xsl:template>

  <xsl:template match="game">
    <html>
       <xsl:apply-templates/>

    <body>

    <p>Board size: <xsl:value-of select="$size"/></p>

    <p>Moves: <xsl:value-of select="$moves"/></p>

    <p>Black captures: <xsl:value-of select="count(//move[@colour = 'black'][@order &lt; $moves]/remove/vertex)"/></p>

    <p>White captures: <xsl:value-of select="count(//move[@colour = 'white'][@order &lt; $moves]/remove/vertex)"/></p>

      <table>
        <xsl:call-template name="tablerow">
            <xsl:with-param name="rownumber" select="$size - 1"/>
        </xsl:call-template>
     </table>
    </body>
    </html>	
  </xsl:template>

</xsl:stylesheet>


---------

<!-- test1.go.xml -->


<?xml version="1.0"?>
<?xml-stylesheet type="text/xml" href="xml2xhtml.xslt"?>
<game>
  <board type="rectangular" dimensiony="3" dimensionx="3" />
  <move colour="black" order="0" >
    <vertex x="0" y="1" />
  </move>
  <annotate>
    <text></text>
  </annotate>
  <move colour="white" order="1">
    <vertex x="0" y="0" />
  </move>
  <move colour="black" order="2">
    <vertex x="1" y="0" />
    <remove>
      <vertex x="0" y="0" />
    </remove>
    <ko>
      <vertex x="0" y="0" />
    </ko>
  </move>
  <annotate>
    <score type="estimated" estimator="gnugo" version="9.7"/>
  </annotate>
  <move colour="white" order="3">
    <vertex x="1" y="1" />
  </move>
  <move colour="black" order="4">
    <vertex x="0" y="0" />
  </move>
</game>



---------

<!-- test2.go.xml -->

<?xml version="1.0"?>
<?xml-stylesheet type="text/xml" href="./xml2xhtml.xslt"?>
<game>
  <board type="rectangular" dimensiony="4" dimensionx="4" />
  <annotation> 
     <text> this is a comment at the start of the file</text>
  </annotation>
  <move colour="black" order="0" id="00001">
    <vertex x="0" y="1" />
  </move>
  <move colour="white" order="1" id="00002">
    <vertex x="0" y="0" />
  </move>
  <move colour="black" order="2" id="00003">
    <vertex x="1" y="0" />
    <remove>
      <vertex x="0" y="0" />
    </remove>
  </move>

  <variation>
  <move colour="white" order="3" id="00004">
    <vertex x="2" y="1" />
  </move>
  <move colour="black" order="4" id="00005">
    <vertex x="1" y="1" />
  </move>
  </variation>

  <variation>
  <move colour="white" order="3" id="00006">
    <vertex x="1" y="1" />
  </move>
  <move colour="black" order="4" id="00007">
    <vertex x="0" y="0" />
  </move>
  </variation>

</game>




---------

<!-- test3.go.xml -->

<?xml version="1.0"?>
<?xml-stylesheet type="text/xml" href="./xml2xhtml.xslt"?>
<game>
  <board type="rectangular" dimensiony="4" dimensionx="4" />
  <annotation> 
     <text> this is a comment at the start of the file</text>
  </annotation>
  <move colour="black" order="0" id="00001">
    <vertex x="0" y="1" />
  </move>
  <move colour="white" order="1" id="00002">
    <vertex x="0" y="0" />
  </move>
  <move colour="black" order="2" id="00003">
    <vertex x="1" y="0" />
    <remove>
      <vertex x="0" y="0" />
    </remove>
  </move>

  <variation>
    <move colour="white" order="3" id="00004">
      <vertex x="2" y="1" />
    </move>
    <variation>
      <move colour="black" order="4" id="00005">
        <vertex x="1" y="1" />
      </move>
    </variation>
    <variation>
      <move colour="black" order="4" id="00006">
        <vertex x="1" y="2" />
      </move>
    </variation>
  </variation>

  <variation>
    <move colour="white" order="3" id="00007">
      <vertex x="1" y="1" />
    </move>
    <move colour="black" order="4" id="00008">
      <vertex x="0" y="0" />
    </move>
  </variation>

</game>

Current Thread

PURCHASE STYLUS STUDIO ONLINE TODAY!

Purchasing Stylus Studio from our online shop is Easy, Secure and Value Priced!

Buy Stylus Studio Now

Download The World's Best XML IDE!

Accelerate XML development with our award-winning XML IDE - Download a free trial today!

Don't miss another message! Subscribe to this list today.
Email
First Name
Last Name
Company
Subscribe in XML format
RSS 2.0
Atom 0.3
Site Map | Privacy Policy | Terms of Use | Trademarks
Free Stylus Studio XML Training:
W3C Member
Stylus Studio® and DataDirect XQuery ™are products from DataDirect Technologies, is a registered trademark of Progress Software Corporation, in the U.S. and other countries. © 2004-2013 All Rights Reserved.