24
 その他の配置手段(座標配置と格子配置) 



今までは「並べ配置」と言うスタイルで、上から下へ、あるいは左から右へと順序良くウィジェットを並べていくものでした。(並べ配置については 配置の基礎配置の詳しい解説 を参照)
複数のウィジェットを単純に縦あるいは横に並べるには向いている配置方法でしたが、少し複雑な配置に対しては、フレームを使うなど手間がかかる面があります。そのような場面では、別の配置機構である「座標配置」と「格子配置」を使うと簡単に実現できることがあり、本章ではそれらについて解説をおこないます。


 
 
座標配置
 
 

 図形の描画のように、座標を指定してウィジェットを配置する仕組みです。
 正確には、ウィンドウ(またはフレーム)の左上隅を 0, 0 とするようなピクセル単位の座標で位置を指定するものです。
 座標の指定方法には2通りあり、30, 20 のような座標指定のほか、小数点を使い、0.3, 0.5 のような指定も可能です。ウィンドウ右下隅を 1.0 , 1.0 とみなすような比例計算となります。
 座標配置では、並べ配置のときのような配置IDという概念はありません。対象となるウィジェットに直接働きかけて配置をする方式であるため、別に配置用のIDを持つ必要はありません。

■座標配置を利用時のウィンドウサイズ
 座標配置を使う場合、ウィンドウ(またはフレーム)のサイズを明示することを勧めます。もちろん、並べ配置の時と同様に、ウィンドウはウィジェットに連動して自動的かつ適切に開きますが、ウィジェットの座標を明示している以上、ウィンドウサイズ(またはフレームサイズ)も明示したほうが全体として見通しが良くなります。

■座標配置を準備(必須)

構文=
<ウィジェットID>を 座標配置を準備 → ・         注:複数のウィジェットがある場合、それぞれ           のウィジェットに上記を施してください

       プログラム例:
    ラベル1を 座標配置を準備し
 指定したウィジェットの座標配置の手続きを開始します。そのウィジェットについての属性設定が途中になっているとエラーになるので、属性設定は完了した段階で使ってください。たとえば次のようなケースです。
    / ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄\
    (誤)
    ○○とは
        ・・で ラベルのIDを取得し ラベル1に 入れ
        ラベル1を 座標配置を準備し  ←誤り(「有効化」の前は誤り)
        ラベル1を 有効化し

    (正)
    ○○とは
        ・・で ラベルのIDを取得し ラベル1に 入れ
        ラベル1を 有効化し
        ラベル1を 座標配置を準備し
    \___________________________/

■座標配置(必須)

構文=
<ウィジェットID>を 座標配置する → ・         注:複数のウィジェットがある場合、それぞれ           のウィジェットに上記を施してください
       プログラム例:
    ラベル1を 座標配置する
 「座標配置を準備」のあと、以降に示す必要なパラメータの設定をし、最後に「座標配置」を呼び出してください。これによってウィジェットがウィンドウに現れます。

■ウィジェットの位置を設定(必須)(座標配置用)

構文=
<X>と <Y>を <ウィジェットID>に ウィジェットの位置を設定 → ・         記:XとYは整数または小数を指定します
 ウィジェットの位置を指定します。
 座標位置に整数を与えた場合は、そのウィジェットの親(たとえばウィンドウ)の左上隅を原点とした座標となります。親ウィジェットがフレームの場合にはフレームの左上隅を原点とみなします。単位はピクセルです。
 座標位置に小数を与えた場合は、そのウィジェットの親(たとえばウィンドウ)の左上隅を 0, 0 、右下隅を 1.0, 1.0 とした比例値とみなされます。小数を指定するメリットとしては、将来的にウィジェットが増えてウィンドウサイズが大きくなった場合でも大まかなレイアウトが維持されることです。(注:ウィンドウを手動で広げることには追従しません)
 メニューバー を併用している場合、指定座標はメニューバーを除いた領域の左上隅が原点になります。
 なお、指定した座標がウィジェットのどの位置に対応するのかの設定が別途あります。後述する「基準点を設定」の解説を合わせてお読みください。

