Window programming in linux

Создаем приложение используя GTK в Линуксе

Разрабатывать приложения в Линуксе можно с помощью фреймворка GTK. Эта библиотека предназначенная для построения графического интерфейса пользователя. GTK — это свободное программное обеспечение, которое распространяется по лицензии GNU LGPL, что позволяет создавать как бесплатные так и коммерческие приложения.

С документациею и описанием библиотеки, Вы можете ознакомиться по следующей ссылке: https://www.gtk.org

Перед написанием приложения необходимо подготовить среду разработки. Для этих целей буду использовать ОС Ubuntu 22.04. Так как приложение будет разрабатываться на языке программирования Си необходимо установить необходимые пакеты и компилятор.

Откройте терминал от имени пользователя root и введите следующую команду:

sudo apt-get install build-essential

Также нам необходимо установить пакеты GTK для разработки приложения. Вводим следующую команду в терминале:

sudo apt-get install -y libgtk-3-dev

Теперь все готово для написания первого приложения. Открываем любой текстовый редактор и пишем следующий код:

#include int main (int argc, char *argv[])

Этот код создает окно. Но прежде чем выполнить приложение, давайте разберемся немного с кодом.
#include — здесь мы подключаем библиотеку gtk. Без этой библиотеки не будет работать графическое окно и мы не сможем запустить приложение;
GtkWidget *window; — задаем имя/метку окна;
window = gtk_window_new(GTK_WINDOW_TOPLEVEL); — эта строка создает стандартное окно с рамкой;
gtk_widget_show(window); — отображаем окно на дисплее.

Теперь давайте запустим приложение. Я сохранил код приложения в файле ex1.c в домашней папки.
Открывает терминал и вводим следующие команды:

