00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00027
00028
00029
00030
00031
00032 #include <liberdm/display.h>
00033 #include "browserTypes.h"
00034 #include "pagebar.h"
00035 #include "indexFileHandler.h"
00036 #include "main.h"
00037 #include "browser.h"
00038 #include "toolbar.h"
00039 #include "displayUpdate.h"
00040 #include "browserLog.h"
00041 #include <libermanifest/ermanifest.h>
00042 #include "mozilla_api.h"
00043 #include <signal.h>
00044 #include <sys/types.h>
00045 #include <sys/stat.h>
00046
00047
00048 #include "prenv.h"
00049 #include "mozEmbedCallbacks.h"
00050
00051
00052
00053
00054
00055 class CPersist
00056 {
00057 private:
00058 static Ereader *s_pBrowser;
00059 static const int MAX_PATH = 1024;
00060 static char s_url[MAX_PATH];
00061 static char s_inputUrl[MAX_PATH];
00062 static char s_ManifestPathName[MAX_PATH];
00063 static void OnTerminated(int sig);
00064 static void PreparePath();
00065
00066 public:
00067 CPersist() {}
00068 ~CPersist() {}
00069 public:
00070 static void SetBrowser(Ereader *p) { s_pBrowser = p; }
00071 static Ereader *GetBrowser() { return s_pBrowser; }
00072 static char* GetPageLastRead(const char * input);
00073 static void StorePageLastRead(const char *url);
00074 static void SetManifestPathName(const char *pathName);
00075 static void InstallTermHandler();
00076 static void UninstallTermHandler();
00077 static gboolean FileExist(const char *p);
00078 };
00079
00080 Ereader * CPersist::s_pBrowser = NULL;
00081 char CPersist::s_ManifestPathName[];
00082 char CPersist::s_url[];
00083 char CPersist::s_inputUrl[];
00084
00085 void CPersist::SetManifestPathName(const char *pathName)
00086 {
00087 if (pathName)
00088 {
00089 strncpy(s_ManifestPathName, pathName, MAX_PATH);
00090 }
00091 }
00092
00093 void CPersist::InstallTermHandler()
00094 {
00095
00096 struct sigaction on_term;
00097 memset(&on_term, 0x00, sizeof(on_term));
00098 on_term.sa_handler = OnTerminated;
00099 sigaction(SIGTERM, &on_term, NULL);
00100 }
00101
00102 void CPersist::UninstallTermHandler()
00103 {
00104
00105 struct sigaction on_term;
00106 memset(&on_term, 0x00, sizeof(on_term));
00107 on_term.sa_handler = SIG_DFL;
00108 sigaction(SIGTERM, &on_term, NULL);
00109 }
00110
00111 void CPersist::OnTerminated(int sig)
00112 {
00113
00114 destroy_ereader(s_pBrowser);
00115 s_pBrowser = NULL;
00116 exit(0);
00117 }
00118
00119 gboolean CPersist::FileExist(const char *pathName)
00120 {
00121 struct stat statbuf;
00122 if (0 != stat(pathName, &statbuf))
00123 {
00124 return FALSE;
00125 }
00126 return TRUE;
00127 }
00128
00129 void CPersist::StorePageLastRead(const char *url)
00130 {
00131
00132
00133
00134 BR_LOGPRINTF("Input url %s\n", url);
00135 char * path = mozilla_uri_to_path(url);
00136 char * mem = path;
00137 if (path == NULL)
00138 {
00139 BR_LOGPRINTF("No local path %s", url);
00140
00141
00142 path = strdup(s_inputUrl);
00143 }
00144 else
00145 {
00146 BR_LOGPRINTF("Output path %s\n", path);
00147 char * tmp = &s_ManifestPathName[0];
00148 while (path && tmp && *path == *tmp)
00149 {
00150 ++path; ++tmp;
00151 }
00152 if (path)
00153 {
00154 while (*path != '/')
00155 {
00156 --path;
00157 }
00158 path++;
00159 }
00160 }
00161 BR_LOGPRINTF("Last location in relative path %s\n", path);
00162 erManifest manifest;
00163 if (RET_OK == ermXmlOpenFile(s_ManifestPathName, &manifest))
00164 {
00165
00166 if (RET_OK != ermXmlExist(&manifest, "/package/last-location/document"))
00167 {
00168 ermXmlNewString(&manifest, "/package", "last-location", "");
00169 ermXmlNewString(&manifest, "/package/last-location", "document", "");
00170 }
00171 ermXmlSetString(&manifest, "/package/last-location/document", path);
00172 ermXmlSaveAndClose(&manifest);
00173 }
00174 if (mem)
00175 {
00176 free(mem);
00177 }
00178 }
00179
00180
00181
00182
00183
00184
00185
00186 char * CPersist::GetPageLastRead(const char * input)
00187 {
00188 BR_LOGPRINTF("input %s", input);
00189
00190
00191 strncpy(s_inputUrl, input, MAX_PATH);
00192
00193
00194 char * url = NULL;
00195 erManifest manifest;
00196 memset(s_url, 0, MAX_PATH);
00197 if (RET_OK == ermXmlOpenFile(s_ManifestPathName, &manifest))
00198 {
00199
00200 if (RET_OK == ermXmlGetString(&manifest, "/package/last-location/document", s_url, MAX_PATH))
00201 {
00202 url = &s_url[0];
00203 }
00204 ermXmlClose(&manifest);
00205 }
00206
00207
00208 BR_LOGPRINTF("url from manifest %s", url);
00209 if (NULL == url)
00210 {
00211 BR_LOGPRINTF("Could not retrieve url from manifest file %s!", s_ManifestPathName);
00212 return (char *)input;
00213 }
00214
00215
00216 int prefix = strlen("file://");
00217 char tmp[MAX_PATH] = {0};
00218 strcpy(tmp, "file://");
00219 char *path = mozilla_uri_to_path(url);
00220 if (path && FileExist(path))
00221 {
00222
00223 strncpy(&s_url[0], path, MAX_PATH);
00224 free(path);
00225 return &s_url[0];
00226 }
00227 else
00228 {
00229
00230 if (path)
00231 {
00232 free(path);
00233 }
00234
00235
00236 strcpy(tmp + prefix, s_ManifestPathName);
00237 char * pos = strrchr(tmp + prefix, '/');
00238 ++pos;
00239 strcpy(pos, url);
00240 pos += strlen(url); *pos = 0;
00241 strncpy(s_url, tmp , strlen(tmp));
00242 }
00243
00244
00245 BR_LOGPRINTF("check again the input %s", s_url);
00246 if (FileExist(s_url + prefix))
00247 {
00248 BR_LOGPRINTF("url result %s", s_url);
00249 return s_url;
00250 }
00251 return NULL;
00252 }
00253
00254 static CPersist s_recorder;
00255
00256
00257
00258 gboolean delete_cb(GtkWidget * widget, GdkEventAny * event, Ereader * reader);
00259 gboolean browser_main_window_expose_event(GtkWidget * widget, GdkEventExpose * event, Ereader * reader);
00260
00261
00262 static void browser_create(Ereader * browser, gchar * URL_input);
00263 static GtkWidget *create_window(char *title);
00264 static void maximize_window(GtkWidget * src);
00265
00266 Ereader *new_gtk_ereader(char *manifest, char *input_URL)
00267 {
00268 Ereader *theEreader;
00269
00270 BR_LOGPRINTF("entry");
00271
00272
00273 theEreader = g_new0(Ereader, 1);
00274
00275 if (theEreader)
00276 {
00277 theEreader->pageStatus = browser_create_page_status();
00278 browser_set_page_status_indexfile(theEreader->pageStatus, manifest);
00279
00280 BR_LOGPRINTF("theEreader 0x%x - theEreader->pageStatus 0x%x", theEreader, theEreader->pageStatus);
00281
00282 theEreader->topLevelWindow = create_window("E-reader");
00283
00284
00285 theEreader->topLevelVBox = gtk_vbox_new(FALSE, 0);
00286 gtk_widget_show(theEreader->topLevelVBox);
00287 gtk_container_add(GTK_CONTAINER(theEreader->topLevelWindow), theEreader->topLevelVBox);
00288
00289
00290 theEreader->eventBox = gtk_event_box_new();
00291 gtk_box_pack_start(GTK_BOX(theEreader->topLevelVBox), theEreader->eventBox, TRUE, TRUE, 0);
00292 gtk_widget_show(theEreader->eventBox);
00293
00294 g_signal_connect(G_OBJECT(theEreader->topLevelVBox), "expose-event", G_CALLBACK(browser_main_window_expose_event), theEreader);
00295
00296
00297 #ifdef LOCAL_DISPLAY
00298
00299 BR_WARNPRINTF("LOCAL_DISPLAY is defined => toolbar");
00300
00301 theEreader->toolbar = gtk_toolbar_new();
00302 gtk_widget_set_usize(GTK_WIDGET(theEreader->toolbar), (-1), TOOLBAR_HEIGTH);
00303 gtk_widget_show(theEreader->toolbar);
00304
00305 gtk_box_pack_start(GTK_BOX(theEreader->topLevelVBox), GTK_WIDGET(theEreader->toolbar), FALSE,
00306 FALSE,
00307 0);
00308 #endif //LOCAL_DISPLAY
00309
00310 gtk_widget_show(theEreader->topLevelWindow);
00311
00312
00313 s_recorder.SetManifestPathName(manifest);
00314
00315 char *url = s_recorder.GetPageLastRead(input_URL);
00316 if (url)
00317 {
00318 input_URL = url;
00319
00320 }
00321
00322
00323 browser_create(theEreader, input_URL);
00324
00325
00326 g_signal_connect(GTK_OBJECT(theEreader->topLevelWindow), "delete_event", G_CALLBACK(delete_cb), theEreader);
00327
00328
00329 gtk_signal_connect(GTK_OBJECT(theEreader->topLevelWindow), "key_press_event", G_CALLBACK(on_mainWindow_keypress), theEreader);
00330
00331
00332 s_recorder.InstallTermHandler();
00333 s_recorder.SetBrowser(theEreader);
00334 }
00335 else
00336 {
00337 BR_ERRORPRINTF("unable to allocate gEreader");
00338 }
00339
00340 return theEreader;
00341 }
00342
00343 void browser_quit()
00344 {
00345 s_recorder.UninstallTermHandler();
00346 destroy_ereader(s_recorder.GetBrowser());
00347 }
00348
00349 void destroy_ereader(Ereader * theEreader)
00350 {
00351
00352 gchar * type = NULL;
00353 gboolean page_type_known = FALSE;
00354 int page = -1;
00355
00356
00357 gchar *url = gtk_moz_embed_get_location(GTK_MOZ_EMBED(theEreader->mozEmbed));
00358
00359
00360 if (page_type_known = mozilla_get_page_type(GTK_MOZ_EMBED(theEreader->mozEmbed), &type))
00361 {
00362 page = index_file_get_page_number(&theEreader->pageStatus->index, type, url);
00363 }
00364 BR_LOGPRINTF("url last visited %s %d page\n", url, page);
00365 s_recorder.StorePageLastRead(url);
00366 if (url)
00367 {
00368 free(url);
00369 }
00370
00371 if (theEreader)
00372 {
00373 BR_LOGPRINTF("cleaning up browser allocations");
00374
00375 if (theEreader->pageStatus)
00376 {
00377 browser_destroy_page_status(theEreader->pageStatus);
00378 }
00379
00380 g_free(theEreader);
00381 theEreader = NULL;
00382 }
00383 }
00384
00385
00386 gboolean delete_cb(GtkWidget * widget, GdkEventAny * event, Ereader * reader)
00387 {
00388 BR_LOGPRINTF("entry");
00389 destroy_ereader(reader);
00390 gtk_widget_destroy(widget);
00391 return TRUE;
00392 }
00393
00394
00403 static void browser_create(Ereader * browser, gchar * URL_input)
00404 {
00405 browser->mozEmbed = gtk_moz_embed_new();
00406
00407
00408
00409
00410 gtk_container_add(GTK_CONTAINER(browser->eventBox), browser->mozEmbed);
00411
00412 BR_LOGPRINTF("browser 0x%x - created mozEmbed 0x%x", browser, browser->mozEmbed);
00413
00414 g_signal_connect(GTK_OBJECT(browser->mozEmbed), "location", G_CALLBACK(location_changed_cb), browser);
00415 g_signal_connect(GTK_OBJECT(browser->mozEmbed), "visibility", G_CALLBACK(visibility_cb), browser);
00416 g_signal_connect(GTK_OBJECT(browser->mozEmbed), "net_stop", G_CALLBACK(load_finished_cb), browser);
00417
00418
00419
00420
00421 g_signal_connect(GTK_OBJECT(browser->mozEmbed), "open_uri", G_CALLBACK(open_uri_cb), browser);
00422
00423 #ifndef PC_ENVIRONMENT
00424
00425
00426 gtk_moz_embed_set_chrome_mask(GTK_MOZ_EMBED(browser->mozEmbed), GTK_MOZ_EMBED_FLAG_DEFAULTCHROME);
00427 #endif
00428
00429 gtk_widget_set_size_request(browser->mozEmbed, SCREEN_WIDTH, CLIENT_AREA);
00430
00431 if (URL_input)
00432 {
00433 BR_LOGPRINTF("loading URL %s", URL_input);
00434
00435
00436 display_update_increase_level(MOZEMBED_UPDATE_LEVEL);
00437
00438 gtk_moz_embed_load_url(GTK_MOZ_EMBED(browser->mozEmbed), URL_input);
00439 }
00440 else
00441 {
00442 BR_ERRORPRINTF("No default URL available");
00443 }
00444
00445 BR_LOGPRINTF("show mozEmbed 0x%x", browser->mozEmbed);
00446 set_browser_visibility(browser, TRUE);
00447 }
00448
00449 void set_browser_visibility(Ereader * browser, gboolean visibility)
00450 {
00451 BR_LOGPRINTF("%s", (visibility == TRUE) ? "TRUE" : "FALSE");
00452
00453 if (!visibility)
00454 {
00455 gtk_widget_hide(browser->mozEmbed);
00456 }
00457 else
00458 {
00459 gtk_widget_show(browser->mozEmbed);
00460 gtk_widget_grab_focus(browser->mozEmbed);
00461 }
00462 }
00463
00464 static void maximize_window(GtkWidget * src)
00465 {
00466 #ifndef PC_ENVIRONMENT
00467 #ifndef LOCAL_DISPLAY
00468
00469
00470
00471
00472
00473
00474
00475
00476
00477
00478
00479
00480
00481
00482
00483
00484 #endif //LOCAL_DISPLAY
00485 #endif //PC_ENVIRONMENT
00486 }
00487
00488
00489 static GtkWidget *create_window(char *title)
00490 {
00491 GtkWidget *window;
00492
00493 window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
00494 gtk_window_set_title(GTK_WINDOW(window), (title));
00495 gtk_window_position(GTK_WINDOW(window), GTK_WIN_POS_CENTER);
00496 gtk_container_set_border_width(GTK_CONTAINER(window), 0);
00497 gtk_widget_set_size_request(GTK_WIDGET(window), SCREEN_WIDTH, SCREEN_HEIGHT - TOOLBAR_HEIGTH - PAGEBAR_HEIGHT);
00498 gtk_window_set_modal(GTK_WINDOW(window), FALSE);
00499 gtk_window_set_resizable(GTK_WINDOW(window), FALSE);
00500 gtk_signal_connect(GTK_OBJECT(window), "realize", GTK_SIGNAL_FUNC(maximize_window), NULL);
00501 return window;
00502 }
00503
00504 gboolean browser_main_window_expose_event(GtkWidget * widget, GdkEventExpose * event, Ereader * theEreader)
00505 {
00506 BR_DISPLAYPRINTF("entry");
00507 display_update_request_screen_refresh(MAIN_WINDOW_EXPOSE_LEVEL, NULL);
00508 return FALSE;
00509 }