26 June 2010

(Gtk2-Perl) 基本的な入力操作系ダイアログボックスの作成方法メモ

Gtk2-Perlライブラリを用いて、基本的なダイアログボックスの作成方法メモ。

・1行テキスト入力ダイアログボックス
・コンボボックスでの選択ダイアログボックス
・ファイル、ディレクトリ選択ダイアログボックス
・色の選択ダイアログボックス

■ 参考資料
Gtk2-Perl公式ページ
Gtk2-Perlライブラリのリファレンス
定数一覧はこちら(Gtk2::enums)
チュートリアル (Gtk2-Perl Study Guide)

■ 1行テキスト入力ダイアログボックス

こんな感じのものをイメージしている

20100626-gdk2-entry.png

以下、ソースコード

#!/usr/bin/perl use strict; use warnings; use utf8; use Gtk2 qw/-init/; binmode( STDOUT, ":utf8" ); # "Wide character in print at ..." 警告を抑止 MainDialog(); exit; sub MainDialog { my $strInput = ""; # ダイアログに渡す文字列(リファレンス) my $window; # メインウインドウ $window = Gtk2::Window->new('toplevel'); $window->signal_connect( "destroy" => sub { Gtk2::main_quit; } ); # ウインドウの閉じるボタンの処理 $window->set_title("Dialogのテスト(メインウインドウ)"); $window->set_border_width(5); my $vbox = Gtk2::VBox->new(); $window->add($vbox); my $label = Gtk2::Label->new("各種コントロールのテストをします"); $vbox->add($label); # Entryのテスト my $hbox = Gtk2::HBox->new(); $vbox->add($hbox); my $entry = Gtk2::Entry->new(); $entry->set_text("サンプル文字列"); $entry->set_width_chars(30); $hbox->add($entry); my $button_opendlg = Gtk2::Button->new("Entry"); $button_opendlg->signal_connect("clicked" => sub { $strInput = $entry->get_text(); if(InputDialog_Entry($window, \$strInput, "文字列を入力:" ) == '1') { $entry->set_text($strInput); } else { $entry->set_text("Cancelが押されました"); } } ); $hbox->add($button_opendlg); # 閉じるボタン my $button_cancel = Gtk2::Button->new("プログラム終了"); $button_cancel->signal_connect("clicked" => sub { Gtk2->main_quit; }); $vbox->add($button_cancel); $window->show_all(); Gtk2->main(); return(0); } sub InputDialog_Entry { my $window_main = shift; # 関数の引数(親ウインドウのハンドル) my $ref_strInput = shift; # 関数の引数(参照渡し。テキストボックスの文字列を返す) my $sMessage = shift; # 関数の引数(メッセージとして表示する文字列) my $nResult = 0; # 戻り値(OK=1, Cancel=0) my $dialog = Gtk2::Dialog->new("Entryコントロールのテスト", $window_main, ['destroy-with-parent'], 'gtk-cancel' => 'cancel', 'gtk-ok' => 'ok'); # 水平ボックスを、DialogのビルトインのVBoxの中に配置。 my $hbox = Gtk2::HBox->new(); $hbox->set_border_width(10); # コントロール周囲の余白設定 $dialog->vbox->add($hbox); # プロンプト文字列とテキストボックスを水平に配置 my $label = Gtk2::Label->new($sMessage); $hbox->add($label); my $entry = Gtk2::Entry->new; $entry->set_text($$ref_strInput); $entry->set_width_chars(50); $hbox->pack_start($entry, 0, 0, 0); # ダイアログの余白があっても自動拡張しない $dialog->set_default_response ('ok'); $dialog->show_all(); # ダイアログの応答ループ my $response = $dialog->run(); if($response eq 'ok') { $nResult = 1; $$ref_strInput = $entry->get_text(); } else{$nResult = 0;} $dialog->destroy; return($nResult); }

■ コンボボックスでの選択ダイアログボックス

20100626-gdk2-combobox.png

