Jakožto závěrečnou semestrální práci v předmětu Programování v jazyce C jsem se rozhodl vypracovat aplikaci pracující s GUI (grafické uživatelské rozhraní). Do té chvíle jsem s GUI pracoval pouze v Javě, a proto jsem se musel porozhlédnou po nějaké knihovně kterou bych mohl použít v Céčku. Po chvilce strávené na všemohoucím Google bylo rozhodnuto pro GTK+ ostatní knihovny jsem vyloučil, buď kvůli nesplnění multiplatformnosti, nebo nemožnosti je používat v čistém Céčku. Multiplatformnost hrála důležitou roli při výběru, poněvadž se považuji za spokojeného uživatele Linuxu, bohužel má škola není zrovna moc „Linux friendly”. Rozhodl jsem se tedy, že aplikaci napíšu pod Linuxem, a potom se ji pokusím portovat pro Windows. Při tomto úkonu může spousta lidí zabloudit, jelikož česky o tomto problému moc informací nenaleznete, proto jsem se rozhodl celou věc sepsat a usnadnit portaci pro mé následovníky.

Kompilace GTK+ aplikace pod Linuxem

Jako první je třeba nainstalovat libgtk2.0-dev, glade-3 (v Ubuntu příkazem: $ sudo apt-get install libgtk2.0-dev glade-3). Dále jsem přemluvil mé oblíbené NetBeans IDE, aby pracovalo s GTK+ podle tohoto návodu. Pokud píšete pouze v textovém editoru a kompilujete pomocí GCC, vystačíte s příkazem $ gcc -Wall aplikace.c -o aplikace -export-dynamic `pkg-config --cflags --libs gtk+-2.0`

Kompilace GTK+ aplikace pod Windows

