hello-world/src/db.c

Go to the documentation of this file.
00001 /*
00002  * File Name: db.c
00003  */
00004 
00005 /*
00006  * This file is part of hello-world.
00007  *
00008  * hello-world is free software: you can redistribute it and/or modify
00009  * it under the terms of the GNU General Public License as published by
00010  * the Free Software Foundation, either version 2 of the License, or
00011  * (at your option) any later version.
00012  *
00013  * hello-world is distributed in the hope that it will be useful,
00014  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00015  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
00016  * GNU General Public License for more details.
00017  *
00018  * You should have received a copy of the GNU General Public License
00019  * along with this program. If not, see <http://www.gnu.org/licenses/>.
00020  */
00021 
00022 /**
00023  * Copyright (C) 2009 iRex Technologies B.V.
00024  * All rights reserved.
00025  */
00026 
00027 //----------------------------------------------------------------------------
00028 // Include Files
00029 //----------------------------------------------------------------------------
00030 
00031 // system include files, between < >
00032 #include <unistd.h>
00033 #include <gtk/gtk.h>
00034 
00035 // local include files, between " "
00036 #include <db.h>
00037 #include "log.h"
00038 
00039 
00040 //----------------------------------------------------------------------------
00041 // Type Declarations
00042 //----------------------------------------------------------------------------
00043 
00044 
00045 //----------------------------------------------------------------------------
00046 // Constants
00047 //----------------------------------------------------------------------------
00048 
00049 #define THUMBNAIL_MINI   0
00050 #define THUMBNAIL_SMALL  1
00051 #define THUMBNAIL_MEDIUM 2
00052 #define THUMBNAIL_LARGE  3
00053 #define THUMBNAIL_COUNT  4
00054 
00055 // Column names for table file_metadata in metadb
00056 static const char* FILE_TITLE          = "title";
00057 static const char* FILE_AUTHOR         = "author";
00058 
00059 // Columns in database table thumbnails.
00060 static const char* THUMBNAIL_COLUMNS[THUMBNAIL_COUNT] =
00061 {
00062     "thumb_data_mini",
00063     "thumb_data_small",
00064     "thumb_data_medium",
00065     "thumb_data_large"
00066 };
00067 
00068 static const int THUMBNAIL_SIZES[THUMBNAIL_COUNT] =
00069 {
00070     30, 60, 120, 300
00071 };
00072 
00073 
00074 //----------------------------------------------------------------------------
00075 // Static Variables
00076 //----------------------------------------------------------------------------
00077 
00078 
00079 //============================================================================
00080 // Local Function Definitions
00081 //============================================================================
00082 
00083 static void  set_pixel_value(GdkPixbuf * pixbuf, int x, int y, gint color);
00084 
00085 
00086 //============================================================================
00087 // Functions Implementation
00088 //============================================================================
00089 
00090 erMetadb open_database(const char* IN dir)
00091 {
00092     g_assert(dir != NULL);
00093 
00094     erMetadb db = ermetadb_global_open(dir, FALSE);
00095     if ( NULL == db) {
00096         ERRORPRINTF("Could not open database %s", dir );
00097     } 
00098     return db;
00099 }
00100 
00101 
00102 void close_database(erMetadb IN db) 
00103 {
00104     g_assert ( NULL != db );
00105     
00106     ermetadb_close(db);
00107     // explicit sync since ermetadb_close_database does not flush to disk
00108     sync();
00109 }
00110 
00111 
00112 gboolean load_file_metadata(erMetadb        IN  db,
00113                             const gchar*    IN  filepath,
00114                             const gchar*    IN  filename,
00115                             GString*        OUT title,
00116                             GString*        OUT author,
00117                             thumbType*      OUT small,
00118                             thumbType*      OUT medium)
00119 {
00120     g_assert(db != NULL);
00121     g_assert(filename != NULL);
00122 
00123     metadata_table* name_table = metadata_table_new();
00124     g_return_val_if_fail( NULL != name_table, FALSE);
00125 
00126     // add columns, caller is owner of OUT parameters
00127     if (title   ) { metadata_table_add_column(name_table, FILE_TITLE       ); }
00128     if (author  ) { metadata_table_add_column(name_table, FILE_AUTHOR      ); }
00129     if (small   ) { metadata_table_add_column(name_table, THUMBNAIL_COLUMNS[THUMBNAIL_SMALL]);  }
00130     if (medium  ) { metadata_table_add_column(name_table, THUMBNAIL_COLUMNS[THUMBNAIL_MEDIUM]); }
00131 
00132     // query
00133     metadata_table* results_table = NULL; // must be NULL, created by function below
00134     int rc = ermetadb_global_get_file(db, filepath, filename, name_table, &results_table);
00135 
00136     if (rc != ER_OK)
00137     {
00138         ERRORPRINTF("ermetadb_get_file_metadata() returns [%d]", rc);
00139         metadata_table_free(name_table);
00140         metadata_table_free(results_table);
00141         return FALSE;
00142     }
00143 
00144     if (title) 
00145     {
00146         // Get title.
00147         const char *column = FILE_TITLE;
00148         int index = metadata_table_find_column(results_table, column);
00149         if (index >= 0)
00150         {
00151             const metadata_cell *cell = metadata_table_get_cell(results_table, index);
00152 
00153             if (cell && cell->type == METADATA_TEXT)
00154             {
00155                 g_string_assign(title, cell->value.v_text->str );
00156             }
00157         }
00158         else
00159         {
00160             ERRORPRINTF("Cannot find column %s", column);
00161         }
00162     }
00163 
00164     if (author)
00165     {
00166         // get author
00167         const char* column = FILE_AUTHOR;
00168         int index = metadata_table_find_column(results_table, column);
00169         if (index >= 0)
00170         {
00171             const metadata_cell *cell = metadata_table_get_cell(results_table, index);
00172 
00173             if (cell && cell->type == METADATA_TEXT)
00174             {
00175                 g_string_assign(author, cell->value.v_text->str );
00176             }
00177         }
00178         else
00179         {
00180             ERRORPRINTF("Cannot find column %s", column);
00181         }
00182     }
00183 
00184     if (small)
00185     {
00186         // get file thumbnail (medium)
00187         const char* column = THUMBNAIL_COLUMNS[THUMBNAIL_SMALL];
00188         int index = metadata_table_find_column(results_table, column);
00189         if (index >= 0)
00190         {
00191             const metadata_cell *cell = metadata_table_get_cell(results_table, index);
00192 
00193             if (cell && cell->type != METADATA_BLOB)
00194             {
00195                 if (cell->type != METADATA_NULL) {
00196                     ERRORPRINTF("illegal cell type [%d] for thumbnail", cell->type);
00197                 }
00198                 small->data = NULL ;
00199                 small->size = 0;
00200             }
00201             else {
00202                 small->size = cell->value.v_blob.len;
00203                 memcpy((guchar*) small->data, (guchar*) cell->value.v_blob.data, small->size);
00204             }
00205         }
00206         else
00207         {
00208             ERRORPRINTF("Cannot find column %s", column);
00209         }
00210     }
00211 
00212     if (medium)
00213     {
00214         // get file thumbnail (medium)
00215         const char* column = THUMBNAIL_COLUMNS[THUMBNAIL_MEDIUM];
00216         int index = metadata_table_find_column(results_table, column);
00217         if (index >= 0)
00218         {
00219             const metadata_cell *cell = metadata_table_get_cell(results_table, index);
00220 
00221             if (cell && cell->type != METADATA_BLOB)
00222             {
00223                 if (cell->type != METADATA_NULL) {
00224                     ERRORPRINTF("illegal cell type [%d] for thumbnail", cell->type);
00225                 }
00226                 medium->data = NULL ;
00227                 medium->size = 0;
00228             }
00229             else {
00230                 medium->size = cell->value.v_blob.len;
00231                 memcpy((guchar*) medium->data, (guchar*) cell->value.v_blob.data, medium->size);
00232             }
00233         }
00234         else
00235         {
00236             ERRORPRINTF("Cannot find column %s", column);
00237         }
00238     }
00239 
00240     // clean up
00241     metadata_table_free(name_table);
00242     metadata_table_free(results_table);
00243 
00244     return TRUE;
00245 }
00246 
00247 
00248 gboolean save_file_metadata(erMetadb        IN db,
00249                             const gchar*    IN filepath,
00250                             const gchar*    IN filename,
00251                             GString*        IN title,
00252                             GString*        IN author,
00253                             thumbType*      IN small,
00254                             thumbType*      IN medium)
00255 {
00256     g_assert(db != NULL);
00257     g_assert(filename != NULL);
00258 
00259     // create table
00260     metadata_table *value_table = metadata_table_new();
00261     g_return_val_if_fail( NULL != value_table, FALSE);
00262 
00263     int value_index = -1;
00264 
00265     int rc = ER_FAIL;
00266     gboolean save_needed = FALSE;
00267 
00268     // NOTE: This could be optimized; right now all information that is present is
00269     //       always written to the metadata library, even if nothing has changed
00270     if (title)
00271     {
00272         // set title
00273         gchar* tmp_title =   g_strdup(title->str);
00274         // get rid of some special characters
00275         g_strdelimit(tmp_title, "\t\n\r", ' ');
00276         // trim the heading and tailing spaces
00277         g_strstrip(tmp_title);
00278 
00279         metadata_table_add_column(value_table, FILE_TITLE);
00280         value_index++;
00281         rc = metadata_table_set_text(value_table, value_index, tmp_title);
00282         if (rc == ER_OK)
00283         {
00284             save_needed = TRUE;
00285         }
00286         else
00287         {
00288             ERRORPRINTF("Cannot write value %s to table.", tmp_title);
00289         }
00290         g_free(tmp_title);
00291     }
00292 
00293     // set author
00294     if (author)
00295     {
00296         gchar * tmp =   g_strdup(author->str);
00297         // get rid of some special characters
00298         g_strdelimit(tmp, "\t\n\r", ' ');
00299         // trim the heading and tailing spaces
00300         g_strstrip(tmp);
00301 
00302         metadata_table_add_column(value_table, FILE_AUTHOR);
00303         value_index++;
00304         rc = metadata_table_set_text(value_table, value_index, tmp);
00305         if (rc == ER_OK)
00306         {
00307             save_needed = TRUE;
00308         }
00309         else
00310         {
00311             ERRORPRINTF("Cannot write value %s to table.", tmp);
00312         }
00313 
00314         g_free(tmp);
00315     }
00316 
00317     if ( small )
00318     {
00319         gchar* blob = (gchar*) small->data;
00320         gsize  blob_size = small->size;
00321 
00322         // add column according to the size
00323         metadata_table_add_column(value_table, THUMBNAIL_COLUMNS[THUMBNAIL_SMALL]);
00324         value_index++;
00325         rc = metadata_table_set_blob(value_table, value_index, blob, blob_size);
00326         if (rc== ER_OK)
00327         {
00328             save_needed = TRUE;
00329         }
00330         else
00331         {
00332             ERRORPRINTF("Cannot write thumbnail %s to table.", "small");
00333         }
00334     }
00335 
00336     if ( medium )
00337     {
00338         gchar* blob = (gchar*) medium->data;
00339         gsize  blob_size = medium->size;
00340 
00341         // add column according to the size
00342         metadata_table_add_column(value_table, THUMBNAIL_COLUMNS[THUMBNAIL_MEDIUM]);
00343         value_index++;
00344         rc = metadata_table_set_blob(value_table, value_index, blob, blob_size);
00345         if (rc== ER_OK)
00346         {
00347             save_needed = TRUE;
00348         }
00349         else
00350         {
00351             ERRORPRINTF("Cannot write thumbnail %s to table.", "medium");
00352         }
00353     }
00354 
00355     // write values to database
00356     if (save_needed)
00357     {
00358         rc = ermetadb_global_change_file(db, filepath, filename, value_table);
00359     }
00360     else
00361     {
00362         ERRORPRINTF("No metadata saved, options empty?");
00363     }
00364 
00365     // clean up
00366     metadata_table_free(value_table);
00367 
00368     if (rc != ER_OK)  { return FALSE; }
00369     
00370     return TRUE;
00371 }
00372 
00373 
00374 gboolean pixbuf_to_blob(GdkPixbuf * pixbuf, gchar ** buffer, gsize * buf_size)
00375 {
00376     return gdk_pixbuf_save_to_buffer(pixbuf,
00377             buffer,
00378             buf_size,
00379             "png",
00380             NULL,
00381             NULL);
00382 }
00383 
00384 
00385 // Set the pixel at (x, y) with color. Caller must check the input parameters
00386 static void  set_pixel_value(GdkPixbuf * pixbuf, int x, int y, gint color)
00387 {
00388     gint channel = gdk_pixbuf_get_n_channels(pixbuf);
00389     gint rowstride = gdk_pixbuf_get_rowstride(pixbuf);
00390     guchar * pixel = gdk_pixbuf_get_pixels(pixbuf);
00391     guchar * p = pixel + y * rowstride + x * channel;
00392 
00393     p[0] = (color & 0xFF000000) >> 24;
00394     p[1] = (color & 0x00FF0000) >> 16;
00395     p[2] = (color & 0x0000FF00) >> 8;
00396 }
00397 
00398 
00399 void pixbuf_draw_rectangle(GdkPixbuf* pixbuf, gint xx, gint yy, gint ww, gint hh, gint color)
00400 {
00401     if (pixbuf == NULL)
00402     {
00403         return;
00404     }
00405 
00406     gint w = gdk_pixbuf_get_width (pixbuf);
00407     gint h = gdk_pixbuf_get_height (pixbuf);
00408 
00409     gint i, j, x, y;
00410     
00411     // draw top, buttom line
00412     for (i = 0; i < 2; ++i)
00413     {
00414         if (i == 0)
00415         {
00416             y = yy;
00417         }
00418         else
00419         {
00420             y = yy + hh - 1;
00421         }
00422 
00423         x = xx;
00424         for (j = 0; j < ww; ++j)
00425         {
00426             if ((x + j) < w && y < h)
00427                 set_pixel_value(pixbuf, x + j, y, color);
00428         }
00429     }
00430 
00431     // draw left, right line
00432     for (i = 0; i < 2; ++i)
00433     {
00434         if (i == 0)
00435         {
00436             x = xx;
00437         }
00438         else
00439         {
00440             x = xx + ww -1;
00441         }
00442 
00443         y = yy;
00444         for (j = 0; j < hh; ++j)
00445         {
00446             if (x < w && (y + j) < h)
00447             {
00448                 set_pixel_value(pixbuf, x, y + j, color);
00449             }
00450         }
00451     }
00452 }
Generated by  doxygen 1.6.2-20100208