From 7445d7b5f4e3f11b97b62407e88a1cae1dd59026 Mon Sep 17 00:00:00 2001 From: Mario Voigt Date: Mon, 5 Jul 2021 15:41:42 +0200 Subject: [PATCH] added table support extension --- .../chip_scratches/chip_scratches.py | 38 - .../table_support/base_transform.py | 266 ++++++ .../fablabchemnitz/table_support/install | 3 + .../table_support/install_shortcuts.py | 57 ++ .../fablabchemnitz/table_support/keys.xml | 3 + .../fablabchemnitz/table_support/table.py | 850 ++++++++++++++++++ .../table_support/table_add_columns.inx | 23 + .../table_support/table_add_columns.py | 40 + .../table_support/table_add_guides.inx | 18 + .../table_support/table_add_guides.py | 34 + .../table_support/table_add_rows.inx | 23 + .../table_support/table_add_rows.py | 40 + .../table_support/table_create.inx | 28 + .../table_support/table_create.py | 38 + .../table_support/table_edit_columns.inx | 20 + .../table_support/table_edit_columns.py | 34 + .../table_support/table_edit_rows.inx | 20 + .../table_support/table_edit_rows.py | 34 + .../table_support/table_edit_table.inx | 22 + .../table_support/table_edit_table.py | 35 + .../table_support/table_edit_text.inx | 19 + .../table_support/table_edit_text.py | 34 + .../table_support/table_fit_height.inx | 18 + .../table_support/table_fit_height.py | 32 + .../table_support/table_fit_page.inx | 18 + .../table_support/table_fit_page.py | 31 + .../table_support/table_fit_width.inx | 18 + .../table_support/table_fit_width.py | 32 + .../table_support/table_merge_merge.inx | 18 + .../table_support/table_merge_merge.py | 32 + .../table_support/table_merge_split.inx | 18 + .../table_support/table_merge_split.py | 32 + .../table_support/table_remove_columns.inx | 18 + .../table_support/table_remove_columns.py | 32 + .../table_support/table_remove_rows.inx | 18 + .../table_support/table_remove_rows.py | 32 + 36 files changed, 1990 insertions(+), 38 deletions(-) create mode 100644 extensions/fablabchemnitz/table_support/base_transform.py create mode 100755 extensions/fablabchemnitz/table_support/install create mode 100755 extensions/fablabchemnitz/table_support/install_shortcuts.py create mode 100644 extensions/fablabchemnitz/table_support/keys.xml create mode 100644 extensions/fablabchemnitz/table_support/table.py create mode 100644 extensions/fablabchemnitz/table_support/table_add_columns.inx create mode 100755 extensions/fablabchemnitz/table_support/table_add_columns.py create mode 100644 extensions/fablabchemnitz/table_support/table_add_guides.inx create mode 100755 extensions/fablabchemnitz/table_support/table_add_guides.py create mode 100644 extensions/fablabchemnitz/table_support/table_add_rows.inx create mode 100755 extensions/fablabchemnitz/table_support/table_add_rows.py create mode 100644 extensions/fablabchemnitz/table_support/table_create.inx create mode 100755 extensions/fablabchemnitz/table_support/table_create.py create mode 100644 extensions/fablabchemnitz/table_support/table_edit_columns.inx create mode 100755 extensions/fablabchemnitz/table_support/table_edit_columns.py create mode 100644 extensions/fablabchemnitz/table_support/table_edit_rows.inx create mode 100755 extensions/fablabchemnitz/table_support/table_edit_rows.py create mode 100644 extensions/fablabchemnitz/table_support/table_edit_table.inx create mode 100755 extensions/fablabchemnitz/table_support/table_edit_table.py create mode 100644 extensions/fablabchemnitz/table_support/table_edit_text.inx create mode 100755 extensions/fablabchemnitz/table_support/table_edit_text.py create mode 100644 extensions/fablabchemnitz/table_support/table_fit_height.inx create mode 100644 extensions/fablabchemnitz/table_support/table_fit_height.py create mode 100644 extensions/fablabchemnitz/table_support/table_fit_page.inx create mode 100644 extensions/fablabchemnitz/table_support/table_fit_page.py create mode 100644 extensions/fablabchemnitz/table_support/table_fit_width.inx create mode 100644 extensions/fablabchemnitz/table_support/table_fit_width.py create mode 100644 extensions/fablabchemnitz/table_support/table_merge_merge.inx create mode 100644 extensions/fablabchemnitz/table_support/table_merge_merge.py create mode 100644 extensions/fablabchemnitz/table_support/table_merge_split.inx create mode 100755 extensions/fablabchemnitz/table_support/table_merge_split.py create mode 100644 extensions/fablabchemnitz/table_support/table_remove_columns.inx create mode 100755 extensions/fablabchemnitz/table_support/table_remove_columns.py create mode 100644 extensions/fablabchemnitz/table_support/table_remove_rows.inx create mode 100755 extensions/fablabchemnitz/table_support/table_remove_rows.py diff --git a/extensions/fablabchemnitz/chip_scratches/chip_scratches.py b/extensions/fablabchemnitz/chip_scratches/chip_scratches.py index 2d721a1f..3b3a4460 100644 --- a/extensions/fablabchemnitz/chip_scratches/chip_scratches.py +++ b/extensions/fablabchemnitz/chip_scratches/chip_scratches.py @@ -718,44 +718,6 @@ specks=( "M -0.0742332 -0.173289 c -0.15768,0.0526 0.1494,0.70495 0.19313,0.0823 -0.0947,-0.0745 -0.15647,-0.0942 -0.19313,-0.0823 z", ) -inxhead = """ - - <_name>ChipScratches - ca.sfu.AT.kurn.ChipScratches - chipScratches.py - inkex.py -""" - -inxfoot = """ - all - - - - - - - - -""" - -inxtype = { - "i" : '%s\n', - "f" : '%s\n', - "s" : '%s\n', - "b" : '%s\n', - "n" : '\n', - } - -inxbk = { - "tabs" : '\n\n', - "tab" : '\n\n', - "tabe" : '\n\n', - "lit" : '<_param name="%(s)s" type="description" >%(s)s\n', - - } - def mt( s ) : return s.isspace() or len(s) == 0 diff --git a/extensions/fablabchemnitz/table_support/base_transform.py b/extensions/fablabchemnitz/table_support/base_transform.py new file mode 100644 index 00000000..7365808b --- /dev/null +++ b/extensions/fablabchemnitz/table_support/base_transform.py @@ -0,0 +1,266 @@ +#!/usr/bin/env python3 +""" +base_transform.py +Base matemathical operations for SVG 3x3 matrices + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" + +import re +import inkex +import os +from math import * + +class BaseTransform(inkex.Effect): + unitMatrix = [[1, 0, 0], [0, 1, 0], [0, 0, 1]] + + def isset(self, v, i = None): + try: + if (i is None): + v + else: + v[i] + return True + except: + return False + + def __init__(self): + inkex.Effect.__init__(self) + + def sizeToPx(self, s, dim = "y"): + root = self.document.getroot() + try: + factor = float(root.attrib[inkex.addNS('export-' + dim + 'dpi', 'inkscape')]) + except: + factor = 90 + unit = '' + pattern = '[\\-\\d\\.]+([a-zA-Z][a-zA-Z])' + if (re.search(pattern, s)): + res = re.search(pattern, s) + unit = res.group(1) + pattern = '^([\\-\\d\\.]*)' + res = re.search(pattern, s) + n = float(res.group(1)) + if unit == 'cm': + return (n / 2.54) * factor + elif unit == 'ft': + return n * 12 * factor + elif unit == 'in': + return n * factor + elif unit == 'm': + return ((n * 10) / 2.54) * factor + elif unit == 'mm': + return ((n / 10) / 2.54) * factor + elif unit == 'pc': + return ((n * 2.36228956229) / 2.54) * factor + elif unit == 'pt': + return (((n / 2.83464646465) / 10) / 2.54) * factor + elif unit == 'px' or unit == '': + return n + + return 0 + + def transform(self, el): + result = self.unitMatrix + if (el.tag == inkex.addNS('svg', 'svg')): + return result + + if (not self.isset(el.attrib, 'transform')): + return self.multiply(self.transform(el.getparent()), result) + pattern = '(matrix|translate|scale|rotate|skewX|skewY)[\\s|,]*\\(([^\\)]*)\\)' + transforms = re.findall(pattern, el.attrib['transform']) + + for transform in transforms: + values = re.split('[\\s|,]+', transform[1]) + for i in range(len(values)): + values[i] = float(values[i]) + function = transform[0] + if (function == 'matrix'): + a = [[values[0], values[2], values[4]], + [values[1], values[3], values[5]], + [0, 0, 1]] + result = self.multiply(result, a) + elif (function == 'translate'): + a = [[1, 0, values[0]], + [0, 1, values[1]], + [0, 0, 1]] + result = self.multiply(result, a) + elif (function == 'scale'): + a = [[values[0], 0, 0], + [0, values[1], 0], + [0, 0, 1]] + result = self.multiply(result, a) + elif (function == 'rotate'): + if (len(values) == 1): + a = [[math.cos(values[0]), -math.sin(values[0]), 0], + [math.sin(values[0]), math.cos(values[0]), 0], + [0, 0, 1]] + result = self.multiply(result, a) + else: + a = [[1, 0, values[2]], + [0, 1, values[2]], + [0, 0, 1]] + result = self.multiply(result, a) + a = [[math.cos(values[0]), -math.sin(values[0]), 0], + [math.sin(values[0]), math.cos(values[0]), 0], + [0, 0, 1]] + result = self.multiply(result, a) + a = [[1, 0, -values[2]], + [0, 1, -values[2]], + [0, 0, 1]] + result = self.multiply(result, a) + elif (function == 'skewX'): + a = [[1, math.tan(values[0]), 0], + [0, 1, 0], + [0, 0, 1]] + result = self.multiply(result, a) + elif (function == 'skewY'): + a = [[1, 0, 0], + [math.tan(values[0]), 1, 0], + [0, 0, 1]] + result = self.multiply(result, a) + + return self.multiply(self.transform(el.getparent()), result) + + + def getPosition(self, el): + if not self.isset(el.attrib, 'x'): + return False + + x = self.sizeToPx(el.attrib['x'], 'x') + y = self.sizeToPx(el.attrib['y'], 'y') + v = [x, y, 1] + t = self.transform(el) + v = self.multiply(t, v) + + return {'coordinates': v, 'matrix': t} + + def setPosition(self, el, position): + c = position['coordinates'] + a = position['matrix'] + if (not self.isUnitMatrix(a)): + c = self.multiply(self.inverse(a), c) + el.set('x', str(c[0])) + el.set('y', str(c[1])) + + + def determinant(self, a): + if len(a) != 3: + return False + if (len(a[0]) != 3): + return False + + det = a[0][0] * (a[1][1] * a[2][2] - a[2][1] * a[1][2]) - a[0][1] * (a[1][0] * a[2][2] - a[2][0] * a[1][2]) + a[0][2] * (a[1][0] * a[2][1] - a[2][0] * a[1][1]) + + if (det == 0): + det = 0.00001 + + return det + + def minors(self, a): + if len(a) != 3: + return False + if (len(a[0]) != 3): + return False + + return [[a[1][1] * a[2][2] - a[2][1] * a[1][2], a[1][0] * a[2][2] - a[2][0] * a[1][2], a[1][0] * a[2][1] - a[2][0] * a[1][1]], + [a[0][1] * a[2][2] - a[2][1] * a[0][2], a[0][0] * a[2][2] - a[0][2] * a[2][0], a[0][0] * a[2][1] - a[2][0] * a[0][1]], + [a[0][1] * a[1][2] - a[1][1] * a[0][2], a[0][0] * a[1][2] - a[0][1] * a[0][2], a[0][0] * a[1][1] - a[1][0] * a[0][1]] + ] + + def cofactors(self, a): + if len(a) != 3: + return False + if (len(a[0]) != 3): + return False + + return [[a[0][0], -a[0][1], a[0][2]], + [-a[1][0], a[1][1], -a[1][2]], + [a[2][0], -a[2][1], a[2][2]] + ] + + def adjoint(self, a): + if len(a) != 3: + return False + if (len(a[0]) != 3): + return False + + return [[a[0][0], a[1][0], a[2][0]], + [a[0][1], a[1][1], a[2][1]], + [a[0][2], a[1][2], a[2][2]] + ] + + def inverse(self, a): + if len(a) != 3: + return False + if (len(a[0]) != 3): + return False + + det = self.determinant(a) + m = self.minors(a) + c = self.cofactors(m) + adj = self.adjoint(c) + + return [[adj[0][0] / det, adj[0][1] / det, adj[0][2] / det], + [adj[1][0] / det, adj[1][1] / det, adj[1][2] / det], + [adj[2][0] / det, adj[2][1] / det, adj[2][2] / det] + ] + + def multiply(self, a, v): + if len(a) != 3: + return False + if (len(a[0]) != 3): + return False + + if (len(v) != 3): + return False + + if (not self.isset(v[0], 0)): + return [a[0][0] * v[0] + a[0][1] * v[1] + a[0][2] * v[2], + a[1][0] * v[0] + a[1][1] * v[1] + a[1][2] * v[2], + a[2][0] * v[0] + a[2][1] * v[1] + a[2][2] * v[2] + ] + else: + return [[a[0][0] * v[0][0] + a[0][1] * v[1][0] + a[0][2] * v[2][0], a[0][0] * v[0][1] + a[0][1] * v[1][1] + a[0][2] * v[2][1], a[0][0] * v[0][2] + a[0][1] * v[1][2] + a[0][2] * v[2][2]], + [a[1][0] * v[0][0] + a[1][1] * v[1][0] + a[1][2] * v[2][0], a[1][0] * v[0][1] + a[1][1] * v[1][1] + a[1][2] * v[2][1], a[1][0] * v[0][2] + a[1][1] * v[1][2] + a[1][2] * v[2][2]], + [a[2][0] * v[0][0] + a[2][1] * v[1][0] + a[2][2] * v[2][0], a[2][0] * v[0][1] + a[2][1] * v[1][1] + a[2][2] * v[2][1], a[2][0] * v[0][2] + a[2][1] * v[1][2] + a[2][2] * v[2][2]] + ] + + def isUnitMatrix(self, a): + if (len(a) != 3): + return False + if (len(a[0]) != 3): + return False + + for i in range(3): + for j in range(3): + if (a[i][j] != self.unitMatrix[i][j]): + return False + + return True + + def reParse(self): + if os.name == 'nt': + path = os.environ['USERPROFILE'] + else: + path = os.path.expanduser("~") + text = inkex.etree.tostring(self.document.getroot()) + f = open(path + '/tmp.svg', 'w') + f.write(text) + f.close() + self.parse(path + '/tmp.svg') + + os.remove(path + '/tmp.svg') + + def matrix2string(self, a): + return 'matrix(' + str(a[0][0]) + ',' + str(a[1][0]) + ',' + str(a[0][1]) + ',' + str(a[1][1]) + ',' + str(a[0][2]) + ',' + str(a[1][2]) + ')' \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/install b/extensions/fablabchemnitz/table_support/install new file mode 100755 index 00000000..ccd5943b --- /dev/null +++ b/extensions/fablabchemnitz/table_support/install @@ -0,0 +1,3 @@ +#!/bin/sh + +./install_shortcuts.py -i keys.xml -o `inkscape -x`/../keys/default.xml \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/install_shortcuts.py b/extensions/fablabchemnitz/table_support/install_shortcuts.py new file mode 100755 index 00000000..e69d5e96 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/install_shortcuts.py @@ -0,0 +1,57 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" + +import sys, os, optparse +sys.path.append(os.path.dirname(sys.argv[0])) + +class install(): + OptionParser = optparse.OptionParser(usage="usage: %prog [options] SVGfile") + + def __init__(self): + opts = [('-i', '--input', 'string', 'input', '/tmp/i', + 'The input file'), + ('-o', '--output', 'string', 'output', '/tmp/o', + 'The output file'), + ] + for o in opts: + self.OptionParser.add_option(o[0], o[1], action="store", type=o[2], + dest=o[3], default=o[4], help=o[5]) + self.getoptions() + + def getoptions(self,args=sys.argv[1:]): + """Collect command line arguments""" + self.options, self.args = self.OptionParser.parse_args(args) + + def do_install(self): + f = open(self.options.input, 'r') + content = f.read() + f.close() + + f = open(self.options.output, 'r') + _c = f.read() + f.close() + + _c = _c.replace('', content + '\n') + + f = open(self.options.output, 'w') + f.write(_c) + f.close() + +if __name__ == '__main__': #pragma: no cover + e = install() + e.do_install() diff --git a/extensions/fablabchemnitz/table_support/keys.xml b/extensions/fablabchemnitz/table_support/keys.xml new file mode 100644 index 00000000..0650bdd5 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/keys.xml @@ -0,0 +1,3 @@ + + + diff --git a/extensions/fablabchemnitz/table_support/table.py b/extensions/fablabchemnitz/table_support/table.py new file mode 100644 index 00000000..0a90b62b --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table.py @@ -0,0 +1,850 @@ +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" +import math + +import inkex +from inkex import Guide +from lxml import etree +import base_transform +import re + +class TableEngine(base_transform.BaseTransform): + + defaultId = 'inkscape-table' + cell_type_row = 'row' + cell_type_column = 'column' + normalizeFactor = 5 + tablesCount = 0 + tables = None + selectedTables = {} + mergedCells = {} + tablesTexts = {} + get_tables = True + auto_split = True + delimiter = ',' + + def __init__(self, get_tables = True, auto_split = True): + inkex.NSS['inkex'] = 'http://sodipodi.sourceforge.net/DTD/inkex-0.dtd' + self.get_tables = get_tables + self.auto_split = auto_split + base_transform.BaseTransform.__init__(self) + + def getTablesCount(self): + node = self.document.xpath('//inkex:tables', namespaces = inkex.NSS) + if len(node) == 0: + xml = '' + self.document.getroot().append(etree.fromstring(xml)) + node = self.document.xpath('//inkex:tables', namespaces = inkex.NSS) + else: + self.tablesCount = int(node[0].attrib['count']) + + self.tables = node[0] + + def isTableCell(self, id): + el = self.svg.getElementById(id) + if (el == None): + return False + + if (self.isset(el.attrib, inkex.addNS('table-id', 'inkex'))): + tableId = el.attrib[inkex.addNS('table-id', 'inkex')] + if (re.search('\\-text$', tableId)): + return False + else: + return True + + return False + + def effect(self): + self.getTablesCount() + if (self.get_tables): + self.getAllTables() + if (self.auto_split): + for id, table in self.selectedTables.items(): + for i in range(len(table)): + for j in range(len(table[i])): + if (table[i][j] != None): + points = self.splitCell(table[i][j]) + if (points != False): + if (self.isset(self.mergedCells, id)): + self.mergedCells[id].append(points) + else: + self.mergedCells[id] = [points] + for tableId in self.mergedCells: + self.getTable(tableId) + self.doinkex() + if (self.get_tables): + if (self.auto_split): + for tableId in self.mergedCells: + self.getTableText(tableId) + for points in self.mergedCells[tableId]: + if (not self.isset(points, 'removed')): + self.mergeTable(tableId, points) + + def newCell(self, x, y, width, height, id, i, j, transform = None): + #path = '//*[@inkex:table-id="%s"]' % id + _id = self.svg.get_unique_id(id) + etree.SubElement(self.svg.get_current_layer(), 'rect', { + 'id': _id, + 'style': 'fill:none;stroke:#000000;stroke-width:1px;stroke-miterlimit:4;stroke-opacity:1;stroke-dasharray:none', + 'width': str(width) + 'px', + 'height': str(height) + 'px', + 'x': str(x) + 'px', + 'y': str(y) + 'px', + inkex.addNS('table-id', 'inkex'): id, + inkex.addNS('row', 'inkex'): str(i), + inkex.addNS('column', 'inkex'): str(j) + }) + + if (transform != None): + el = self.svg.getElementById(_id) + el.set('transform', transform) + + return _id + + ''' + _id = self.svg.get_unique_id(id) + content = '' + + self.svg.get_current_layer().append(etree.XML(content)) + el = self.svg.getElementById(_id) + el.set(inkex.addNS('table-id', 'inkex'), id) + el.set(inkex.addNS('row', 'inkex'), str(i)) + el.set(inkex.addNS('column', 'inkex'), str(j)) + ''' + + def create(self, width, height, cols, rows): + tableId = self.defaultId + str(self.tablesCount) + self.tablesCount += 1 + self.tables.set('count', str(self.tablesCount)) + content = '' + self.tables.append(etree.fromstring(content)) + + width = self.sizeToPx(width, 'x') + height = self.sizeToPx(height, 'y') + + x = 0 + y = 0 + + content = '' + + for i in range(rows): + x = 0 + for j in range(cols): + self.newCell(x, y, width, height, tableId, i, j) + x += width + y += height + + def getTree(self, id): + ids = [id] + el = self.svg.getElementById(id) + for _el in list(el): + for _id in self.getTree(_el.attrib['id']): + ids.append(_id) + return ids + + + def getSubSelectedIds(self): + ids = [] + for id in self.svg.selected.ids: + for _id in self.getTree(id): + ids.append(_id) + return ids + + def getAllTables(self): + ids = self.getSubSelectedIds() + for id in ids: + el = self.svg.getElementById(id) + if (self.isTableCell(id)): + tableId = el.attrib[inkex.addNS('table-id', 'inkex')] + if (not self.isset(self.selectedTables, tableId)): + self.getTable(tableId) + self.tablesTexts[tableId] = self.getTableText(tableId) + + def getTableDimensions(self, tableId): + nodes = self.tables.xpath('//inkex:table[@table-id="' + tableId + '"]', namespaces = inkex.NSS) + if (len(nodes) > 0): + return {'rows': int(nodes[0].attrib['rows']), 'cols': int(nodes[0].attrib['columns'])} + return False + + def setTableDimensions(self, tableId, dimensions): + table_dim = self.tables.xpath('//inkex:table[@table-id="' + tableId + '"]', namespaces = inkex.NSS) + if (len(table_dim) > 0): + table_dim[0].set('rows', str(dimensions['rows'])) + table_dim[0].set('columns', str(dimensions['cols'])) + + + def getTable(self, tableId): + nodes = self.tables.xpath('//inkex:table[@table-id="' + tableId + '"]', namespaces = inkex.NSS) + if (len(nodes) > 0): + cols = int(nodes[0].attrib['columns']) + rows = int(nodes[0].attrib['rows']) + table = [[None for i in range(cols)] for j in range(rows)] + path = '//*[@inkex:table-id="' + tableId + '"]' + cells = self.document.xpath(path, namespaces = inkex.NSS) + for cell in cells: + i = int(cell.attrib[inkex.addNS('row', 'inkex')]) + j = int(cell.attrib[inkex.addNS('column', 'inkex')]) + table[i][j] = cell.attrib['id'] + self.selectedTables[tableId] = table + + def getTableText(self, tableId): + nodes = self.tables.xpath('//inkex:table[@table-id="' + tableId + '"]', namespaces = inkex.NSS) + if (len(nodes) > 0): + cols = int(nodes[0].attrib['columns']) + rows = int(nodes[0].attrib['rows']) + texts = [[None for i in range(cols)] for j in range(rows)] + path = '//*[@inkex:table-id="' + tableId + '-text"]' + cells = self.document.xpath(path, namespaces = inkex.NSS) + for cell in cells: + i = int(cell.attrib[inkex.addNS('row', 'inkex')]) + j = int(cell.attrib[inkex.addNS('column', 'inkex')]) + texts[i][j] = cell.attrib['id'] + return texts + return None + + def doAddGuide(self, el, type): + px = self.sizeToPx(str(self.svg.unittouu(self.document.getroot().attrib['height'])), 'y') + + position = self.getPosition(el) + if (position != False): + c = position['coordinates'] + a = position['matrix'] + x = c[0] + y = c[1] + angle = math.acos(a[0][0]) * 180 / math.pi + if angle < 90: + angle = 90 - angle + elif angle < 180: + angle = 180 - angle + elif angle < 270: + angle = 270 - angle + else: + angle = 360 - angle + if (type == self.cell_type_row): + angle += 90 + self.svg.namedview.add(Guide().move_to(str(x), str(px - y), angle)) + + def _addGuides(self, tableId, type): + table = self.selectedTables[tableId] + + count = len(table) + if (type == self.cell_type_column): + count = len(table[0]) + + for i in range(count): + _i = i + _j = 0 + if (type == self.cell_type_column): + _i = 0 + _j = i + el = self.svg.getElementById(table[_i][_j]) + self.doAddGuide(el, type) + + if (i == count - 1): + if (type == self.cell_type_column): + el.attrib['x'] = str(self.sizeToPx(el.attrib['x'], 'x') + self.sizeToPx(el.attrib['width'], 'x')) + else: + el.attrib['y'] = str(self.sizeToPx(el.attrib['y'], 'y') + self.sizeToPx(el.attrib['height'], 'y')) + self.doAddGuide(el, type) + if (type == self.cell_type_column): + el.attrib['x'] = str(self.sizeToPx(el.attrib['x'], 'x') - self.sizeToPx(el.attrib['width'], 'x')) + else: + el.attrib['y'] = str(self.sizeToPx(el.attrib['y'], 'y') - self.sizeToPx(el.attrib['height'], 'y')) + + def addGuides(self, type): + for tableId in self.selectedTables: + self._addGuides(tableId, type) + + def doEditText(self, id, fontSize): + el = self.svg.getElementById(id) + if (not self.isTableCell(id)): + return + + position = self.getPosition(el) + if (position != False): + a = position['matrix'] + if (not self.isUnitMatrix(a)): + transform = 'transform="' + self.matrix2string(a) + '"' + else: + transform = '' + content = 'text here' + + self.svg.get_current_layer().append(etree.fromstring(content)) + + def editText(self, fontSize): + ids = self.getSubSelectedIds() + + for id in ids: + self.doEditText(id, fontSize) + + def getColumnIndex(self, id): + el = self.svg.getElementById(id) + if (self.isset(el.attrib, inkex.addNS('column', 'inkex'))): + return int(el.attrib[inkex.addNS('column', 'inkex')]) + + return -1 + + def getRowIndex(self, id): + el = self.svg.getElementById(id) + if (self.isset(el.attrib, inkex.addNS('row', 'inkex'))): + return int(el.attrib[inkex.addNS('row', 'inkex')]) + + return -1 + + def setTextRect(self, text, c): + for child in list(text): + if (child.tag == inkex.addNS('flowRegion', 'svg')): + for subchild in list(child): + if (subchild.tag == inkex.addNS('rect', 'svg')): + for key, value in c.iteritems(): + if value != None: + subchild.set(key, str(value)) + break + + def getTextRect(self, text): + for child in list(text): + if (child.tag == inkex.addNS('flowRegion', 'svg')): + for subchild in list(child): + if (subchild.tag == inkex.addNS('rect', 'svg')): + return subchild + + return None + + def moveCells(self, tableId, idx, delta, type): + table = self.selectedTables[tableId] + texts = self.tablesTexts[tableId] + if (type == self.cell_type_column): + starti = 0 + startj = idx + else: + starti = idx + startj = 0 + + for i in range(starti, len(table)): + for j in range(startj, len(table[i])): + el = self.svg.getElementById(table[i][j]) + position = self.getPosition(el) + if (position != False): + c = [self.sizeToPx(el.attrib['x'], 'x'), self.sizeToPx(el.attrib['y'], 'y')] + c[0] += delta[0] + c[1] += delta[1] + el.set('x', str(c[0])) + el.set('y', str(c[1])) + if (texts != None): + if (texts[i][j] != None): + el = self.svg.getElementById(texts[i][j]) + rect = self.getTextRect(el) + if (rect != None): + c[0] = self.sizeToPx(rect.attrib['x'], 'x') + delta[0] + c[1] = self.sizeToPx(rect.attrib['y'], 'y') + delta[1] + self.setTextRect(el, {'x': c[0], 'y': c[1]}) + + def setCellSize(self, tableId, idx, size, type): + table = self.selectedTables[tableId] + texts = self.tablesTexts[tableId] + if (type == self.cell_type_column): + size = self.sizeToPx(size, 'x') + old_size = self.sizeToPx(self.svg.getElementById(table[0][idx]).attrib['width'], 'x') + else: + size = self.sizeToPx(size, 'y') + old_size = self.sizeToPx(self.svg.getElementById(table[idx][0]).attrib['height'], 'y') + + if (type == self.cell_type_column): + delta = [size - old_size, 0, 1] + else: + delta = [0, size - old_size, 1] + + if ((idx + 1 < len(table) and type == self.cell_type_row) or (idx + 1 < len(table[0]) and type == self.cell_type_column)): + self.moveCells(tableId, idx + 1, delta, type) + + count = len(table[idx]) + if (type == self.cell_type_column): + count = len(table) + + for i in range(count): + _i = idx + _j = i + if type == self.cell_type_column: + _i = i + _j = idx + el = self.svg.getElementById(table[_i][_j]) + param = 'height' + if (type == self.cell_type_column): + param = 'width' + + el.set(param, str(size)) + + if texts != None: + if texts[_i][_j] != None: + el = self.svg.getElementById(texts[_i][_j]) + self.setTextRect(el, {param: size}) + + def editSize(self, size, type): + processed = {} + for node in self.svg.selected.values(): + id = node.get('id') + if (self.isTableCell(id)): + tableId = node.attrib[inkex.addNS('table-id', 'inkex')] + if (type == self.cell_type_column): + idx = self.getColumnIndex(id) + else: + idx = self.getRowIndex(id) + if (not self.isset(processed, tableId)): + processed[tableId] = [] + + if (not self.isset(processed[tableId], idx)): + self.setCellSize(tableId, idx, size, type) + processed[tableId].append(idx) + + def getTableWidth(self, tableId): + table = self.selectedTables[tableId] + width = 0 + for i in range(len(table[0])): + el = self.svg.getElementById(table[0][i]) + width += self.sizeToPx(el.attrib['width'], 'x') + + return width + + def getTableHeight(self, tableId): + table = self.selectedTables[tableId] + height = 0 + for i in range(len(table)): + el = self.svg.getElementById(table[i][0]) + height += self.sizeToPx(el.attrib['height'], 'y') + + return height + + def setTableSize(self, tableId, size, type): + if (type == self.cell_type_column): + size = self.sizeToPx(size, 'x') + old_size = self.getTableWidth(tableId) + else: + size = self.sizeToPx(size, 'y') + old_size = self.getTableHeight(tableId) + + factor = size / old_size + table = self.selectedTables[tableId] + count = len(table) + if (type == self.cell_type_column): + count = len(table[0]) + + for i in range(count): + if (type == self.cell_type_column): + el = self.svg.getElementById(table[0][i]) + new_size = self.sizeToPx(el.attrib['width'], 'x') * factor + else: + el = self.svg.getElementById(table[i][0]) + new_size = self.sizeToPx(el.attrib['height'], 'y') * factor + self.setCellSize(tableId, i, str(new_size), type) + + def editTable(self, width, height): + for id in self.selectedTables: + self.setTableSize(id, width, self.cell_type_column) + self.setTableSize(id, height, self.cell_type_row) + + def getTablePosition(self, tableId): + table = self.selectedTables[tableId] + el = self.svg.getElementById(table[0][0]) + return self.getPosition(el) + + def fitPage(self): + width = str(self.svg.unittouu(self.document.getroot().attrib['width'])) + height = str(self.svg.unittouu(self.document.getroot().attrib['height'])) + + for id in self.selectedTables: + position = self.getTablePosition(id) + if (position != False): + c = position['coordinates'] + self.moveCells(id, 0, [-c[0], -c[1], 1], type) + self.setTableSize(id, width, self.cell_type_column) + self.setTableSize(id, height, self.cell_type_row) + + def fitPageWidth(self): + width = str(self.svg.unittouu(self.document.getroot().attrib['width'])) + + for id in self.selectedTables: + position = self.getTablePosition(id) + if (position != False): + c = position['coordinates'] + self.moveCells(id, 0, [-c[0], 0, 1], type) + self.setTableSize(id, width, self.cell_type_column) + + def fitPageHeight(self): + height = str(self.svg.unittouu(self.document.getroot().attrib['height'])) + + for id in self.selectedTables: + position = self.getTablePosition(id) + if (position != False): + c = position['coordinates'] + self.moveCells(id, 0, [0, -c[1], 1], type) + self.setTableSize(id, height, self.cell_type_row) + + def getSelectedListIds(self): + idList = [] + for id in self.getSubSelectedIds(): + idList.append(id) + return idList + + def getCellText(self, tableId, i, j): + texts = self.tablesTexts[tableId] + if (texts != None): + if (texts[i][j] != None): + return self.svg.getElementById(texts[i][j]) + return None + + def getMergePoints(self, tableId): + dim = self.getTableDimensions(tableId) + table = self.selectedTables[tableId] + idList = self.getSelectedListIds() + start = [] + for i in range(dim['rows']): + for j in range(dim['cols']): + if (idList.count(table[i][j]) > 0): + start = [i, j] + break + if len(start) > 0: + break + + if (len(start) != 2): + return False + + end = [1, 1] + + for i in range(start[0] + 1, len(table)): + if (idList.count(table[i][start[1]]) > 0): + end[0] += 1 + else: + break + + for i in range(start[1] + 1, len(table[0])): + if (idList.count(table[start[0]][i]) > 0): + end[1] += 1 + else: + break + + for i in range(start[0], start[0] + end[0]): + for j in range(start[1], start[1] + end[1]): + if (idList.count(table[i][j]) == 0): + return False + + return {'i': start[0], 'j': start[1], 'rows': end[0], 'cols': end[1]} + + def mergeTable(self, tableId, points = None): + if (points == None): + points = self.getMergePoints(tableId) + if (points == False): + inkex.errormsg('You have to select the cells to form a rectangle from a single table.') + return + + table = self.selectedTables[tableId] + cell = self.svg.getElementById(table[points['i']][points['j']]) + width = 0 + height = 0 + widths = '' + heights = '' + + for i in range(points['i'], points['i'] + points['rows']): + el = self.svg.getElementById(table[i][points['j']]) + height += self.sizeToPx(el.attrib['height'], 'y') + if (heights != ''): + heights += self.delimiter + heights += el.attrib['height'] + + for j in range(points['j'], points['j'] + points['cols']): + el = self.svg.getElementById(table[points['i']][j]) + width += self.sizeToPx(el.attrib['width'], 'x') + if (widths != ''): + widths += self.delimiter + widths += el.attrib['width'] + + for i in range(points['i'], points['i'] + points['rows']): + for j in range(points['j'], points['j'] + points['cols']): + if (i != points['i'] or j != points['j']): + el = self.svg.getElementById(table[i][j]) + el.getparent().remove(el) + text = self.getCellText(tableId, i, j) + if (text != None): + text.getparent().remove(text) + + cell.set('width', str(width) + 'px') + cell.set('height', str(height) + 'px') + cell.set(inkex.addNS('merged', 'inkex'), str(points['rows']) + self.delimiter + str(points['cols'])) + cell.set(inkex.addNS('merged-columns-widths', 'inkex'), widths) + cell.set(inkex.addNS('merged-rows-heights', 'inkex'), heights) + + text = self.getCellText(tableId, points['i'], points['j']) + + if (text != None): + rect = self.getTextRect(text) + rect.set('width', str(width) + 'px') + rect.set('height', str(height) + 'px') + + + def mergeMerge(self): + for id in self.selectedTables: + self.mergeTable(id) + + def splitCell(self, cellId): + cell = self.svg.getElementById(cellId) + if (self.isset(cell.attrib, inkex.addNS('merged', 'inkex'))): + tableId = cell.attrib[inkex.addNS('table-id', 'inkex')] + row = int(cell.attrib[inkex.addNS('row', 'inkex')]) + column = int(cell.attrib[inkex.addNS('column', 'inkex')]) + position = self.getPosition(cell) + + merge_size = cell.attrib[inkex.addNS('merged', 'inkex')].split(self.delimiter) + widths = cell.attrib[inkex.addNS('merged-columns-widths', 'inkex')].split(self.delimiter) + heights = cell.attrib[inkex.addNS('merged-rows-heights', 'inkex')].split(self.delimiter) + + y = self.sizeToPx(cell.attrib['y'], 'y') + + for i in range(row, row + int(merge_size[0])): + x = self.sizeToPx(cell.attrib['x'], 'x') + for j in range(column, column + int(merge_size[1])): + if (i != row or j != column): + transform = None + if position != False: + a = position['matrix'] + if (not self.isUnitMatrix(a)): + transform = self.matrix2string(a) + self.newCell(x, y, self.sizeToPx(widths[j - column], 'x'), self.sizeToPx(heights[i - row], 'y'), tableId, i, j, transform) + x += self.sizeToPx(widths[j - column], 'x') + y += self.sizeToPx(heights[i - row], 'y') + + result = {'i': row, 'j': column, 'rows': int(merge_size[0]), 'cols': int(merge_size[1])} + cell.set('width', widths[0]) + cell.set('height', heights[0]) + text = self.getCellText(tableId, row, column) + if (text != None): + rect = self.getTextRect(text) + rect.set('width', widths[0]) + rect.set('height', heights[0]) + del cell.attrib[inkex.addNS('merged', 'inkex')] + del cell.attrib[inkex.addNS('merged-columns-widths', 'inkex')] + del cell.attrib[inkex.addNS('merged-rows-heights', 'inkex')] + + return result + return False + + def mergeSplit(self): + for id in self.svg.selected.ids: + self.splitCell(id) + + def updateMergedPoints(self, tableId, idx, delta, type): + if (self.get_tables): + if (self.auto_split): + if (self.isset(self.mergedCells, tableId)): + for points in self.mergedCells[tableId]: + cond1 = idx > points['i'] and idx < points['i'] + points['rows'] + cond2 = idx <= points['i'] + if (type == self.cell_type_column): + cond1 = idx > points['j'] and idx < points['j'] + points['cols'] + cond2 = idx <= points['j'] + + if (cond1): + if (type == self.cell_type_column): + points['cols'] += delta + if (points['cols'] <= 1): + points['removed'] = 1 + else: + points['rows'] += delta + if (points['rows'] <= 1): + points['removed'] = 1 + elif (cond2): + if (type == self.cell_type_column): + if (delta == -1 and idx == points['j']): + points['cols'] += delta + if (points['cols'] <= 1): + points['removed'] = 1 + else: + points['j'] += delta + else: + if (delta == -1 and idx == points['i']): + points['rows'] += delta + if (points['rows'] <= 1): + points['removed'] = 1 + else: + points['i'] += delta + + def incrementCoordonate(self, tableId, idx, inc, type): + table = self.selectedTables[tableId] + texts = self.getTableText(tableId) + starti = idx + startj = 0 + dim = self.getTableDimensions(tableId) + if type == self.cell_type_column: + dim['cols'] += inc + else: + dim['rows'] += inc + self.setTableDimensions(tableId, dim) + + if (type == self.cell_type_column): + starti = 0 + startj = idx + + for i in range(starti, len(table)): + for j in range(startj, len(table[i])): + cell = self.svg.getElementById(table[i][j]) + text = self.svg.getElementById(texts[i][j]) + if (type == self.cell_type_column): + cell.set(inkex.addNS('column', 'inkex'), str(int(cell.attrib[inkex.addNS('column', 'inkex')]) + inc)) + if (text != None): + text.set(inkex.addNS('column', 'inkex'), str(int(text.attrib[inkex.addNS('column', 'inkex')]) + inc)) + else: + cell.set(inkex.addNS('row', 'inkex'), str(int(cell.attrib[inkex.addNS('row', 'inkex')]) + inc)) + if (text != None): + text.set(inkex.addNS('row', 'inkex'), str(int(text.attrib[inkex.addNS('row', 'inkex')]) + inc)) + + def addCell(self, tableId, idx, type): + table = self.selectedTables[tableId] + if (type == self.cell_type_column): + if (idx != -1): + delta = [self.sizeToPx(self.svg.getElementById(table[0][idx]).attrib['width'], 'x'), 0, 1] + else: + delta = [self.sizeToPx(self.svg.getElementById(table[0][0]).attrib['width'], 'x'), 0, 1] + else: + if (idx != -1): + delta = [0, self.sizeToPx(self.svg.getElementById(table[idx][0]).attrib['height'], 'y'), 1] + else: + delta = [0, self.sizeToPx(self.svg.getElementById(table[0][0]).attrib['height'], 'y'), 1] + + count = len(table) + if type == self.cell_type_row: + if (idx != -1): + count = len(table[idx]) + else: + count = len(table[0]) + for i in range(count): + if (type == self.cell_type_column): + if (idx != -1): + cell = self.svg.getElementById(table[i][idx]) + else: + cell = self.svg.getElementById(table[i][0]) + else: + if (idx != -1): + cell = self.svg.getElementById(table[idx][i]) + else: + cell = self.svg.getElementById(table[0][i]) + + position = self.getPosition(cell) + transform = '' + if (position != False): + a = position['matrix'] + if (not self.isUnitMatrix(a)): + transform = self.matrix2string(a) + x = self.sizeToPx(cell.attrib['x'], 'x') + y = self.sizeToPx(cell.attrib['y'], 'y') + width = self.sizeToPx(cell.attrib['width'], 'x') + height = self.sizeToPx(cell.attrib['height'], 'y') + + if (type == self.cell_type_column): + if (idx != -1): + x += width + self.newCell(x, y, width, height, tableId, i, idx + 1, transform) + else: + if (idx != -1): + y += height + self.newCell(x, y, width, height, tableId, idx + 1, i, transform) + + self.moveCells(tableId, idx + 1, delta, type) + self.updateMergedPoints(tableId, idx + 1, 1, type) + self.incrementCoordonate(tableId, idx + 1, 1, type) + self.getTable(tableId) + self.tablesTexts[tableId] = self.getTableText(tableId) + + def addColumns(self, count, where): + for id in self.svg.selected.ids: + el = self.svg.getElementById(id) + if (self.isTableCell(id)): + tableId = el.attrib[inkex.addNS('table-id', 'inkex')] + idx = self.getColumnIndex(id) + if (where == 'before'): + idx -= 1 + + for i in range(count): + self.addCell(tableId, idx, self.cell_type_column) + + def addRows(self, count, where): + for id in self.svg.selected.ids: + el = self.svg.getElementById(id) + if (self.isTableCell(id)): + tableId = el.attrib[inkex.addNS('table-id', 'inkex')] + idx = self.getRowIndex(id) + if (where == 'before'): + idx -= 1 + + for i in range(count): + self.addCell(tableId, idx, self.cell_type_row) + + break + + def removeCell(self, tableId, idx, type): + table = self.selectedTables[tableId] + texts = self.tablesTexts[tableId] + if (type == self.cell_type_column): + delta = [-self.sizeToPx(self.svg.getElementById(table[0][idx]).attrib['width'], 'x'), 0, 1] + else: + delta = [0, -self.sizeToPx(self.svg.getElementById(table[idx][0]).attrib['height'], 'y'), 1] + + count = len(table) + if type == self.cell_type_row: + count = len(table[idx]) + + for i in range(count): + if (type == self.cell_type_column): + cell = self.svg.getElementById(table[i][idx]) + text = self.svg.getElementById(texts[i][idx]) + else: + cell = self.svg.getElementById(table[idx][i]) + text = self.svg.getElementById(texts[idx][i]) + + if (cell != None): + cell.getparent().remove(cell) + if (text != None): + text.getparent().remove(text) + + self.moveCells(tableId, idx + 1, delta, type) + self.updateMergedPoints(tableId, idx, -1, type) + self.incrementCoordonate(tableId, idx + 1, -1, type) + self.getTable(tableId) + self.tablesTexts[tableId] = self.getTableText(tableId) + + def removeRowsColumns(self, type): + for id in self.svg.selected.ids: + el = self.svg.getElementById(id) + if (el != None): + if (self.isTableCell(id)): + tableId = el.attrib[inkex.addNS('table-id', 'inkex')] + if (type == self.cell_type_column): + idx = self.getColumnIndex(id) + else: + idx = self.getRowIndex(id) + + self.removeCell(tableId, idx, type) diff --git a/extensions/fablabchemnitz/table_support/table_add_columns.inx b/extensions/fablabchemnitz/table_support/table_add_columns.inx new file mode 100644 index 00000000..e442c071 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_add_columns.inx @@ -0,0 +1,23 @@ + + + Columns + fablabchemnitz.de.table_add_columns + 1 + + + + + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_add_columns.py b/extensions/fablabchemnitz/table_support/table_add_columns.py new file mode 100755 index 00000000..d188c041 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_add_columns.py @@ -0,0 +1,40 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + def __init__(self): + table.TableEngine.__init__(self, True, True) + opts = [('-n', '--number', 'int', 'number', '1', + 'The number of rows'), + ('-w', '--where', 'string', 'where', 'after', + 'Where to add'), + ] + for o in opts: + self.OptionParser.add_option(o[0], o[1], action="store", type=o[2], + dest=o[3], default=o[4], help=o[5]) + + def doinkex(self): + self.addColumns(self.options.number, self.options.where) + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_add_guides.inx b/extensions/fablabchemnitz/table_support/table_add_guides.inx new file mode 100644 index 00000000..0cf1c39a --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_add_guides.inx @@ -0,0 +1,18 @@ + + + Guide Lines + fablabchemnitz.de.table_add_guides + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_add_guides.py b/extensions/fablabchemnitz/table_support/table_add_guides.py new file mode 100755 index 00000000..8cdda97c --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_add_guides.py @@ -0,0 +1,34 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" + +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + def __init__(self): + table.TableEngine.__init__(self) + + def doinkex(self): + self.addGuides(self.cell_type_row) + self.addGuides(self.cell_type_column) + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_add_rows.inx b/extensions/fablabchemnitz/table_support/table_add_rows.inx new file mode 100644 index 00000000..26844555 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_add_rows.inx @@ -0,0 +1,23 @@ + + + Rows + fablabchemnitz.de.table_add_rows + 1 + + + + + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_add_rows.py b/extensions/fablabchemnitz/table_support/table_add_rows.py new file mode 100755 index 00000000..b315f917 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_add_rows.py @@ -0,0 +1,40 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + def __init__(self): + table.TableEngine.__init__(self, True, True) + opts = [('-n', '--number', 'int', 'number', '1', + 'The number of rows'), + ('-w', '--where', 'string', 'where', 'after', + 'Where to add'), + ] + for o in opts: + self.OptionParser.add_option(o[0], o[1], action="store", type=o[2], + dest=o[3], default=o[4], help=o[5]) + + def doinkex(self): + self.addRows(self.options.number, self.options.where) + +if __name__ == '__main__': #pragma: no cover + Table().run() \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_create.inx b/extensions/fablabchemnitz/table_support/table_create.inx new file mode 100644 index 00000000..0420a5ce --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_create.inx @@ -0,0 +1,28 @@ + + + Create + fablabchemnitz.de.table_create + + + 2 + 2 + 100mm + 20mm + + + + + + + + all + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_create.py b/extensions/fablabchemnitz/table_support/table_create.py new file mode 100755 index 00000000..40d4f8c1 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_create.py @@ -0,0 +1,38 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" + +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + + def add_arguments(self, pars): + pars.add_argument("--rows", type=int, default=2, help='The number of table rows') + pars.add_argument("--cols", type=int, default=2, help='The number of table columns') + pars.add_argument("--width", default='100mm', help='The width of the table') + pars.add_argument("--height", default='20mm', help='The height of the table') + pars.add_argument("--tab") + + def doinkex(self): + self.create(self.options.width, self.options.height, self.options.cols, self.options.rows) + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_edit_columns.inx b/extensions/fablabchemnitz/table_support/table_edit_columns.inx new file mode 100644 index 00000000..be1890d3 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_edit_columns.inx @@ -0,0 +1,20 @@ + + + Selected columns width + fablabchemnitz.de.table_edit_columns + 10mm + + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_edit_columns.py b/extensions/fablabchemnitz/table_support/table_edit_columns.py new file mode 100755 index 00000000..a36b8218 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_edit_columns.py @@ -0,0 +1,34 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" + +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + + def add_arguments(self, pars): + pars.add_argument("--width", default='10mm', help='The new width') + + def doinkex(self): + self.editSize(self.options.width, self.cell_type_column) + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_edit_rows.inx b/extensions/fablabchemnitz/table_support/table_edit_rows.inx new file mode 100644 index 00000000..22a7ae3c --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_edit_rows.inx @@ -0,0 +1,20 @@ + + + Selected rows height + fablabchemnitz.de.table_edit_rows + 10mm + + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_edit_rows.py b/extensions/fablabchemnitz/table_support/table_edit_rows.py new file mode 100755 index 00000000..e71f847b --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_edit_rows.py @@ -0,0 +1,34 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" + +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + + def add_arguments(self, pars): + pars.add_argument("--height", default='10mm', help='The new height') + + def doinkex(self): + self.editSize(self.options.height, self.cell_type_row) + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_edit_table.inx b/extensions/fablabchemnitz/table_support/table_edit_table.inx new file mode 100644 index 00000000..bdea4b2e --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_edit_table.inx @@ -0,0 +1,22 @@ + + + Selected table width and height + fablabchemnitz.de.table_edit_table + table_edit_table.py + 150mm + 60mm + + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_edit_table.py b/extensions/fablabchemnitz/table_support/table_edit_table.py new file mode 100755 index 00000000..01ccedf0 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_edit_table.py @@ -0,0 +1,35 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" + +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + + def add_arguments(self, pars): + pars.add_argument("--width", default='150mm', help='The new width') + pars.add_argument("--height", default='60mm', help='The new height') + + def doinkex(self): + self.editTable(self.options.width, self.options.height) + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_edit_text.inx b/extensions/fablabchemnitz/table_support/table_edit_text.inx new file mode 100644 index 00000000..2b8413e9 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_edit_text.inx @@ -0,0 +1,19 @@ + + + Selected cells text + fablabchemnitz.de.table_edit_text + 12px + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_edit_text.py b/extensions/fablabchemnitz/table_support/table_edit_text.py new file mode 100755 index 00000000..b21b10ff --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_edit_text.py @@ -0,0 +1,34 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" + +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + + def add_arguments(self, pars): + pars.add_argument("--size", default='12px', help='The font size') + + def doinkex(self): + self.editText(self.options.size) + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_fit_height.inx b/extensions/fablabchemnitz/table_support/table_fit_height.inx new file mode 100644 index 00000000..b830aa1d --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_fit_height.inx @@ -0,0 +1,18 @@ + + + Selected table to page height + fablabchemnitz.de.table_fit_height + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_fit_height.py b/extensions/fablabchemnitz/table_support/table_fit_height.py new file mode 100644 index 00000000..7b6d6cb0 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_fit_height.py @@ -0,0 +1,32 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + def __init__(self): + table.TableEngine.__init__(self) + + def doinkex(self): + self.fitPageHeight() + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_fit_page.inx b/extensions/fablabchemnitz/table_support/table_fit_page.inx new file mode 100644 index 00000000..f371f7bd --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_fit_page.inx @@ -0,0 +1,18 @@ + + + Selected table to page + fablabchemnitz.de.table_fit_page + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_fit_page.py b/extensions/fablabchemnitz/table_support/table_fit_page.py new file mode 100644 index 00000000..2689e466 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_fit_page.py @@ -0,0 +1,31 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" + +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + + def doinkex(self): + self.fitPage() + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_fit_width.inx b/extensions/fablabchemnitz/table_support/table_fit_width.inx new file mode 100644 index 00000000..779f481d --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_fit_width.inx @@ -0,0 +1,18 @@ + + + Selected table to page width + fablabchemnitz.de.table_fit_width + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_fit_width.py b/extensions/fablabchemnitz/table_support/table_fit_width.py new file mode 100644 index 00000000..1ac7626e --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_fit_width.py @@ -0,0 +1,32 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + def __init__(self): + table.TableEngine.__init__(self) + + def doinkex(self): + self.fitPageWidth() + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_merge_merge.inx b/extensions/fablabchemnitz/table_support/table_merge_merge.inx new file mode 100644 index 00000000..ebd93393 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_merge_merge.inx @@ -0,0 +1,18 @@ + + + Merge selected cells + fablabchemnitz.de.table_merge_merge + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_merge_merge.py b/extensions/fablabchemnitz/table_support/table_merge_merge.py new file mode 100644 index 00000000..89d0a027 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_merge_merge.py @@ -0,0 +1,32 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + def __init__(self): + table.TableEngine.__init__(self) + + def doinkex(self): + self.mergeMerge() + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_merge_split.inx b/extensions/fablabchemnitz/table_support/table_merge_split.inx new file mode 100644 index 00000000..1c7134c7 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_merge_split.inx @@ -0,0 +1,18 @@ + + + Split selected cells + fablabchemnitz.de.table_merge_split + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_merge_split.py b/extensions/fablabchemnitz/table_support/table_merge_split.py new file mode 100755 index 00000000..c62c8cb8 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_merge_split.py @@ -0,0 +1,32 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + def __init__(self): + table.TableEngine.__init__(self, True, False) + + def doinkex(self): + self.mergeSplit() + +if __name__ == '__main__': #pragma: no cover + Table().run() \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_remove_columns.inx b/extensions/fablabchemnitz/table_support/table_remove_columns.inx new file mode 100644 index 00000000..eb840bf2 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_remove_columns.inx @@ -0,0 +1,18 @@ + + + Selected columns + fablabchemnitz.de.table_remove_columns + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_remove_columns.py b/extensions/fablabchemnitz/table_support/table_remove_columns.py new file mode 100755 index 00000000..053f03ee --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_remove_columns.py @@ -0,0 +1,32 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + def __init__(self): + table.TableEngine.__init__(self, True, True) + + def doinkex(self): + self.removeRowsColumns(self.cell_type_column) + +if __name__ == '__main__': #pragma: no cover + Table().run() diff --git a/extensions/fablabchemnitz/table_support/table_remove_rows.inx b/extensions/fablabchemnitz/table_support/table_remove_rows.inx new file mode 100644 index 00000000..01f5dbc7 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_remove_rows.inx @@ -0,0 +1,18 @@ + + + Selected rows + fablabchemnitz.de.table_remove_rows + + all + + + + + + + + + + \ No newline at end of file diff --git a/extensions/fablabchemnitz/table_support/table_remove_rows.py b/extensions/fablabchemnitz/table_support/table_remove_rows.py new file mode 100755 index 00000000..11a3b3f5 --- /dev/null +++ b/extensions/fablabchemnitz/table_support/table_remove_rows.py @@ -0,0 +1,32 @@ +#!/usr/bin/env python3 +""" +table.py +Table support for Inkscape + +Copyright (C) 2011 Cosmin Popescu, cosminadrianpopescu@gmail.com + +This program is free software; you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation; either version 2 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. +""" +import sys +import os +import table + +sys.path.append(os.path.dirname(sys.argv[0])) + +class Table(table.TableEngine): + def __init__(self): + table.TableEngine.__init__(self, True, True) + + def doinkex(self): + self.removeRowsColumns(self.cell_type_row) + +if __name__ == '__main__': #pragma: no cover + Table().run()