|
前頁は、矢印について考えてみました。今回は、SXF仕様書の次の構造化要素の「直線寸法」について考えてみます。
一般的に、CADで寸法線を作図する前には様々な寸法設定を行います。寸法補助線(寸法引出し線)は図形とどれくらい離すのか、寸法線の上にどれくらいはみ出す(突出する)のか、矢印は内向きなのか外向きなのか、寸法値は寸法線からどれくらい離すのか、等々。そういった設定をした上で、寸法線を作図しますので、CADソフトによっては、寸法設定データの登録と寸法線データの登録を双方とも行い、寸法線データにどの寸法設定を使ったのかを示すコードをデータ項目として所持させているものもあるでしょうし、寸法設定データは図面データに登録せず、寸法線データのみ登録するものもあるでしょう。その場合、寸法設定データは別の設定ファイルとして保存・呼び出しをする、という状態でしょうか。
SXF仕様には、寸法設定データというものは見当たりません。基本的に、生データさえ受け渡しが出来れば良い、というスタンスかもしれませんし、寸法設定というのはCADソフトによって種々様々ですからそこまで考慮する必要もない・CAD依存で構わない、という事かもしれません。
また、寸法線の場合、対象とする図形の寸法が変わった場合、それに連動して寸法線も変形され、寸法値もそれに応じて変化する、という機能が求められます。その場合、どの図形を示しているのか?という事を示すデータ項目を追加する場合もあるかもしれませんし、寸法線の形状が変化すればそれに従えばいいので図形を示すデータ項目は必要無いという場合もあるかもしれません。尤も、この場合、半径寸法等に対応出来るのかどうかは不明ですが…。
更に、CADによっては、寸法線の寸法値を指定し、新たな寸法値を入力して、それに伴い寸法線が変形され、その寸法線が示す図形もそれに応じて変形される、という機能を持つものもあります。この場合も、図形を示すデータ項目を、という場合もあれば、変形させたい図形を選択しておけばいい、という場合もあります。この場合、前者のパターンだと、線1本だけが変形されても余り意味はないので、その他の図形をどう扱うのかという別の問題も出てきます。所謂パラメトリック機能ですが、この場合は、データ同士の関連性を考えないといけないため、それなりの仕組みが必要になってきます。
・・・などと考えていくと中々キリがありません。
ここは単純に、SXF仕様のようにまずデータとして実装してしまおう、とだけ考えておきます。後で追加が必要になれば、そのときに追加すればいいでしょう、と割り切っておきます。
SXF仕様書では以下のように記載されています。
構造化要素|直線寸法 |
※SXF Ver.3.1仕様書より |
パラメータ | 型 | 説明 | 範囲 |
Layer | Int | レイヤコード |
|
Color | Int | 色コード |
|
Type | Int | 線種コード |
|
line_width | Int | 線幅コード |
|
sun_x1 | double | 寸法線始点X座標 |
double(64bits)の
範囲(有効桁15桁) |
sun_y1 | double | 寸法線始点Y座標 |
double(64bits)の
範囲(有効桁15桁) |
sun_x2 | double | 寸法線終点X座標 |
double(64bits)の
範囲(有効桁15桁) |
sun_y2 | double | 寸法線終点Y座標 |
double(64bits)の
範囲(有効桁15桁) |
flg2 | Int | 補助線1の有無フラグ(0:無、1:有) |
|
ho1_x0 | double | 補助線1基点X座標 |
double(64bits)の
範囲(有効桁15桁) |
ho1_y0 | double | 補助線1基点Y座標 |
double(64bits)の
範囲(有効桁15桁) |
ho1_x1 | double | 補助線1始点X座標 |
double(64bits)の
範囲(有効桁15桁) |
ho1_y1 | double | 補助線1始点Y座標 |
double(64bits)の
範囲(有効桁15桁) |
ho1_x2 | double | 補助線1終点X座標 |
double(64bits)の
範囲(有効桁15桁) |
ho1_y2 | double | 補助線1終点Y座標 |
double(64bits)の
範囲(有効桁15桁) |
flg3 | Int | 補助線2の有無フラグ(0:無、1:有) |
|
ho2_x0 | double | 補助線2基点X座標 |
double(64bits)の
範囲(有効桁15桁) |
ho2_y0 | double | 補助線2基点Y座標 |
double(64bits)の
範囲(有効桁15桁) |
ho2_x1 | double | 補助線2始点X座標 |
double(64bits)の
範囲(有効桁15桁) |
ho2_y1 | double | 補助線2始点Y座標 |
double(64bits)の
範囲(有効桁15桁) |
ho2_x2 | double | 補助線2終点X座標 |
double(64bits)の
範囲(有効桁15桁) |
ho2_y2 | double | 補助線2終点Y座標 |
double(64bits)の
範囲(有効桁15桁) |
arr1_code1 | Int | 始点側矢印コード |
|
arr1_code2 | Int | 始点側矢印内外コード(0:なし,1:外向き,2:内向き) |
|
arr1_x | double | 始点側矢印配置点X座標 |
double(64bits)の
範囲(有効桁15桁) |
arr1_y | double | 始点側矢印配置点Y座標 |
double(64bits)の
範囲(有効桁15桁) |
arr1_r | double | 始点側矢印配置倍率 | 0<倍率<1.0×1015 |
arr2_code1 | Int | 終点側矢印コード |
|
arr2_code2 | Int | 終点側矢印内外コード(0:なし,1:外向き,2:内向き) |
|
arr2_x | double | 終点側矢印配置点X座標 |
double(64bits)の
範囲(有効桁15桁) |
arr2_y | double | 終点側矢印配置点Y座標 |
double(64bits)の
範囲(有効桁15桁) |
arr2_r | double | 終点側矢印配置倍率 | 0<倍率<1.0×1015 |
flg4 | Int | 寸法値の有無フラグ(0:無、1:有) |
|
Font | Int | 文字フォントコード |
|
str[257] | Char | 文字列 | 0<文字列長≦256バイト |
text_x | double | 文字列配置基点X座標 |
double(64bits)の
範囲(有効桁15桁) |
text_y | double | 文字列配置基点Y座標 |
double(64bits)の
範囲(有効桁15桁) |
Height | double | 文字範囲高 | 0<高さ<1.0×1015 |
Width | double | 文字範囲幅 | 0< 幅 <1.0×1015 |
Spc | double | 文字間隔 | 0≦間隔<1.0×1015 |
Angle | double | 文字列回転角 | 0≦ 度 <360 |
Slant | double | スラント角度 | -85≦ 度 ≦85 |
b_pnt | Int | 文字配置基点(1:左下,2:中下,3:右下,4:左中,5:中中,6:右中,7:左上,8:中上,9:右上) |
|
Direct | Int | 文字書出し方向(1:横書き, 2:縦書き) |
|
備考
・矢印コードは、1: blanked arrow, 2: blanked box, 3: blanked dot, 4: dimension origin, 5: filled box, 6: filled arrow, 7: filled dot, 8: integral symbol, 9: open arrow, 10: slash, 11: unfilled arrowから選ぶ。矢印の形状は【補足】を参照のこと。
・矢印の大きさは、用紙座標系で解釈する。
・補助線の基点、始点、終点は一直線上に存在しなければならない。
・補助線1ギャップは、補助線1始点座標と補助線1基準点座標の間の距離である。
・補助線2ギャップは、補助線2始点座標と補助線2基準点座標の間の距離である。
・補助線は、補助線上高も含めて1本の直線で表すため、補助線上高を指定する必要がない。
・角度は水平右側が0度、反時計廻りが正、単位は度とする。
・個別に、寸法線(狭義)、補助線、文字、矢印の色、線幅、線種を設定することはできない。 |
※SXF Ver.3.1仕様書より
なぜフラグが flg2・flg3・flg4と、1からではなく 2からなのか、よく分かりませんが、まぁこのまま利用する事にします。データ構造についてですが、
UnitData.pas |
type
・・・
TDataDimLine = record // 構造化要素|直線寸法
exf : Boolean ; // 存在フラグ(True:有り False:無し)
Layer : Integer ; // レイヤ(1〜256)
sun : TDataLine ;
ho1 : TDataLine ;
ho2 : TDataLine ;
・・・ |
のように記述したほうが見た目にも簡単なのですが、余分なデータが増えますし、メンバ変数もパラメータの名前と変わってしまいますので、ここでは敢えてベタにそのまま記述する事にします。
CADソフトによっては、寸法線・寸法補助線・寸法値の色をそれぞれ別々に指定出来るものがありますし、それと同様にしたい場合には、上記のようなデータ構造にする必要がありますが、SXFネイティブとならなくなりますし、寸法設定の項目もその分増えるでしょう。どちらが良いか、ではなく、どちらにしたいのか?で決めればよいと思います。私自身は、色をそれぞれ別個に指定する必要性は無いと思いますので、SXF風にする事とします。
UnitData.pas |
type
・・・
TDataDimLine = record // 構造化要素|直線寸法
exf : Boolean ; // 存在フラグ(True:有り False:無し)
Layer : Integer ; // レイヤ(1〜256)
Color : Integer ; // 色 (0:レイヤ色 1〜256)
Ltype : Integer ; // 線種 (0:レイヤ線種 1〜32)
line_width: Integer ; // 線幅 (0:レイヤ線幅 1〜16)
sun_x1 : double ; // 寸法線始点X座標
sun_y1 : double ; // 寸法線始点Y座標
sun_x2 : double ; // 寸法線終点X座標
sun_y2 : double ; // 寸法線終点Y座標
flg2 : integer ; // 補助線1の有無フラグ(0:無、1:有)
ho1_x0 : double ; // 補助線1基点X座標
ho1_y0 : double ; // 補助線1基点Y座標
ho1_x1 : double ; // 補助線1始点X座標
ho1_y1 : double ; // 補助線1始点Y座標
ho1_x2 : double ; // 補助線1終点X座標
ho1_y2 : double ; // 補助線1終点Y座標
flg3 : integer ; // 補助線2の有無フラグ(0:無、1:有)
ho2_x0 : double ; // 補助線2基点X座標
ho2_y0 : double ; // 補助線2基点Y座標
ho2_x1 : double ; // 補助線2始点X座標
ho2_y1 : double ; // 補助線2始点Y座標
ho2_x2 : double ; // 補助線2終点X座標
ho2_y2 : double ; // 補助線2終点Y座標
arr1_code1 : integer ; // 始点側矢印コード(1-11)
arr1_code2 : integer ; // 始点側矢印内外コード
arr1_x : double ; // 始点側矢印配置点X座標
arr1_y : double ; // 始点側矢印配置点Y座標
arr1_r : double ; // 始点側矢印配置倍率
arr2_code1 : integer ; // 終点側矢印コード(1-11)
arr2_code2 : integer ; // 終点側矢印内外コード
arr2_x : double ; // 終点側矢印配置点X座標
arr2_y : double ; // 終点側矢印配置点Y座標
arr2_r : double ; // 終点側矢印配置倍率
flg4 : integer ; // 寸法値の有無フラグ(0:無、1:有)
Font : Integer ; // 文字フォントコード
str : string ; // 文字列 (最大256バイト)
text_x : double ; // 文字列配置基点X座標
text_y : double ; // 文字列配置基点Y座標
Height : double ; // 文字範囲高
Width : double ; // 文字範囲幅
Spc : double ; // 文字間隔
Angle : double ; // 文字列回転角[°]
Slant : double ; // スラント角[°]
b_pnt : Integer ; // 文字配置基点 (1-9)
Direct : Integer ; // 文字書出し方向(1,2)
end;
・・・ |
データ追加用の関数は、少し長いですが
function AddDataDimLine(s,st:string;lay,col,ltp,wid,
f2,f3,f4,ar11,ar12,ar21,ar22,fnt,bp,dir:integer;
sx1,sy1,sx2,sy2, h1x0,h1y0,h1x1,h1y1,h1x2,h1y2,
h2x0,h2y0,h2x1,h2y1,h2x2,h2y2, ar1x,ar1y,ar1r, ar2x,ar2y,ar2r,
tx,ty,th,tw,ts,an,sl:double) : Boolean ; |
のようにします。線分・折線等と同様、最初に「データ追加先の複合図形名/シンボル名 null:用紙へ追加」を指定するようにしています。
UnitData.pas |
// 直線寸法 データ項目の追加登録
function TDataClass.AddDataDimLine(s,st:string;lay,col,ltp,wid,f2,f3,f4,
ar11,ar12,ar21,ar22,fnt,bp,dir:integer;
sx1,sy1,sx2,sy2, h1x0,h1y0,h1x1,h1y1,h1x2,h1y2,
h2x0,h2y0,h2x1,h2y1,h2x2,h2y2, ar1x,ar1y,ar1r, ar2x,ar2y,ar2r,
tx,ty,th,tw,ts,an,sl:double) : Boolean ;
var
m : integer ;
a1,a2,w1,w2 : double ;
begin
Result := False;
if (st = '') then
f4 := 0
else
if not(StrCheck(st)) then exit; // 文字列数チェック
if (lay < 1) or (lay > zLayN) then lay := 1 ;
if (col < 0) or (col > zColN) then col := 0 ;
if (ltp < 0) or (ltp > zLtpN) then ltp := 0 ;
if (wid < 0) or (wid > zWidN) then wid := 0 ;
if (f2 <> 0) then f2 := 1;
if (f3 <> 0) then f3 := 1;
if (f4 <> 0) then f4 := 1;
if (ar11 < 1)or(ar11 > 11) then ar11 := 9;
if (ar21 < 1)or(ar21 > 11) then ar21 := 9;
if (ar12 < 0)or(ar12 > 2) then ar12 := 2;
if (ar22 < 0)or(ar22 > 2) then ar22 := 2;
if (ar1r < LIMIT8) then ar1r := 1.0;
if (ar2r < LIMIT8) then ar2r := 1.0;
if (f4 = 1)and( (th < LIMIT10)or(tw < LIMIT10) ) then exit ;
if (fnt < 0) or (fnt > zFntN) then fnt := 0 ;
if (bp < 1) or (bp > 9) then bp := 2 ; // 中下
if (dir <> 1) then dir := 2 ;
if (ts < 0.0) then ts := 0.0;
an := SetAngle(an);
if (sl < -85.0) or (sl > 85.0) then sl := 0.0;
// 座標チェック
if (SamePosCheck(sx1,sy1, sx2,sy2)) then exit ;
if (SamePosCheck(h1x1,h1y1, h1x2,h1y2)) then f2 := 0 ;
if (SamePosCheck(h2x1,h2y1, h2x2,h2y2)) then f3 := 0 ;
// 補助線の1直線上チェック
if (f2 = 1) then begin
a1 := dAngle((h1x1-h1x0),(h1y1-h1y0));
a2 := dAngle((h1x2-h1x0),(h1y2-h1y0));
a2 := SetAngle(a1-a2) ;
if (Abs(a2) > LIMIT10) then begin
dRev(w1,w2, h1x2,h1y2, h1x0,h1y0, -a1);
if (Abs(w1-h1x0) < LIMIT10) then
f2 := 0
else
dRev(h1x2,h1y2, w1,h1y0, h1x0,h1y0, a1);
end;
end;
if (f3 = 1) then begin
a1 := dAngle((h2x1-h2x0),(h2y1-h2y0));
a2 := dAngle((h2x2-h2x0),(h2y2-h2y0));
a2 := SetAngle(a1-a2) ;
if (Abs(a2) > LIMIT10) then begin
dRev(w1,w2, h2x2,h2y2, h2x0,h2y0, -a1);
if (Abs(w1-h2x0) < LIMIT10) then
f3 := 0
else
dRev(h2x2,h2y2, w1,h2y0, h2x0,h2y0, a1);
end;
end;
//
if (s = '') then begin
// 用紙へ追加
・・・ |
これで直線寸法データの登録は出来るようになりましたので次は描画についてです。これは単純に、線分3つ・矢印2つ・文字1つ描画するだけですので別段問題は無いでしょう。
UnitDataGraph.pas |
// 直線寸法の表示
procedure DisplayDimLine(lay,col,ltp,wid,f2,f3,f4,
ar11,ar12,ar21,ar22,fnt,bp,dir:integer;sx1,sy1,sx2,sy2,
h1x0,h1y0,h1x1,h1y1,h1x2,h1y2, h2x0,h2y0,h2x1,h2y1,h2x2,h2y2,
ar1x,ar1y,ar1r, ar2x,ar2y,ar2r,
tx,ty,th,tw,ts,an,sl:double;st:string;t:TMatrix);
var
lx1,ly1,lx2,ly2,lx3,ly3, a,aa : double ;
begin
a := dAngle((sx2-sx1),(sy2-sy1));
// 寸法線
MtxXY(lx1,ly1, sx1,sy1, t);
MtxXY(lx2,ly2, sx2,sy2, t);
DisplayLine(lay,col,ltp,wid, lx1,ly1,lx2,ly2);
// 補助線1
if (f2 = 1) then begin
MtxXY(lx1,ly1, h1x1,h1y1, t);
MtxXY(lx2,ly2, h1x2,h1y2, t);
DisplayLine(lay,col,ltp,wid, lx1,ly1,lx2,ly2);
end;
// 補助線2
if (f3 = 1) then begin
MtxXY(lx1,ly1, h2x1,h2y1, t);
MtxXY(lx2,ly2, h2x2,h2y2, t);
DisplayLine(lay,col,ltp,wid, lx1,ly1,lx2,ly2);
end;
// 矢印1
if (ar12 = 2) then
aa := a/180.0*Pi
else
aa := (a+180.0)/180.0*Pi ;
if (ar12 > 0) then begin
MtxXY(lx1,ly1, ar1x,ar1y, t);
lx2 := ar1x + 10.0*Cos(aa);
ly2 := ar1y + 10.0*Sin(aa);
MtxXY(lx3,ly3, lx2,ly2, t);
aa := Angle(lx3-lx1,ly3-ly1);
DisplayArrow(lay,col,ar11,lx1,ly1,aa,ar1r);
end;
// 矢印2
if (ar22 = 2) then
aa := (a+180.0)/180.0*Pi
else
aa := a/180.0*Pi ;
if (ar22 > 0) then begin
MtxXY(lx1,ly1, ar2x,ar2y, t);
lx2 := ar2x + 10.0*Cos(aa);
ly2 := ar2y + 10.0*Sin(aa);
MtxXY(lx3,ly3, lx2,ly2, t);
aa := Angle(lx3-lx1,ly3-ly1);
DisplayArrow(lay,col,ar21,lx1,ly1,aa,ar2r);
end;
// 寸法値
if (f4 = 1) then begin
DisplayText(lay,col,fnt,bp,dir, tx,ty,th,tw,ts,an,sl,st,t);
end;
end; |
それでは、ここまでのテストプログラムです。実行ファイル、gdiplus.dll、gdipフォルダは入っていません。ソースのみです。
|
|
CAD装置(1)
CAD装置(2)
メディア
AutoCADの
DIESELマクロ
CSV
DXF
PCES
IGES
STEP
数学とCAD
CAD作ろ!
CADを考える
▲PREV
▼NEXT
M7
Jw_cad
|