end0tknr's kipple - web写経開発

太宰府天満宮の狛犬って、妙にカワイイ

SolidPython for OpenSCAD の 手習い

# -*- coding: utf-8 -*-
# https://github.com/SolidCode/SolidPython
import solid
import solid.utils
import sys

def main():
    base_obj  = base_board()
    base_obj -= solid.translate([565.5,2226,0])( base_hole() )
    surface_obj = tiles_surface()
    surface_obj -= solid.translate([522,2193,0])( surface_hole() )
    surface_obj = solid.translate([0,25,14])( surface_obj )
    pipes_obj   = pipes()
    render_data = solid.utils.union()([surface_obj,
                                       base_obj,
                                       pipes_obj])
    
    solid.scad_render_to_file(render_data,
                              "foo3.scad",
                              include_orig_code=False)

def base_hole():
    hole_obj = solid.translate([0,0,-1])( solid.cube( [210,108,16] ) )
    return hole_obj
def surface_hole():
    hole_obj = solid.translate([0,0,-1])( solid.cube( [297,174,10] ) )
    return hole_obj

    
def pipe(height,rot):
    return solid.rotate(rot)( solid.cube([32,14,height]) )

def pipes():
    ret_datas = []
    # 縦枠
    rot_v = [-90,0,0]
    len_v =2432
    ret_datas.append( pipe(len_v,rot_v) )
    ret_datas.append( solid.translate([891-32,0,0])( pipe(len_v,rot_v)) )
    # 横枠
    rot_h = [-90,0,-90]
    len_h = 891-32-32
    pos_hs = [32/2+109,
              32/2+109+407,
              32/2+109+407+730,
              32/2+109+407+730+633,
              109+407+730+633+553 ]
    for pos_h in pos_hs:
        ret_datas.append( solid.translate([32,pos_h,0])( pipe(len_h,rot_h)) )
    return solid.utils.union()( *ret_datas )

def base_board():
    size = [891, 2432, 14]
    return solid.cube( size )

def tiles_surface():
    tile_size  = [217,60,8]             # tile 1枚のsize
    tiles_size = [891, 2432-25-35]      # tile群のsize
    tiles_gap  = 8                      # tile間のgap
    ret_datas = []

    # まず、tile群を並べる
    row = 0
    while True:
        y = (tile_size[1]+tiles_gap) * row
        if y >= tiles_size[1]:
            break
        
        col = 0
        while True:
            x = (tile_size[0]+tiles_gap) * col - tile_size[0]/2 * (row % 2)
            if x >= tiles_size[0]:
                break
            tile_obj = solid.translate([x,y,0])( tile(tile_size) )
            col += 1

            ret_datas.append( tile_obj )
        row += 1
    tiles_spread = solid.utils.union()( *ret_datas )

    # tile群のsizeに併せてtrim
    tiles_container = solid.cube( [tiles_size[0],tiles_size[1],tile_size[2]] )
    tiles_obj = tiles_container * tiles_spread
    
    return tiles_obj

    
def tile( size ):
    cube = solid.cube( size ) # タイル メイン部
    
    def chamfer(rot): # cylinder()で面取りを表現
        return solid.rotate(rot)(
            solid.cylinder(h=size[0], r1=4, r2=4, segments=4) )

    cube -= solid.translate([      0,      0,size[2]])( chamfer([  0,90,0]) )
    cube -= solid.translate([      0,size[1],size[2]])( chamfer([  0,90,0]) )
    cube -= solid.translate([      0,      0,size[2]])( chamfer([-90, 0,0]) )
    cube -= solid.translate([size[0],      0,size[2]])( chamfer([-90, 0,0]) )
    return cube

if __name__ == '__main__':
    main()