#!/usr/bin/perl use strict; use warnings; use utf8; use Gtk2 qw/-init/; binmode( STDOUT, ":utf8" ); # "Wide character in print at ..." 警告を抑止 MainDialog(); exit; sub MainDialog { my $strInput = ""; # ダイアログに渡す文字列(リファレンス) my $window; # メインウインドウ $window = Gtk2::Window->new('toplevel'); $window->signal_connect( "destroy" => sub { Gtk2::main_quit; } ); # ウインドウの閉じるボタンの処理 $window->set_title("Dialogのテスト(メインウインドウ)"); $window->set_border_width(5); my $vbox = Gtk2::VBox->new(); $window->add($vbox); my $label = Gtk2::Label->new("各種コントロールのテストをします"); $vbox->add($label); # ComboBoxのテスト my $hbox = Gtk2::HBox->new(); $vbox->add($hbox); my $entry = Gtk2::Entry->new(); $entry->set_text("サンプル文字列"); $entry->set_width_chars(30); $hbox->add($entry); my $button_opendlg = Gtk2::Button->new("ComboBox"); $button_opendlg->signal_connect("clicked" => sub { $strInput = $entry->get_text(); if(InputDialog_ComboBox($window, \$strInput, "ひとつ選択:" ) == '1') { $entry->set_text($strInput); } else { $entry->set_text("Cancelが押されました"); } } ); $hbox->add($button_opendlg); # 閉じるボタン my $button_cancel = Gtk2::Button->new("プログラム終了"); $button_cancel->signal_connect("clicked" => sub { Gtk2->main_quit; }); $vbox->add($button_cancel); $window->show_all(); Gtk2->main(); return(0); } sub InputDialog_ComboBox { my $window_main = shift; # 関数の引数(親ウインドウのハンドル) my $ref_strInput = shift; # 関数の引数(参照渡し。テキストボックスの文字列を返す) my $sMessage = shift; # 関数の引数(メッセージとして表示する文字列) my $nResult = 0; # 戻り値(OK=1, Cancel=0) my $dialog = Gtk2::Dialog->new("ComboBoxコントロールのテスト", $window_main, ['destroy-with-parent'], 'gtk-cancel' => 'cancel', 'gtk-ok' => 'ok'); # 水平ボックスを、DialogのビルトインのVBoxの中に配置。 my $hbox = Gtk2::HBox->new(); $hbox->set_border_width(10); # コントロール周囲の余白設定 $dialog->vbox->add($hbox); # プロンプト文字列とコンボボックスを水平に配置 my $label = Gtk2::Label->new($sMessage); $hbox->add($label); my $combobox = Gtk2::ComboBox->new_text(); $combobox->append_text("Windows"); $combobox->append_text("MacOS X"); $combobox->append_text("Linux"); $combobox->append_text("Free BSD"); $combobox->set_active(2); $hbox->add($combobox); $dialog->set_default_response ('ok'); $dialog->show_all(); # ダイアログの応答ループ my $response = $dialog->run(); if($response eq 'ok') { $nResult = 1; # $$ref_strInput = $combobox->get_active(); $$ref_strInput = $combobox->get_active_text(); } else{$nResult = 0;} $dialog->destroy; return($nResult); }


■ ファイル、ディレクトリ選択ダイアログボックス

20100626-gdk2-file.png

