19 мая 2009 г.

Базовые элементы интерфейса. Часть 1.

Вы уже знаете, как создавать окно и помещать в него виджеты. Сегодня я расскажу о нескольких элементах интерфейса (виджетах) и о соответствующих им сигналах, которые говорят программе о действиях пользователя.


  1. GtkButton(). Операционная система отображает данный виджет в виде кнопки. Она выглядит примерно так:

    Первым параметром этому классу передаётся текст, который будет помещён на кнопку. Это может быть и не одна строка. Можно передать такой параметр:
    "Строка1\nСтрока2\nСтрока3"
    И тогда на кнопке будет располагаться многострочный текст.
    Второй параметр указывает, обрабатывать ли комбинации клавиш, типа Alt+К, для нажатия на кнопку. По умолчанию этот параметр имеет значени TRUE.

    GtkButton() имеет несколько сигналов, но интерес представляют только три:

    • clicked - срабатывает в момент отпускания нажатой кнопки.

    • pressed - срабатывает в момент нажатия на кнопку. Первые два сигнала пракически равносильны, но я предпочитаю использовать 'clicked', т.к. он предоставляет пользователю возможность передумать уже после нажатия на кнопку.

    • enter - этот сигнал срабатывает в момент наведения указателя мыши на кнопку.

    $button->connect('clicked', 'on_button');
     
    function on_button($button)
    {
    echo $button->get_label()."\n";
    }
    Здесь я использовал метод connect() вместо connect_simple(). Он отличается только тем, что первым параметром автоматически передаёт функции много дополнительной информации о виджете (можете сами посмотреть, насколько много - print_r($button);). Данная функция вернёт текст, расположенный на кнопке.

  2. GtkEntry(). Этот виджет представляет из себя обычное поле для ввода текста.

    Первым параметром ему передаётся текст, расположенный в поле по умолчанию. Вторым параметром указывается максимальное количество символов в поле.

    GtkEntry() также имеет несколько видов сигналов, но я раскажу только об одном.

    • activate - срабатывает, если нажать Enter при вводе текста. Зачастую, при заполнении поля GtkEntry() бывает удобно нажать Enter и ожидать, что программа обработает введённые данные. Именно это и делает данный сигнал.

    $entry->connect('activate', 'on_entry');
     
    function on_entry($entry)
    {
    echo $entry->get_text()."\n";
    }
    Здесь для получения введённого текста используется метод get_text().

Полный код программы:
<?php
 
$window = new GtkWindow();
$window->set_size_request(200, -1);
$window->set_position(Gtk::WIN_POS_CENTER);
$window->connect_simple('destroy', array('Gtk', 'main_quit'));
 
$vbox = new GtkVBox();
 
/**
* Кнопка.
*/

$button = new GtkButton('_Кнопка', TRUE);
$button->connect('clicked', 'on_button');
 
function on_button($button)
{
echo $button->get_label()."\n";
}
 
// Пустые GtkLabel() используются для визуального
// отделения виджетов друг от друга.
$vbox->pack_start(new GtkLabel(), FALSE, FALSE);
$vbox->pack_start($button, FALSE, FALSE);
 
/**
* Поле ввода.
*/

$entry = new GtkEntry('Текст', 10);
$entry->connect('activate', 'on_entry');
 
function on_entry($entry)
{
echo $entry->get_text()."\n";
}
 
$vbox->pack_start(new GtkLabel(), FALSE, FALSE);
$vbox->pack_start($entry, FALSE, FALSE);
$vbox->pack_start(new GtkLabel(), FALSE, FALSE);
 
$window->add($vbox);
$window->show_all();
Gtk::main();
 
?>

6 комментариев:

valdays комментирует...

$entry->connect('activate', 'on_entry');

я вот хотел уточнить... 'on_entry' это имя функции, которая будет обрабатывать событие и может быть указана любая?

Shecspi комментирует...

Да, конечно. Имя функции Вы выбираете самостоятельно по Вашему усмотрению. Главное не забыть объявить эту функцию.

Nick комментирует...

А параметры этой функции передавать можно?

Shecspi комментирует...

Да, параметры указываются в третьем и следующих параметрах. Пример:
$entry->connect('activate', 'on_entry', 'Shecspi', 'php-gtk');
function on_entry($widget, $param1, $param2)
{
echo $param1.' - '.$param2;
}

zloiia комментирует...

И такой вопрос. Насколько я понял, в функции я могу менять "реакцию" кнопки на событие. Для примера написал такую вот простую программу



$window=new GtkWindow();
$window->connect_simple('destroy', array('Gtk', 'main_quit'));
$button=new GtkButton("_Старт", TRUE);
$button->connect_simple('clicked', 'stop');
$window->add($button);
$window->show_all();
Gtk::main();

function stop()
{
global $button;
$button->set_label("_Стоп");
$button->connect_simple('clicked', 'start');
}

function start()
{
global $button;
$button->set_label("_Старт");
$button->connect_simple('clicked', 'stop');
}



при первых нажатиях все работает замечательно. Но чем больше раз я нажимаю, тем больше времени уходит на обработку и в один прекрасный момент программа виснет. И никаких сообщений об ошибках. В чем может быть проблема?

LegioNemesis комментирует...

zloiia
Задавайте вопросы в группе лучше, Shecspi теперь ответит нескоро.
По вашему вопросу. Думаю, что для реализации паузы, как у вас, лучше подойдёт GtkToggleButton
http://shecspi.blogspot.com/2009/06/3.html
В Вашей реализации, по всей видимости, течёт память.