lets see how it looks
This commit is contained in:
parent
02abf4f70a
commit
b6c508015f
1 changed files with 65 additions and 63 deletions
128
README.adoc
128
README.adoc
|
|
@ -1,6 +1,6 @@
|
||||||
= High level GTK3 bindings for the Nim programming language
|
= High level GTK3 bindings for the Nim programming language
|
||||||
(c) Stefan Salewski
|
(c) Stefan Salewski
|
||||||
Version 0.1 2017
|
//Version 0.1 2017
|
||||||
:experimental:
|
:experimental:
|
||||||
:imagesdir: http://ssalewski.de/tmp
|
:imagesdir: http://ssalewski.de/tmp
|
||||||
:source-highlighter: pygments
|
:source-highlighter: pygments
|
||||||
|
|
@ -10,8 +10,10 @@ Version 0.1 2017
|
||||||
:GIR: GObject-Introspection
|
:GIR: GObject-Introspection
|
||||||
:MAC: MacOSX
|
:MAC: MacOSX
|
||||||
|
|
||||||
(c) Stefan Salewski +
|
//(c) Stefan Salewski +
|
||||||
2017
|
//2017
|
||||||
|
|
||||||
|
TIP: A more fancy copy of this document with dark source code background is available at http://ssalewski.de/gintroreadme.html[GIntro README]
|
||||||
|
|
||||||
NOTE: This work is partly based on earlier works of J. Mansour and has been supported by A. Rumpf and other _Nim_ and _GTK/Gnome_ developers.
|
NOTE: This work is partly based on earlier works of J. Mansour and has been supported by A. Rumpf and other _Nim_ and _GTK/Gnome_ developers.
|
||||||
The `combinatorics` module was kindly provided by R. Behrends.
|
The `combinatorics` module was kindly provided by R. Behrends.
|
||||||
|
|
@ -37,33 +39,33 @@ are Windows and {MAC} and you desire a real native look and feel there, then you
|
||||||
Also, when you only need a minimal restricted GUI which is very easy to install on Windows and {MAC}, then you may find better suited packages
|
Also, when you only need a minimal restricted GUI which is very easy to install on Windows and {MAC}, then you may find better suited packages
|
||||||
in the Nim package repository. _Android OS_ is currently not supported by GTK at all.
|
in the Nim package repository. _Android OS_ is currently not supported by GTK at all.
|
||||||
|
|
||||||
While low level _Nim_ bindings for _GTK3_ are already available since a few years, this one is an attempt to
|
While low level Nim bindings for GTK3 are already available since a few years, this one is an attempt to
|
||||||
provide real high level bindings with full type safety, full _Garbage Collector_ (_GC_) support and an idiomatic
|
provide real high level bindings with full type safety, full _Garbage Collector_ (_GC_) support and an idiomatic
|
||||||
_application interface_ (_API_).
|
_Application Programming Interface_ (_API_)
|
||||||
|
|
||||||
The low level bindings available at https://github.com/ngtk3 where generated with the _Nim_ tool `c2nim` directly from the _C_ header files, are already tested
|
The low level bindings available at https://github.com/ngtk3 where generated with the Nim tool `c2nim` directly from the _C_ header files, are already tested
|
||||||
with some applications (https://github.com/ngtk3/NEd[NEd Nim Editor], https://github.com/StefanSalewski/nim-chess3[Chess Game])
|
with some applications (https://github.com/ngtk3/NEd[NEd Nim Editor], https://github.com/StefanSalewski/nim-chess3[Chess Game])
|
||||||
and generally work fine. Indeed missing _Garbage Collector_ support is generally not really a problem, as widgets are generally
|
and generally work fine. Indeed missing Garbage Collector support is generally not really a problem, as widgets are generally
|
||||||
put into containers and were automatically deleted together with its parents due to _GTK_'s reference counting.
|
put into containers and were automatically deleted together with its parents due to GTK's reference counting.
|
||||||
|
|
||||||
Still there can be some demand for really high level bindings -- so this repository tries to provide them.
|
Still there can be some demand for really high level bindings -- so this repository tries to provide them.
|
||||||
|
|
||||||
High level _GTK3_ bindings, as available for many other programming languages like _Python_, _Ruby_ or _D_ already,
|
High level GTK3 bindings, as available for many other programming languages like _Python_, _Ruby_ or _D_ already,
|
||||||
would have these advantages:
|
would have these advantages:
|
||||||
|
|
||||||
* full _Garbage Collector_ support -- you should never have to free resources manually
|
* full Garbage Collector support -- you should never have to free resources manually
|
||||||
* Widgets are _Nim_ objects, so inheritance and sub-classing can be used
|
* Widgets are Nim objects, so inheritance and sub-classing can be used
|
||||||
* full type safety -- no needs for casts or other unsafe and dangerous operations
|
* full type safety -- no needs for casts or other unsafe and dangerous operations
|
||||||
|
|
||||||
These high level bindings are based on _{GIR}_, an _XML_ based database like interface description. Compared to the _C_ header
|
These high level bindings are based on _{GIR}_, an _XML_ based database like interface description. Compared to the _C_ header
|
||||||
files this description gives us more and deeper information about data types and function calls, for example ownership transfer of objects and
|
files this description gives us more and deeper information about data types and function calls, for example ownership transfer of objects and
|
||||||
in or out direction of procedure variables, which makes writing the glue code much easier.
|
in or out direction of procedure variables, which makes writing the glue code much easier.
|
||||||
And it should work with no or minimal
|
And it should work with no or minimal
|
||||||
modifications also for the upcoming _GTK4_.
|
modifications also for the upcoming GTK4.
|
||||||
|
|
||||||
Unfortunately there are also some drawbacks:
|
Unfortunately there are also some drawbacks:
|
||||||
|
|
||||||
* The _Application Programmer Interface_ (API) will be different from what is known from _C API_, so using _C_ examples or _C_ tutorials is not really straight forward
|
* The Application Programming Interface (API) will be different from what is known from _C_ API, so using _C_ examples or _C_ tutorials is not really straight forward
|
||||||
* The high level source code will differ from available _C_ examples, so there would be a big demand for tutorials
|
* The high level source code will differ from available _C_ examples, so there would be a big demand for tutorials
|
||||||
* We need a lot of glue code, which has much room for bugs. So much testing is necessary.
|
* We need a lot of glue code, which has much room for bugs. So much testing is necessary.
|
||||||
* There is some overhead due to indirect calls, leading to some code size increase and minimal
|
* There is some overhead due to indirect calls, leading to some code size increase and minimal
|
||||||
|
|
@ -74,19 +76,19 @@ nim prefix.
|
||||||
|
|
||||||
== Current state of these bindings
|
== Current state of these bindings
|
||||||
|
|
||||||
We are still in an early stage, but it is already more than a proof of concept. _GTK_ and related libraries have many thousand of
|
We are still in an early stage, but it is already more than a proof of concept. GTK and related libraries have many thousand of
|
||||||
callable functions and nearly as many data types. Testing all that is nearly impossible for a small team with limited resources.
|
callable functions and nearly as many data types. Testing all that is nearly impossible for a small team with limited resources.
|
||||||
The initial approach was to generate low level
|
The initial approach was to generate low level
|
||||||
bindings, which looked similar to the ones generated by the `c2nim` tool from the _C_ headers. After that was done, we have associated all
|
bindings, which looked similar to the ones generated by the `c2nim` tool from the _C_ headers. After that was done, we have associated all
|
||||||
the _C_ structs and _GObject_ data types with _Nim_ proxy objects. A well defined relation between these proxy object and the low level _C_ data types
|
the _C_ structs and _GObject_ data types with Nim proxy objects. A well defined relation between these proxy object and the low level _C_ data types
|
||||||
should ensure fully automatic garbage collection. This is supported by smart type conversion, for example _C_ strings returned by `glib` library
|
should ensure fully automatic garbage collection. This is supported by smart type conversion, for example _C_ strings returned by `glib` library
|
||||||
are assigned to newly created _Nim_ strings, while the memory of the _C_ strings is automatically freed. For most cases this seems to work. But there
|
are assigned to newly created Nim strings, while the memory of the _C_ strings is automatically freed. For most cases this seems to work. But there
|
||||||
exists a few more complicated cases, for example functions may return whole arrays of _C_ strings or other non elementary data types,
|
exists a few more complicated cases, for example functions may return whole arrays of _C_ strings or other non elementary data types,
|
||||||
or function arguments or results may be so called _glists_,
|
or function arguments or results may be so called _glists_,
|
||||||
list structures of `glib` library. These cases can not be processed automatically but needs carefully manual investigations. And there may be still functions and data
|
list structures of `glib` library. These cases can not be processed automatically but needs carefully manual investigations. And there may be still functions and data
|
||||||
types missing: _{GIR}_ query gives us many thousand lines of _Nim_ interface code, and it is not really obvious if and what is missing.
|
types missing: {GIR} query gives us many thousand lines of Nim interface code, and it is not really obvious if and what is missing.
|
||||||
Some functions and data types are missing for sure -- at least some low level ones, which are considered unneeded for high level bindings by _{GIR}_.
|
Some functions and data types are missing for sure -- at least some low level ones, which are considered unneeded for high level bindings by _{GIR}_.
|
||||||
But maybe more is missing, we have to investigate that. Until now these bindings have been tested only for 64 bit _Linux_ systems with _GTK 3.22_.
|
But maybe more is missing, we have to investigate that. Until now these bindings have been tested only for 64 bit Linux systems with GTK 3.22.
|
||||||
|
|
||||||
These basic libraries are already partly tested:
|
These basic libraries are already partly tested:
|
||||||
|
|
||||||
|
|
@ -103,16 +105,16 @@ These basic libraries are already partly tested:
|
||||||
* Gdk
|
* Gdk
|
||||||
* Gtk
|
* Gtk
|
||||||
|
|
||||||
In best case it should be possible to add more _GObject_ based libraries to this list without larger modifications of the generator source code.
|
In best case it should be possible to add more GObject based libraries to this list without larger modifications of the generator source code.
|
||||||
Unfortunately the _cairo_ bindings provided by _{GIR}_ are only a minimal stub -- later we will have to extend it manually.
|
Unfortunately the bindings for the _cairo_ drawing library provided by {GIR} are only a minimal stub -- later we will have to extend it manually.
|
||||||
|
|
||||||
== How to try it out
|
== How to try it out
|
||||||
|
|
||||||
Of course you will need a working _Nim_ installation with a recent compiler version and you have to ensure that _GTK_ and related libraries are installed on your system. For some _Linux_
|
Of course you will need a working Nim installation with a recent compiler version and you have to ensure that GTK and related libraries are installed on your system. For some Linux
|
||||||
distributions which provide mainly pre-compiled software you may have to also install some _GTK_ related developer files.
|
distributions which provide mainly pre-compiled software you may have to also install some GTK related developer files.
|
||||||
|
|
||||||
This package now supports the _nimble package manager_, so ideally a plain `nimble install gintro` should do. But as this package does not
|
This package now supports the _Nimble Package Manager_, so ideally a plain `nimble install gintro` should do. But as this package does not
|
||||||
only provide some plain text files, but uses _{GIR}_ database query on your local computer to generate
|
only provide some plain text files, but uses {GIR} database query on your local computer to generate
|
||||||
binding files exactly matching your system, that does not work currently. We have to download the files, compile and execute
|
binding files exactly matching your system, that does not work currently. We have to download the files, compile and execute
|
||||||
the `gen.nim` generator program and finally to install the generated bindings modules on your computer as a _nimble package_.
|
the `gen.nim` generator program and finally to install the generated bindings modules on your computer as a _nimble package_.
|
||||||
|
|
||||||
|
|
@ -128,12 +130,12 @@ nimble install
|
||||||
|
|
||||||
NOTE: Nimble prepare should run for about 20 seconds, it compiles and executes the generator program `gen.nim`.
|
NOTE: Nimble prepare should run for about 20 seconds, it compiles and executes the generator program `gen.nim`.
|
||||||
Unfortunately we can not guarantee that the generator command will be able to really build all the
|
Unfortunately we can not guarantee that the generator command will be able to really build all the
|
||||||
desired modules. The built process highly depends on your _OS_ and installed _GTK_ version. For 64 bit _Linux_ systems
|
desired modules. The built process highly depends on your OS and installed GTK version. For 64 bit Linux systems
|
||||||
with _GTK 3.22_ and all required dependencies installed it should work. For never _GTK_ versions it may fail, when that _GTK_
|
with GTK 3.22 and all required dependencies installed it should work. For never GTK versions it may fail, when that GTK
|
||||||
release introduces for example new unknown data types like array containers. In that case manual fixes may be necessary.
|
release introduces for example new unknown data types like array containers. In that case manual fixes may be necessary.
|
||||||
The _{GIR}_ based built process generates bindings customized to the _OS_ where the generator is executed,
|
The {GIR} based built process generates bindings customized to the OS where the generator is executed,
|
||||||
so for older _GTK_ releases or a 32 bit system different files are created. Later we may also provide pre-generated
|
so for older GTK releases or a 32 bit system different files are created. Later we may also provide pre-generated
|
||||||
files for various _OS_ and _GTK_ versions, but building locally is preferred when possible.
|
files for various OS and GTK versions, but building locally is preferred when possible.
|
||||||
|
|
||||||
Now you can built `app0.nim` and launch it:
|
Now you can built `app0.nim` and launch it:
|
||||||
|
|
||||||
|
|
@ -145,11 +147,11 @@ nim c app0.nim
|
||||||
|
|
||||||
== A few basic examples
|
== A few basic examples
|
||||||
|
|
||||||
_GTK3_ programs can use still the old _GTK2_ design, where you first initialize the _GTK_ library, create your widgets and finally enter the _GTK_ main loop.
|
GTK3 programs can use still the old GTK2 design, where you first initialize the GTK library, create your widgets and finally enter the GTK main loop.
|
||||||
This style is still used in many tutorials as in http://zetcode.com/gui/gtk2/[Zetcode tutorial] or in the _GTK_ book of _A. Krause_.
|
This style is still used in many tutorials as in http://zetcode.com/gui/gtk2/[Zetcode tutorial] or in the GTK book of A. Krause.
|
||||||
Or you can use the new _GTK3 App style_, this is generally recommended by newer original _GTK_ documentation.
|
Or you can use the new _GTK3 App style_, this is generally recommended by newer original GTK documentation.
|
||||||
Unfortunately the _GTK3_ original documentation is mostly restricted to the _GTK3 API_ documentation, which is generally very good, but makes
|
Unfortunately the GTK3 original documentation is mostly restricted to the GTK3 API documentation, which is generally very good, but makes
|
||||||
it not really easy for beginners to start with _GTK_. _API_ docs and some basic introduction is available here:
|
it not really easy for beginners to start with GTK. API docs and some basic introduction is available here:
|
||||||
|
|
||||||
* https://www.gnome.org/
|
* https://www.gnome.org/
|
||||||
* https://www.gtk.org/
|
* https://www.gtk.org/
|
||||||
|
|
@ -158,9 +160,9 @@ it not really easy for beginners to start with _GTK_. _API_ docs and some basic
|
||||||
* https://developer.gnome.org/gtk3/stable/ch01s04.html#id-1.2.3.12.5
|
* https://developer.gnome.org/gtk3/stable/ch01s04.html#id-1.2.3.12.5
|
||||||
* https://developer.gnome.org/gnome-devel-demos/stable/c.html.en
|
* https://developer.gnome.org/gnome-devel-demos/stable/c.html.en
|
||||||
|
|
||||||
TIP: If you should decide to continue developing software with _GTK_, then you may consider installing the so called
|
TIP: If you should decide to continue developing software with GTK, then you may consider installing the so called
|
||||||
`devhelp` tool. It gives you easy and fast access to the _GTK API_ docs. For example, if you want to use a _Button Widget_ in your
|
`devhelp` tool. It gives you easy and fast access to the GTK API docs. For example, if you want to use a _Button Widget_ in your
|
||||||
_GUI_ and wants to learn more about related functions and signals, you just enter _Button_ in that tool and are guided to
|
GUI and wants to learn more about related functions and signals, you just enter _Button_ in that tool and are guided to
|
||||||
all the relevant information.
|
all the relevant information.
|
||||||
|
|
||||||
We start with a minimal traditional old style example, which should be familiar to most of us:
|
We start with a minimal traditional old style example, which should be familiar to most of us:
|
||||||
|
|
@ -187,12 +189,12 @@ proc main =
|
||||||
main()
|
main()
|
||||||
----
|
----
|
||||||
|
|
||||||
This is the traditional layout of _GTK2_ programs. When using this style then it is important to initialize the _GTK_ library by calling `gtk.init()`
|
This is the traditional layout of GTK2 programs. When using this style then it is important to initialize the GTK library by calling `gtk.init()`
|
||||||
at the very beginning. Then we create the desired widgets, connect signals, show all widgets and finally enter the _GTK_ main loop
|
at the very beginning. Then we create the desired widgets, connect signals, show all widgets and finally enter the GTK main loop
|
||||||
by calling `gtk.main`. About connecting signals we will learn more soon, for now it is only important that we have to connect to
|
by calling `gtk.main`. About connecting signals we will learn more soon, for now it is only important that we have to connect to
|
||||||
the destroy signal here to enable the user to terminate program execution by clicking the window close button.
|
the destroy signal here to enable the user to terminate program execution by clicking the window close button.
|
||||||
|
|
||||||
Now a really minimal but complete _App style_ example, which displays an empty window.
|
Now a really minimal but complete App style example, which displays an empty window.
|
||||||
|
|
||||||
NOTE: The source text of all these examples is contained in the examples directory. Unfortunately _github_
|
NOTE: The source text of all these examples is contained in the examples directory. Unfortunately _github_
|
||||||
seems to not allow to include that sources directly into this document, so there may be minimal
|
seems to not allow to include that sources directly into this document, so there may be minimal
|
||||||
|
|
@ -252,11 +254,11 @@ window.defaultSize = (width: 200, height: 200) # <6>
|
||||||
<5> tupel assignment
|
<5> tupel assignment
|
||||||
<6> tupel assignment with named members
|
<6> tupel assignment with named members
|
||||||
|
|
||||||
Well, that empty window is really not very interesting. The _GTK_ and _Gnome_ team provides some _GTK_ examples
|
Well, that empty window is really not very interesting. The GTK and Gnome team provides some GTK examples
|
||||||
at https://developer.gnome.org/gnome-devel-demos/.
|
at https://developer.gnome.org/gnome-devel-demos/.
|
||||||
The https://developer.gnome.org/gnome-devel-demos/3.22/c.html.en[C demos] seems to be most actual and complete,
|
The https://developer.gnome.org/gnome-devel-demos/3.22/c.html.en[C demos] seems to be most actual and complete,
|
||||||
and are easy to port to _Nim_. So we start with these,
|
and are easy to port to Nim. So we start with these,
|
||||||
but if you are familiar with the other listed languages, then you can try to port them to _Nim_ as well.
|
but if you are familiar with the other listed languages, then you can try to port them to Nim as well.
|
||||||
Let us start with https://developer.gnome.org/gnome-devel-demos/3.22/button.c.html.en as it is
|
Let us start with https://developer.gnome.org/gnome-devel-demos/3.22/button.c.html.en as it is
|
||||||
still short and easy to understand, but shows already some interesting topics.
|
still short and easy to understand, but shows already some interesting topics.
|
||||||
|
|
||||||
|
|
@ -328,13 +330,13 @@ main (int argc, char **argv)
|
||||||
|
|
||||||
----
|
----
|
||||||
|
|
||||||
Converting it to _Nim_ is straight forward with some basic _C_ and _Nim_ knowledge, and _Nim_ does not force us
|
Converting it to Nim is straight forward with some basic _C_ and Nim knowledge, and Nim does not force us
|
||||||
to convert its shape into all the classes known from pure _Object Orientated_ (_OO_) languages. We can either use the
|
to convert its shape into all the classes known from pure _Object Orientated_ (_OO_) languages. We can either use the
|
||||||
_Nim_ tool `c2nim` to help us with the conversion, or do it manually. Indeed `c2nim` can be very helpful by
|
Nim tool `c2nim` to help us with the conversion, or do it manually. Indeed `c2nim` can be very helpful by
|
||||||
converting _C_ sources to _Nim_. Most of the time it works well. Personally I generally pre-process _C_ files, for example
|
converting _C_ sources to Nim. Most of the time it works well. Personally I generally pre-process _C_ files, for example
|
||||||
by removing too strange `macros` and `defines, or by replacing strange constructs, like _C_ `for loops`, to simpler
|
by removing too strange `macros` and `defines, or by replacing strange constructs, like _C_ `for loops`, to simpler
|
||||||
ones like `while loops`. Then I apply `c2nim` to the _C_ file and finally manually compare the result line by line and
|
ones like `while loops`. Then I apply `c2nim` to the _C_ file and finally manually compare the result line by line and
|
||||||
fine tune the _Nim_ code. But for this short source text we may do all that manually and finally get something like
|
fine tune the Nim code. But for this short source text we may do all that manually and finally get something like
|
||||||
this:
|
this:
|
||||||
|
|
||||||
[[button.nim]]
|
[[button.nim]]
|
||||||
|
|
@ -366,15 +368,15 @@ main()
|
||||||
----
|
----
|
||||||
|
|
||||||
Again we have the basic shape already known from <<app0.nim>> example: `Main proc` creates the application, connect
|
Again we have the basic shape already known from <<app0.nim>> example: `Main proc` creates the application, connect
|
||||||
to the activate signal and finally runs the application. When _GTK_ launches the application and emits the `activate` signal, then
|
to the activate signal and finally runs the application. When GTK launches the application and emits the `activate` signal, then
|
||||||
our activate proc is called, which creates a main window containing a button widget. That button is again connected with a
|
our activate proc is called, which creates a main window containing a button widget. That button is again connected with a
|
||||||
signal, in this case named `clicked`. That signal is emitted by _GTK_ whenever that button is clicked with the mouse and results
|
signal, in this case named `clicked`. That signal is emitted by GTK whenever that button is clicked with the mouse and results
|
||||||
in a call of our provided `buttonClicked()` proc. The procs connected to signals are called _callbacks_ and generally got the widget
|
in a call of our provided `buttonClicked()` proc. The procs connected to signals are called _callbacks_ and generally got the widget
|
||||||
on which the signal was emitted as first parameter. They can also get a second optional parameter of arbitrary type -- we will
|
on which the signal was emitted as first parameter. They can also get a second optional parameter of arbitrary type -- we will
|
||||||
see that in a later example. This callback here gets only the button itself as parameter, and it's task is to reverse the
|
see that in a later example. This callback here gets only the button itself as parameter, and it's task is to reverse the
|
||||||
text displayed by the button. Not very interesting basically, but we are indeed using the _glib_ function `utf8Strreverse()`
|
text displayed by the button. Not very interesting basically, but we are indeed using the _glib_ function `utf8Strreverse()`
|
||||||
for this task. While that function internally works with `cstrings`, and in _C_ we have to free the memory of the returned `cstring`,
|
for this task. While that function internally works with `cstrings`, and in _C_ we have to free the memory of the returned `cstring`,
|
||||||
in our _Nim_ example that is done automatically by _Nim_'s _Garbage Collector_. When you compare our example carefully with the _C_ code,
|
in our Nim example that is done automatically by Nim's Garbage Collector. When you compare our example carefully with the _C_ code,
|
||||||
then you may notice a difference. The _C_ code passes the window containing the button as an additional parameter to the
|
then you may notice a difference. The _C_ code passes the window containing the button as an additional parameter to the
|
||||||
callback function, but that parameter is not really used. We simple ignore it here, as it is not used at all.
|
callback function, but that parameter is not really used. We simple ignore it here, as it is not used at all.
|
||||||
//and I assume that passing a widget in this way in our nim code
|
//and I assume that passing a widget in this way in our nim code
|
||||||
|
|
@ -382,12 +384,12 @@ callback function, but that parameter is not really used. We simple ignore it he
|
||||||
//working soon...
|
//working soon...
|
||||||
In one of the following examples you will learn how passing (nearly) arbitrary parameters in a type safe way is done.
|
In one of the following examples you will learn how passing (nearly) arbitrary parameters in a type safe way is done.
|
||||||
Another difference is, that the _C_ code returns an `integer` status value returned by `g_application_run()` to the _OS_. We
|
Another difference is, that the _C_ code returns an `integer` status value returned by `g_application_run()` to the _OS_. We
|
||||||
could do the same by using the `quit() proc` of _Nim_'s _OS_ module, but as that would give us no additional benefit, we simply ignore it.
|
could do the same by using the `quit() proc` of Nim's _OS_ module, but as that would give us no additional benefit, we simply ignore it.
|
||||||
|
|
||||||
TIP: The command `nim c sourcetext.nim` generates an executable which contains code for runtime checks and debugging,
|
TIP: The command `nim c sourcetext.nim` generates an executable which contains code for runtime checks and debugging,
|
||||||
which increases executable size and decreases performance.
|
which increases executable size and decreases performance.
|
||||||
After you have tested your software carefully, you may give the additional parameter `-d:release` to avoid this. For the `gcc` backend
|
After you have tested your software carefully, you may give the additional parameter `-d:release` to avoid this. For the `gcc` backend
|
||||||
you may additional enable _link time optimization_ (_LTO_), which reduces executable size further. To enable _LTO_ you may put
|
you may additional enable _Link Time Optimization_ (_LTO_), which reduces executable size further. To enable LTO you may put
|
||||||
a `nim.cfg` file in your sources directory with content like
|
a `nim.cfg` file in your sources directory with content like
|
||||||
|
|
||||||
----
|
----
|
||||||
|
|
@ -396,14 +398,14 @@ nimcache:"/tmp/$projectdir"
|
||||||
gcc.options.speed = "-march=native -O3 -flto -fstrict-aliasing"
|
gcc.options.speed = "-march=native -O3 -flto -fstrict-aliasing"
|
||||||
----
|
----
|
||||||
|
|
||||||
With that optimization, your executable sizes should be in the range of about 50 _kB_ only!
|
With that optimization, your executable sizes should be in the range of about 50 kB only!
|
||||||
|
|
||||||
=== Optional, type safe parameters for callbacks
|
=== Optional, type safe parameters for callbacks
|
||||||
|
|
||||||
The next example shows, how we can pass (nearly) arbitrary parameters to our connect procs.
|
The next example shows, how we can pass (nearly) arbitrary parameters to our connect procs.
|
||||||
We pass a string, an object from the stack, a reference to an object allocated on the heap
|
We pass a string, an object from the stack, a reference to an object allocated on the heap
|
||||||
and finally a widget (in this case the application window itself, you may also try passing
|
and finally a widget (in this case the application window itself, you may also try passing
|
||||||
another button). As the main window itself is a so called _GTK_ `bin` and can contain only one
|
another button). As the main window itself is a so called GTK `bin` and can contain only one
|
||||||
single child widget, we create a container widget, a vertical box in this case, fill that box with
|
single child widget, we create a container widget, a vertical box in this case, fill that box with
|
||||||
some buttons, and add that box to the window.
|
some buttons, and add that box to the window.
|
||||||
|
|
||||||
|
|
@ -487,7 +489,7 @@ proc b1Callback(button: Button; str: int)
|
||||||
It may be not always really obvious what the compiler wants to tell us, but at least we
|
It may be not always really obvious what the compiler wants to tell us, but at least we
|
||||||
are told that it got a string and expected an int.
|
are told that it got a string and expected an int.
|
||||||
|
|
||||||
Currently the connect function is realized by a _Nim_ type safe `macro`. Connect accepts two or three
|
Currently the connect function is realized by a Nim type safe `macro`. Connect accepts two or three
|
||||||
arguments -- the widget, the signal name and the optional argument. When the optional argument
|
arguments -- the widget, the signal name and the optional argument. When the optional argument
|
||||||
is a ref (reference to objects on the heap) then it is passed as a reference, otherwise a deep copy
|
is a ref (reference to objects on the heap) then it is passed as a reference, otherwise a deep copy
|
||||||
of the argument is passed. For the above code this means, that `r` and the `window` variables are passed
|
of the argument is passed. For the above code this means, that `r` and the `window` variables are passed
|
||||||
|
|
@ -495,22 +497,22 @@ as references, while the string and the stack object are deep copied. Currently
|
||||||
to release the memory of passed arguments again. This should be no real problem, as in most
|
to release the memory of passed arguments again. This should be no real problem, as in most
|
||||||
cases no arguments are passed at all, and when arguments are passed, then they are general
|
cases no arguments are passed at all, and when arguments are passed, then they are general
|
||||||
small in size like plain numbers or strings, or maybe references to widgets which could not be freed
|
small in size like plain numbers or strings, or maybe references to widgets which could not be freed
|
||||||
at all, as they are part of the _GUI_. Later we may add more variants of that connect macro.
|
at all, as they are part of the GUI. Later we may add more variants of that connect macro.
|
||||||
|
|
||||||
NOTE: Navigation can be hard for beginners. You may have basic knowledge of _GTK_ and want
|
NOTE: Navigation can be hard for beginners. You may have basic knowledge of GTK and want
|
||||||
to build a _GUI_ for your application. But how to find what you need. Well, we offer no separate
|
to build a GUI for your application. But how to find what you need. Well, we offer no separate
|
||||||
automatically generated _API_ documentation currently, as that is not really helpful. In most cases
|
automatically generated API documentation currently, as that is not really helpful. In most cases
|
||||||
it is easy to just guess _Nim_ symbol names, proc parameters and all that. Using a smart editor
|
it is easy to just guess Nim symbol names, proc parameters and all that. Using a smart editor
|
||||||
with good `nimsuggest` support further supports navigation -- for example `NEd` shows us
|
with good `nimsuggest` support further supports navigation -- for example `NEd` shows us
|
||||||
all the needed proc parameters when we move the cursor on a proc name, or we press kbd:[Ctrl+W] and jump
|
all the needed proc parameters when we move the cursor on a proc name, or we press kbd:[Ctrl+W] and jump
|
||||||
to the definition of that symbol. For unknown stuff the original _C_ function name is often a good starting point.
|
to the definition of that symbol. For unknown stuff the original _C_ function name is often a good starting point.
|
||||||
Assume you don't know much about _GTK_'s buttons, but you know that you want to have a button in
|
Assume you don't know much about GTK's buttons, but you know that you want to have a button in
|
||||||
your _GUI_ application. _GTK_ generally offers generator functions containing the string `new` in their name.
|
your GUI application. GTK generally offers generator functions containing the string `new` in their name.
|
||||||
So it is easy to guess that there exists a _C_ function named `gtk_button_new`. That name is also
|
So it is easy to guess that there exists a _C_ function named `gtk_button_new`. That name is also
|
||||||
contained in the bindings files, in this case in `gtk.nim`. So we open that file in a text editor and search for
|
contained in the bindings files, in this case in `gtk.nim`. So we open that file in a text editor and search for
|
||||||
that term. So it is really easy to find first starting points for related procs and data types. Most data types
|
that term. So it is really easy to find first starting points for related procs and data types. Most data types
|
||||||
are located near by their related functions, so you should be able to find all relevant information fast.
|
are located near by their related functions, so you should be able to find all relevant information fast.
|
||||||
Remember the _GTK_ `devhelp` tool, and use also `grep` or the `nimgrep` variant.
|
Remember the GTK `devhelp` tool, and use also `grep` or the `nimgrep` variant.
|
||||||
|
|
||||||
NOTE: Related work: https://github.com/jdmansour/nim-smartgi
|
NOTE: Related work: https://github.com/jdmansour/nim-smartgi
|
||||||
|
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue