omdl  v0.9.5
OpenSCAD Mechanical Design Library
repeat.scad
Go to the documentation of this file.
1 //! Shape repetition tools.
2 /***************************************************************************//**
3  \file
4  \author Roy Allen Sutton
5  \date 2015-2019
6 
7  \copyright
8 
9  This file is part of [omdl] (https://github.com/royasutton/omdl),
10  an OpenSCAD mechanical design library.
11 
12  The \em omdl is free software; you can redistribute it and/or modify
13  it under the terms of the [GNU Lesser General Public License]
14  (http://www.gnu.org/licenses/lgpl.html) as published by the Free
15  Software Foundation; either version 2.1 of the License, or (at
16  your option) any later version.
17 
18  The \em omdl is distributed in the hope that it will be useful,
19  but WITHOUT ANY WARRANTY; without even the implied warranty of
20  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
21  Lesser General Public License for more details.
22 
23  You should have received a copy of the GNU Lesser General Public
24  License along with the \em omdl; if not, write to the Free Software
25  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
26  02110-1301, USA; or see <http://www.gnu.org/licenses/>.
27 
28  \details
29 
30  \amu_define group_name (Repeat)
31  \amu_define group_brief (Shape repetition tools.)
32 
33  \amu_include (include/amu/pgid_path_pstem_pg.amu)
34 *******************************************************************************/
35 
36 //----------------------------------------------------------------------------//
37 // group and macros.
38 //----------------------------------------------------------------------------//
39 
40 /***************************************************************************//**
41  \amu_include (include/amu/group_in_parent_start.amu)
42  \amu_include (include/amu/includes_required.amu)
43 
44  \amu_define image_view (diag)
45 
46  \amu_define group_id (${parent})
47  \amu_include (include/amu/scope_diagrams_3d_in_group.amu)
48 
49  \amu_define group_id (${group})
50  \amu_include (include/amu/scope_diagrams_3d_in_group.amu)
51 
52  \amu_include (include/amu/scope_diagram_3d_object.amu)
53 *******************************************************************************/
54 
55 //----------------------------------------------------------------------------//
56 
57 //! Distribute copies of a 2d or 3d shape equally about a z-axis radius.
58 /***************************************************************************//**
59  \param n <integer> The number of equally spaced radii.
60  \param r <decimal> The radial move distance.
61  \param o <decimal> The rotational angular offset.
62  \param angle <boolean> Rotate each copy about z-axis.
63  \param move <boolean> Move each shape copy to radii coordinate.
64 
65  \details
66 
67  \amu_eval ( object=repeat_radial ${object_ex_diagram_3d} )
68 *******************************************************************************/
69 module repeat_radial
70 (
71  n,
72  r = 1,
73  o = 0,
74  angle = true,
75  move = false
76 )
77 {
78  for ( p = polygon_regular_p( n=n, r=r, o=o ) )
79  {
80  translate(move==true ? p : origin2d)
81  rotate(angle==true ? [0, 0, angle_ll(x_axis2d_uv, p)] : origin3d)
82  children();
83  }
84 }
85 
86 //! Distribute copies of 2d or 3d shapes about Cartesian grid.
87 /***************************************************************************//**
88  \param g <integer-list-3 | integer> The grid division count. A list
89  [x, y, z] of integers or a single integer for (x=y=z).
90  \param i <decimal-list-3 | decimal> The grid increment size. A list
91  [x, y, z] of decimals or a single decimal for (x=y=z).
92  \param c <integer> The number of copies. Number of times to iterate
93  over children.
94  \param center <boolean> Center distribution about origin.
95 
96  \details
97 
98  \amu_eval ( object=repeat_grid ${object_ex_diagram_3d} )
99 *******************************************************************************/
100 module repeat_grid
101 (
102  g,
103  i,
104  c = 1,
105  center = false
106 )
107 {
108  gridd = is_scalar(g) ? g : 1;
109 
110  gridx = defined_e_or(g, 0, gridd);
111  gridy = defined_e_or(g, 1, gridd);
112  gridz = defined_e_or(g, 2, gridd);
113 
114  incrd = is_scalar(i) ? i : 0;
115 
116  incrx = defined_e_or(i, 0, incrd);
117  incry = defined_e_or(i, 1, incrd);
118  incrz = defined_e_or(i, 2, incrd);
119 
120  if ( ( $children * c ) > ( gridx * gridy * gridz ) )
121  {
122  log_warn("more objects than grid capacity, shapes will overlap.");
123  log_info
124  (
125  str
126  (
127  "children=", $children,
128  ", copies=", c,
129  ", objects=", $children * c
130  )
131  );
132  log_info
133  (
134  str
135  (
136  "grid[x,y,z]=[", gridx, ", ", gridy, ", ", gridz, "]",
137  ", capacity=", gridx * gridy * gridz
138  )
139  );
140  }
141 
142  translate
143  (
144  center==true
145  ? [
146  -( min($children * c, gridx) -1 ) * incrx / 2,
147  -( min(ceil($children * c/gridx), gridy) -1 ) * incry / 2,
148  -( min(ceil($children * c/gridx/gridy), gridz) -1 ) * incrz / 2
149  ]
150  : origin3d
151  )
152  if ( c > 0 )
153  {
154  for
155  (
156  y = [0 : (c-1)],
157  x = [0 : ($children-1)]
158  )
159  {
160  j = y * $children + x;
161 
162  translate
163  (
164  [
165  incrx * (j%gridx),
166  incry * (floor(j/gridx)%gridy),
167  incrz * (floor(floor(j/gridx)/gridy)%gridz)
168  ]
169  )
170  children([x]);
171  }
172  }
173 }
174 
175 //! @}
176 //! @}
177 
178 //----------------------------------------------------------------------------//
179 // openscad-amu auxiliary scripts
180 //----------------------------------------------------------------------------//
181 
182 /*
183 BEGIN_SCOPE diagram;
184  BEGIN_OPENSCAD;
185  include <omdl-base.scad>;
186 
187  shape = "repeat_radial";
188  $fn = 36;
189 
190  if (shape == "repeat_radial")
191  repeat_radial( n=7, r=6, move=true ) square( [20,1], center=true );
192  else if (shape == "repeat_grid")
193  repeat_grid( g=[5,5,4], i=10, c=50, center=true ) {cube(10, center=true); sphere(10);}
194  END_OPENSCAD;
195 
196  BEGIN_MFSCRIPT;
197  include --path "${INCLUDE_PATH}" {var_init,var_gen_png2eps}.mfs;
198 
199  views name "views" views "diag";
200  defines name "shapes" define "shape"
201  strings "
202  repeat_radial
203  repeat_grid
204  ";
205  variables add_opts_combine "views shapes";
206  variables add_opts "--viewall --autocenter --view=axes";
207 
208  include --path "${INCLUDE_PATH}" scr_make_mf.mfs;
209  END_MFSCRIPT;
210 END_SCOPE;
211 */
212 
213 //----------------------------------------------------------------------------//
214 // end of file
215 //----------------------------------------------------------------------------//
module log_warn(m)
Output warning message to console.
Definition: console.scad:333
module log_info(m)
Output information message to console.
Definition: console.scad:318
origin2d
<point-2d> The origin point coordinate in 2d Euclidean space.
Definition: constants.scad:407
origin3d
<point-3d> The origin point coordinate in 3-dimensional Euclidean space.
Definition: constants.scad:425
x_axis2d_uv
<vector-2d> The unit vector of the positive x-axis in 2d Euclidean space.
Definition: constants.scad:410
function angle_ll(l1, l2, s=true)
Compute the angle between two lines or vectors in a 3d or 2d-space.
function defined_e_or(v, i, d)
Return an element of an iterable when it exists or a default value otherwise.
function is_scalar(v)
Test if a value is a single non-iterable value.
function polygon_regular_p(n, r, a, c=origin2d, o=0, vr, cw=true)
Compute coordinates for an n-sided regular polygon in 2D.
module repeat_radial(n, r=1, o=0, angle=true, move=false)
Distribute copies of a 2d or 3d shape equally about a z-axis radius.
Definition: repeat.scad:459
module repeat_grid(g, i, c=1, center=false)
Distribute copies of 2d or 3d shapes about Cartesian grid.
Definition: repeat.scad:495
function angle(a, from=angle_unit_default, to=angle_unit_base)
Convert an angle from some units to another.