A developers tutorial how to write an application with the new eTemplates.
It is also an introduction how to write a phpgw- and setup(3)-compatible app.
As an example we will run now through the necessary steps to create a simple media database using eTemplates and other tools and classes from the eTemplate app: db-tools and class.so_sql.inc.php.
Out media database should have the usual fields: name, author, description, type: BOOK, CD, VIDEO and should be able to edit records and search for them.
As a preaquistion you need to get / checkout the etemplate app, install the app via setup/manage applications and enable your account for using the app (Admin/User account: check eTemplates).
Each app need a name, eg. 'et_media'. We now need to create the following directory structur above the phpgroupware dir:
et_media (that has to be identical to our app-name) + setup (files necessary for the setup Programm, give the webserver write-permission to that dir) + inc (class-files) + templates (templates, still need to store the images and get around a lot of complains from the api) + default + images (here goes our images / icons)
To be able to see the app in the navbar and call it we need to do the following steps (later this can be done via setup)
That files contains the necessary information for setup to install the app.
<?php $setup_info['et_media']['name'] = 'et_media'; $setup_info['et_media']['title'] = 'eT-Media'; $setup_info['et_media']['version'] = '0.9.15.001'; $setup_info['et_media']['app_order'] = 100; // at the end $setup_info['et_media']['tables'] = array('phpgw_et_media'); $setup_info['et_media']['enable'] = 1; /* Dependacies for this app to work */ $setup_info['et_media']['depends'][] = array( 'appname' => 'phpgwapi', 'versions' => Array('0.9.13','0.9.14','0.9.15') ); $setup_info['et_media']['depends'][] = array( // this is only necessary as long the etemplate-class is not in the api 'appname' => 'etemplate', 'versions' => Array('0.9.13','0.9.14','0.9.15') );
To enable setup to create a db-table for us, we need to define the fields we want.
We can use the db-Tools from the etemplate app to create the file for us:
Now we need a nice edit dialog and use the eTemplate editor to set it up:
As you see above i added an application titel, a horizontal rule after it and some space (empty label's). Do so if you want.
The index page is only used if someone clicks on the navbar icon (or on the black cross as we haven't supplied one so far).
Create the file /et_media/index.php with the following content:
<?php $GLOBALS['phpgw_info']['flags'] = array( 'currentapp' => 'et_media', 'noheader' => True, 'nonavbar' => True ); include('../header.inc.php'); $et_media = CreateObject('et_media.et_media'); $et_media->edit(); $GLOBALS['phpgw']->common->phpgw_footer();
As a first step, we only save new entries. The code of the app is in /et_media/inc/class.et_media.inc.php:
<?php /**************************************************************************\ * phpGroupWare - eTemplates - Tutoria Example - a simple MediaDB * * http://www.phpgroupware.org * * Written by Ralf Becker* * -------------------------------------------- * * This program is free software; you can redistribute it and/or modify it * * under the terms of the GNU General Public License as published by the * * Free Software Foundation; either version 2 of the License, or (at your * * option) any later version. * \**************************************************************************/ /* $Id$ */ if(!isset($GLOBALS['phpgw_info']['flags']['included_classes']['so_sql'])) { include(PHPGW_API_INC . '/../../etemplate/inc/class.so_sql.inc.php'); $GLOBALS['phpgw_info']['flags']['included_classes']['so_sql'] = True; } class et_media extends so_sql { var $messages = array( 'nothing_found' => 'Nothing matched search criteria !!!', 'anz_found' => '%d matches on search criteria', 'saved' => 'Entry saved', 'error_writeing' => 'Error: writeing !!!' ); var $types = array( '' => 'Select one ...', 'cd' => 'Compact Disc', 'dvd' => 'DVD', 'book' => 'Book', 'video' => 'Video Tape' ); function et_media($lang_on_messages = True) { $this->tmpl = CreateObject('etemplate.etemplate','et_media.edit'); $this->so_sql('et_media','phpgw_et_media'); // sets up our storage layer using the table 'phpgw_et_media' $this->empty_on_write = "''"; // that means if a column is empty how to write in the db, the default is NULL $this->public_functions += array( 'edit' => True, 'writeLangFile' => True ); if ($lang_on_messages) { reset($this->messages); while (list($key,$msg) = each($this->messages)) $this->messages[$key] = lang($msg); } } function edit($content='',$msg = '') { if (is_array($content)) // not first call from index { if ($content['id'] > 0) { $this->read($content); } $this->data_merge($content); if (isset($content['save'])) { $msg .= $this->messages[!$this->save() ? 'saved' : 'error_writeing']; } elseif (isset($content['read'])) { unset($content['id']); $found = $this->search($content,False,'name,author'); if (!$found) { $msg .= $this->messages['nothing_found']; } else { $this->init($found[0]); } } } // now we filling the content array for the next call to etemplate.exec $content = $this->data + array( 'msg' => $msg ); $sel_options = array( 'type' => $this->types ); $no_button = array( 'delete' => !$this->data[$this->db_key_cols[$this->autoinc_id]] ); $this->tmpl->exec('et_media.et_media.edit',$content,$sel_options,$no_button,array( 'id' => $this->data['id'] )); } }
As saveing and reading of entries is working now we want to search for an entry and show a list of the result (if it's more than one).
First we need to create an other eTemplate to show the list: 'et_media.show'
As you see the templates includes an other template: 'et_media.show.rows'
We need some code in the class to call the template and fill the content:
function show($found) { if (!is_array($found) || !count($found)) { $this->edit(); return; } reset($found); for ($row=1; list($key,$data) = each($found); ++$row) { $entry[$row] = $data; } $content = array( 'msg' => sprintf($this->messages['anz_found'],count($found)), 'entry' => $entry ); $this->tmpl->read('et_media.show'); $this->tmpl->exec('et_media.et_media.edit',$content); }
To call the show function, we need to make some changes to the edit-function too:
elseif (isset($content['read'])) { unset($content['id']); $found = $this->search($content,False,'name,author'); if (!$found) { $msg .= $this->messages['nothing_found']; } elseif (count($found) == 1) { $this->init($found[0]); } else { $this->show($found); return; } } elseif (isset($content['entry']['edit'])) { list($id) = each($content['entry']['edit']); if ($id > 0) { $this->read(array('id' => $id)); } }
While makeing this changes we can add a [Cancel] and [Delete] button too:
elseif (isset($content['cancel'])) { $this->init(); } elseif (isset($content['delete'])) { $this->delete(); $this->init(); }Of course we have to add this buttons to the template 'et_media.edit'
9. creating the english lang-file
To get rid of the stars '*' behind each Label and to be able to translate the app in other languages we need to create a lang-file
There are 2 possibilties to create it automaticaly:
function writeLangFile() { $etm = new et_media(False); // no lang on messages $this->tmpl->writeLangFile('et_media','en',$etm->messages); }