演算スクリプトを自作してみたはいいのですが、途中から分からなくなってきてしまいました。
以下、書きかけのスクリプトの詳細です。
・重心のみ動作しているように見えるが、これで正解かは不明
・内心、外心は作ってはみたが失敗している
・垂心、傍心は未実装
;vec2演算用モジュール #module vec2_compute #include "hspmath.as" #defcfunc double_mix double u_x, double u_y, double u_coe return u_x * (1.0 - u_coe) + u_y * u_coe #deffunc vec2_multiply array u_res, array u_x, array u_y u_res.0 = u_x.0 * u_y.0 u_res.1 = u_x.1 * u_y.1 return #deffunc vec2_multiply_value array u_res, array u_x, double u_v u_res.0 = u_x.0 * u_v u_res.1 = u_x.1 * u_v return #deffunc vec2_divide array u_res, array u_x, array u_y if u_x.0 == 0.0 : dialog "0.0で除算しようとしています", 1, "vec2_divide error" : end if u_x.1 == 0.0 : dialog "0.0で除算しようとしています", 1, "vec2_divide error" : end if u_y.0 == 0.0 : dialog "0.0で除算しようとしています", 1, "vec2_divide error" : end if u_y.1 == 0.0 : dialog "0.0で除算しようとしています", 1, "vec2_divide error" : end u_res.0 = u_x.0 / u_y.1 u_res.1 = u_x.1 / u_y.1 return #deffunc vec2_divide_value array u_res, array u_x, double u_v if u_v == 0.0 : dialog "0.0で除算しようとしています", 1, "vec2_divide_value error" : end u_res.0 = u_x.0 / u_v u_res.1 = u_x.1 / u_v return #deffunc vec2_divide_value2 array u_res, double u_v, array u_x if u_v == 0.0 : dialog "0.0で除算しようとしています", 1, "vec2_divide_value2 error" : end u_res.0 = u_v / u_x.0 u_res.1 = u_v / u_x.1 return #deffunc vec2_subtract array u_res, array u_x, array u_y u_res.0 = u_x.0 - u_y.0 u_res.1 = u_x.1 - u_y.1 return #deffunc vec2_subtract_value array u_res, array u_x, double u_v u_res.0 = u_x.0 - u_v u_res.1 = u_x.1 - u_v return #deffunc vec2_subtract_value2 array u_res, double u_v, array u_x u_res.0 = u_v - u_x.0 u_res.1 = u_v - u_x.1 return #deffunc vec2_add array u_res, array u_x, array u_y u_res.0 = u_x.0 + u_y.0 u_res.1 = u_x.1 + u_y.1 return #deffunc vec2_add_value array u_res, array u_x, double u_v u_res.0 = u_x.0 + u_v u_res.1 = u_x.1 + u_v return ;distance2と同じ #defcfunc vec2_distance array u_fv0, array u_fv1 return distance2(u_fv0, u_fv1) #deffunc vec2_set_value array u_i, double u_i2 u_i = u_i2, u_i2 return #deffunc vec2_degToRad array u_i, array u_i2 u_i = deg2rad(u_i2.0), deg2rad(u_i2.1) return #deffunc vec2_01toRad array u_i, array u_i2 vec2_multiply_value u_i, u_i2, M_PI2 return #deffunc vec2_radTo01 array u_i, array u_i2 if vec2_calc_equivalence_value(u_i2, 0.0) : vec2_set_value u_i, 0.0 : return vec2_divide_value2 u_i, M_PI2, u_i2 return #deffunc vec2_degTo01 array u_i, array u_i2 vec2_degToRad u_i2, u_i2 vec2_radTo01 u_i2, u_i2 return #deffunc vec2_mix array u_res, array u_x, array u_y, double u_coe u_res.0 = double_mix( u_x.0, u_y.0, u_coe ) u_res.1 = double_mix( u_x.1, u_y.1, u_coe ) return #deffunc vec2_sin array u_res, array u_x u_res.0 = sin(u_x.0) u_res.1 = sin(u_x.1) return #deffunc vec2_cos array u_res, array u_x u_res.0 = cos(u_x.0) u_res.1 = cos(u_x.1) return #deffunc vec2_tan array u_res, array u_x u_res.0 = tan(u_x.0) u_res.1 = tan(u_x.1) return ; ベクトルを正規化(単位長) #deffunc vec2_normalize array u_i l = vector_length(u_i) if l == 0.0 : dialog "ベクトルの長さが0.0です", 1, "vec2_normalize error" : end u_i.0 /= l u_i.1 /= l return #defcfunc vec2_dot array u_x, array u_y return u_x.0*u_y.0 + u_x.1*u_y.1 #global ;------------------------------------------------------------------------------------ ;三角形の五心を扱う #ifndef mod_triangle_center #module mod_triangle_center ;数学用語が辞書に載ってなかったので、関数名の英語はニュアンスで付けた ;vec2版 /* u_vertの仕様 ・vec2版は2次元 ・頂点がOpenGLと同じく右回りに入っている */ ;頂点の配列の順番 #enum VEC2_VERT_A_X = 0 #enum VEC2_VERT_A_Y #enum VEC2_VERT_B_X #enum VEC2_VERT_B_Y #enum VEC2_VERT_C_X #enum VEC2_VERT_C_Y ;定数 #const double DOUBLE_HALF 0.5 ;1.0の半分 #const double GRAVITY_INNER_POINT 1.0 / 3.0 ;重心の内分点 ;重心(高速版) #deffunc vec2_triangle_gravity_center array u_result, array u_vert ;u_vertからそれぞれの頂点が入った配列を作成する a.0 = u_vert.VEC2_VERT_A_X ; 頂点AのX a.1 = u_vert.VEC2_VERT_A_Y ; 頂点AのY b.0 = u_vert.VEC2_VERT_B_X ; 頂点BのX b.1 = u_vert.VEC2_VERT_B_Y ; 頂点BのY c.0 = u_vert.VEC2_VERT_C_X ; 頂点CのX c.1 = u_vert.VEC2_VERT_C_Y ; 頂点CのY ;辺の中心点を取得する vec2_mix center_ab, a, b, DOUBLE_HALF ;GRAVITY_INNER_POINTの内分点が重心の中心位置のはず vec2_mix u_result, center_ab, c, GRAVITY_INNER_POINT return ;外心はsinに要約される? ;外心 #deffunc vec2_triangle_circum_center array u_result, array u_vert ;u_vertからそれぞれの頂点が入った配列を作成する a.0 = u_vert.VEC2_VERT_A_X ; 頂点AのX a.1 = u_vert.VEC2_VERT_A_Y ; 頂点AのY b.0 = u_vert.VEC2_VERT_B_X ; 頂点BのX b.1 = u_vert.VEC2_VERT_B_Y ; 頂点BのY c.0 = u_vert.VEC2_VERT_C_X ; 頂点CのX c.1 = u_vert.VEC2_VERT_C_Y ; 頂点CのY vec2_sin sin_a, a : vec2_multiply_value sin_2a, sin_a, 2.0 vec2_sin sin_b, b : vec2_multiply_value sin_2b, sin_b, 2.0 vec2_sin sin_c, c : vec2_multiply_value sin_2c, sin_c, 2.0 vec2_set_value t0, 0.0 vec2_add t0, sin_2a, sin_2b vec2_add t0, t0, sin_2c vec2_set_value t1, 0.0 vec2_add t1, sin_a, sin_b vec2_add t1, t1, sin_c vec2_divide u_result, t1, t0 return ;内心 #deffunc vec2_triangle_inner_center array u_result, array u_vert ;u_vertからそれぞれの頂点が入った配列を作成する a.0 = u_vert.VEC2_VERT_A_X ; 頂点AのX a.1 = u_vert.VEC2_VERT_A_Y ; 頂点AのY b.0 = u_vert.VEC2_VERT_B_X ; 頂点BのX b.1 = u_vert.VEC2_VERT_B_Y ; 頂点BのY c.0 = u_vert.VEC2_VERT_C_X ; 頂点CのX c.1 = u_vert.VEC2_VERT_C_Y ; 頂点CのY ;角度を取得する ab_rad = atan(a(1)-b(1), a(0)-b(0));value bc_rad = atan(b(1)-c(1), b(0)-c(0));value ca_rad = atan(c(1)-a(1), c(0)-a(0));value ;角度のmix a_rad_center = double_mix(ab_rad, ca_rad, DOUBLE_HALF) ;b_rad_center = double_mix(bc_rad, ca_rad, DOUBLE_HALF) ;c_rad_center = double_mix(ca_rad, bc_rad, DOUBLE_HALF) ;ベクトル算出 vec2_subtract ab, b, a vec2_subtract bc, c, b vec2_subtract ca, a, c ;ベクトルのmix vec2_mix a_v_center, ab, ca, DOUBLE_HALF ;vec2_mix b_v_center, bc, ab, DOUBLE_HALF ;vec2_mix c_v_center, ca, bc, DOUBLE_HALF ;d = a_v_center + b_v_center + c_v_center vec2_mix u_result, a, a_v_center, a_rad_center return ;垂心はtanに要約される? ;垂心 #deffunc vec2_triangle_ortho_center array u_result, array u_vert ;u_vertからそれぞれの頂点が入った配列を作成する a.0 = u_vert.VEC2_VERT_A_X ; 頂点AのX a.1 = u_vert.VEC2_VERT_A_Y ; 頂点AのY b.0 = u_vert.VEC2_VERT_B_X ; 頂点BのX b.1 = u_vert.VEC2_VERT_B_Y ; 頂点BのY c.0 = u_vert.VEC2_VERT_C_X ; 頂点CのX c.1 = u_vert.VEC2_VERT_C_Y ; 頂点CのY dialog "未実装" return ;傍心 #deffunc vec2_triangle_neighboring_center array u_result_0, array u_result_1, array u_result_2, array u_vert ;u_vertからそれぞれの頂点が入った配列を作成する a.0 = u_vert.VEC2_VERT_A_X ; 頂点AのX a.1 = u_vert.VEC2_VERT_A_Y ; 頂点AのY b.0 = u_vert.VEC2_VERT_B_X ; 頂点BのX b.1 = u_vert.VEC2_VERT_B_Y ; 頂点BのY c.0 = u_vert.VEC2_VERT_C_X ; 頂点CのX c.1 = u_vert.VEC2_VERT_C_Y ; 頂点CのY dialog "未実装" return #global #endif ;------------------------------------------------------------------------------------ ;ここから上記のモジュールを使用するスクリプト gosub *setup goto *jyuushin *setup w = 512 screen 0, w, w title "五心" button goto "重心", *jyuushin button goto "内心", *naishin button goto "外心", *gaishin button goto "垂心", *suishin button goto "傍心", *boushin return *reset ;三角形の位置をランダムに生成 ddim a, 2 ddim b, 2 ddim c, 2 ddim abc, 6 ddim res, 2 ddim res2, 2 ;傍心用 ddim res3, 2 ;傍心用 randomize a = double(rnd(w)), double(rnd(w)) b = double(rnd(w)), double(rnd(w)) c = double(rnd(w)), double(rnd(w)) abc.0 = a.0, a.1, b.0, b.1, c.0, c.1 return *jyuushin gosub *reset vec2_triangle_gravity_center res, abc ;重心取得(成功?) goto *draw *naishin gosub *reset vec2_triangle_inner_center res, abc ;内心取得(失敗) goto *draw *gaishin gosub *reset vec2_triangle_circum_center res, abc ;外心取得(失敗) goto *draw *boushin gosub *reset ;傍心は3つの答えがあるが、ここではresだけ描画対象とする vec2_triangle_neighboring_center res, res2, res3, abc ;傍心取得(未実装) goto *draw *suishin gosub *reset vec2_triangle_ortho_center res, abc ;垂心取得(未実装) goto *draw ;三角形描写 ;青い線の交わる部分が中心 *draw redraw 0 pos 0,0 color $f0,$f0,$f0 boxf pos 0,0 color 0,0,0 line int(a.0),int(a.1), int(b.0),int(b.1) line int(b.0),int(b.1), int(c.0),int(c.1) line int(c.0),int(c.1), int(a.0),int(a.1) color 0,0,$f0 line int(a.0),int(a.1), int(res.0),int(res.1) line int(b.0),int(b.1), int(res.0),int(res.1) line int(c.0),int(c.1), int(res.0),int(res.1) pos 0,w-18 mes "中心の位置 "+str(res.0)+", "+str(res.1) redraw 1 stop
恐らく、2Dベクトル演算の組み合わせで演算できるのだと思います。
アドバイスお願い致します。