■基準点を設定(任意)
(キャンバスウィジェットにも同名の単語があり、解説は重複します)
 ウィジェットの位置を指定するのに座標を指定しますが、描画されるウィジェットは広さのある領域であり、それだけでは位置があいまいです。このあいまいさを解消するための指示となります。

構文=
<基準点指示>を <ウィジェットID>に 基準点を設定 → ・    基準点として以下のいずれかのシンボルを記述(文字列定数)           上端           下端           左端           右端           左上隅    ←デフォルト           左下隅           右上隅           右下隅           中央
       プログラム例:(ウィジェットをウィンドウの右下隅にくっつけて表示)
1.0、1.0を ラベル1に ウィジェットの位置を設定し
右下隅を  ラベル1に 基準点を設定し
 「基準点を設定」をおこなわない場合(デフォルト)は左上隅となります。

■ウィジェットのサイズを設定(任意)

構文=
<Xサイズ>と <Yサイズ>を        <ウィジェットID>に ウィジェットのサイズを設定 → ・ <Xサイズ>を        <ウィジェットID>に ウィジェットの幅を設定  → ・ <Yサイズ>を        <ウィジェットID>に ウィジェットの高さを設定 → ・          注1:サイズの単位はピクセルです          注2:「座標配置を準備」の後でおこなってください。             (前ではエラーにならないものの正しく動作しません)
 ウィジェットのサイズ指定は一般のウィジェットでも使うものなので改めて記載します。
  ●一般ウィジェットでは単位が文字数だったりピクセル数だったり
   しましたが、座標配置においては常にピクセル数です。
  ●これらの処理単語を呼び出すタイミングですが、一般ウィジェッ
   ト操作としての適用ではなく、「座標配置を準備」の後に記述し、
   座標配置の一環としておこなってください。
/ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄\
 (誤)
   ・・で ラベルのIDを取得し ラベル1に 入れ
   ・・と ・・を ラベル1に ウィジェットのサイズを設定し  ←記述個所誤り
   ラベル1を 有効化し

   ラベル1を 座標配置を準備し
   ・・と ・・を ラベル1に ・・・・し
   ラベル1を 座標配置する
 \___________________________/
 / ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄\
 (正)
   ・・で ラベルのIDを取得し ラベル1に 入れ
   ・・と ・・を ラベル1に ・・・・し
   ラベル1を 有効化し

   ラベル1を 座標配置を準備し
   ・・と ・・を ラベル1に ウィジェットのサイズを設定し  ←この個所で
   ラベル1を 座標配置する
 \___________________________/
 なお、ウィジェットを座標配置した後でウィジェットのサイズを設定する(つまり変更)こともできます。最後に「変更を反映」をおこなってください。

■座標配置のサンプルプログラム
       サンプルプログラム:
place.exe
2つのラベルと1つのボタンがありますがすべて座標配置です。
ボタンの座標は右下隅を基準点として、0.98,0.96としているのでボタンはほとんどウィンドウの右下隅に配置されています。
ボタンを押すとラベル2のサイズが変化するだけでなく、ボタンの位置も変わります。
ラベル2が大きくなるので結果的にラベル1にかぶさって表示されますが、これは並べ配置ではできなかったことです。


 
 
格子配置
 
 

 電卓のテンキーのようなウィジェットの配置は、並べ配置でできなくはありませんが、テンキーのように元々が格子状になっているものは「格子配置」という機能を使うと簡単に実現できます。
記: きれいな格子状でなくても(一見すると格子に見えない配列でも)適用でき、かなり柔軟です。
 格子配置とは、縦に何行分、横に何列分という仮想のテーブルを想定し、そこにウィジェットを当てはめていくものです。それぞれの行や列の幅は柔軟であり、すべての行幅を同じにしたり、すべての列幅を同じにする必要はありません。
 格子配置では並べ配置のときのような配置IDという概念はありません。対象となるウィジェットに直接働きかける方式であるため、別に配置用のIDを持つ必要はありません。

■格子配置利用時のウィンドウサイズ
 格子配置は仮想のテーブルを想定するものであり、そのサイズまで規定するものではありません(指定はできます)。
 格子配置の親となるウィンドウあるいはフレームのサイズもまた収容する格子に合わせて自動的に決定されるため、ウィンドウサイズ、フレームサイズは明示する必要はありません(指定はできます)。

■格子配置を準備(必須)

構文=
<ウィジェットID>を 格子配置を準備 → ・         注:複数のウィジェットがある場合、それぞれ           のウィジェットに上記を施してください
       プログラム例:
ラベル1を 格子配置を準備し
 指定したウィジェットの格子配置の手続きを開始します。そのウィジェットについての属性設定が途中になっているとエラーになるので、属性設定は完了した段階で使ってください。たとえば次のようなケースです。
    / ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄\
    (誤)
    ○○とは
        ・・で ラベルのIDを取得し ラベル1に 入れ
        ラベル1を 格子配置を準備し  ←誤り(「有効化」の前は誤り)
        ラベル1を 有効化し

    (正)
    ○○とは
        ・・で ラベルのIDを取得し ラベル1に 入れ
        ラベル1を 有効化し
        ラベル1を 格子配置を準備し
    \___________________________/

■格子配置(必須)

構文=
<ウィジェットID>を 格子配置する → ・         注:複数のウィジェットがある場合、それぞれ           について上記をおこなってください
       プログラム例:
ラベル1を 格子配置する
 「格子配置を準備」のあと、以降に示す必要なパラメータの設定をし、最後に「格子配置」を呼び出してください。これによってウィジェットがウィンドウに現れます。


 
セルに対する属性の設定
 

■ウィジェットの位置を設定(必須)(格子配置用)

構文=
<行位置>と <列位置>を <ウィジェットID>に ウィジェットの位置を設定 → ・
       プログラム例:
3行と 2列を ラベル1に ウィジェットの位置を設定し
 指定した行・列位置にウィジェットの位置を決めます。
 座標配置にも同名の単語がありましたが、格子配置では行・列の指定である点が異なります。

■行結合を設定、列結合を設定(任意)

構文=
<行数>を <ウィジェットID>に 行結合を設定 → ・ <列数>を <ウィジェットID>に 列結合を設定 → ・             注:両者を併用できます
       プログラム例1:(行結合)
3行と 2列を ラベル1に ウィジェットの位置を設定し
2行を ラベル1に 行結合を設定し
       プログラム例2:(列結合)
3行と 2列 ラベル1に ウィジェットの位置を設定し
2列を ラベル1に 列結合を設定し
 隣接するn行分 または 隣接するn列分を占有するよう指示します。表計算ソフトの行結合・列結合と同じ概念です。
 上のプログラム例1では、本来であれば3行/2列目のセルだけに置くべきウィジェットを3行〜4行/2列目にかけ、縦方向に長い領域に確保します。
 ウィジェットが長くなった占有域の中のどの位置に置かれるかは、これとは別の指示となります。具体的には”基準点を設定”で決まりますが、デフォルトでは広くなった占有域の左上に置かれます。
 上のプログラム例2では、本来であれば3行/2列目のセルだけに置くべきウィジェットを3行/2列〜3列目にかけ、横方向に長い領域に確保します。
 両者を併用した場合には縦横に広がった領域を確保することになります。

■寄せを設定(任意)
 前記した「行結合を設定」「列結合を設定」を使って占有域を広げた場合、空白が現れますが、広くなった領域のどの位置にウィジェットを置くかを指定します。
記: 結合を使って領域を広げた場合に限らず、他のセルの設定条件の影響でセル周辺に空間が出来た場合も「寄せを設定」が使えます