gcc ex1.c -o ex1 `pkg-config —cflags —libs gtk+-3.0

Теперь давайте улучшим код и создадим текстовую метку.

#include int main (int argc, char *argv[])

GtkWidget *label1; — задаем имя текстовой метки;
label1 = gtk_label_new(«Hello! My first Program»); — создаем текстовую метку;
gtk_container_add(GTK_CONTAINER(window), label1); — эта строка кода добавляет метку в контейнер;
gtk_widget_show(label1); — отображаем метку в окне.

Надеюсь эта публикация была полезная. Так как фреймворк GTK имеет очень много полезных и интересных функций, что не дает возможности объяснить все в одной публикации.

Источник

Window programming in linux

Библиотека сайта rus-linux.net

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

  • реализация алгоритмов цифровой обработки сигналов (DSP): быстрые спектральные преобразования (FFT и другие), вэйвлеты, авторегрессионные разложения. ;
  • обработка аудио-потоков (пакеты: sox, ogg, speex и другие);
  • задачи IP-телефонии, SIP протокола, реализация разнообразных программных SoftSwitch;

Это сравнительный ряд автономных областей развития приведен как пример таких частных классов, одним из которых является и разработка GUI приложений. И как частный класс, со своей спецификой инструментов и средств, он не заслуживал бы отдельного упоминания, если бы не одно обстоятельство — принципиально отличающееся, диаметрально противоположное отношение к GUI в операционных системах семейства Windows и в UNIX (и в Linux, как его частный вид):

  • В Windows каждое приложение является принципиально GUI, неотъемлемым атрибутом любого приложения в Win32 API (низкого уровня) является главное окно приложения, уже само приложение «вяжется» вокруг его главного окна. Операционная система регистрирует классы окон и уже далее к ним соотносит конкретные приложения. Не может существовать приложения (взаимодействующего с пользователем, не системные службы) без окна, с этим были связаны и первоначальные сложности Windows в реализации консольных (терминальных) приложений.
  • в UNIX картина принципиально обратная: первичным является приложение, которое, по умолчанию, является консольным, текстовым, вся графическая система не является составной частью операционной системы, а является надстройкой пользовательского уровня. Чаще всего такой графической надстройкой является X11 (в реализации Xorg или X11R5), но и это не обязательно: практиковались и другие графические системы, хороший пример тому графические системы Qwindow, а затем Photon в операционной системе QNX, сосуществующие там одновременно с X11.
  • Показательно в этом смысле то, что вся оригинальная часть реализации X11 работает в пространстве пользователя, не в привилегированном режиме ядра (супервизора): работа с аппаратурой видеоадаптеров, устройствами ввода и другое. Отдельные реализации (видеосистемы NVIDIA или ATI Radeon) могут быть реализованы в режиме ядра (модули), но это а) сторонние относительно X11 разработки, и б) решение вопросов только производительности.
Читайте также:  Как перезагрузить linux mint через терминал

Из-за обозначенной специфики, разработка GUI приложений в UNIX (Linux) принципиально отличается:

  • вся работа GUI приложений ведётся через промежуточные слои (библиотеки) пользовательского уровня;
  • из-за того, что это ординарный пользовательский уровень, для разработчика предлагается широкий спектр альтернативных инструментов (библиотек), практически равнозначных, и конкурирующих друг с другом: Xlib, GTK+, Qt, wxWorks и многие другие.
  • базовый API работы с X11 предоставляет Xlib, все другие используют уже её функционал, как это показано на рисунке.

  • разработчик имеет возможность широкого выбора тех уровня и инструментов, которые он предполагает использовать, начиная от Xlib и выше (хотя уровень Xlib и слишком низок и работа с ним громоздкая).

Из-за названной специфики GUI приложений в Linux, все они, независимо от используемых средств создания, имеют абсолютно сходную структуру. Рассмотрим, для сравнения, код нескольких простейших GUI приложений, подготовленных с помощью различных инструментов. Важнейшей задачей такой экспозиции будут команды компиляции и сборки, чтобы, исходя из таких примеров, показать возможность начать создавать свои собственные GUI приложения.

Средства Xlib (архив Xlib.tgz ):

#include #include #include #include #include extern int errno; int main( void ) < Display *d; Window w; XEvent e; char *msg = "Hello, World!"; int s; if( ( d = XOpenDisplay( getenv("DISPLAY" ) ) ) == NULL ) < // Соединиться с X сервером, printf( "Can't connect X server: %s\n", strerror( errno ) ); exit( 1 ); >s = DefaultScreen( d ); w = XCreateSimpleWindow( d, RootWindow( d, s ), // Создать окно 10, 10, 200, 200, 1, BlackPixel( d, s ), WhitePixel( d, s ) ); XSelectInput( d, w, ExposureMask | KeyPressMask ); // На какие события будем реагировать? XMapWindow( d, w ); // Вывести окно на экран while( 1 ) < // Бесконечный цикл обработки событий XNextEvent( d, &e ); if( e.type == Expose ) < // Перерисовать окно XFillRectangle( d, w, DefaultGC( d, s ), 20, 20, 10, 10 ); XDrawString( d, w, DefaultGC( d, s ), 50, 50, msg, strlen( msg ) ); >if( e.type == KeyPress ) // При нажатии кнопки - выход break; > XCloseDisplay( d ); // Закрыть соединение с X сервером return 0; >

Средства GTK+ (архив GTK+.tgz ):

# include /* Подключаем библиотеку GTK+ */ int main( int argc, char *argv[] ) < //Объявляем виджеты: GtkWidget *label; // Метка GtkWidget *window; // Главное окно gtk_init( &argc, &argv ); // Инициализируем GTK+ window = gtk_window_new( GTK_WINDOW_TOPLEVEL ); // Создаем главное окно gtk_window_set_title( GTK_WINDOW( window ), // Устанавливаем заголовок окна "Здравствуй, мир!"); label = gtk_label_new( "Здравствуй, мир!" ); // Создаем метку с текстом gtk_container_add( GTK_CONTAINER( window ), label ); // Вставляем метку в главное окно gtk_widget_show_all( window ); // Показываем окно вместе с виджетами g_signal_connect( G_OBJECT( window ), "destroy", // Соединяем сигнал завершения с выходом G_CALLBACK( gtk_main_quit ), NULL ); gtk_main(); // Приложение переходит в цикл ожидания return 0; >

$ gcc gtk.c -o gtk `pkg-config —cflags —libs gtk+-2.0`

Читайте также:  What is best linux server

Средства Qt (архив Qt.tgz ):

Средства Qt предполагают написание приложений на языке С++, и имеют развитый инструментарий, в частности, построения сценария сборки приложения. Создадим в рабочем каталоге (изначально пустом) файл исходного кода приложения с произвольным именем:

#include #include int main( int argc, char** argv )

Теперь проделываем последовательно:

$ ls index.cc $ qmake -project $ ls index.cc Qt.pro $ qmake $ ls index.cc Makefile Qt.pro

Исходя из «подручных» файлов исходных кодов, у нас сгенерировался файл проекта и, далее, сценарий сборки ( Makefile ). Далее проделываем традиционную сборку, а заодно и посмотрим опции компиляции и сборки, которые нам сгенерировал проект:

g++ -c -pipe -Wall -W -O2 -g -pipe -Wall -Wp,-D_FORTIFY_SOURCE=2 -fexceptions -fstack-protector —param=ssp-buffer-size=4 -m32 -march=i686 -mtune=atom -fasynchronous-unwind-tables

g++ -o Qt index.o -L/usr/lib/qt-3.3/lib -lqt-mt -lXext -lX11 -lm

index.cc index.o Makefile Qt Qt.pro

Средства wxWidgets (архив wxWidgets.tgz):

#include class Simple : public wxFrame < public: Simple( const wxString& title >; Simple::Simple( const wxString& title ) : wxFrame( NULL, wxID_ANY, title, wxDefaultPosition, wxSize( 250, 150 ) ) < Centre(); >class MyApp : public wxApp < public: virtual bool OnInit(); >; bool MyApp::OnInit() < Simple *simple = new Simple( wxT( "Simple" ) ); simple->Show(true); // старт петли обработки событий return true; > IMPLEMENT_APP(MyApp ) // этот макрос реализует функцию main() в приложениях wxWidgets, // скрывая подробности главного цикла ожидания события.

$ g++ simple.cc `wx-config —cxxflags` `wx-config —libs` -o simple

Средства GLUT (архив glut.tgz):

OpenGL Utility Toolkit, как и следует из названия, это средства использования технологии OpenGL в приложениях, которая требует определённой поддержки со стороны видео оборудования.

#include void Draw( void ) < glClear( GL_COLOR_BUFFER_BIT ); glColor3f( 0.0f, 0.0f, 1.0f ); glLineWidth( 1 ); glBegin( GL_LINES ); glVertex2f( 0, 0.5f ); glVertex2f( 0, -0.5f ); glEnd(); glFlush(); >int main( int argc, char *argv[] )

$ gcc glut.c -o glut -lX11 -lglut

То, что показано выше, это фактически не приложения, а скелеты приложений, но они позволяют: а) сравнить подобие всех GUI технологий в X11, и б) быть отправной точкой для сборки более содержательных GUI приложений. Показано только несколько GUI технологий, применяемых в X11 (большинство из них являются кросс-платформенными, и применимы в большинстве существующих операционных систем). Каждая из этих технологий, а названы только немногие из значительно большего числа, присутствующих в UNIX, могут быть полной альтернативой любой другой из этого же ряда, они взаимно заменимы, и даже взаимно дополняемые.

В данной статье были показаны образцы кода GUI приложений. Естественно, визуальные образы таких приложений строятся не путём непосредственного кодирования, а при использовании некоторых визуальных построителей, в составе тех или иных интегрированных средств разработки (IDE).

Источник

Programming: Simple X11 Code Sample for Linux and Mac OS X

X Window System, Mac OS X

X Window (or X11) is the low level windowing system (the equivalent of the Win32 API under Windows) available with Unix / Linux and Mac OS X. According to this page, X11 is an option under Mac OS X (on my Lion-based system, X11 is available by default). Desktop environments like KDE or Gnome are built on top of X11. Then using X11 API can be an interesting solution if you need to quickly test an piece of code under Linux and Max OS X (it’s my case…).

Читайте также:  Права пользователей linux через консоль

And nice news, the compilation has the same syntax under both operating systems.

Here is the full source code of a simple X11 app that creates a X window and displays some basic information about the system. To quit the app, two ways are available:

  • 1 – ESC key. This is the simplest way to stop the app. Just catch the KeyPress event and test the presence of the XK_Escape code.
  • 2 – Window close button (the cross). Don’t know why, but it’s not obvious to manage the close button. Once you have found that the WM_DELETE_WINDOW
    message is the key of all your troubles, you can easily code the management of the close button.

To compile and link the code sample, just open a terminal in the folder of your source code (too easy under Linux, a bit less easy under Mac 😉 ) and type:

$ g++ xl01.cpp -o xl01 -I/usr/X11R6/include -I/usr/X11R6/include/X11 -L/usr/X11R6/lib -L/usr/X11R6/lib/X11 -lX11

X Window X11 app demo under Linux

Terminal, Linux Mint 10

Under Linux, you should see something like this:

X Window X11 app demo under Linux

X11 demo under Linux Mint 10

And under Mac OS X, you should see something like this:

X Window X11 app demo under Mac OS X

X11 demo under Mac OS X Lion

And now the full cross-platform source code that all of you are waiting for:

#include #include #include #include #include #include #include int main(int argc, char** argv) < Display* dpy = XOpenDisplay(NULL); if (dpy == NULL) < fprintf(stderr, "Cannot open display\n"); exit(1); >int s = DefaultScreen(dpy); Window win = XCreateSimpleWindow(dpy, RootWindow(dpy, s), 10, 10, 660, 200, 1, BlackPixel(dpy, s), WhitePixel(dpy, s)); XSelectInput(dpy, win, ExposureMask | KeyPressMask); XMapWindow(dpy, win); #if defined(__APPLE_CC__) XStoreName(dpy, win, "Geeks3D.com - X11 window under Mac OS X (Lion)"); #else XStoreName(dpy, win, "Geeks3D.com - X11 window under Linux (Mint 10)"); #endif Atom WM_DELETE_WINDOW = XInternAtom(dpy, "WM_DELETE_WINDOW", False); XSetWMProtocols(dpy, win, &WM_DELETE_WINDOW, 1); bool uname_ok = false; struct utsname sname; int ret = uname(&sname); if (ret != -1) < uname_ok = true; >XEvent e; while (1) < XNextEvent(dpy, &e); if (e.type == Expose) < int y_offset = 20; #if defined(__APPLE_CC__) const char* s1 = "X11 test app under Mac OS X Lion"; #else const char* s1 = "X11 test app under Linux"; #endif const char* s2 = "(C)2012 Geeks3D.com"; XDrawString(dpy, win, DefaultGC(dpy, s), 10, y_offset, s1, strlen(s1)); y_offset += 20; XDrawString(dpy, win, DefaultGC(dpy, s), 10, y_offset, s2, strlen(s2)); y_offset += 20; if (uname_ok) < char buf[256] = ; sprintf(buf, "System information:"); XDrawString(dpy, win, DefaultGC(dpy, s), 10, y_offset, buf, strlen(buf)); y_offset += 15; sprintf(buf, "- System: %s", sname.sysname); XDrawString(dpy, win, DefaultGC(dpy, s), 10, y_offset, buf, strlen(buf)); y_offset += 15; sprintf(buf, "- Release: %s", sname.release); XDrawString(dpy, win, DefaultGC(dpy, s), 10, y_offset, buf, strlen(buf)); y_offset += 15; sprintf(buf, "- Version: %s", sname.version); XDrawString(dpy, win, DefaultGC(dpy, s), 10, y_offset, buf, strlen(buf)); y_offset += 15; sprintf(buf, "- Machine: %s", sname.machine); XDrawString(dpy, win, DefaultGC(dpy, s), 10, y_offset, buf, strlen(buf)); y_offset += 20; > XWindowAttributes wa; XGetWindowAttributes(dpy, win, &wa); int width = wa.width; int height = wa.height; char buf[128]=; sprintf(buf, "Current window size: %dx%d", width, height); XDrawString(dpy, win, DefaultGC(dpy, s), 10, y_offset, buf, strlen(buf)); y_offset += 20; > if (e.type == KeyPress) < char buf[128] = ; KeySym keysym; int len = XLookupString(&e.xkey, buf, sizeof buf, &keysym, NULL); if (keysym == XK_Escape) break; > if ((e.type == ClientMessage) && (static_cast(e.xclient.data.l[0]) == WM_DELETE_WINDOW)) < break; >> XDestroyWindow(dpy, win); XCloseDisplay(dpy); return 0; >

Источник

Оцените статью
Adblock
detector