#!/usr/bin/perl use strict; use warnings; use utf8; use Gtk2 qw/-init/; binmode( STDOUT, ":utf8" ); # "Wide character in print at ..." 警告を抑止 MainDialog(); exit; sub MainDialog { my $strInput = ""; # ダイアログに渡す文字列(リファレンス) my $window; # メインウインドウ $window = Gtk2::Window->new('toplevel'); $window->signal_connect( "destroy" => sub { Gtk2::main_quit; } ); # ウインドウの閉じるボタンの処理 $window->set_title("Dialogのテスト(メインウインドウ)"); $window->set_border_width(5); my $vbox = Gtk2::VBox->new(); $window->add($vbox); my $label = Gtk2::Label->new("各種コントロールのテストをします"); $vbox->add($label); # FileChooserDialog(open)のテスト(テキストボックスとボタンを水平配置する) my $hbox_filechooser = Gtk2::HBox->new(); $vbox->add($hbox_filechooser); my $entry_filechooser = Gtk2::Entry->new(); $entry_filechooser->set_text("/home"); $entry_filechooser->set_width_chars(30); $hbox_filechooser->add($entry_filechooser); my $button_opendlg_filechooser = Gtk2::Button->new("FileChooserDialog(open)"); $button_opendlg_filechooser->signal_connect("clicked" => sub { $strInput = $entry_filechooser->get_text(); if(InputDialog_FileChooser($window, \$strInput, "open", "ファイルを選択してください" ) == '1') { $entry_filechooser->set_text($strInput); } else { $entry_filechooser->set_text("Cancelが押されました"); } } ); $hbox_filechooser->add($button_opendlg_filechooser); # FileChooserDialog(save)のテスト(テキストボックスとボタンを水平配置する) my $hbox_filechooser2 = Gtk2::HBox->new(); $vbox->add($hbox_filechooser2); my $entry_filechooser2 = Gtk2::Entry->new(); $entry_filechooser2->set_text("/home"); $entry_filechooser2->set_width_chars(30); $hbox_filechooser2->add($entry_filechooser2); my $button_opendlg_filechooser2 = Gtk2::Button->new("FileChooserDialog(save)"); $button_opendlg_filechooser2->signal_connect("clicked" => sub { $strInput = $entry_filechooser2->get_text(); if(InputDialog_FileChooser($window, \$strInput, "save", "ファイルを選択してください" ) == '1') { $entry_filechooser2->set_text($strInput); } else { $entry_filechooser2->set_text("Cancelが押されました"); } } ); $hbox_filechooser2->add($button_opendlg_filechooser2); # FileChooserDialog(select-folder)のテスト(テキストボックスとボタンを水平配置する) my $hbox_filechooser3 = Gtk2::HBox->new(); $vbox->add($hbox_filechooser3); my $entry_filechooser3 = Gtk2::Entry->new(); $entry_filechooser3->set_text("/home"); $entry_filechooser3->set_width_chars(30); $hbox_filechooser3->add($entry_filechooser3); my $button_opendlg_filechooser3 = Gtk2::Button->new("FileChooserDialog(select-folder)"); $button_opendlg_filechooser3->signal_connect("clicked" => sub { $strInput = $entry_filechooser3->get_text(); if(InputDialog_FileChooser($window, \$strInput, "select-folder", "ファイルを選択してください" ) == '1') { $entry_filechooser3->set_text($strInput); } else { $entry_filechooser3->set_text("Cancelが押されました"); } } ); $hbox_filechooser3->add($button_opendlg_filechooser3); # 閉じるボタン my $button_cancel = Gtk2::Button->new("プログラム終了"); $button_cancel->signal_connect("clicked" => sub { Gtk2->main_quit; }); $vbox->add($button_cancel); $window->show_all(); Gtk2->main(); return(0); } sub InputDialog_FileChooser { my $window_main = shift; # 関数の引数(親ウインドウのハンドル) my $ref_strInput = shift; # 関数の引数(参照渡し。テキストボックスの文字列を返す) my $strMode = shift; # 関数の引数(ダイアログのモード。open, save, select-folder, create-folderのいづれか) my $sMessage = shift; # 関数の引数(メッセージとして表示する文字列) my $nResult = 0; # 戻り値(OK=1, Cancel=0) my $dialog = Gtk2::FileChooserDialog->new("FileChooserDialog(open)のテスト", $window_main, $strMode, 'gtk-cancel' => 'cancel', 'gtk-ok' => 'ok'); $dialog->set_current_folder($$ref_strInput); if($strMode ne "select-folder" && $strMode ne "create-folder") { # ファイル表示のフィルタ my $filter_text = Gtk2::FileFilter->new(); $filter_text->set_name("テキストファイル"); $filter_text->add_mime_type("text/*"); $dialog->add_filter($filter_text); my $filter_all = Gtk2::FileFilter->new(); $filter_all->set_name("全てのファイル"); $filter_all->add_pattern("*"); $dialog->add_filter($filter_all); } # 保存モードの時は、「無題.txt」と表示する if($strMode eq "save"){ $dialog->set_current_name("無題.txt"); } # ダイアログの応答ループ my $response = $dialog->run(); if($response eq 'ok') { $nResult = 1; $$ref_strInput = $dialog->get_filename(); } else{$nResult = 0;} $dialog->destroy; return($nResult); }