構文=
<寄せ指定>を <ウィジェットID>に 寄せを設定 → ・      寄せ指定:以下のいずれかの単語名を指定してください。         西寄せ         北西寄せ         北寄せ         北東寄せ         東寄せ         南東寄せ         南寄せ         南西寄せ         中央寄せ   ←デフォルト         −−−−−         東西伸ばし  ←ここから先は格子配置のみで使う         南北伸ばし         東西南北伸ばし
 上の寄せ指定について補足します。「西寄せ」〜「中央寄せ」までは、一般ウィジェット操作でも使うもので、空いた領域に対して自セルをどの方向に寄せて配置するかを決めます。寄せを指定しない場合は「中央寄せ」となります。
 一方、「○○伸ばし」は、寄せるというよりは引き延ばすことで空間を埋める意味になります。たとえば「東西南北伸ばし」は空いた領域いっぱいにセルを表示することになります。

■結合と寄せの組み合わせ例
       サンプルプログラム:
grid-9cell-span.exe
このサンプルでは3×3のセル表示をおこないますが、ボタン5では行・列を2つずつ結合しており、ボタン5のみセルが大きくなっています。さらに「東西南北伸ばし」で寄せを設定しているので、ボタン自体も大きなセル領域いっぱいに表示されています。

■内側パディングの設定(任意)

構文=
<Xサイズ>と <Yサイズ>を <ウィジェットID>に 内側パディングを設定 → ・ <Xサイズ>を <ウィジェットID>に 内側パディングの幅を設定  → ・ <Yサイズ>を <ウィジェットID>に 内側パディングの高さを設定 → ・           注:サイズの単位はピクセル
 ウィジェットの”内部に描画した文字周辺”に空白を作ります。

■外側パディングの設定(任意)

構文=
<Xサイズ>と <Yサイズ>を <ウィジェットID>に 外側パディングを設定 → ・ <Xサイズ>を <ウィジェットID>に 外側パディングの幅を設定  → ・ <Yサイズ>を <ウィジェットID>に 外側パディングの高さを設定 → ・           注:サイズの単位はピクセル
 ウィジェットの外側(ウィジェットの周囲)に空間を作ります。
一般ウィジェット操作としての「パディングの設定」はウィジェット内部に作用しましたが、格子配置においては内側と外側どちらも設定できるため、内側・外側を明示しています。

 
親ウィジェットへの属性の設定
 

 以下では親ウィジェットに対する格子配置のための属性設定を解説します。
 これまでのウィジェットに対する位置やパディングなどの設定はあくまで個々のウィジェットに対するものでした。
 その一方で、1行全部あるいは1列全部に対して属性設定したいこともあります。そのような場合に個別のウィジェットへの設定を使うのでは煩雑なので、ウィジェットの親に対して属性設定をおこなう方式により、行または列への設定を行えるようにしてあります。

■親に対し行属性/列属性を設定準備(単独行、単独列)

構文=
(ステップ1)     <行番号>を      <親ウィジェットID>に 親に対し行属性を設定準備 → ・      --または--     <列番号>を      <親ウィジェットID>に 親に対し列属性を設定準備 → ・ (ステップ2)     ・・・を <親ウィジェットID>に 親に対し・・を設定し     ・・・を <親ウィジェットID>に 親に対し・・を設定し (ステップ3)     <親ウィジェットID>を 変更を反映
       プログラム例:
2行目を メインウィンドウに 親に対し行属性を設定準備し
1を   メインウィンドウに 親に対し行・列のウェイトを設定し
メインウィンドウを 変更を反映する
 親ウィジェットに対する格子配置の属性設定を開始します。指定する1行または1列をまとめて設定するモードに入ります。
 後続して属性設定をおこない、最後に「変更を反映」することで反映されます。

■親に対し行範囲/列範囲の属性を設定準備(行範囲、列範囲)

構文=
(ステップ1) <行番号>から <行番号>までを      <親ウィジェットID>に 親に対する行範囲の属性を設定準備 → ・      --または-- <列番号>から <列番号>までを      <親ウィジェットID>に 親に対する列範囲の属性を設定準備 → ・ (ステップ2)     ・・・を <親ウィジェットID>に 親に対し・・を設定し     ・・・を <親ウィジェットID>に 親に対し・・を設定し (ステップ3)     <親ウィジェットID>を 変更を反映
       プログラム例:
