diff options
Diffstat (limited to '')
-rwxr-xr-x | share/extensions/guides_creator.py | 268 |
1 files changed, 268 insertions, 0 deletions
diff --git a/share/extensions/guides_creator.py b/share/extensions/guides_creator.py new file mode 100755 index 0000000..7f4e332 --- /dev/null +++ b/share/extensions/guides_creator.py @@ -0,0 +1,268 @@ +#!/usr/bin/env python +# coding=utf-8 +# +# Copyright (C) 2008 Jonas Termeau - jonas.termeau **AT** 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; version 2 of the License. +# +# 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. +# +# You should have received a copy of the GNU General Public License +# along with this program; if not, write to the Free Software +# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. +# +# Thanks to: +# +# Bernard Gray - bernard.gray **AT** gmail.com (python helping) +# Jamie Heames (english translation issues) +# ~suv (bug report in v2.3) +# http://www.gutenberg.eu.org/publications/ (9x9 margins settings) +# +""" +This basic extension allows you to automatically draw guides in inkscape. +""" + +from math import cos, sin, sqrt + +import inkex +from inkex import Guide + + +class GuidesCreator(inkex.EffectExtension): + """Create a set of guides based on the given options""" + def add_arguments(self, pars): + pars.add_argument("--tab", type=self.arg_method('generate'), default="regular_guides",\ + help="Type of guides to create.") + pars.add_argument('--guides_preset', default='custom', help='Preset') + pars.add_argument('--vertical_guides', type=int, default=3, help='Vertical guides') + pars.add_argument('--horizontal_guides', type=int, default=3, help='Horizontal guides') + pars.add_argument('--start_from_edges', type=inkex.Boolean, help='Start from edges') + pars.add_argument('--ul', type=inkex.Boolean, default=True, help='Upper left corner') + pars.add_argument('--ur', type=inkex.Boolean, default=True, help='Upper right corner') + pars.add_argument('--ll', type=inkex.Boolean, default=True, help='Lower left corner') + pars.add_argument('--lr', type=inkex.Boolean, default=True, help='Lower right corner') + pars.add_argument('--margins_preset', default='custom', help='Margins preset') + pars.add_argument('--vert', type=int, default=0, help='Vert subdivisions') + pars.add_argument('--horz', type=int, default=0, help='Horz subdivisions') + pars.add_argument('--header_margin', default=6, help='Header margin') + pars.add_argument('--footer_margin', default=6, help='Footer margin') + pars.add_argument('--left_margin', default=6, help='Left margin') + pars.add_argument('--right_margin', default=6, help='Right margin') + pars.add_argument('--delete', type=inkex.Boolean, help='Delete existing guides') + + def effect(self): + # getting the width and height attributes of the canvas + self.width = float(self.svg.width) + self.height = float(self.svg.height) + + # getting edges coordinates + self.h_orientation = '0,' + str(round(self.width, 4)) + self.v_orientation = str(round(self.height, 4)) + ',0' + + if self.options.delete: + for guide in self.svg.namedview.get_guides(): + guide.delete() + + return self.options.tab() + + def generate_regular_guides(self): + """Generate a regular set of guides""" + preset = self.options.guides_preset + from_edges = self.options.start_from_edges + if preset == 'custom': + h_division = self.options.horizontal_guides + v_division = self.options.vertical_guides + if from_edges: + v_division = v_division or 1 + h_division = h_division or 1 + + self.draw_guides(v_division, from_edges, vert=True) + self.draw_guides(h_division, from_edges, vert=False) + + elif preset == 'golden': + gold = (1 + sqrt(5)) / 2 + + # horizontal golden guides + position1 = '0,' + str(self.height / gold) + position2 = '0,' + str(self.height - (self.height / gold)) + + self.draw_guide(position1, self.h_orientation) + self.draw_guide(position2, self.h_orientation) + + # vertical golden guides + position1 = str(self.width / gold) + ',0' + position2 = str(self.width - (self.width / gold)) + ',0' + + self.draw_guide(position1, self.v_orientation) + self.draw_guide(position2, self.v_orientation) + + if from_edges: + # horizontal borders + self.draw_guide('0,' + str(self.height), self.h_orientation) + self.draw_guide(str(self.height) + ',0', self.h_orientation) + + # vertical borders + self.draw_guide('0,' + str(self.width), self.v_orientation) + self.draw_guide(str(self.width) + ',0', self.v_orientation) + + elif ';' in preset: + v_division = int(preset.split(';')[0]) + h_division = int(preset.split(';')[1]) + self.draw_guides(v_division, from_edges, vert=True) + self.draw_guides(h_division, from_edges, vert=False) + else: + raise inkex.AbortExtension("Unknown guide guide preset: {}".format(preset)) + + def generate_diagonal_guides(self): + """Generate diagonal guides""" + # Dimentions + left, bottom = (0, 0) + right, top = (self.width, self.height) + + # Diagonal angle + angle = 45 + + if self.options.ul: + ul_corner = str(top) + ',' + str(left) + from_ul_to_lr = str(cos(angle)) + ',' + str(cos(angle)) + self.draw_guide(ul_corner, from_ul_to_lr) + + if self.options.ur: + ur_corner = str(right) + ',' + str(top) + from_ur_to_ll = str(-sin(angle)) + ',' + str(sin(angle)) + self.draw_guide(ur_corner, from_ur_to_ll) + + if self.options.ll: + ll_corner = str(bottom) + ',' + str(left) + from_ll_to_ur = str(-cos(angle)) + ',' + str(cos(angle)) + self.draw_guide(ll_corner, from_ll_to_ur) + + if self.options.lr: + lr_corner = str(bottom) + ',' + str(right) + from_lr_to_ul = str(-sin(angle)) + ',' + str(-sin(angle)) + self.draw_guide(lr_corner, from_lr_to_ul) + + def generate_margins(self): + """Generate margin guides""" + header_margin = int(self.options.header_margin) + footer_margin = int(self.options.footer_margin) + left_margin = int(self.options.left_margin) + right_margin = int(self.options.right_margin) + h_subdiv = int(self.options.horz) + v_subdiv = int(self.options.vert) + + if self.options.start_from_edges: + # horizontal borders + self.draw_guide('0,' + str(self.height), self.h_orientation) + self.draw_guide(str(self.height) + ',0', self.h_orientation) + + # vertical borders + self.draw_guide('0,' + str(self.width), self.v_orientation) + self.draw_guide(str(self.width) + ',0', self.v_orientation) + + if self.options.margins_preset == 'custom': + y_header = self.height + y_footer = 0 + x_left = 0 + x_right = self.width + + if header_margin != 0: + y_header = (self.height / header_margin) * (header_margin - 1) + self.draw_guide('0,' + str(y_header), self.h_orientation) + + if footer_margin != 0: + y_footer = self.height / footer_margin + self.draw_guide('0,' + str(y_footer), self.h_orientation) + + if left_margin != 0: + x_left = self.width / left_margin + self.draw_guide(str(x_left) + ',0', self.v_orientation) + + if right_margin != 0: + x_right = (self.width / right_margin) * (right_margin - 1) + self.draw_guide(str(x_right) + ',0', self.v_orientation) + + elif self.options.margins_preset == 'book_left': + # 1/9th header + y_header = (self.height / 9) * 8 + self.draw_guide('0,' + str(y_header), self.h_orientation) + + # 2/9th footer + y_footer = (self.height / 9) * 2 + self.draw_guide('0,' + str(y_footer), self.h_orientation) + + # 2/9th left margin + x_left = (self.width / 9) * 2 + self.draw_guide(str(x_left) + ',0', self.v_orientation) + + # 1/9th right margin + x_right = (self.width / 9) * 8 + self.draw_guide(str(x_right) + ',0', self.v_orientation) + + elif self.options.margins_preset == 'book_right': + # 1/9th header + y_header = (self.height / 9) * 8 + self.draw_guide('0,' + str(y_header), self.h_orientation) + + # 2/9th footer + y_footer = (self.height / 9) * 2 + self.draw_guide('0,' + str(y_footer), self.h_orientation) + + # 2/9th left margin + x_left = (self.width / 9) + self.draw_guide(str(x_left) + ',0', self.v_orientation) + + # 1/9th right margin + x_right = (self.width / 9) * 7 + self.draw_guide(str(x_right) + ',0', self.v_orientation) + + # setting up properties of the rectangle created between guides + rectangle_height = y_header - y_footer + rectangle_width = x_right - x_left + + if h_subdiv != 0: + begin_from = y_footer + # creating horizontal guides + self._draw_guides( + (rectangle_width, rectangle_height), h_subdiv, + edges=0, shift=begin_from, vert=False) + + if v_subdiv != 0: + begin_from = x_left + # creating vertical guides + self._draw_guides( + (rectangle_width, rectangle_height), v_subdiv, + edges=0, shift=begin_from, vert=True) + + def draw_guides(self, division, edges, vert=False): + """Draw a vertical or horizontal lines""" + return self._draw_guides((self.width, self.height), division, edges, vert=vert) + + def _draw_guides(self, vector, division, edges, shift=0, vert=False): + if division <= 0: + return + + # Vert controls both ort template and vector calculation + ort = '{},0' if vert else '0,{}' + var = int(bool(edges)) + for x in range(0, division - 1 + 2 * var): + div = vector[not bool(vert)] / division + position = str(round(div + (x - var) * div + shift, 4)) + orientation = str(round(vector[bool(vert)], 4)) + self.draw_guide(ort.format(position), ort.format(orientation)) + + def draw_guide(self, position, orientation): + """Create a guide directly into the namedview""" + if isinstance(position, tuple): + x, y = position + elif isinstance(position, str): + x, y = position.split(',') + self.svg.namedview.add(Guide().move_to(float(x), float(y), orientation)) + +if __name__ == '__main__': + GuidesCreator().run() |