(2017.8.25 追加記事;
gtk2,gtk3 で作ったウィンドウに GUIの部品(Widget;ウィジェット)を配置していきます。1.ウィンドウに 1つの部品を配置する
・Gtk::Container#add(widget, child_properties = nil)
ウィンドウに部品(ウィジェット)を配置します
→・Ruby/GTK2 チュートリアル - Ruby/GTK2のHello World
(license; public domain)
・gtk_window_add.rb

GUI部品の一つボタンを作ってウィンドウに配置した例です。
部品の大きさは、ウィンドウ一杯に表示され、ウィンドウのサイズを変えると部品の大きさもそれと共に大きくなります。
部品の大きさ、配置位置を設定するには、次のパッキングが必要になります。
2.ウィンドウに複数の部品を配置する
ウィンドウには 1つの部品しか配置できません。そのため、まず部品(ウィジェット)を配置するためのパッキング用ウィジット(Box や Fixed)を作ります。パッキングウィジェットには複数の部品やパッキングウィジェットを入れ子のように配置できるので、さまざまな部品を配置した後、最後にウィンドウに(1つの)パッキングウィジットを配置します。
→・Ruby/GTK2 チュートリアル - ウィジェットのパッキング
2-A.Gtk::Fixed
部品の配置を縦(x)、横(y)でピクセル単位で設定するFixedクラス
・Gtk::Fixed.new
Fixedクラスを作ります
・Gtk::Fixed.put(widget, x, y)
ウィジェットを x, y の位置に配置します
・gtk_fixed.rb
・gtk_vbox_gtk2.rb
・gtk_hbox_gtk2.rb

※ ボックスに部品を配置すると、VBoxならウィンドウの横一杯に、HBoxならウィンドウの縦一杯に部品が表示されます。この時、部品のサイズを設定していても、それぞれ横サイズや縦サイズは無視されます。
さらに、VBox/HBox/Box で homogeneous = true だったり、pack_start で expand = true、fill = true だったりすると、残りのサイズも無視されます。
これは、ウィンドウをリサイズしても、部品のサイズもリサイズされるので同じです。
3.部品を配置した時に、ウィンドウの内側に余白を作る
・Gtk::Container#set_border_width(border_width)
余白をピクセル単位で指定します
・gtk_vbox_gtk3_border.rb
・Gtk::Container#add(widget, child_properties = nil)
ウィンドウに部品(ウィジェット)を配置します
→・Ruby/GTK2 チュートリアル - Ruby/GTK2のHello World
(license; public domain)
・gtk_window_add.rb
require 'gtk3'#require 'gtk2' # gtk2ライブラリでも実行可能window = Gtk::Window.newbutton = Gtk::Button.new # GUI部品(ボタン)を作成button.set_label('Button') # ボタンに文字を設定window.add(button) # ウィンドウにボタンを配置するwindow.show_allwindow.signal_connect("destroy") { Gtk.main_quit }Gtk.main

GUI部品の一つボタンを作ってウィンドウに配置した例です。
部品の大きさは、ウィンドウ一杯に表示され、ウィンドウのサイズを変えると部品の大きさもそれと共に大きくなります。
部品の大きさ、配置位置を設定するには、次のパッキングが必要になります。
2.ウィンドウに複数の部品を配置する
ウィンドウには 1つの部品しか配置できません。そのため、まず部品(ウィジェット)を配置するためのパッキング用ウィジット(Box や Fixed)を作ります。パッキングウィジェットには複数の部品やパッキングウィジェットを入れ子のように配置できるので、さまざまな部品を配置した後、最後にウィンドウに(1つの)パッキングウィジットを配置します。
→・Ruby/GTK2 チュートリアル - ウィジェットのパッキング
2-A.Gtk::Fixed
部品の配置を縦(x)、横(y)でピクセル単位で設定するFixedクラス
・Gtk::Fixed.new
Fixedクラスを作ります
・Gtk::Fixed.put(widget, x, y)
ウィジェットを x, y の位置に配置します
・gtk_fixed.rb
require 'gtk3'#require 'gtk2' # gtk2ライブラリでも実行可能window = Gtk::Window.newwindow.set_size_request(300, 200) # ウィンドウのサイズ指定(幅300,高さ200)button1 = Gtk::Button.newbutton1.set_label('Button 1')button1.set_size_request(100, 50) # ボタン1のサイズを指定(幅100,高さ50)button2 = Gtk::Button.newbutton2.set_label('Button 2')button2.set_size_request(150, 80) # ボタン2のサイズを指定(幅150,高さ80)fixed = Gtk::Fixed.new # 表示位置指定Fixedクラスを作成fixed.put(button1, 10, 10) # button1を x=10, y=10 の位置に配置fixed.put(button2, 80, 100) # button2を x=80, y=100 の位置に配置window.add(fixed) # ウィンドウにfixedを貼り付けるwindow.show_allwindow.signal_connect("destroy") { Gtk.main_quit }Gtk.main
2-B.ボックス,テーブル(Gtk::VBox,Gtk::HBox,Gtk::Box,Gtk::Table)
・Gtk::VBox.new(homogeneous = false, spacing = nil) ;gtk3では deprecated
・Gtk::Box.new(:vertical, spacing) ;gtk3 のみ
部品を縦方向に配置するボックスウィジェットを作ります
homogeneous = true;全部の部品の高さが同じ
spacing;部品同士の間隔(ピクセル単位)
・Gtk::HBox.new(homogeneous = false, spacing = nil) ;gtk3では deprecated
・Gtk::Box.new(:horizontal, spacing) ;gtk3 のみ
部品を横方向に配置するボックスウィジェットを作ります
・Gtk::Box#pack_start(child, expand = true, fill = true, padding = 0) ;gtk3では deprecated
・Gtk::Box#pack_start(child, :expand => true, :fill => true, :padding => 0) ;gtk3のみ
ボックスウィジェットに部品(child)を配置します
expand = true;大きさが違うときに、大きい方の部品のサイズに揃えます
fill = true;小さい部品の大きさを大きい部品のサイズまで引き延ばします
(expand = true の時のみ有効)
padding;部品同士の間隔(ピクセル単位)
・Gtk::Table.new(rows, columns, homogeneous = false)
・部品を表のように縦横に配置するテーブルウィジェットを作ります
・Gtk::Table#attach(child, left, right, top, bottom, xopt = Gtk::EXPAND|Gtk::FILL, yopt = Gtk::EXPAND|Gtk::FILL, xpad = 0, ypad = 0)
テーブルウィジェットに部品(child)を配置します
・gtk_vbox_gtk3.rb
・Gtk::VBox.new(homogeneous = false, spacing = nil) ;gtk3では deprecated
・Gtk::Box.new(:vertical, spacing) ;gtk3 のみ
部品を縦方向に配置するボックスウィジェットを作ります
homogeneous = true;全部の部品の高さが同じ
spacing;部品同士の間隔(ピクセル単位)
・Gtk::HBox.new(homogeneous = false, spacing = nil) ;gtk3では deprecated
・Gtk::Box.new(:horizontal, spacing) ;gtk3 のみ
部品を横方向に配置するボックスウィジェットを作ります
・Gtk::Box#pack_start(child, expand = true, fill = true, padding = 0) ;gtk3では deprecated
・Gtk::Box#pack_start(child, :expand => true, :fill => true, :padding => 0) ;gtk3のみ
ボックスウィジェットに部品(child)を配置します
expand = true;大きさが違うときに、大きい方の部品のサイズに揃えます
fill = true;小さい部品の大きさを大きい部品のサイズまで引き延ばします
(expand = true の時のみ有効)
padding;部品同士の間隔(ピクセル単位)
・Gtk::Table.new(rows, columns, homogeneous = false)
・部品を表のように縦横に配置するテーブルウィジェットを作ります
・Gtk::Table#attach(child, left, right, top, bottom, xopt = Gtk::EXPAND|Gtk::FILL, yopt = Gtk::EXPAND|Gtk::FILL, xpad = 0, ypad = 0)
テーブルウィジェットに部品(child)を配置します
・gtk_vbox_gtk3.rb
require 'gtk3'window = Gtk::Window.newwindow.set_size_request(300, 200)button1 = Gtk::Button.newbutton1.set_label('Button 1')button1.set_size_request(100, 50) # ボタン1のサイズを指定(幅100,高さ50)button2 = Gtk::Button.newbutton2.set_label('Button 2')button2.set_size_request(150, 80) # ボタン2のサイズを指定(幅150,高さ80)vbox = Gtk::Box.new(:vertical) # パッキングBox(縦方向)を作成# button1、button2をvboxに配置vbox.pack_start(button1, :expand => false, :fill => false, :padding => 0)vbox.pack_start(button2, :expand => false, :fill => false, :padding => 0)window.add(vbox) # ウィンドウにvboxを貼り付ける
window.show_allwindow.signal_connect("destroy") { Gtk.main_quit }Gtk.main
・gtk_vbox_gtk2.rb
require 'gtk2'window = Gtk::Window.newwindow.set_size_request(300, 200) # ウィンドウのサイズ指定(幅300,高さ200)button1 = Gtk::Button.newbutton1.set_label('Button 1')button1.set_size_request(100, 50) # ボタンのサイズを指定(幅100,高さ50)button2 = Gtk::Button.newbutton2.set_label('Button 2')button2.set_size_request(150, 80)vbox = Gtk::VBox.new # パッキングVBoxを作成vbox.pack_start(button1, false, false, 0) # button1をvboxに配置vbox.pack_start(button2, false, false, 0) # button2をvboxに配置window.add(vbox) # ウィンドウにfixedを貼り付けるwindow.show_allwindow.signal_connect("destroy") { Gtk.main_quit }Gtk.main
require 'gtk3'window = Gtk::Window.newwindow.set_size_request(300, 200) # ウィンドウのサイズ指定(幅300,高さ200)button1 = Gtk::Button.newbutton1.set_label('Button 1')button1.set_size_request(100, 50) # ボタン1のサイズを指定(幅100,高さ50)button2 = Gtk::Button.newbutton2.set_label('Button 2')button2.set_size_request(150, 80) # ボタン2のサイズを指定(幅150,高さ80)hbox = Gtk::Box.new(:horizontal) # パッキングBox(横方向)を作成# button1、button2をhboxに配置hbox.pack_start(button1, :expand => false, :fill => false, :padding => 0)hbox.pack_start(button2, :expand => false, :fill => false, :padding => 0)window.add(hbox) # ウィンドウにhboxを貼り付けるwindow.show_allwindow.signal_connect("destroy") { Gtk.main_quit }Gtk.main
・gtk_hbox_gtk2.rb
require 'gtk2'window = Gtk::Window.newwindow.set_size_request(300, 200)button1 = Gtk::Button.newbutton1.set_label('Button 1')button1.set_size_request(100, 50) # ボタン1のサイズを指定(幅100,高さ50)button2 = Gtk::Button.newbutton2.set_label('Button 2')button2.set_size_request(150, 80) # ボタン2のサイズを指定(幅150,高さ80)hbox = Gtk::HBox.new # パッキングHBoxを作成hbox.pack_start(button1, false, false, 0) # button1をhboxに配置hbox.pack_start(button2, false, false, 0) # button2をhboxに配置window.add(hbox) # ウィンドウにhboxを貼り付けるwindow.show_allwindow.signal_connect("destroy") { Gtk.main_quit }Gtk.main

※ ボックスに部品を配置すると、VBoxならウィンドウの横一杯に、HBoxならウィンドウの縦一杯に部品が表示されます。この時、部品のサイズを設定していても、それぞれ横サイズや縦サイズは無視されます。
さらに、VBox/HBox/Box で homogeneous = true だったり、pack_start で expand = true、fill = true だったりすると、残りのサイズも無視されます。
これは、ウィンドウをリサイズしても、部品のサイズもリサイズされるので同じです。
3.部品を配置した時に、ウィンドウの内側に余白を作る
・Gtk::Container#set_border_width(border_width)
余白をピクセル単位で指定します
・gtk_vbox_gtk3_border.rb
require 'gtk3'window = Gtk::Window.newwindow.set_size_request(300, 200)window.set_border_width(20) # ウィンドウの内側に余白を作るbutton1 = Gtk::Button.newbutton1.set_label('Button 1')button1.set_size_request(100, 50)button2 = Gtk::Button.newbutton2.set_label('Button 2')button2.set_size_request(150, 80)vbox = Gtk::Box.new(:vertical)vbox.pack_start(button1, :expand => false, :fill => false, :padding => 0)vbox.pack_start(button2, :expand => false, :fill => false, :padding => 0)window.add(vbox)window.show_allwindow.signal_connect("destroy") { Gtk.main_quit }Gtk.main