1行目から 2行目を メインウィンドウに 親に対する行範囲の属性を設定準備し
1を         メインウィンドウに 親に対し行・列のウェイトを設定し
メインウィンドウを 変更を反映する
 親ウィジェットに対する格子配置の属性設定を開始します。行範囲または 列範囲を指定することで連続した複数の行、複数の列を設定できます。
 後続して属性設定をおこない、最後に「変更を反映」することで反映されます。

■親に対し行・列のウェイトを設定

構文=
<ウェイト>を <親ウィジェットID>に 親に対し行・列のウェイトを設定 → ・          注:ウェイトは1以上の整数で、比率を表す
       プログラム例:
2行目を メインウィンドウに 親に対し行属性を設定準備し
1を   メインウィンドウに 親に対し行・列のウェイトを設定し
メインウィンドウを 変更を反映する
 ウェイトについて説明します。簡単そうに見えますが効果を持たせるのに少し配慮が必要な機能です。
 この機能は親のウィンドウまたはフレームの広さが配下のウィジェット群に対して余裕があるときに意味を持ちます。たとえばウィンドウのサイズを指定することで広いウィンドウとし、配下ウィジェット周辺に隙間が作れるケースで使われます。
 逆に、ウィンドウサイズやフレームサイズを指定せず、ウィジェット群を収容するとウィンドウやフレームがぴったりになるようなケースでは効果がありません。
 たとえば1行目よりも2行目を広くしたい場合、その絶対幅を指定するのではなく、相対的な比率を指定することでおこないます。
 たとえば、
    1行目のウェイト=1
    2行目のウェイト=2
とすると、2行目は1行目に比べて2倍の行高さとなります。
 列についても同様で、
    1列目のウェイト=1
    2列目のウェイト=2
とすると、2列目は1列目に比べて2倍の列幅となります。
行に対して働くのか、列に対して働くのかは、その直前に実行したものが、「親に対し行属性を設定準備」だったか「親に対し列属性を設定準備」だったかにより判定されます。
本機能で指定する高さ/幅ですが、あくまで 行または列の領域サイズ であり、ウィジェットの大きさではない点に注意してください。
ウェイト指定で行・列が大きくなると同時にウィジェット自体も大きくしたい場合には「寄せを設定」に特殊な値を指定することにより行います。
       サンプルプログラム:grid-4cell-weight-1and2-stickey.src
/ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄ ̄\
  東西南北伸ばしを _ボタンに 寄せを設定
\______________________/
 ウェイトを設定した際の副産物として、ウィンドウ(またはフレーム)を広くした場合に行・列も追従して大きくなる点があります。
 サンプルプログラムとして次の2つを起動して比べてみてください(いずれも、行に対するウェイト指定です)。
grid-4cell-weight-no.exe
ウェイト無し
grid-4cell-weight-1and2.exe
ウェイト有り(1対2)
grid-4cell-weight-1and2-stickey.exe
ウェイト有り(1対2)・寄せを設定
 2番目のプログラムは1行目と2行目に1対2のウェイトを設定しているので、行の高さが1対2になっています。ただし、ウィジェット自体は広がらず隙間があります。
 3番目のプログラムはさらに、”東西南北伸ばし”で ”寄せを設定”しているため、ウィジェットの高さが行領域いっぱいに伸びて表示されています。

■親に対し行・列のパディングを設定

構文=
<値>を <親ウィジェット>に 親に対し行・列のパディングを設定 → ・             注:値の単位はピクセル
 既に「親に対し行(範囲の)属性を設定準備」または「親に対し列(範囲の)属性を設定準備」が行われていることを前提とし、事前指定した行または列に対してパディングを設定します。単位はピクセルです。
 設定すると、この親の配下となるウィジェットの格子配置において、指定した行または列に対してパディングを行います。(ウィジェットの外側に隙間ができます)

■格子配置を除去

構文=
<ウィジェットID>の 格子配置を除去 → ・
 格子配置したウィジェットを削除します。元のウィジェットの格子配置属性も除去されます。