Pod Windows si instalování užijeme trošku víc :-( .

(1) Instalace GCC kompilátoru

Stáhněte si instalační soubor pro MinGW (umožňuje pracovat s GCC pod Windows)

V instalace zatrhněte balíky: gcc-core a gnu-make

Poté přidejte do systémové proměnné (Ovládací Panely -> Systém -> Upřesnit -> Systémové Proměnné) Path cestu C:\mingw\bin; (dle instalační cesty)

Do příkazového řádku(cmd.exe) napište příkaz: gcc Pokud se na výstupu objeví: "no input files" instalace se povedla v opačném případě je zřejmě špatně nastavena proměnná Path.

(2) Instalace GTK+

Stáhněte si instalační soubor GTK+ a nainstalujte jej do C:\GTK\. (Pozn.: POZOR! S některými instalátory se mi nepovedlo GTK+ rozběhat, proto použijte odkazovaný!)

Spusťte příkazovou řádku (cmd.exe) a napište do ní: pkg-config --libs --cflags gtk+-2.0 Na výstupu by se měl objevit výpis knihoven GTK+. Pokud se objeví hlášení ze pkg-config není vnitřním příkazem… přidejte do Systémové proměnné Path cestu%GTK_BASEPATH%\bin; Pokud pkg-config nemůze najít knihovnu GTK+ nastavte Sys. proměnnou PKG_CONFIG_PATH na %GTK_BASEPATH%\lib\pkgconfig;

(3) Samotná kompilace

  1. Spusťte příkazovou řádku
  2. Příkaz $: pkg-config --libs --cflags gtk+-2.0 > libs.txt
  3. Příkaz $: libs.txt
  4. Pomocí CTRL+C zkopírujte obsah souboru libs.txt
  5. Příkaz $: gcc -Wall -mwindows -g application.c -o application.exe <libs*> Místo <libs*> vložte text ze souboru libs.txt (klikněte pravým tlačítkem na cmd a dejte vložit) Pokud chcete spouštět program i s příkazovou řádkou vynechte argument -mwindows

Závěr

Už víme jak zkompilovat stejný program na různých platformách. Příště se zaměřím, na to jak jej psát aby šel na obou platformách zkompilovat a vypadal zhruba stejně.

Kódovaní zpráv QIP → Pidgin

20 Led 2009 V kategorii: Jen tak

Při používání Pidginu jako IM klienta pro ICQ každý určitě narazil na problém s kódováním příchozích zpráv od uživatelů používajících ruského klienta QIP. Namísto českých znaků s diakritikou se zobrazuje mix češtiny a azbuky. Tato chyba, i když není na straně Pidginu, neumožňuje tento klient používat, protože zhruba polovina uživatelů ICQ (bráno dle mého seznamu kontaktů) používá právě QIP.

Špatné a dobré kódování

Naštěstí existuje řešení v podobě rozšíření pro Pidgin pojmenovaném QIP decoder.

Instalace QIP decoderu

Pozn. Testováno na Pidginu v. 2.5.2.

Instalace na Linuxu

Vývojáři před připravily zkompilované rozšíření pro Ubuntu 8.04, x86, Ubuntu 8.10, x86-64. Stažené archivy stačí rozbalit do složky /usr/lib/pidgin (nutné superuživatelské heslo).

Pokud používáte jinou distribuci jste bohužel nuceni kompilovat.

  1. Nainstalujte balíček pidgin-devel pomocí správce balíčků
  2. Stáhněte si QIP decoder v1.0 source
  3. Zkopírujte soubor qip-decoder.c do /usr/src/pidgin-2.5.2/libpurple/plugins
  4. Spusťte příkaz make qip-decoder.so
  5. qip-decoder.so zkopírujte do /usr/lib/pidgin

Instalace na Windows

  1. Stáhněte si QIP Decoder
  2. Zkopírujte obsah archivu do složky plugins v instalačním adresáři Pidginu

Povolení rozšíření

Spusťte Pidgin, a v rozhraní Nástroje -> Zásuvné moduly zaškrtněte QIP Decoder v 1.0.

Rozhraní zásuvných modulů Pidginu

Pokud jej nenaleznete v seznamu udělali jste zřejmě chybu při instalaci. V opačném případě vesele do chatování!

Výpočet řádků v projektu

7 Říj 2008 V kategorii: PHP, Programování, Webdesign

Po dopsání docela robustní aplikace v PHP, jsem zatoužil vědět, do kolika řádků jsem tuto aplikaci vlastně vměstnal. Po krátké úvaze jsem navrhl a napsal malou třídu která tuto čínnost umožňuje.

Počítání řádků v souboru

Pro tuto akci lze použít funkci file(), která načte doubor do pole, kde každý prvek je jeden řádek souboru. Stačí tedy potom zjistit velikost pole pomocí fukce count() a počet řádků souboru je na světě.

Hierarchické prohledávání adresářů

Jistě by bylo od věci nehledat soubory jen v základním adresáři ale i v jeho podadresářích. Pro takový případ je nejlepším řešením použít rekurzivní funkci.

Výsledná třída

Z uvedených informací již není složité naprogramovat script který bude tyto akce zvládat.

PHP:
  1. <?php
  2. /**
  3. * LineCounter
  4. * @author Ondřej Fibich
  5. * @version 1.1
  6. *
  7. * Class counts number of lines, files, dirs in $dir and it's subdirs
  8. */
  9. class LineCounter extends Object {
  10.     /** field of files where you want to count lines */
  11.     protected static $ACCEPT_FILES = array("php", "js", "html", "htm", "xhtml", "xml", "css", "xsl");
  12.     /** dirs which sill be ignored */
  13.     protected static $IGNORE_DIRS = array("fckeditor");
  14.     /** count of lines */
  15.     protected $line_count;
  16.     /** count of dirs */
  17.     protected $dir_count;
  18.     /** count of files */
  19.     protected $file_count;
  20.     /** root dir */
  21.     protected $dir;
  22.     /**
  23.      * Construct - null value
  24.      */
  25.     public function __contruct() {
  26.         $this->setNullValue();
  27.     }
  28.     /**
  29.      * Nulls value for new countion
  30.      */
  31.     public function setNullValue() {
  32.         $this->line_count = 0;
  33.         $this->dir_count = 0;
  34.         $this->file_count = 0;
  35.     }
  36.     /**
  37.      * Counts number of lines in $file
  38.      * @param string $file path o file
  39.      * @return void
  40.      */
  41.     protected function getLinesCount($file) {
  42.         if (! is_file($file) {           
  43.             return;
  44.         }
  45.         $this->file_count++; // another file => increment
  46.         $this->line_count += count(file($file)); // add lines count
  47.     }
  48.     /**
  49.      * Scand root dir($this->dir) for files to count line. Countion is recursive so it's scan any subdir in root dir
  50.      * @param string $dir path of dir to scan
  51.      * @return void
  52.      */
  53.     protected function scaner($dir) {
  54.         if (! is_dir($dir) || ! file_exists($dir)) { // test dir
  55.             throw new InvalidArgumentException("Can't found {$dir}"); // not dir => exception
  56.         }
  57.         foreach (self::$IGNORE_DIRS as $ignore) {
  58.             if (mb_eregi("{$ignore}$", $dir)) { // ignored dir
  59.                 return;
  60.             }
  61.         }
  62.         $files = scandir($dir); // scans dir
  63.         $this->dir_count++; // another dir => increment
  64.         foreach ($files as $file) {
  65.             if (($file == ".") || ($file == "..")) { // needed step
  66.                 continue; // we must ignore . .. or script will call recursive function again and again
  67.             } else if (is_dir("{$dir}/{$file}")) { // file is dir
  68.                 $this->scaner("{$dir}/{$file}"); // scan it with recursive function
  69.                 continue; // dir so jump to start
  70.             }
  71.             foreach (self::$ACCEPT_FILES as $bin) { // is it the file we want?
  72.                 if (mb_eregi("{$bin}$", $file)) {
  73.                     $this->getLinesCount("{$dir}/{$file}"); // count line
  74.                     break;
  75.                 }
  76.             }
  77.         }
  78.     }
  79.     /**
  80.      * Starts scan
  81.      */
  82.     public function calculation() {
  83.         $this->scaner($this->dir);
  84.     }
  85. }
  86. $lineCounter = new LineCounter();
  87. $lineCounter->set("dir", "..");
  88. $lineCounter->calculation();
  89. ?>

** Pozn.: třída object již byla představena v mém předchozím čánku Zlepšujeme PHP vlastnostmi Javy, díl 1.

Použití třídy

PHP:
  1. <?php
  2. $lineCounter = new LineCounter();
  3. $lineCounter->set("dir", "."); // vybereme aktuální adresář
  4. $lineCounter->calculation(); // vypočítáme
  5. echo $lineCounter->get("dir_count") . "<br/>"; // počet adresářů, které jsme prohledaly
  6. echo $lineCounter->get("file_count") . "<br/>"; // počet souborů, ve kterých jsme počítali řádky
  7. echo $lineCounter->get("line_count"). "<br/>"; // celkový počet řádků
  8. ?>

Stažení celého programu

Stáhnout line_counter.zip

Pro start aplikace spusťte line_counter.php

Mých 10 nejoblíbenějších programů

4 Říj 2008 V kategorii: Jen tak
  1. Opera webový prohlížeč, na který nedám dopustit
  2. NetBeans vývojové prostředí, používám je pro Javu, PHP, XML, AJAX, CSS, C++ (je super když všechno můžete dělat v jednom IDE)
  3. Audacious hudební přehrávač podobný Winampu
  4. VirtualBox virtualizační nástroj (testování OS)
  5. QIP ICQ messenger
  6. OpenOffice.org svobodná náhrada MS Office
  7. Adobe Photoshop mocný nástroj pro tvorbu grafiky (ovládám jen základní prvky)
  8. Synaptic správce balíčků pro Debian (důvod proč už nechci zpět Winy)
  9. Wine API pro rozběhání programů napsaných Windows (sem tam nějaká oddechová hra bodne ;-) )
  10. Gajim Jabber messenger

A jákých je Vašich top 10? Pochlubte se!

QIP pro Linux

26 Srp 2008 V kategorii: Linux

Donedávna jsem jako ICQ klient v Linuxu používal QIP běžící pod WINE. To se změnilo po nalezení qutIM. Hlavní jeho výhodou je, že jako jediný mně známý Linuxový klient pro ICQ zvládá dokonale x-statusy. Klient je sice stále ve vývoji, ale po týdnu používání jsem nenarazil na vážnější problémy. Doporučuju vyzkoušet, jsou dostupné i verze pro Windows a OSX.

Zlepšujeme PHP vlastnostmi Javy, díl 1.

24 Srp 2008 V kategorii: PHP

Poslední dobou jsem se věnoval hlavně Javě, kdo ji zakusil už u ní obvykle zůstal. Proto když jsem před časem dělal web na objednávku v PHP přenesl jsem jsi pár „manýrů” k ulehčení práce z Javy do PHP.

Základní vlastnosti Objektu

Kdo alespoň o Javu někde zakopl, ví, že je to jazyk založený na OOP, kde každá třída dědí třídu Object, která má ve svém kódu uloženy základní metody (JavaDoc).

Rozhraní ObjectInterface

Když jsem programoval datové třídy pro přístup databázi. Byl jsem znechucen neustálým psaním, přístupu k proměnným stylem getProměnná(), setProměnná(value), který zbytečně zvětšoval objem kódu u jednoduchých tříd. Jako řešení s může nabídnout změnit přístup k proměnným na public a přistupovat k nim jednoduše $class->value. Toto řešení je ovšem z pohledu OOP trochu zvrácené, proto jsem naprogramoval následující rozhraní(interface), které poskytuje 2 metody pro manipulaci s proměnnýma třídy.

PHP:
  1. <?php
  2. /**
  3. * ObjectInterface interface
  4. * @author Ondřej Fibich
  5. * @version 1.0
  6. *
  7. * This interface was created, because of I was bored use Java Beans structure
  8. * to set and get inner values from class.
  9. * @example JavaBeans structure for inner value $property:
  10. *      Object getProperty() and void setProperty(Object $value)
  11. * This type of structure is the best, but if you have more values in your class.
  12. * it's better to just implement this interface and have less code in your class.
  13. * @example My structure for inner value Property:
  14. *      Object get(string $property) and void setProperty(string $property, Object $value)
  15. */
  16. interface ObjectInterface {
  17.   /**
  18.      * Sets inner value of class named as key with value
  19.      * @param string $key
  20.      * @param string $value
  21.      */
  22.     public function set($key, $value);
  23.    /**
  24.      * @return inner value of class named as key
  25.      */
  26.     public function get($key);
  27. }
  28. ?>

Třída Object

Dalším krokem bylo vytvoření třídy Object, která bude rozhraní implementovat a budou ji dědit všechny ostatní třídy. Na první pohled se zdá ObjectInterface jako zbytečné, stačilo by přece jen třída Object, ne? Samozřejmě, ale představte si situaci kdy potřebujete implementaci pozměnit, v potomku můžete sice překrýt metody, ale není to tak precizní a přehledné řešení jako implementace ObjectInterface. Druhým důvodem je třída, která už dědí z jiné a proto nemůže dědit z Object. (V PHP může každá třída dědit jen z 1 jiné třídy, ale implementovat libovolný počet rozhraní.)

PHP:
  1. <?php
  2. /**
  3. * Class Object
  4. * @author Ondřej Fibich
  5. * @version 1.0
  6. */
  7. class Object implements ObjectInterface {
  8.     public function set($key, $value) {
  9.         if (isset($this->$key)) {
  10.             $this->$key = $value;
  11.         }
  12.     }
  13.     public function get($key) {
  14.         if (isset($this->$key)) {
  15.             return $this->$key;
  16.         } else {
  17.             return null;
  18.         }
  19.     }
  20. }
  21. ?>

Pozn. Třída ignoruje chyby (nedefinovaná proměnná), doporučuji však použít vyjímek k oznamování chyb.

Použití Object

Jak jsem psal výše, nápad jsem dostal při programování datových tříd databáze, proto uvedu příklad právě s ní. Vezměme tedy tabulku Osoba, která by mohla vypadat zhruba nápodobně:

MySQL:
  1. CREATE TABLE `Osoba` (
  2. `ID` INT( 11 ) NOT NULL ,
  3. `name` VARCHAR( 100 ) NOT NULL ,
  4. PRIMARY KEY ( `ID` )
  5. ) ENGINE = MYISAM

Datová třída vypadá následovně:

PHP:
  1. <?php
  2.  class Osoba extends Object {
  3.      protected $ID;
  4.      protected $name;
  5.      public function __construct($ID) {
  6.          // načte data z databáze do třídy s ID == $ID
  7.      }
  8.      public function __destruct() {
  9.          // uloží data do databáze
  10.      }
  11.  }
  12. ?>

Práce se třídou:

PHP:
  1. <?php
  2.  $osoba = new Osoba(1); // načtení dat
  3.  echo $osoba->get("name"); // výpis dat
  4.  $osoba->set("name", "Otto von Bismarck"); // změna hodnoty
  5.  unset($osoba); // volám destructor
  6. ?>

Závěr

Ukázali jsme jsi jak jednoduše přistupovat k vnitřním proměnným třídy. Příště implementujeme Javovskou třídu Properties.

Stránkování v PHP

9 Čvc 2008 V kategorii: PHP

Na webu který spravuji se začala v MySQL databázi kupit data, výpis všech začal být zbytečný, tak jsem ztvořil za pár minut jednoduchý skriptík na jejich stránkování. Článek je určen začátečníkům, kteří si s tímto problémem neví rady.

Skript jsem patřičně okomentoval aby byl přehledný. Výstupní HTML neobsahuje řádnou strukturu HTML dokumentu, protože můj skript byl určen pro vložení do jiné stránky opatřené hlavičkami. Aktuální strana je předávána pomocí parametru src v URL.

PHP:
  1. <?php
  2. /**
  3. * Jednoduchý Skript pro stránkování záznamů z databáze
  4. * @author Ondřej Fibich
  5. */
  6.  
  7.  $PZS = 6; // pocet záznamů na stranu
  8.  $str = 1; // aktuální strana (počítáno od 1)
  9.  $message = "Error"; // chybová zpráva
  10.  
  11.  if (isset($_GET['str']) &&
  12.      $_GET['str']> 0) { // z parametrů URL vybere aktuální stránku
  13.     $str = $_GET['str'];
  14.  }
  15.  
  16.  // připojení k databázi
  17.  $sql = mysql_connect("localhost", "user", "password") or die($message);
  18.  // výběr počtu prvků v tabulce
  19.  $resultCount = mysql_query($sql, "SELECT COUNT(0) as COUNT_TABLE FROM table");
  20.  // uložení počtu záznamů
  21.  $pocetZaznamu = mysql_result($resultCount, 0);
  22.  
  23.  // SQL funkce LIMIT(START, COUNTS)
  24.  // výpočet STARTU
  25.  $start = ($str - 1) * $PZS;
  26.  // výběr vhodných položek
  27.  $result = mysql_query($sql,"SELECT*FROM table LIMIT ".$start.",".$PZS);
  28.  
  29.  // výpis výsledků
  30.  while($zapis = mysql_fetch_object($result)) {
  31.     echo "<p>Vypis dat. Např.: $zapis->sloupec</p>";
  32.  }
  33.  
  34.  //
  35.  // Jednoduché listování mezi stranami
  36.  //
  37.  echo "<div style='float: right; clear: both; margin-top: 25px;'>" .
  38.       "<a href='str=" .($str> 1 ? $str - 1 : "1"). "'>&laquo;</a>&nbsp";
  39.  
  40.  // počet stránek
  41.  $pocet = (($pocetZaznamu % $PZS)> 0) ? (int)($pocetZaznamu / $PZS) + 1 : $pocetZaznamu / $PZS;
  42.  
  43.  // výpis odkazů na stránky
  44.  for ($i = 1; $i <= $pocet; $i++) {
  45.     if ($i != $str) {
  46.         echo "<a href='?str=".$i."'>".$i."</a>&nbsp;";
  47.     } else { // aktuální strana
  48.         echo "<a href='?str=".$i."'><b>".$i."</b></a>&nbsp;";
  49.     }
  50.  }
  51.  
  52.  echo "<a href='?str=" .(($str <$pocet) ? $str + 1 : $pocet) ."'>&raquo;</a>" .
  53.       "</div>";
  54. ?>

Doufám, že článek někomu pomůže.

Vítejte, otevíráme

5 Čvc 2008 V kategorii: Jen tak

Je to již docela dlouho co jsem se snažil vytvořit nějaký web, který by sděloval světu, že někdo jako má maličkost vůbec existuje. První pokus o vytvoření blogu byl docela kostrbatý. O většině webových technologií jsem neměl ani páru, a přesto jsem se snažil radit, těm ještě méně schopným než jsem byl já, v jejich tvorbě. Před zhruba třemi lety vznikl první LOLO Blog (existuje dodnes: http://www.lolo-blog.wz.cz/) tehdy ještě ve statické podobě. Euforie trvala asi 2 měsíce, poté jsem blog "opustil" a nezajímal jsem se o něj, a proto se jeho obsah za poslední 3 roky nezměnil a jeho kvalita odpovídá mím nicotným znalostem kolem IT technologií před třemi lety.

Po dlouhé odmlce (asi 2 roky) jsem začal toužit po blogu. Tehdy ještě plný elánu při programování v PHP jsem začal psát redakční systém. Po 2 měsících proseděných u počítače jsem ztratil trpělivost a rozepsatý systém jsem dlouhodobě uskladnil na HDD mého počítače, kde čeká na dokončení, kterého se asi nikdy nedočká. Na čas zálusk na vlastní blog opět utichl.

Zhruba před týdnem jsem opět zatoužil po blogu, nevybral jsem si cestu zdlouhavého programování vlatního blogu, namísto toho jsem stáhl WordPress, pěkné téma a začal psát. Časem se možná naučím i tvořit témata pro WordPress a pokusím se nakreslit nějaký vzhledný design, ale prozatím se budu snažit psát alespoň nějaké ty příspěvky.

Tak tolik k historii mého blogování a založení tohoto blogu, snad se Vám bude můj nový blog líbit a časem si jej oblíbíte.

Vítejte na LOLO blogu

Zdravím všechny človíčky, které trochu baví informatika jako mně. Stránky jsou prozatím ve výstavbě, proto omluvte jejich práznost. Postupem času by se zde měli nacházem typy a triky v programovaní, Linuxu a mé osobní poznatky. Přeji příjemný pobyt!


Moje aktuální plocha (Ubuntu 9.10)

 

Červenec 2010
P Ú S Č P S N
« Led    
 1234
567891011
12131415161718
19202122232425
262728293031