/** * この関数は、引数値からパラメータをインスタンスへコピーします。 * @param i_source * コピー元のオブジェクト */ public void copyFrom(NyARLinear i_source) { this.b = i_source.b; this.a = i_source.a; this.c = i_source.c; return; }
/** * この関数は、指定サイズのオブジェクト配列を作ります。 * @param i_number * 作成する配列の長さ * @return * 新しい配列。 */ public static NyARLinear[] createArray(int i_number) { NyARLinear[] ret = new NyARLinear[i_number]; for (int i = 0; i < i_number; i++) { ret[i] = new NyARLinear(); } return(ret); }
/** * この関数は、指定サイズのオブジェクト配列を作ります。 * @param i_number * 作成する配列の長さ * @return * 新しい配列。 */ public static NyARLinear[] createArray(int i_number) { NyARLinear[] ret = new NyARLinear[i_number]; for (int i = 0; i < i_number; i++) { ret[i] = new NyARLinear(); } return ret; }
/** * この関数は、i_x,i_yを通過する、i_linearの法線を計算して、インスタンスへ格納します。 * @param i_x * 通過点X * @param i_y * 通過点Y * @param i_linear * 法線を計算する直線式(この引数にはthisを指定できます。) */ public void normalLine(double i_x, double i_y, NyARLinear i_linear) { double la = i_linear.a; double lb = i_linear.b; this.a = lb; this.b = -la; this.c = -(lb * i_x - la * i_y); }
/** * この関数は、直線の交点を計算します。 * @param l_line_2 * 交点を計算する直線式 * @param o_point * 交点座標を格納するオブジェクト * @return * 交点が求まればtrue */ public bool crossPos(NyARLinear l_line_2, NyARDoublePoint2d o_point) { double w1 = this.a * l_line_2.b - l_line_2.a * this.b; if (w1 == 0.0) { return(false); } o_point.x = (this.b * l_line_2.c - l_line_2.b * this.c) / w1; o_point.y = (l_line_2.a * this.c - this.a * l_line_2.c) / w1; return(true); }
/** * この関数は、i_x,i_yを通るこの直線の法線と、i_linearが交わる点を返します。 * @param i_x * 法線が通過する点X * @param i_y * 法線が通過する点Y * @param i_linear * 交点を計算する直線式 * @param o_point * 交点を返却するオブジェクト * @return * 交点が求まれば、trueを返します。 */ public bool normalLineCrossPos(double i_x, double i_y, NyARLinear i_linear, NyARDoublePoint2d o_point) { //thisを法線に変換 double la = this.b; double lb = -this.a; double lc = -(la * i_x + lb * i_y); //交点を計算 double w1 = i_linear.a * lb - la * i_linear.b; if (w1 == 0.0) { return(false); } o_point.x = ((i_linear.b * lc - lb * i_linear.c) / w1); o_point.y = ((la * i_linear.c - i_linear.a * lc) / w1); return(true); }
/** * この関数は、i_lineの直線を、インスタンスにセットします。 * {@link #x},{@link #y}の値は、(i_x,i_y)を通過するi_lineの法線とi_lineの交点をセットします。 * @param i_line * セットする直線式 * @param i_x * {@link #x},{@link #y}を確定するための、法線の通過点 * @param i_y * {@link #x},{@link #y}を確定するための、法線の通過点 * @return * セットに成功すると、trueを返します。 */ public bool setLinear(NyARLinear i_line, double i_x, double i_y) { double la = i_line.b; double lb = -i_line.a; double lc = -(la * i_x + lb * i_y); //交点を計算 double w1 = -lb * lb - la * la; if (w1 == 0.0) { return(false); } this.x = ((la * lc - lb * i_line.c) / w1); this.y = ((la * i_line.c + lb * lc) / w1); this.dy = -lb; this.dx = -la; return(true); }
/** * この関数は、2直線に直交するベクトルを計算して、その3次元ベクトルをインスタンスに格納します。 * (多分) * @param i_linear1 * 直線1 * @param i_linear2 * 直線2 */ public void exteriorProductFromLinear(NyARLinear i_linear1, NyARLinear i_linear2) { //1行目 NyARPerspectiveProjectionMatrix cmat = this._projection_mat_ref; double w1 = i_linear1.a * i_linear2.b - i_linear2.a * i_linear1.b; double w2 = i_linear1.b * i_linear2.c - i_linear2.b * i_linear1.c; double w3 = i_linear1.c * i_linear2.a - i_linear2.c * i_linear1.a; double m0 = w1 * (cmat.m01 * cmat.m12 - cmat.m02 * cmat.m11) + w2 * cmat.m11 - w3 * cmat.m01; //w1 * (cpara[0 * 4 + 1] * cpara[1 * 4 + 2] - cpara[0 * 4 + 2] * cpara[1 * 4 + 1]) + w2 * cpara[1 * 4 + 1] - w3 * cpara[0 * 4 + 1]; double m1 = -w1 * cmat.m00 * cmat.m12 + w3 * cmat.m00; //-w1 * cpara[0 * 4 + 0] * cpara[1 * 4 + 2] + w3 * cpara[0 * 4 + 0]; double m2 = w1 * cmat.m00 * cmat.m11; //w1 * cpara[0 * 4 + 0] * cpara[1 * 4 + 1]; double w = Math.Sqrt(m0 * m0 + m1 * m1 + m2 * m2); this.v1 = m0 / w; this.v2 = m1 / w; this.v3 = m2 / w; return; }
/** * この関数は、直線の交点を計算します。 * @param l_line_2 * 交点を計算する直線式 * @param o_point * 交点座標を格納するオブジェクト * @return * 交点が求まればtrue */ public bool crossPos(NyARLinear l_line_2, NyARDoublePoint2d o_point) { double w1 = this.a * l_line_2.b - l_line_2.a * this.b; if (w1 == 0.0) { return false; } o_point.x = (this.b * l_line_2.c - l_line_2.b * this.c) / w1; o_point.y = (l_line_2.a * this.c - this.a * l_line_2.c) / w1; return true; }
/** * この関数は、i_lineの直線を、インスタンスにセットします。 * {@link #x},{@link #y}の値は、(i_x,i_y)を通過するi_lineの法線とi_lineの交点をセットします。 * @param i_line * セットする直線式 * @param i_x * {@link #x},{@link #y}を確定するための、法線の通過点 * @param i_y * {@link #x},{@link #y}を確定するための、法線の通過点 * @return * セットに成功すると、trueを返します。 */ public bool setLinear(NyARLinear i_line, double i_x, double i_y) { double la = i_line.b; double lb = -i_line.a; double lc = -(la * i_x + lb * i_y); //交点を計算 double w1 = -lb * lb - la * la; if (w1 == 0.0) { return false; } this.x = ((la * lc - lb * i_line.c) / w1); this.y = ((la * i_line.c + lb * lc) / w1); this.dy = -lb; this.dx = -la; return true; }
//override public override sealed bool initRotBySquare(NyARLinear[] i_linear, NyARDoublePoint2d[] i_sqvertex) { bool ret = base.initRotBySquare(i_linear, i_sqvertex); if (ret) { //Matrixからangleをロード this.updateAngleFromMatrix(); } return ret; }
/** * 予想位置を基準に四角形をトレースして、一定の基準をクリアするかを評価します。 * @param i_reader * @param i_edge_size * @param i_prevsq * @return * @throws NyARException */ private bool traceSquareLine(INyARVectorReader i_reader, int i_edge_size, NyARRectTargetStatus i_prevsq, NyARLinear[] o_line) { NyARDoublePoint2d p1,p2; VecLinearCoordinates vecpos=this._ref_my_pool._vecpos; //NyARIntRect i_rect p1=i_prevsq.estimate_vertex[0]; int dist_limit=i_edge_size*i_edge_size; //強度敷居値(セルサイズ-1) // int min_th=i_edge_size*2+1; // min_th=(min_th*min_th); for(int i=0;i<4;i++) { p2=i_prevsq.estimate_vertex[(i+1)%4]; //クリップ付きで予想位置周辺の直線のトレース i_reader.traceLineWithClip(p1,p2,i_edge_size,vecpos); //クラスタリングして、傾きの近いベクトルを探す。(限界は10度) this._ref_my_pool._vecpos_op.MargeResembleCoords(vecpos); //基本的には1番でかいベクトルだよね。だって、直線状に取るんだもの。 int vid=vecpos.getMaxCoordIndex(); //データ品質規制(強度が多少強くないと。) // if(vecpos.items[vid].sq_dist<(min_th)){ // return false; // } //@todo:パラメタ調整 //角度規制(元の線分との角度を確認) if(vecpos.items[vid].getAbsVecCos(i_prevsq.vertex[i],i_prevsq.vertex[(i+1)%4])<NyARMath.COS_DEG_5){ //System.out.println("CODE1"); return false; } //@todo:パラメタ調整 //予想点からさほど外れていない点であるか。(検出点の移動距離を計算する。) double dist; dist=vecpos.items[vid].sqDistBySegmentLineEdge(i_prevsq.vertex[i],i_prevsq.vertex[i]); if(dist<dist_limit){ o_line[i].setVectorWithNormalize(vecpos.items[vid]); }else{ //System.out.println("CODE2:"+dist+","+dist_limit); return false; } //頂点ポインタの移動 p1=p2; } return true; }
/** * この関数は、i_x,i_yを通るこの直線の法線と、i_linearが交わる点を返します。 * @param i_x * 法線が通過する点X * @param i_y * 法線が通過する点Y * @param i_linear * 交点を計算する直線式 * @param o_point * 交点を返却するオブジェクト * @return * 交点が求まれば、trueを返します。 */ public bool normalLineCrossPos(double i_x, double i_y, NyARLinear i_linear, NyARDoublePoint2d o_point) { //thisを法線に変換 double la = this.b; double lb = -this.a; double lc = -(la * i_x + lb * i_y); //交点を計算 double w1 = i_linear.a * lb - la * i_linear.b; if (w1 == 0.0) { return false; } o_point.x = ((i_linear.b * lc - lb * i_linear.c) / w1); o_point.y = ((la * i_linear.c - i_linear.a * lc) / w1); return true; }
/** * この関数は、2直線に直交するベクトルを計算して、その3次元ベクトルをインスタンスに格納します。 * (多分) * @param i_linear1 * 直線1 * @param i_linear2 * 直線2 */ public void exteriorProductFromLinear(NyARLinear i_linear1, NyARLinear i_linear2) { //1行目 NyARPerspectiveProjectionMatrix cmat = this._projection_mat_ref; double w1 = i_linear1.a * i_linear2.b - i_linear2.a * i_linear1.b; double w2 = i_linear1.b * i_linear2.c - i_linear2.b * i_linear1.c; double w3 = i_linear1.c * i_linear2.a - i_linear2.c * i_linear1.a; double m0 = w1 * (cmat.m01 * cmat.m12 - cmat.m02 * cmat.m11) + w2 * cmat.m11 - w3 * cmat.m01;//w1 * (cpara[0 * 4 + 1] * cpara[1 * 4 + 2] - cpara[0 * 4 + 2] * cpara[1 * 4 + 1]) + w2 * cpara[1 * 4 + 1] - w3 * cpara[0 * 4 + 1]; double m1 = -w1 * cmat.m00 * cmat.m12 + w3 * cmat.m00;//-w1 * cpara[0 * 4 + 0] * cpara[1 * 4 + 2] + w3 * cpara[0 * 4 + 0]; double m2 = w1 * cmat.m00 * cmat.m11;//w1 * cpara[0 * 4 + 0] * cpara[1 * 4 + 1]; double w = Math.Sqrt(m0 * m0 + m1 * m1 + m2 * m2); this.v1 = m0 / w; this.v2 = m1 / w; this.v3 = m2 / w; return; }
/** * この関数は、2次元座標系の矩形を表す直線式と、3次元座標系の矩形のオフセット座標値から、回転行列を計算します。 * <p>メモ - * Cで実装するときは、配列のポインタ版関数と2重化すること * </p> * @param i_linear * 直線式。4要素である必要があります。 * @param i_sqvertex * 矩形の3次元オフセット座標。4要素である必要があります。 * @ */ public virtual bool initRotBySquare(NyARLinear[] i_linear, NyARDoublePoint2d[] i_sqvertex) { NyARRotVectorV2 vec1 = this.__initRot_vec1; NyARRotVectorV2 vec2 = this.__initRot_vec2; //向かい合った辺から、2本のベクトルを計算 //軸1 vec1.exteriorProductFromLinear(i_linear[0], i_linear[2]); if (!vec1.checkVectorByVertex(i_sqvertex[0], i_sqvertex[1])) { return false; } //軸2 vec2.exteriorProductFromLinear(i_linear[1], i_linear[3]); if (!vec2.checkVectorByVertex(i_sqvertex[3], i_sqvertex[0])) { return false; } //回転の最適化? if (!NyARRotVectorV2.checkRotation(vec1, vec2)) { return false; } this.m00 = vec1.v1; this.m10 = vec1.v2; this.m20 = vec1.v3; this.m01 = vec2.v1; this.m11 = vec2.v2; this.m21 = vec2.v3; //最後の軸を計算 double w02 = vec1.v2 * vec2.v3 - vec1.v3 * vec2.v2; double w12 = vec1.v3 * vec2.v1 - vec1.v1 * vec2.v3; double w22 = vec1.v1 * vec2.v2 - vec1.v2 * vec2.v1; double w = Math.Sqrt(w02 * w02 + w12 * w12 + w22 * w22); this.m02 = w02 / w; this.m12 = w12 / w; this.m22 = w22 / w; return true; }
/** * この関数は、2直線が交差しているかを返します。 * @param l_line_2 * 交差しているか確認するオブジェクト * @return * 交差していればtrue */ public bool isCross(NyARLinear l_line_2) { double w1 = this.a * l_line_2.b - l_line_2.a * this.b; return (w1 == 0.0) ? false : true; }
/** * この関数は、2直線が交差しているかを返します。 * @param l_line_2 * 交差しているか確認するオブジェクト * @return * 交差していればtrue */ public bool isCross(NyARLinear l_line_2) { double w1 = this.a * l_line_2.b - l_line_2.a * this.b; return((w1 == 0.0) ? false : true); }