■ 色の選択ダイアログボックス

20100626-gdk2-color.png

#!/usr/bin/perl use strict; use warnings; use utf8; use Gtk2 qw/-init/; binmode( STDOUT, ":utf8" ); # "Wide character in print at ..." 警告を抑止 MainDialog(); exit; sub MainDialog { my $strInput = ""; # ダイアログに渡す文字列(リファレンス) my $window; # メインウインドウ $window = Gtk2::Window->new('toplevel'); $window->signal_connect( "destroy" => sub { Gtk2::main_quit; } ); # ウインドウの閉じるボタンの処理 $window->set_title("Dialogのテスト(メインウインドウ)"); $window->set_border_width(5); my $vbox = Gtk2::VBox->new(); $window->add($vbox); my $label = Gtk2::Label->new("各種コントロールのテストをします"); $vbox->add($label); # colorselectionDialogのテスト(テキストボックスとボタンを水平配置する) my $hbox = Gtk2::HBox->new(); $vbox->add($hbox); my $entry = Gtk2::Entry->new(); $entry->set_text("808080"); $entry->set_width_chars(30); $hbox->add($entry); my $button_opendlg = Gtk2::Button->new("ColorSelection"); $button_opendlg->signal_connect("clicked" => sub { $strInput = $entry->get_text(); if(InputDialog_ColorSelection($window, \$strInput, "ファイルを選択してください" ) == '1') { $entry->set_text($strInput); } else { $entry->set_text("Cancelが押されました"); } } ); $hbox->add($button_opendlg); # 閉じるボタン my $button_cancel = Gtk2::Button->new("プログラム終了"); $button_cancel->signal_connect("clicked" => sub { Gtk2->main_quit; }); $vbox->add($button_cancel); $window->show_all(); Gtk2->main(); return(0); } sub InputDialog_ColorSelection { my $window_main = shift; # 関数の引数(親ウインドウのハンドル) my $ref_strInput = shift; # 関数の引数(参照渡し。テキストボックスの文字列を返す) my $sMessage = shift; # 関数の引数(メッセージとして表示する文字列) my $nResult = 0; # 戻り値(OK=1, Cancel=0) my $dialog = Gtk2::ColorSelectionDialog->new("ColorSelectionDialogのテスト"); my($r, $g, $b) = convert_hex_to_color($$ref_strInput); my $color = Gtk2::Gdk::Color->new($r,$g,$b); $dialog->colorsel->set_current_color($color); $dialog->show_all(); # ダイアログの応答ループ my $response = $dialog->run(); if($response eq 'ok') { $nResult = 1; $color = $dialog->colorsel->get_current_color(); $$ref_strInput = sprintf("%02X%02X%02X", ($color->red /256), ($color->green /256), ($color->blue /256)); } else{$nResult = 0;} $dialog->destroy; return($nResult); } sub convert_hex_to_color { my ($colour) = @_; my ($red, $green, $blue) = $colour =~ /(..)(..)(..)/; $red = hex($red)*256; $green = hex($green)*256; $blue = hex($blue)*256; return ($red, $green, $blue); }