Curl® 言語でアプレットを作成する場合、Curl® GUI Toolkit のレイアウト システムによってページ レイアウト処理が実行されます。つまり、グラフィカル オブジェクトがレイアウトに合わせて自動的に整列、伸長、および圧縮されます。なお、ユーザー アプリケーションのニーズに合わせてレイアウトを微調整することもできます。
レイアウトにおいて、幅と高さをピクセル(px)単位で指定することには潜在的に問題があります。コンピューター システム上での文字のフォント サイズは、通常ポイント(pt)で指定されます。1ポイントは、72分の1インチと定義されます。1ピクセルは、スクリーンの解像度の単位です。実際のピクセルのサイズは、モニタの物理特性とマシンの設定に依存します。96dpi(ドット パー インチ)の解像度のスクリーン上でレイアウトを作成し、10ptのフォントを使用してテキスト オブジェクトを作成すると仮定してください。テキストを含むのに充分大きくする為に、ピクセル単位を使ってテキスト ボックスの幅と高さを設定します。そして、ユーザーがそのアプレットを解像度が120dpiのスクリーンで実行すると考えてください。その様なスクリーンでは、1ピクセルは、1ポイントよりも小さいので、ユーザーは、ボックスは小さすぎて文字を納めることが出来ず、幾つかの文字がクリップされていることに気がつきます。
Curl 言語は、ネストしたグラフィカル コンテナを使ってオブジェクトを配置します。
グラフィカル コンテナの章は、ネストしたグラフィック階層を作成することが出来るコンテナを説明しています。Curlは、
HBox や
VBox や
Tableなどのようなコンテナを使用し、Curl レイアウト システムにコンテナ オブジェクトのサイズをそのコンテンツに基づいて計算させるようにすることをお勧めします。この方法で作成されたアプレットは、異なる設定のマシンで実行された時により正確に表示することが出来ます。
この章では、グラフィカル オブジェクトを整列、伸長、圧縮するための基本的な手法について説明します。この章は次のセクションに分かれています。
グラフィカル オブジェクトの整列は、次の 2 つの観点から考えることができます。
以下のセクションでは、この両方の観点による例を示します。
各グラフィカル オブジェクトの境界は、その起点を基準にして定義されます。この起点を内側起点と呼びます。内側起点は通常、そのオブジェクトの幾何学上の中心、またはそのオブジェクトの四隅のいずれか (例:左上隅、左下隅) に配置されます。
ネストされたオブジェクトのグラフィック階層の内部において、各グラフィカル コンテナは固有の方法でその子を順序付け、また、それぞれの子の外側起点を使います。グラフィカル オブジェクトの外側起点の位置は移動可能です。つまり、外側起点はグラフィカル オブジェクトの定義の中で設定されるものではありません。なお、外側起点の既定値はそのグラフィカル オブジェクトの内側起点です。
たとえば、
HBox はその子オブジェクトを左から順に水平方向に配置します。これにより、それらの子オブジェクトの外側起点の垂直コンポーネントが整列されます。この例から、
RectangleGraphic、
TextFlowBox、および
Fill の起点はそれぞれ左下、テキストのベース ライン、および中心になると推測できます。これは、左下、テキストのベース ライン、および中心は、それぞれの外側起点の既定値であるからです。
オブジェクトを整列し直すための最も簡単な方法は、オブジェクトの外側起点をより適切な値に設定することです。オブジェクトの外側起点をより適切な値に設定するには、各グラフィカル オブジェクトの vorigin オプションを設定します。vorigin は、グラフィカル オブジェクトの垂直コンポーネントを示すオプションです。
次の例では、オプション指定の行をコメント アウトするだけで結果を確認できます。
例:
vorigin の設定 |
|
{HBox
border-width=3pt,
border-color="green",
{RectangleGraphic
||vorigin="center",
width=1cm,
height=1cm
},
{TextFlowBox
||vorigin="center",
border-width=1pt,
border-color="black",
"Quick Kangaroo"
},
{Fill
||vorigin="center",
background="purple",
width=2cm,
height=1.2cm}
}
| |
オブジェクトを整列するもう一つの方法は、親の側からオブジェクトを扱うことです。グラフィカル コンテナの種類によって、
halign や
valign を使って親の側から整列を実行する方法が異なります。これらのオプションを使う場合、子の起点は無視されます。
グラフィカル コンテナの種類は次のとおりです。
次の例は、valign オプションを "top" に設定して子の上境界を揃える HBox を示しています。このオプションを使う場合、子の外側起点の値は使われません。そのため、それぞれの子の外側起点がどこに配置されているかは重要ではありません。
例:
valign の設定 |
|
{HBox
|| set the parent's alignment option
valign="top",
border-width=3pt,
border-color="green",
{RectangleGraphic
width=1cm,
height=1cm
},
{TextFlowBox
border-width=1pt,
border-color="black",
"Quick Kangaroo"
},
{Fill
background="purple",
width=2cm,
height=1.2cm}
}
| |
アプレットを作成する際、一般にネストされたグラフィカル オブジェクトを使います。ほとんどの場合、GUI Toolkit では適切なレイアウト処理が自動実行されます。つまり、グラフィカル オブジェクトはその親オブジェクトおよび兄弟オブジェクトを基準にして、適切に伸長または圧縮されます。伸長や圧縮が適切でない場合、子オブジェクトが切り詰められ、スクロールバーが表示されることがあります。TextFlowBox の場合は、テキストが自動改行されます。
一方、既定の動作を使わずに、オブジェクトの幅と高さの動作を指定したい場合もあります。その場合、次のセクションで説明するエラスティックの基本原則について理解しておくとよいでしょう。
グラフィカル オブジェクトの幅と高さをあらかじめ設定された距離と見なすこともできますが (例:
8pt、
1in) グラフィカル オブジェクトの幅と高さの基本となっているのは
Elastic です。エラスティックの存在は、ほとんどの場合ユーザーからは見えません。
レイアウト処理の中にレイアウト ネゴシエーションという段階があります。この段階では、グラフィック階層の最上位から各グラフィカル オブジェクトのサイズ設定が検査されます (通常は、最初に幅設定が検査されます)。このサイズ設定がそのグラフィカル オブジェクトの親に渡されます。
グラフィカル オブジェクトの
width オプションおよび
height オプションは、そのグラフィカル オブジェクトの幅設定と高さ設定の一つの側面を表しています。技術的に見ると、これらのオプションは
Dimension 型ですが、実際にはさまざまなデータ型を利用できます。これらのデータ型は、内部的に
Dimension オブジェクトに変換されます。
Dimension は内部的には
Elastic、より具体的に言えば
OriginElastic として解釈されます。
したがって、エラスティックはあるグラフィカル オブジェクトの親コンテナ、兄弟オブジェクト、子オブジェクトを基準にしてそのグラフィカル オブジェクトの動作を定義します。
この複雑な流れを単純化するため、レイアウト ネゴシエーションの結果、各オブジェクトにはあるサイズが割り当てられます。このサイズは、そのオブジェクトの設定と一致していない場合もあります。この設定は、エラスティックのフォームの中で記述します。
エラスティックは次の 6 個のパラメータによって制御されます。
エラスティック パラメータについて検討する場面としては、次のようなケースが考えられます。
- 子の preferred-size が親のレイアウト サイズよりも小さいために、子が伸長される。
- 子の preferred-size が親のレイアウト サイズよりも大きく、子の compress-order が高いため、子が (親によって) 圧縮される。
- 次のケースにおいて、サイズの大きい親の中にある子 X が子 Y よりも伸長する。
- 子 X と子 Y の伸長単位が同じであり、かつ、子 X の stretch-order が子 Y の stretch-order よりも大きい場合。
- 子 X の stretch-order が子 Y よりも大きい場合。
グラフィカル オブジェクトの幅オプションを Distance (例:3in) に設定した場合、結果的に、変更不能なエラスティック (preferred-size = 3 インチ) を指定したことになります。 stretch-order と compress order の値はきわめて低くなります。
以下のセクションでは、例を使ってstretch-orderと stretchness について説明します。同様に、 compress order と compressibility についても説明します。それぞれの例では、
make-elastic を呼び出して
Elastic オブジェクトを作成します。また、上述のパラメータを引数として指定します。
この章では、「エラスティック」という用語を使ってグラフィカル オブジェクトの幅と高さの設定を表していますが、これらの設定は
OriginElastic として実装されます。
OriginElastic は、2 つの
Elastic コンポーネントで構成されており、この 2 つのコンポーネントはグラフィカル オブジェクトの内側起点によって区切られています。
グラフィカル オブジェクトの幅設定における 1 つ目のコンポーネントは左エラスティック、2 つ目のコンポーネントは右エラスティックです。同様に、グラフィカル オブジェクトの高さ設定における 1 つ目のコンポーネントは内側起点の上側のエラスティック、2 つ目のコンポーネントは内側起点の下側のエラスティックです。
前述のとおり、グラフィカル オブジェクトの内側起点は通常、四隅のいずれかまたは幾何学上の中心に配置されます。内側起点が四隅のいずれかにある場合、いずれかのコンポーネントが 0 であることを意味します。このオプションに設定されたエラスティック パラメータは、1 つのコンポーネントにのみ適用されます (幅と高さ)。このケース (多くのグラフィカル オブジェクトに適用されます) において、幅が伸長可能な場合、このグラフィカル オブジェクトの幅はその内側起点の一方の側に向けて伸長されます。
グラフィカル オブジェクトの内側起点が四隅のいずれにも配置されていない場合、1 つ目と 2 つ目のコンポーネントのエラスティックを指定することにより、そのグラフィカル オブジェクトを内側起点の各側に不均等に伸長/圧縮することができます。
次の例は、子グラフィカル オブジェクトを 2 つ含む
HBox です。それぞれのグラフィカル オブジェクトの幅は、
make-elastic を明示的に呼び出すことによって指定されています。次の点に着目してください。
- HBox の 2 つの子オブジェクトの stretch-order は異なっています。
- 2 つの子オブジェクトの stretchness は同じですが、両者の stretch-order が異なるので stretchness は考慮されません。結果的に、CheckButton が伸長され、CommandButton はその下に隠れます。
例:
stretch-order の違い |
|
{value
{HBox
width={make-elastic
preferred-size=10cm},
{CommandButton
width={make-elastic
stretch-order=30,
stretchiness=100
}
},
{CheckButton
background="lime",
width={make-elastic
stretch-order=40,
stretchiness=400
}
}
}
}
| |
次の例は、子グラフィカル オブジェクトを 2 つ含む
HBox です。それぞれのグラフィカル オブジェクトの幅は、
make-elastic を明示的に呼び出すことによって指定されています。次の点に着目してください。
- HBox の 2 つの子オブジェクトの stretch-order は同じです。したがって、両者の stretchness によって、各オブジェクトが HBox に占める割合が決まります。
- 左ボタンの stretchness は 100、右ボタンの stretchness は 400 なので、左ボタンは伸長可能な幅の 20% を占めることになります。
例:
エラスティックに対する幅の明示的な設定 |
|
{value
{HBox
width={make-elastic
preferred-size=10cm},
{CommandButton
width={make-elastic
stretch-order=30,
stretchiness=100
}
},
{CheckButton background="lime",
width={make-elastic
stretch-order=30,
stretchiness=400
}
}
}
}
| |
Curl® GUI Toolkit には、オブジェクトの基礎となるエラスティックを調整するためのさまざまな手段が用意されています。以降のセクションではこれらの手段について説明します。
以降のセクションでは、エラスティックの使用方法、およびさまざまな手法の使用例について説明します。
width オプションおよび height オプションが一般に設定されるのは、次のオブジェクトやプロシージャです。
グラフィカル オブジェクトの width オプションまたは height オプションを設定する際、値がエラスティックでない場合は内部的にエラスティックに変換されます。オブジェクトの幅/高さを直接エラスティックに設定するには、幅/高さを次のプロシージャのいずれかに設定します。
エラスティックを使う手段としては、次のプロシージャを使うという方法もあります。
- vcenter:ユーザーが指定したグラフィックの周りに VBox をラップし、その上下にオブジェクトを 1 つずつ配置します。オブジェクトの高さの stretch-order は、ユーザーが vcenter に対する 2 つ目の引数として指定した値です (既定値は 30)。
- hcenter:ユーザーが指定したグラフィックの周りに HBox をラップし、その左右にオブジェクトを 1 つずつ配置します。オブジェクトの幅の stretch-order は、ユーザーが hcenter に対する 2 つ目の引数として指定した値です (既定値は 30)。
テキストが表示される場合、そのテキストは
TextFlowBox の内部にラップされ、グラフィック階層の中に配置されます。
TextFlowBox の一部のエラスティック特性はテキストのフローに対応しているので、ここで説明します。
- 高さ:TextFlowBox は、常にオブジェクトに対してユーザー定義サイズを適用します。オブジェクトを垂直方向に伸長または圧縮することはありません。
- 幅:TextFlowBox は常にテキストをコンテナの境界に合わせて伸長します。その後、テキストが自動改行されます。また、TextFlowBox の compress-order は他のほとんどのグラフィカル オブジェクトよりも高いので、幅に制限があるときに minimum-size に圧縮されるオブジェクトになります。
- text-width-display は、グラフィックを囲んでいる最も近い TextFlowBox の幅に合わせて伸長されるオブジェクトにおいて引数として指定されたグラフィックをラップします。
- center は、左右に伸長可能なオブジェクトを配置するオブジェクトにおいてグラフィックまたはテキスト (実際にはその TextFlowBox) をラップします。これにより、グラフィックまたはテキストは、それを囲んでいる最も近い TextFlowBox の内部で中央揃えされます。
- right-justify は、左側に伸長可能なオブジェクトを配置するオブジェクトにおいてグラフィックまたはテキスト (実際にはその TextFlowBox) をラップします。これにより、グラフィックまたはテキストは、それを囲んでいる最も近い TextFlowBox の内部で右揃えされます。
text-width-display の使用例を次に示します。
例:
text-width-display の使用 |
|
{paragraph
paragraph-left-indent=1cm,
paragraph-right-indent=1cm,
{paragraph
font-weight="bold",
paragraph-justify="center",
Regional Championship}
{text-width-display
{HBox
{paragraph color="purple",
{underline Purple Team}{br}
Violet Schneider{br}
Lila Lee
},
{Fill},
{paragraph color="green",
{underline Green Team}{br}
Nina Gruengarten{br}
Ching Yi
}
}
}
}
| |
Fill はパディング用としてよく使われます。理由は、クラスの stretch-order と compress-order の既定値がきわめて高い (40) ためです。
コンテナ内のオブジェクトをコンテナの各境界に接するように配置する場合、コンテナ内のスペースを埋めるために Fill を使用できます。Fill の既定の stretch-order は他のほとんどのグラフィカル オブジェクトの既定の stretch-order よりも高いので、オブジェクトを伸長するというよりも、空き領域をスペースで埋めていくことができます。
他のグラフィカル オブジェクトと同様、Fill の幅と高さをエラスティックに明示的に設定できます。
例:
Fill と text-width-display の併用 |
|
{text-width-display
{HBox background={LinearGradientFillPattern
{Fraction2d 0.0, 0.0},
{Fraction2d 1.0, 0.0},
{Spectrum.from-endpoints
"#80b4b3",
"white"
}
},
{text Thank you for using Curl IDE},
{Fill} ,
{link href={url "http://www.curl.com/"}, SCSK Corporation.}
}
}
| |
一部のグラフィカル コンテナには、hstretch? または vstretch? というローカル オプションが設定されています。このオプションが true に設定されている場合、子オブジェクトは伸長されます。
これらのオプションの既定値は
false です。このオプションが false に設定されている場合、 stretch-order が 25 より高い子オブジェクトだけが伸長されます。例については、
Frame.hstretch? を参照してください。
グラフィック階層の中に、同時に 1 つだけ表示すべきオブジェクトがある場合、
OverlayBox を使用できます。
OverlayBox は、その子をそれ自体の境界まで伸長します。つまり、既定では最も前面にある (非透過) オブジェクトだけが見えることになります。
このセクションでは、次の整列オプションとエラスティックを使って整列を行う例を示します。
- valign
- make-elastic
- hcenter
- text-width-display
- Fill
例:
オプションとプロシージャを使った Elastics の利用 |
|
{define-proc {control-box}:VBox
{return
{spaced-vbox
|| use make-elastic to set a minimum size
width={make-elastic
minimum-size=2in,
preferred-size=2in,
stretch-order=30,
compress-order=30
},
margin=0.5cm,
border-width=1pt,
border-color="black",
{text How do you feel about sharks?},
{RadioFrame
{VBox
{RadioButton label="I love sharks."},
{RadioButton label="I am terrified of sharks."},
{RadioButton label="Other"}
}
},
|| use hcenter for padding on both sides of the "Vote" button
{hcenter {CommandButton label="Vote"}}
}
}
}
{HBox
|| use valign to vertically align the 2 children by their centers
valign="center",
margin=0.5cm,
background="#aaaaff",
{TextFlowBox margin=0.5cm,
{center {bold Warning to Tourists}},
"Do not pat the heads of the sharks. They are not pets.
This is not a petting zoo.
Do not stand on the dead whales. They are being consumed
by the sharks. Thank you for your attention."
},
{control-box}
}
|| text-width-display stretches the sum of the objects to the
|| width of the enclosing TextFlowBox (in DefaultDocument or View)
{text-width-display
{HBox
|| use valign to vertically align the 3 children by their centers
valign="center",
margin=0.5cm,
background="#aaaaff",
{Frame margin=0.5cm,
{image
source={url "../../default/images/generic.gif"},
width=2in, height=2in}
},
|| add Fill so that the control box does not get stretched
{Fill},
{control-box}
}
}
| |
ブラウザに表示されるアプレットは、ドキュメントの中に含まれています。ドキュメントには 3 種類のスタイルがあります。3 種類のドキュメント スタイルのいずれかを指定するには、
document-style を使います。このプロシージャを明示的に呼び出さない場合、既定で
DefaultDocument が使われます。
このため、アプレットの伸長/圧縮動作は使用しているドキュメント スタイルによって異なります。アプレットがテキスト ベースの場合、DefaultDocument または TocDocument を使用すべきです。なぜなら、TextFlowBox によってテキストの適切な高さが設定され、また、テキスト全体を ScrollBox で囲めば必要時にスクロールバーが表示されるからです。
アプレットが、最上位レベルでページの垂直方向全体に広がるオブジェクトである場合、そのオブジェクトの祖先が TextFlowBox であってはいけません。つまり、DefaultDocument または TocDocument は使用しないでください。その代わり、PlainDocument を使えば必要な動作を実行できます。PlainDocument は Frame であるからです。
DefaultDocument においてグラフィカル オブジェクトを水平方向に中央揃えする例については、
default-document.curl をクリックしてください。Fill を使ってグラフィカル オブジェクトを垂直方向に中央揃えしようとしても、うまくいきません。グラフィカル オブジェクトを垂直方向に中央揃えするには、PlainDocument を使う必要があります。
Table を使う場合、テーブル全体の幅およびテーブルの各列のエラスティックを制御できます。
オプション (例:幅) を設定するには、*-prototype を追加します。
次の例を見てください。
例:
Table および列の幅を Elastic に設定 |
|
{let t:Table=
{Table
|| Ensure that table's width stretches when the
|| dialog is stretched by the user.
width={add-stretch},
background="#8888aa",
{column-prototype
|| Prevents the first column from stretching
|| when the table stretches.
width={make-elastic
minimum-size=1in,
preferred-size=1in,
stretch-order=10,
compress-order=10,
compressibility=50
},
{cell-prototype {text UserID:}},
{cell-prototype {TextField}},
{cell-prototype colspan=2,
{CommandButton
|| Stretches the "Need Hint" CommandButton
|| to the left and right of its inside origin.
width={add-stretch before?=true,
after?=true},
label="Need Hint"}
}
},
{column-prototype
|| Prevents the 2nd column from stretching
|| when the table stretches.
width={make-elastic
minimum-size=1in,
preferred-size=1in,
stretch-order=10
},
{cell-prototype {text Password:}},
{cell-prototype {PasswordField}},
{skip}
},
{column-prototype
|| Without resizing, the width of the 3rd column is 2in
width={make-elastic minimum-size=2in},
{cell-prototype {text From:}},
{cell-prototype {TextField}}
},
{column-prototype
|| Without resizing, the width of the 4th column is 2in
width={make-elastic minimum-size=2in},
{cell-prototype {text To:}},
{cell-prototype {TextField}},
{cell-prototype
|| Right align the "Search" button within
|| its cell.
{text-width-display
{HBox {Fill}, {CommandButton label="Search"}}
}
}
}
}
}
{CommandButton
label="stretchy table in resizable dialog",
{on Action do
{let dialog:Dialog=
{Dialog
t
}
}
{dialog.show style="resizable", title="Ticket Search"}
}
}
| |
例:
text-width-display に Table を配置 |
|
{text-width-display
{Table columns=2,
width={make-elastic minimum-size=2in, stretch-order=40},
background="#8888aa",
{row-prototype
{cell-prototype
colspan=2,
{text Show me the cheapest round trip ticket for:}
}
},
{row-prototype
{cell-prototype {text From:}},
{cell-prototype {TextField}}
},
{row-prototype
{cell-prototype {text To:}},
{cell-prototype {TextField}}
}
}
}
| |
この章の最初で説明したように、エラスティックはグラフィカル オブジェクトの幅 の Dimension と高さの Dimension の基礎となります。そのため、グラフィック階層においてオブジェクトをネストする場合、オブジェクトは通常、開発者またはユーザーの予想どおりに伸長または圧縮されます。
既定の伸長/圧縮動作が自分の設計に合わない場合、以下に説明する手法を使って動作を調整します。
子は親の境界まで伸長しません。
- 親の preferred-size が不明な場合、子を同じサイズに設定します。
- 親の hstretch? オプションまたは vstretch? オプションを true に設定します。
- 子の compress-order を親よりも低い値に明示的に設定します。
- 親の compress-order を子よりも高い値に明示的に設定します。
Table と
CommandButton を含む
VBox の例を次に示します。この
VBox は、子のサイズに合わせて伸長されます。コメントを解除して次のことを実行してください。
例:
子を親の境界まで伸長 |
|
{VBox
||width=2in,
||hstretch?=true,
spacing=1.5cm,
border-width=1pt,
border-color="navy",
{Table columns=2,
{text Name:},
{TextField},
{text State:},
{DropdownList
"MA",
"RI",
"NH"}
},
{CommandButton
label="Reset all entries"}
}
| |
Curl アプレットのグラフィック レイアウトは、
レイアウト ネゴシエーションのプロセスによって決まります。このプロセスは、グラフィック階層内の
Graphic オブジェクトにかかわっています。
レイアウト ネゴシエーションでは、まず各オブジェクトの幅と高さの設定を調べ、最後に幅と高さを各 Graphic に設定します。幅と高さのどちらを先に処理してもかまいませんが、幅を先に処理するのが一般的です。
グラフィック階層内のすべての
Graphic の幅設定が収集された後、グラフィック階層内のオブジェクトに設定される幅が計算されます。この幅の値は、レイアウト ネゴシエーションの第 2 段階で使われます。第 2 段階では、第 1 段階で幅が設定されている各グラフィックに適した高さが検査されます。この第 2 段階は、グラフィック階層内のすべての
Graphic において
Graphic.constrain-width が呼び出された時点で開始します。検査された高さ設定を使って、最終段階で
Graphic に設定する高さが計算されます。最終段階では、各
Graphic の幅と高さが設定されます。この最終段階は、各
Graphic において
Graphic.set-size が呼び出された時点で開始します。
一部のレイアウト ネゴシエーションでは、第 1 段階が省略されます。ただし、第 2 段階と第 3 段階では、各 Graphic に対して新しいサイズが通知されるので、必ず実行されます。
Copyright © 1998-2019 SCSK Corporation.
All rights reserved.
Curl, the Curl logo, Surge, and the Surge logo are trademarks of SCSK Corporation.
that are registered in the United States. Surge
Lab, the Surge Lab logo, and the Surge Lab Visual Layout Editor (VLE)
logo are trademarks of SCSK Corporation.