This is a read-only archive. Find the latest Linux articles, documentation, and answers at the new Linux.com!

Linux.com

Feature: Python

Scripting Scribus

By Drew Ames on February 13, 2008 (7:00:00 PM)

Share    Print    Comments   

Have you ever said, "This program is pretty nice, but I wish it would ..."? For applications that offer the capability, scripting gives users the ability to customize, extend, and tailor a program to meet their needs. Scribus, a free page layout program that runs on Linux (and Mac OS and Windows) uses the Python programming language for user scripting. Python scripting in Scribus can drastically improve your work flow, and it's relatively easy for beginners to not only use scripts, but also write them.

Scripts are useful for page layout in a few interrelated ways, including automating repetitive tasks and tasks that involve measuring, such as placing page elements and creating page guides.

Not much is required to use Python scripts in Scribus. If your distribution successfully runs Scribus, then you probably have the required Python components. For this evaluation, I downloaded, compiled, and installed the latest stable Python version (1.3.3.11). You can start a Python script from within Scribus by going to the Script menu and choosing either Execute Script..., which opens a dialog box for selecting a script to run, or Scribus Scripts, which lists the scripts in the /usr/share/scribus/scripts directory, which contains the official scripts for Scribus. Placing additional scripts in that directory (as the root user or using sudo) makes those scripts available from the menu.

Two official scripts are provided: CalendarWizard.py and FontSample.py. Both feature dialog boxes with numerous options that showcase how Python scripts can extend the functionality of Scribus. The font sample script can take a long time to run, depending on your processor speed, memory, and number of fonts, but Scribus displays a handy progress bar showing the percentage of script completion.

Additionally, the /usr/share/scribus/samples directory contains 15 scripts intended not just for immediate use, but also as samples to study when creating your own scripts. The scripts in the samples directory are varied and range from a heavily commented boilerplate script (boilerplate.py) to functional scripts that, for example, set up a layout for CD pockets (pochette_CD.py), or add legends to images (legende.py). As the titles of some of the scripts indicate, many have comments and even dialog box text written in the native languages of the script authors, but the script description is usually in English.

More Scripts

More Scribus scripts are available online at the Scribus wiki's page on scripts and plugins. I found here a script to make empty space around an image inside an image frame -- something not yet possible in Scribus. The script works by drawing a second, empty frame 10 measurement units larger than the selected image or text frame. When I first ran the script, I had my default units set to inches, and the script created a 10-inch border around the image I selected. If you want to use this script without modification, be sure that your default units are set for points.

A more comprehensive approach to manipulating images uses a series of scripts for aligning an image inside its frame, scaling an image to fill a frame proportionally (i.e., scaling the image to the largest size possible within the frame while keeping its proportions intact), and scaling and aligning an image via a wizard and an advanced wizard that build upon the first two scripts. These scripts are great examples of how Python scripting extends Scribus's capabilities.

Using scripts that others have written is as simple as copying them from the Web page, pasting them into a text editor (preferably one that is aware of Python syntax, such as Emacs, Vim, Kate, or gedit), and then saving the script to a file ending in .py. You can then run the script from the Scribus script menu. The advantage of pasting the script into a syntax-aware text editor is that white space is important in Python, and a good editor will help you check that everything is aligned correctly.

Writing a script

Prior to doing the research for this article, I had not done any programming in Python. I did, however, have extensive experience using Adobe's scripting language for PageMaker, and I found that most of the principles carried over. A wonderful resource for beginners wanting to learn more about Python is the 110-page PDF tutorial A Byte of Python by Swaroop C H. It is well-written, easy to follow, and may be the best introduction to Python programming available.

Armed with a little bit of knowledge of Python, and having the scripting application programming interface (API) available online and from Scribus's help menu, I set out to write a couple of scripts. With all the sample scripts available, I did not have to start from scratch.

I began by modifying the script for making an empty space around an image so that the space would be 10 points regardless of the default measurement unit set by the user. To do that, I needed to get the current units setting, store it in a variable, temporarily set the units to points, and then reset the units to their original setting. To accomplish those tasks, I added the following commands to the script I downloaded:

  • userUnit = getUnit() -- set a variable storing the current units setting
  • setUnit(0) -- sets the units to points (0). (1) is millimeters (2) is inches and (3) is picas.
  • setUnit(userUnit) -- resets the units to the original setting

The script as modified appears below. Because of the way the original author set the script to make sure the script is run from within Scribus, the commands I added needed to be prefaced with scribus..

#!/usr/bin/env python # -*- coding: utf-8 -*- import sys try: import scribus except ImportError: print "This script only works from within Scribus" sys.exit(1) def makebox(x,y,w,h): a = scribus.createImage(x, y, w, h) scribus.textFlowsAroundFrame(a, 1) def main(): if scribus.haveDoc(): scribus.setRedraw(1) userUnit = scribus.getUnit() scribus.setUnit(0) x,y = scribus.getPosition() w,h = scribus.getSize() x2 = x - border y2 = y - border w2 = w + border * 2 h2 = h + border * 2 makebox(x2,y2,w2,h2) scribus.redrawAll() scribus.setUnit(userUnit) else: result = scribus.messageBox('Error','You need a Document open, and a frame selected.') # Change the 'border' value to change the size of space around your frame border = 10 main()

When I first started working with Scribus, I missed having the ability to make a single underline of a text or image frame. This capability is particularly handy when setting up page headers. Looking at the sample scripts, I saw that legende.py did something similar to what I wanted to do. That script gets the size and location of an image frame and then places a text box a few millimeters below the lower right corner of the box. I needed to do something similar, except that I needed my script to draw the line from the lower left corner to the lower right corner without an offset. So I modified the legende.py script and saved it as underline_block.py.

