Table of Contents

tablemath Plugin

Compatible with DokuWiki

  • 2025-05-14 "Librarian" unknown
  • 2024-02-06 "Kaos" no
  • 2023-04-04 "Jack Jackrum" unknown
  • 2022-07-31 "Igor" no

plugin Adds calculated column to built-in table syntax

Last updated on
2009-08-24
Provides
Syntax

Similar to tablecalc

Tagged with calculation, math, tables

There are significant changes to the previous version, please look at the usage section for new syntax.

Installation

  1. create a folder named “tablemath” in the plugin folder
  2. create 2 files named “syntax.php” and “script.js” in the in tablemath folder, copy the file content below into those 2 files
syntax.php
<?php
// must be run within DokuWiki
if(!defined('DOKU_INC')) die();
 
if(!defined('DOKU_PLUGIN')) define('DOKU_PLUGIN',DOKU_INC.'lib/plugins/');
require_once(DOKU_PLUGIN.'syntax.php');
 
/**
 * All DokuWiki plugins to extend the parser/rendering mechanism
 * need to inherit from this class
 */
class syntax_plugin_tablemath extends DokuWiki_Syntax_Plugin {
 
    /**
     * return some info
     */
    function getInfo() {
        return array(
                'author' => 'James GuanFeng Lin',
                'email'  => 'guanfenglin@gmail.com',
                'date'   => '2009-08-24',
                'name'   => 'Table Math Plugin',
                'desc'   => 'Enables calculated columns in built in table syntax',
                'url'    => 'https://www.dokuwiki.org/plugin:tablemath',
                );
    }
 
    function getType() { return 'substition'; }
    function getSort() { return 1213; }
 
    /**
     * Connect pattern to lexer
     */
    function connectTo($mode) {
        $this->Lexer->addSpecialPattern("~~=[a-zA-Z0-9_]*\([0-9,:]*\)~~", $mode, 'plugin_tablemath');
    }
 
    /**
     * Handle the match
     */
    function handle($match, $state, $pos, &$handler) {
        global $ID, $ACT, $INFO;
        $match = str_replace('~~', '', $match);
        $match = str_replace('=', '', $match);
        $tmp = explode('(', $match);
        if (count($tmp)>1)
        {
                $tmp[1] = str_replace(')', '', $tmp[1]);
                return array('method'=>$tmp[0],'set'=>$tmp[1], 'divid'=>'tm'.rand());
        }
        return array();
    }
 
    function render($mode, &$renderer, $data) {
        global $INFO, $ID, $conf;
        if($mode == 'xhtml'){
                  // get discussion meta file name
          $renderer->doc .= '<html><div id="'.$data['divid'].'"><script type="text/javascript" defer="defer">tablemath("'.$data['divid'].'","'.$data['method'].'","'.$data['set'].'");</script></div></html>';
          return true;
        }
        return false;
    }
 
}
script.js
function tablemath(divID,method,rangeStr)
{
  var result;
  var div = document.getElementById(divID);
  var table = div.parentNode.parentNode.parentNode;
  var setArray = tmSetToArray(table, rangeStr);
  switch(method)
  {
        case 'sum':
        break;
        case 'avg':
        break;
        default:
                method = 'unknown';
        break;
  }
  eval('result = tm'+method+'(setArray);');
  div.innerHTML = result;
}
function tmSetToArray(table, rangeStr)
{
        //range should be like this x,y:x,y
        var range = rangeStr.split(':');
        var start = range[0].split(',');
        var end = range[1].split(',');
        var startX = start[0];
        var startY = start[1];
        var endX = end[0];
        var endY = end[1];
 
        var set = new Array();
        for(var x = startX; x<=endX; x++)
        {
                for(var y = startY; y<=endY; y++)
                {
                        set.push(tmParseValue(table.rows[y].cells[x]));
                }
        }
        //alert(set);
        return set;
}
 
function tmParseValue(cell)
{
    var value = parseInt(cell.innerHTML);
    if (isNaN(value))
    {
      value = 0;
    }
    return value;
}
 
function tmunknown(setArray)
{
        return 'Error';
}
 
function tmsum(setArray)
{
        var sum = 0;
        for (var i=0; i<setArray.length; i++)
        {
                sum += setArray[i];
        }
        return sum;
}
 
function tmavg(setArray)
{
        return tmsum(setArray)/setArray.length;
}

Usage

Put the syntax into the desired column at the last row of the table.

~~=<Method name>(x,y:x1,y1)~~
Method nameDescription
sumcalculate the total value of defined set
avgcalculate the average value of defined set

Range set e.g. 1,1:2,2

defines the range in table you want your calculation method should apply to

0,0 1,0 2,0
0,1 1,1 2,1
0,2 1,2 2,2

Example

^ header1 ^ header2 ^ header3 ^ Average ^
| A       |  1      |  2      |  ~~=avg(1,1:2,1)~~  |
| B       |  2      |  3      |  ~~=avg(1,2:2,2)~~  |
| C       |  3      |  4      |  ~~=avg(1,3:2,3)~~  |
| Total   |  ~~=sum(1,1:1,3)~~  |  ~~=sum(2,1:2,3)~~  |  ~~=sum(1,1:2,3)~~  |

Limitations

Feedback

Please check if the calculations work with decimal points e.g. 10.2+1.5 /alwin kumar Thu Mar 18 2010/

James Powell, I am trying to reactivate this old plugin. I have a fixed version with no idea how to publish it. Leaving a message here in case any one is listening.

James Powell, looking to where I can host the plugin, will also need to update this page as the new source is more complex than what was ok before. Does any one even read these comments?

Yes, I do. Could you create a discussion on the forum?

Hello who ever you are, I have fixed table math plugin, I made massive use of two different AI tools to rewrite the plugin. Should I keep the results to my self, or is it ok to make the changes to this page to bring things up to date? With these changes it works with Kaos, the old code does not work on Kaos. My DokuWiki forum user name is BookerDewitt2. I contacted the original author and he told me he had abandoned the plugin and I was free to do what I wanted.