import sys import re import os import simplejson as json import random from Config import DEFAULT_FINALFORMAT, DEFAULT_HEIGHT, DEFAULT_WIDTH, WORKING_DIR, OUTPUT_IMAGE_TYPES from Config import THREEDROTATE, GRID, BIN_CONVERT, BIN_COMPOSITE import tempfile from Pb import Pb _default_line_color = "silver" class PbGrid(Pb): example_params = { 'bgimage' : 'http://i.asdf.us/im/1a/imBreak_1424909483_xx_abridged___.gif', 'planebgimage' : 'http://i.imgur.com/FICZtph.png', 'tilt' : '30', 'spacing' : '30', 'hlines' : 'true', 'roll' : '30', 'shadow' : 'true', 'trim' : 'true' } def __init__(self, width=None, height=None, linethickness=1, opacity=1.0, linecolor="whitesmoke", spacing=10, vlines=False, hlines=False, shadow=False, bgimage=None, bgcolor="transparent", imageinstead=None, planebgcolor="transparent", planebgimage=None, swing=False, tilt=False, roll=False, zoom=0, skycolor="transparent", transition="background", trim=False, finalformat=DEFAULT_FINALFORMAT, username="" ): super(PbGrid,self).__init__(); self.params.set_val("width", width or 0, value_type="int") self.params.set_val("height", height or 0, value_type="int") self.params.set_val("linethickness", linethickness, value_type="int") self.params.set_val("opacity", opacity, value_type="float") self.params.set_val("linecolor", linecolor, value_type="color") self.params.set_val("linethickness", linethickness, value_type="int") self.params.set_val("spacing", spacing, value_type="int") self.params.set_val("vlines", vlines, value_type="bool") self.params.set_val("hlines", hlines, value_type="bool") self.params.set_val("shadow", shadow, value_type="bool") self.params.set_val("bgimage", bgimage, value_type="img_url") self.params.set_val("bgcolor", bgcolor, value_type="color") self.params.set_val("imageinstead", imageinstead, value_type="img_url") self.params.set_val("planebgcolor", planebgcolor, value_type="color") self.params.set_val("planebgimage", planebgimage, value_type="img_url") self.params.set_val("swing", swing, value_type="int") self.params.set_val("tilt", tilt, value_type="int") self.params.set_val("roll", roll, value_type="int") self.params.set_val("zoom", zoom, value_type="int") self.params.set_val("skycolor", skycolor, value_type="color") self.params.set_val("transition", transition, value_type="enum", enum_values=["background", "dither", "edge", "mirror", "random", "tile"]) #FIXME self.params.set_val("trim", trim, value_type="bool") self.params.set_val("finalformat", finalformat, value_type="enum", enum_values=OUTPUT_IMAGE_TYPES)# FIXME self.params.set_val("username", username, value_type="string"); if self.params.imageinstead: self.filename, self.filepath = self._filename_filepath_create(url=self.params.imageinstead['url'], extension=self.params.finalformat) elif self.params.planebgimage: self.filename, self.filepath = self._filename_filepath_create(url=self.params.planebgimage['url'], extension=self.params.finalformat) else: self.filename, self.filepath = self._filename_filepath_create(extension=self.params.finalformat) #FIXME choose gif frame #makes a canvas file...step 1 (if not bgimage) def _make_canvas(self): dimensions = "{}x{}".format( self.params.width or DEFAULT_WIDTH, self.params.height or DEFAULT_HEIGHT ) if self.params.bgimage: return bgcolor = "xc:{}".format(self.params.bgcolor or 'transparent') cmd = [ BIN_CONVERT, "-size", dimensions, bgcolor, self.filepath ] self._call_cmd(cmd) #2nd step-- run grid def _grid_command(self): cmd = [GRID] if self.params.spacing: if self.params.vlines: width = 2 * int(self.params.width or DEFAULT_WIDTH) cmd += ["-s","{},{}".format(self.params.spacing,width)] elif self.params.hlines: height = 2 * int(self.params.height or DEFAULT_HEIGHT) cmd += ["-s", "{},{}".format(height,self.params.spacing)] else: cmd += ["-s",self.params.spacing] cmd += [ "-c", self.params.linecolor or _default_line_color] if self.params.linethickness: cmd += ['-t',self.params.linethickness] if self.params.opacity: cmd += ['-o',self.params.opacity] cmd += [ self.filepath, self.filepath ] self._call_cmd(cmd) def _shadow_cmd(self): #convert 1.png \( +clone -background black -shadow 110x1+9+9 \) +swap -background none -layers merge +repage 2.png cmd = [ BIN_CONVERT, self.filepath, "(","+clone","-background","black","-shadow","100x2+20+10",")", "+swap","-background","none","-layers","merge","+repage" , self.filepath ] self._call_cmd(cmd) def _threed_rotate_cmd (self): #3rd step--run 3Drotate cmd = [THREEDROTATE] if self.params.swing: cmd += ["pan={}".format(self.params.swing)] if self.params.tilt: cmd += ["tilt={}".format(self.params.tilt)] if self.params.roll: cmd += ["roll={}".format(self.params.roll)] if self.params.zoom: cmd += ["zoom={}".format(self.params.zoom)] if cmd == [THREEDROTATE]: #if nothing has been added return if self.params.planebgcolor and not self.params.planebgimage: cmd += ["bgcolor={}".format(self.params.planebgcolor)] else: cmd += ["bgcolor=none"] cmd += ["skycolor={}".format(self.params.skycolor or 'none')] if self.params.transition: cmd += ["vp={}".format(self.params.transition)] cmd += [ self.filepath, self.filepath ] self._call_cmd(cmd) def _trim_cmd (self): cmd = [BIN_CONVERT, self.filepath, "-trim", "+repage", self.filepath] self._call_cmd(cmd) def _prepare_gridimage(self, image): if image['mimetype'] == 'gif': _frame = self._choose_gif_frame(image['path']) if image['mimetype'] != 'png': cmd = [BIN_CONVERT, image['path'], self.filepath] else: cmd = ['cp', image['path'], self.filepath] self._call_cmd(cmd) def _overlay_planebgimage(self): cmd = [ BIN_COMPOSITE, "-compose", "Dst_Over", "-gravity", "center", self.params.planebgimage["path"], self.filepath, self.filepath ] self._call_cmd(cmd) def create(self): if self.params.bgimage: self._prepare_gridimage(self.params.bgimage) self._grid_command() elif self.params.imageinstead: self._prepare_gridimage(self.params.imageinstead) else: self._make_canvas() self._grid_command() if self.params.shadow: self._shadow_cmd() self._threed_rotate_cmd() if self.params.planebgimage: self._overlay_planebgimage() if self.params.trim: self._trim_cmd() self._cleanup()