Shade3D(ver16), pythonスクリプトで正十二面体をつくる

備忘：Shade3D ver16 pythonスクリプトで正十二面体をつくる

正十二面体、頂点は２０個。辺は３０個。
>オイラーの多面体定理：「頂点の数」−「辺の数」＋「面の数」＝２
>２０−３０＋１２＝２

## 手順

①２０個の頂点の座標を調べる。
②３０辺の点の組み合わせをセットする。
③３次元内の２点間を結ぶスクリプトを書き、辺を結ぶ。

## ２０個の頂点の座標

以下のツイートを参考にさせていただきました。ありがとうございます。

↓引用ここから

>https://twitter.com/hyrodium/status/369819992658698240
>![スクリーンショット 2020-12-06 14.33.13.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/107418/94158560-fc87-5d0c-1dfd-3355f8419174.png)

↑引用ここまで


φを、1.618として、

```python
lst = [0] * 21
lst[1]= [1,1,1]
lst[2]= [1.618,0,1/1.618]
lst[3]= [1.618,0,-1/1.618]
lst[4]= [1,1,-1]
lst[5]= [1/1.618,1.618,0]
lst[6]= [0,1/1.618,1.618]
lst[7]= [1,-1,1]
lst[8]= [1,-1,-1]
lst[9]= [0,1/1.618,-1.618]
lst[10]= [-1/1.618,1.618,0]
lst[11]= [-1,1,1]
lst[12]= [0,-1/1.618,1.618]
lst[13]= [1/1.618,-1.618,0]
lst[14]= [0,-1/1.618,-1.618]
lst[15]= [-1,1,-1]
lst[16]= [-1.618,0,1/1.618]
lst[17]= [-1,-1,1]
lst[18]= [-1/1.618,-1.618,0]
lst[19]= [-1,-1,-1]
lst[20]= [-1.618,0,-1/1.618]
```

## 3０個の辺の組み合わせをセット

[i,j]として、i番の頂点と、j番の頂点を結ぶ

```python
hen = [0] * 31
hen[1] = [1,2]
hen[2] = [2,3]
hen[3] = [3,4]
hen[4] = [4,5]
hen[5] = [5,1]
hen[6] = [1,6]
hen[7] = [2,7]
hen[8] = [3,8]
hen[9] = [4,9]
hen[10] = [5,10]
hen[11] = [6,11]
hen[12] = [6,12]
hen[13] = [7,12]
hen[14] = [7,13]
hen[15] = [8,13]
hen[16] = [8,14]
hen[17] = [9,14]
hen[18] = [9,15]
hen[19] = [10,15]
hen[20] = [10,11]
hen[21] = [11,16]
hen[22] = [12,17]
hen[23] = [13,18]
hen[24] = [14,19]
hen[25] = [15,20]
hen[26] = [16,17]
hen[27] = [17,18]
hen[28] = [18,19]
hen[29] = [19,20]
hen[30] = [20,16]
```

## ３次元内の２点間を結ぶスクリプト

*1)２点を結ぶもの

点P1(x1,y1,z1)から点P2(x2,y2,z2)への単位ベクトルは、

(X,Y,Z) = (x2-x1,y2-y1,z2-z1)
を用いて、r、θ、φを求め、
dx = sinθ cosφ
dy = sinθ sinφ
dz = cosθ
方向に、動かせばよい。

本プログラムでは、rの距離を、20ステップで移動している

```Python
import math
import random
scene = xshade.scene()
scene.begin_creating()
s = 8 #点、となる、球の大きさ
#i
x1 = 10 
y1 = 20 
z1 = 30 
#j
x2 = 100 
y2 = 100 
z2 = 100 
px = -x1+x2 
py = -y1+y2 
pz = -z1+z2 
r =  math.sqrt(px*px + py*py + pz*pz)
th = math.acos(pz / r)
if math.sqrt(px * px + py * py) == 0:
	fi = 0
else:
	if py >= 0:
		fi = 1 *  math.acos(px / math.sqrt(px * px + py * py))
	else:
		fi = -1 * math.acos(px / math.sqrt(px * px + py * py))
dx = math.sin(th) *math.cos(fi) * (r/20)
dy = math.sin(th) *math.sin(fi) * (r/20)
dz = math.cos(th) * (r/20)
cx = x1
cy = y1
cz = z1
for ii in range(0,20+1,1):
	scene.create_primitive_sphere(None,3,True,s,s,[cx, cy, cz],s)
	cx += dx
	cy += dy
	cz += dz
scene.end_creating()
```

↓wikipediaより

>（参考）
>https://ja.wikipedia.org/wiki/%E7%90%83%E9%9D%A2%E5%BA%A7%E6%A8%99%E7%B3%BB
>![スクリーンショット 2020-12-06 18.54.23.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/107418/faae28a7-de7a-9519-1afe-1f7eb68e277e.png)

↑wikipediaより

*2)30の辺のループ

```Python
for i in range(1,30+1,1):
	rd = 50
	pt1 = hen[i][0]
	pt2 = hen[i][1]
	x1 = lst[pt1][0] * rd
	y1 = lst[pt1][1] * rd
	z1 = lst[pt1][2] * rd
	x2 = lst[pt2][0] * rd
	y2 = lst[pt2][1] * rd
	z2 = lst[pt2][2] * rd
```

## 出来上がり

![スクリーンショット 2020-12-06 14.43.26.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/107418/6a44eff4-696b-a615-f8b6-aaf27fbdb255.png)

## ソース

https://github.com/santarou6/shade/blob/main/shade_script_2020_11_A018.py

## STL

https://github.com/santarou6/shade/blob/main/shade_script_2020_11_A018.stl

![スクリーンショット 2020-12-06 16.13.23.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/107418/956447c2-87b1-6afe-41bb-108fe13ea526.png)


## 参考

Shade3D(ver16)で、Pythonスクリプトで生成したデータを、3Dプリンタ用に整形する
https://qiita.com/santarou6/items/4093443416120eafb0c5


①Pythonで画像から色情報抜き出す、②PythonでShade3Dスクリプトで濃淡絵を書く、③３Dプリンタで書き出す
https://qiita.com/santarou6/items/92d4b3f245642bea9862