■格子配置を非表示

構文=
<ウィジェットID>の 格子配置を非表示 → ・
 格子配置したウィジェットを見えなくします。元のウィジェットの格子配置属性は維持されるので、後に「格子配置を再表示」によって再表示させることができます。

■格子配置を再表示

構文=
<ウィジェットID>の 格子配置を再表示 → ・
 「格子配置を非表示」したウィジェットを再度表示します。属性は維持されているので属性設定は不要であり、直ちに配置されます。

■親に対し行の/行範囲の属性を取り除く

構文=
<行番号>を <親ウィジェット>に 親に対し行属性を取り除く → ・ <行番号>から <行番号>までを            <親ウィジェット>に 親に対し行範囲の属性を取り除く → ・
 行に対して属性を設定した後、その属性を取り除く機能です。元となる属性設定が親に対してであるため、取り除きもまた親に対しておこないます。
 このあと、「変更を反映」によって反映してください。
 親に対する属性設定をおこなったときの注意があります。格子配置によってウィジェットを描画したあと、何らかの理由でそられのウィジェットを削除することがあるかもしれません。
 ウィジェットを削除するとウィンドウ内がきれいになるのでそれで終わりのように見えますが、実は配下のウィジェットが削除されても親ウィジェット(たとえばウィンドウ)は残っており、当然ながら親の属性が残っています。そのまま放置して次のウィジェット描画を格子配置で行うと、新しいウィジェットは以前の親属性を引き継ぐことになります。それでは困る場合にこの処理単語を使います。

■親に対し列の/列範囲の属性を取り除く

構文=
<列番号>を <親ウィジェット>に 親に対し列属性を取り除く → ・ <列番号>から <列番号>までを            <親ウィジェット>に 親に対し列範囲の属性を取り除く → ・
 列に対して属性を設定した後、その属性を取り除く機能です。元となる属性設定が親に対してであるため、取り除きもまた親に対しておこないます。
 このあと、「変更を反映」によって反映してください。
 親に対する属性設定をおこなったときの注意があります。格子配置によってウィジェットを描画したあと、何らかの理由でそられのウィジェットを削除することがあるかもしれません。
 ウィジェットを削除するとウィンドウ内がきれいになるのでそれで終わりのように見えますが、実は配下のウィジェットが削除されても親ウィジェット(たとえばウィンドウ)は残っており、当然ながら親の属性が残っています。そのまま放置して次のウィジェット描画を格子配置で行うと、新しいウィジェットは以前の親属性を引き継ぐことになります。それでは困る場合にこの処理単語を使います。

■格子配置のサンプルプログラム
grid-4cell-weight-no.exe
ウェイト無し
grid-4cell-weight-1and2.exe
ウェイト有り(1対2)
grid-4cell-weight-1and2-stickey.exe
ウェイト有り(1対2)・寄せを設定
grid-9cell-span.exe
行・列の結合
grid-complex.exe
すべての格子配置の機能をテスト(どのような機能があるかは、 メニューでご覧ください)
listbox-multi.exe
少し複雑な格子配置
一見すると格子状には見えませんが格子配置がうまく使われています。
ウィジェットの大きさがまちまちでも、このようにまとめることができます。
これと類似のlistbox.exeと見比べてください。listbox.exeでは並べ配置で実現していますが、こちらは格子配置を使っています。同じように見えるものでも違う配置手段が使える例としてご覧ください。


 
 
異なる配置手段の混在
 
 

 これまでに 並べ配置、 座標配置、 格子配置 を解説してきましたが、この3者は混在させられないので注意してください。
 ただし、ある配置手段で配置したウィジェット群をフレームにまとめた場合は、そのフレームと他のウィジェット群を別の手段で配置することができます。
 たとえば、"listbox-multi" というサンプルプログラムがあります。リストボックスはリストボックスウィジェットおよび、それとペアになるスクロールバーが1つのフレーム内に並べ配置を使ってまとめられています。そして、そのフレームと他のウィジェットを格子配置でまとめることは可能で、実際そのようにしています。