The key to making the script work is realizing that the getPosition function gets the x and y page coordinates of the upper left corner of the frame. To get the positions of the other corners, I need the height and width of the frame. When that information is stored in variables, then drawing the line is a matter of specifying the x and y coordinates of the lower two corners in relation to the height and width. The command createLine(x, y+h, x+l, y+h) accomplishes drawing the line from the bottom left to the bottom right. The full script is below:

#!/usr/bin/env python # -*- coding: utf-8 -*- """ Draws a line below the selected frame. """ import sys try: from scribus import * except ImportError: print "This script only runs from within Scribus." sys.exit(1) import os def main(): userUnit = getUnit() setUnit(1) sel_count = selectionCount() if sel_count == 0: messageBox("underline_block.py", "Please select the object to add a line to before running this script.", ICON_INFORMATION) sys.exit(1) x,y = getPosition() l,h = getSize() createLine(x, y+h, x+l, y+h) setUnit(userUnit) if __name__ == '__main__': main()

Like any other type of programming, creating scripts is an iterative process. When writing or modifying a script, it is easy to work in a cycle of edit, save, run, check, and edit. The iterative approach also applies to improving scripts. After using the underline_block.py script for a while, I may want to modify it so that I can choose to add a line above the block rather than below it. To do that, I'll need to add a dialog box so I can choose the position. If I do that, I may want to add something to the dialog so I can choose the line style too. Each of the embellishments make the script more general and more useful.

As the examples illustrate, Python scripts are a useful way to customize and extend Scribus regardless of your level of programming experience.

Drew Ames is a transportation planner in Harrisburg, Penn.

Share    Print    Comments   

Comments

on Scripting Scribus

Note: Comments are owned by the poster. We are not responsible for their content.

Typo?

Posted by: Anonymous [ip: 169.233.25.159] on February 13, 2008 07:52 PM
"For this evaluation, I downloaded, compiled, and installed the latest stable Python version (1.3.3.11). " -> s/Python/Scribus/g ? Surely you aren't using a full major release version old Python.

#

Scripting Scribus

Posted by: Anonymous [ip: 70.91.29.37] on February 13, 2008 08:05 PM
Yes. That's a typo. Darn. I compiled and installed the latest stable Scribus version (1.3.3.11). Thanks for catching that.

-Drew Ames

#

underline_block.py bug?

Posted by: Anonymous [ip: 65.216.75.111] on February 13, 2008 08:28 PM
Unless I'm missing something, you need to restore the userUnit for the error condition:

The "if sel_count == 0:" conditional needs "setUnit(userUnit);" added.

#

Re: underline_block.py bug?

Posted by: Anonymous [ip: 217.33.124.146] on February 14, 2008 08:37 AM
It would make more sense to do

sel_count = selectionCount()

if sel_count == 0:
messageBox("underline_block.py",
"Please select the object to add a line to before running this script.",
ICON_INFORMATION)
sys.exit(1)N

userUnit = getUnit()
setUnit(1)

#

Scripting Scribus

Posted by: Anonymous [ip: 69.128.85.230] on February 14, 2008 02:58 PM
Does scripting like this allow execution of arbitrary executables? Does Python, used this way, require the ability to execute arbitrary executables?

Extensibility without due consideration of security is what got Microsoft it's reputation for a virus haven.

#

Re: Scripting Scribus

Posted by: Anonymous [ip: 85.224.253.80] on February 14, 2008 04:31 PM
About the execution of arbitrary executables: Python will let you do that, but there's a difference in code that is embedded in documents that are being passed around and the ability to add scripts to your application, which won't be spread.
As far as I understand, these scripts are connected to the program, not the produced documents.
Compare with plug-ins in your webbrowser. They can also do pretty much anything, which is the reason you wouldn't install just anything from anyone.

#

re: Scripting Scribus

Posted by: Anonymous [ip: 69.128.85.230] on February 15, 2008 02:52 PM
(this is 2/14/2008 02:58PM)

But if the document won't render without a plugin, won't that effectively make the plugin part of the document and therefore a security concern?

Does Scribus allow private, user-defined plugins as well as system wide plugins?

#

Re(1): Scripting Scribus

Posted by: Anonymous [ip: 144.32.155.78] on February 18, 2008 12:30 AM
No, the script adds a line to the document, which is then stored as any other object in that document. It's a one off process, consider it a quick way to do a repetitive task yourself. Some of the more useful scripts get text form a file/database and add it to relevant parts of a pre-layedout out page, eg to add a serial number or barcode to a product/ticket.

#

More than powerful...

Posted by: Anonymous [ip: 189.141.5.27] on February 15, 2008 03:33 PM
I wrote Scribus/Python-Scripts to manage all the Invoce-printing and Invoice-Backup in PDF here in the company.

With the power of Scribus, you can design and convert to PDF any kind of printing form. This is really really useful when you want to print tons of receipts or invoices with different data and with a same form or model.

We wrote a GUI in Wx-Python(wx-windows is a GUI toolkit) that receives, calculates taxes and saves it into a mysql database, then it communicates with the scribus-python-script to print data in the form.

I know there are other ways to make this, but this is the one that best fits our needs.

In conclusion Scribus-Python-Scripts are more than a simple feature in scribus. This scripts are a very very powerful tools if you know to how to squeeze its features and being creative with it.

Gatuus
gatuus@hotmail.com

#

Scripting Scribus

Posted by: Anonymous [ip: 59.92.173.63] on February 21, 2008 03:11 AM
Articles and content in this section of the website are really amazing. From http://www.endekeralam.com, http://www.chennaiflowerplaza.com

#

This story has been archived. Comments can no longer be posted.



 
Tableless layout Validate XHTML 1.0 Strict Validate CSS Powered by Xaraya