@@ -30,6 +30,41 @@ def mask_layer(layer_index, context):
3030def render (context , index ):
3131 bpy .data .scenes ['Scene' ].render .filepath = get_output_path (context , index )
3232 bpy .ops .render .render ( write_still = True )
33+ return
34+
35+ def rotate_for_vertical_joint (x , y , modifier = 1 ):
36+ vertical_joint = bpy .data .objects ['VerticalJoint' ]
37+ if vertical_joint is None :
38+ return False
39+ angle = - vertical_joint .rotation_euler [2 ] * modifier
40+ return [round (x * math .cos (angle ) - y * math .sin (angle )), round (x * math .sin (angle ) + y * math .cos (angle ))]
41+
42+
43+ def position_cookie_cutter (context , x , y , left , right , enable ):
44+ cookie_cutter = bpy .data .objects ['CookieCutter' ]
45+ if cookie_cutter is None :
46+ return False
47+ cookie_cutter_floor = bpy .data .objects ['CookieCutterFloor' ]
48+ if cookie_cutter_floor is None :
49+ return False
50+ vertical_joint = bpy .data .objects ['VerticalJoint' ]
51+ if vertical_joint is None :
52+ return False
53+ cookie_cutter_floor .hide_render = not enable
54+ angle = vertical_joint .rotation_euler [2 ]
55+ cookie_cutter .location [1 ] = - (x * math .cos (angle ) - y * math .sin (angle )) * 4
56+ cookie_cutter .location [0 ] = - (x * math .sin (angle ) + y * math .cos (angle )) * 4
57+ cookie_cutter .location [2 ] = 0
58+
59+ cookie_cutter_l = bpy .data .objects ['CookieCutterLeft' ]
60+ if cookie_cutter_l is None :
61+ return False
62+ cookie_cutter_l .hide_render = not left
63+ cookie_cutter_r = bpy .data .objects ['CookieCutterRight' ]
64+ if cookie_cutter_r is None :
65+ return False
66+ cookie_cutter_r .hide_render = not right
67+ return True
3368
3469def rotate_rig (context , angle , verAngle = 0 , bankedAngle = 0 , midAngle = 0 ):
3570 object = bpy .data .objects ['Rig' ]
@@ -40,16 +75,33 @@ def rotate_rig(context, angle, verAngle=0, bankedAngle=0, midAngle=0):
4075 vJoint .rotation_euler = (0 ,0 ,math .radians (angle ))
4176 return True
4277
43- def post_render (context , index ):
78+ def post_render (context , index , crop = True ):
4479 magick_path = "magick"
4580 output_path = get_output_path (context , index )
4681
4782 palette_path = context .scene .rct_graphics_helper_general_properties .palette_path
48- result = str (subprocess .check_output (magick_path + " \" " + output_path + "\" -fuzz 0 -fill none -opaque rgb(57,59,57) -quantize RGB -dither FloydSteinberg -define dither:diffusion-amount=30% -remap \" " + palette_path + "\" -colorspace sRGB -bordercolor none -border 1 -trim -format \" %[fx:page.x - page.width/2] %[fx:page.y - page.height/2]\" -write info: \" " + output_path + "\" " , shell = True ))
83+
84+ result = ""
85+ if crop :
86+ result = str (subprocess .check_output (magick_path + " \" " + output_path + "\" -fuzz 0 -fill none -opaque rgb(57,59,57) -quantize RGB -dither FloydSteinberg -define dither:diffusion-amount=30% -remap \" " + palette_path + "\" -colorspace sRGB -bordercolor none -border 1 -trim -format \" %[fx:page.x - page.width/2] %[fx:page.y - page.height/2]\" -write info: \" " + output_path + "\" " , shell = True ))
87+
88+ offset_file = open (get_offset_output_path (context , index ), "w" )
89+ offset_file .write (result [2 :][:- 1 ])
90+ offset_file .close ()
4991
50- offset_file = open (get_offset_output_path (context , index ), "w" )
51- offset_file .write (result [2 :][:- 1 ])
52- offset_file .close ()
92+ else :
93+ result = str (subprocess .check_output (magick_path + " \" " + output_path + "\" -fuzz 0 -fill none -opaque rgb(57,59,57) -quantize RGB -dither FloydSteinberg -define dither:diffusion-amount=30% -remap \" " + palette_path + "\" -colorspace sRGB \" " + output_path + "\" " , shell = True ))
94+ return
95+
96+ def mask (context , base , mask , output , operation = "In" ):
97+ magick_path = "magick"
98+ output_path = get_output_path (context , output )
99+ base_path = get_output_path (context , base )
100+ mask_path = get_output_path (context , mask )
101+
102+ result = str (subprocess .check_output (magick_path + " \" " + mask_path + "\" +repage -gravity center \" " + base_path + "\" -compose " + operation + " -composite \" " + output_path + "\" " , shell = True ))
103+ return
104+
53105
54106class AngleSectionTask (object ):
55107 section = None
@@ -64,6 +116,8 @@ class AngleSectionTask(object):
64116 inverted = False
65117 context = None
66118 render_layer = 0
119+ width = 1
120+ height = 1
67121
68122 def __init__ (self , section_in , out_index_start , context ):
69123 self .render_layer = section_in .render_layer
@@ -78,6 +132,11 @@ def __init__(self, section_in, out_index_start, context):
78132 self .anim_index = 0
79133 self .status = "CREATED"
80134 self .context = context
135+ self .width = section_in .width
136+ self .height = section_in .height
137+ self .wx = 0
138+ self .wy = 0
139+ self .sub_tiles = False
81140
82141 def step (self ):
83142 if self .frame_index == len (self .section ):
@@ -100,13 +159,75 @@ def step(self):
100159 if self .inverted :
101160 extra_roll = 180
102161
162+ has_sub_tiles = self .width > 1 or self .height > 1
163+
103164 self .context .scene .frame_set (self .anim_start + self .anim_index )
104165 rotate_rig (self .context , angle , frame [2 ], frame [3 ] + extra_roll , frame [4 ])
105- render (self .context , self .out_index )
106- post_render (self .context , self .out_index )
107166
108- self .out_index += 1
109- self .anim_index += 1
167+ if self .sub_tiles :
168+ wh = rotate_for_vertical_joint (- 1 , - 1 )
169+ if wh [0 ] < 0 :
170+ wh [0 ] = 0
171+ if wh [1 ] < 0 :
172+ wh [1 ] = 0
173+ xy = rotate_for_vertical_joint (self .wx , self .wy )
174+ position_cookie_cutter (self .context , self .wx , self .wy , abs (xy [0 ]) == wh [1 ] * (self .height - 1 ), abs (xy [1 ]) == wh [0 ] * (self .width - 1 ), True )
175+ else :
176+ position_cookie_cutter (self .context , 0 , 0 , False , False , False )
177+
178+ output = self .out_index
179+ if has_sub_tiles :
180+ output = "full" + "_" + str (self .out_index )
181+ if has_sub_tiles and self .sub_tiles :
182+ output = (self .wy * self .width + self .wx ) * frame [1 ] + self .out_index
183+ render (self .context , output )
184+ post_render (self .context , output , not has_sub_tiles )
185+
186+ if self .sub_tiles :
187+ if self .wx == self .width - 1 :
188+ self .wx = 0
189+ if self .wy == self .height - 1 :
190+ self .wy = 0
191+ self .sub_tiles = False
192+ self .anim_index += 1
193+
194+ for i in range (self .width ):
195+ for j in range (self .height ):
196+ index = (j * self .width + i ) * frame [1 ] + self .out_index
197+ mask (self .context , index , index , "c_" + str (index ), "Dst" )
198+
199+ for i in range (self .width ):
200+ for j in range (self .height ):
201+ posx = rotate_for_vertical_joint (1 , 0 )
202+ posy = rotate_for_vertical_joint (0 , 1 )
203+ index = (j * self .width + i ) * frame [1 ] + self .out_index
204+ indexx2 = ((j + posx [1 ]) * self .width + (i + posx [0 ])) * frame [1 ] + self .out_index
205+ indexy2 = ((j + posy [1 ]) * self .width + (i + posy [0 ])) * frame [1 ] + self .out_index
206+ if i + posx [0 ] < self .width and j + posx [1 ] < self .height and i + posx [0 ] >= 0 and j + posx [1 ] >= 0 :
207+ mask (self .context , "c_" + str (index ), str (indexx2 ), "c_" + str (index ), "Out" )
208+ if i + posy [0 ] < self .width and j + posy [1 ] < self .height and i + posy [0 ] >= 0 and j + posy [1 ] >= 0 :
209+ mask (self .context , "c_" + str (index ), str (indexy2 ), "c_" + str (index ), "Out" )
210+
211+ for i in range (self .width ):
212+ for j in range (self .height ):
213+ index = (j * self .width + i ) * frame [1 ] + self .out_index
214+ mask (self .context , "c_" + str (index ), "full" + "_" + str (self .out_index ), index , "Dst_In" )
215+ os .remove (get_output_path (self .context , "c_" + str (index )))
216+ post_render (self .context , index )
217+
218+ self .out_index += 1
219+ else :
220+ self .wy += 1
221+ else :
222+ self .wx += 1
223+ else :
224+ if has_sub_tiles :
225+ if not self .sub_tiles :
226+ self .sub_tiles = True
227+ else :
228+ self .anim_index += 1
229+ self .out_index += 1
230+
110231 if self .anim_index == self .anim_count :
111232 self .anim_index = 0
112233 self .sub_index += 1
@@ -125,12 +246,16 @@ class RenderTaskSection(object):
125246 render_layer = 0
126247 anim_frame_index = 0
127248 anim_frame_count = 1
128- def __init__ (self , angle_section , render_layer = 0 , inverted = False , frame_index = 0 , frame_count = 1 ):
249+ width = 1
250+ height = 1
251+ def __init__ (self , angle_section , render_layer = 0 , inverted = False , frame_index = 0 , frame_count = 1 , width = 1 , height = 1 ):
129252 self .angle_section = angle_section
130253 self .inverted = inverted
131254 self .render_layer = render_layer
132255 self .anim_frame_index = frame_index
133256 self .anim_frame_count = frame_count
257+ self .width = width
258+ self .height = height
134259
135260
136261class RenderTask (object ):
@@ -141,16 +266,18 @@ class RenderTask(object):
141266 section_task = None
142267 out_index = 0
143268 context = None
269+ use_antialiasing = False
144270 def __init__ (self , out_index_start , context ):
145271 self .out_index = out_index_start
146272 self .sections = []
147273 self .section_index = 0
148274 self .status = "CREATED"
149275 self .section_task = None
150276 self .context = context
277+ self .use_antialiasing = context .scene .render .use_antialiasing
151278
152- def add (self , angle_section , render_layer = 0 , inverted = False , frame_index = 0 , frame_count = 1 ):
153- self .sections .append (RenderTaskSection (angle_section , render_layer , inverted , frame_index , frame_count ))
279+ def add (self , angle_section , render_layer = 0 , inverted = False , frame_index = 0 , frame_count = 1 , width = 1 , height = 1 ):
280+ self .sections .append (RenderTaskSection (angle_section , render_layer , inverted , frame_index , frame_count , width , height ))
154281
155282 def step (self ):
156283 if self .section_task is None :
@@ -165,5 +292,6 @@ def step(self):
165292 self .section_index += 1
166293
167294 if self .section_index == len (self .sections ):
295+ position_cookie_cutter (self .context , 0 , 0 , False , False , False )
168296 self .status = "FINISHED"
169297 return "FINISHED"
0 commit comments